2012-06-11 35 views
2

我有一個從Drupal CMS中檢索數據的Java類。 Drupal中最終會有相當多的內容類型,我需要將它們放入Java並緩存。由於Drupal的工作方式,每種內容類型都是一個單獨的數據庫視圖。通用數據庫方法

我有以下方法,它由服務層調用,它返回一個特定的對象類型。但是,我擔心這些方法對於每種內容類型都會激增。

有人可以提出一種方法,使其更通用?數據庫方法顯示在第二個代碼示例中。我不知道我是否也可以通用,如果它是值得的。也許我可以在第一個方法中調用一個方法,並讓第二個方法使用case語句。

public DeliverySchedule getDeliverySchedule(final String cmsKey) { //  <---- make return type (Del Schedule) generic 

    String cacheKey = TYPEDS + cmsKey; 
    DeliverySchedule cmsInstance = CMSObjectCache.getCachedCMSObject(cacheKey, DeliverySchedule.class); // Make generic 

    // Object not found in cache, go to database. 
    if (cmsInstance == null) { 
     try { 
      cmsInstance = getDeliveryScheduleFromDB(cmsKey); // <---- How can I make this generic so I can avoid DRY? 
      CMSObjectCache.putCachedCMSObject(cacheKey, new CMSObject(DeliverySchedule.class, cmsInstance)); 
      return cmsInstance; 
     } catch (EmptyResultDataAccessException e) { 
      return null; 
     } 
    } else { 
     return cmsInstance; 
    } 
} 

數據庫訪問方法,專用於內容類型以上:

// Called from above 
private List<DeliverySchedule> getDeliverySchedulesFromDB() { 
    JdbcTemplate jdbcTemplate = new JdbcTemplate(dataSource); 
    final String sql = "select * " 
      + "   from cmsutil.delivery_schedules as m " 
      + "   where m.effdate = (select max(mm.effdate) " 
      + "       from cmsutil.delivery_schedules as mm " 
      + "       where mm.cms_key = m.cms_key " 
      + "       and mm.effdate <= current_date)"; 


    List<DeliverySchedule> listcmsObject = jdbcTemplate.query(sql, new DeliveryScheduleMapper()); 
    return jdbcTemplate.query(sql, new DeliveryScheduleMapper()); 
} 

回答

1

通常你就必須爲每個表或視圖(用於DAO和實現它一類的接口的DAO )。這樣,如果特定的表模式發生變化,您的更改將被隔離到一個DAO類。

您可以將內容類型概括爲具有單個接口和實現每種內容類型接口的類。這應該允許您適應通用內容類型層,特定內容類型和數據訪問層的更改。

我同意它可能會變成大量的代碼,但是如果每個組件都與其他組件脫鉤,那麼當您更改/添加組件或處理模式更改時,它可以提供靈活性。在短期內解耦和抽象可能會很痛苦,但從長遠來看,往往會在整個工程團隊中得到回報。

我喜歡這些問題/討論,並且始終接受建議或其他方法。

0

要創建班級的新實例,您需要使用班級對象上的反射裝置。所以你所做的是使用一個通用類,它的實例有該類的記錄。假設你的豆子可以擴展mybean;

abstract class<T extends MyBean> Mapper implements T { 
    abstract void map(ResultSet rs); 
} 

class DAO<T extends MyBean> { 
    Class<Mapper<T>> theMapperClass; 
    DAO(Class<T> clazz) { 
     this.theMapperClass = getMapperClassFor(clazz); 
    } 

    List<T> getAList() { 
     List<T> l = new ArrayList<T>(); 
     ResultSet rs = runTheQuery(); 
     while(rs.next()) { 
      l.add(theMapperClaxx.newInstance().map(rs)); 
     } 
     return l; 
    } 
} 

那樣的事情。

DAO<Foo> fooDao = new Dao<Foo>(Foo.class); 
    List<Foo> l = fooDao.getAList(); 

    List<? extends MyBean> l = someDao.getAList(); 

    static <T extends Mybean> List<T> boink(Class<T> clazz) { 
     DAO<T> tDao = (DAO<T>) daoMap.get(clazz); 
     return tDao.getAList(); 
    } 

    List<Foo> l = boink(Foo.class);