我正在尝试找出布局此设计的最佳方法,并且遇到了一些问题。
我有一个Dao接口,其中R是返回类型,U是数据库记录impl:
public interface Dao<U extends UpdatableRecordImpl> {
public List<U> insert(List<U> dbRecords);
public List<U> fetchAll(Select<U> selectQuery);
}
我有一个默认的Dao,它通过以下方式实现Dao:
public class BasicDao<U extends UpdatableRecordImpl> implements Dao<U>{
protected final DSLContext _dslContext;
public BasicDao(Configuration configuration, T table) {
_dslContext = DSL.using(configuration);
_table = table;
}
/**
* Fetch multiple records from database
*
* @param selectQuery input query
* @return list of records representing the database records
*/
public List<U> fetchAll(Select<U> selectQuery) {
return selectQuery.fetchStream().collect(Collectors.toList());
}
/**
* Persists db records
* <p>
* Performs a batch operation for more than one record
*
* @param dbRecords list of records that need to be persisted
* @return list of records with updated with id's which were generated by database
*/
public List<U> insert(List<U> dbRecords) {
if (dbRecords.isEmpty()) {
return ImmutableList.of();
}
// prepare insert statement
Result<U> inserted = //insert records
return inserted;
}
}
现在我想做的是在此之上有一个映射层。这样我们就可以拥有一个如下所示的类:
@Override
public List<M> insert(List<M> mappedRecords) {
// Map record templates to db records
List<U> dbRecords = mapList(mappedRecords, this::map);
//Map the result of inserting to DefaultDao
return mapList(_defaultDao.insert(dbRecords), this::map);
}
@Override
public List<M> fetchAll(Select<U> select) {
return StreamEx.of(_defaultDao.fetchAll(select)).map(this::map).toList();
}
/**
* Map list of POJOs' of one type to the list of POJOs' of another type
*
* @param records list of POJOs' that need to be mapped
* @param mapper function to map a single POJO of one type to other POJO type
* @param <P> Input POJO type
* @param <B> Output POJO type
* @return
*/
protected <P, B> List<B> mapList(List<P> records, Function<P, B> mapper) {
return StreamEx.of(records).map(mapper).toList();
}
/**
* Transforms a representative record to it's database representation
* @param mappedRecord mapped representation of database record
* @return database record
*/
protected U map(M mappedRecord) {
return _mapper.map(mappedRecord);
}
/**
* Maps database record to it's mapped representation
* @param dbRecord database record
* @return representation of the database record in M type
*/
M map(U dbRecord) {
return _mapper.inverse().map(dbRecord);
}
我曾尝试在BasicDao周围添加一个Decorator层,但是遇到了一个相同的闭包(List<U> insert(List<U> dbRecords)
和List<M> insert(List<M> dbRecords)
具有相同的闭包)的问题。
使用此设置的建议方法是什么?我发现通过让Dao接受两个类(return和recordImpl)发现了一些hacky方式,但这在基本impl(implements Dao<U, U>
)中看起来很hacky,并且破坏了执行通用类边界的类中的某些现有功能({{1 }}。
感谢您的帮助。