或在 GUI 中显示所有列和所有实体的列表,我需要动态加载表、实体、属性和列名、类型、setter、getter 甚至漂亮标签的完整列表,我就是这样做的基于@Tom Redfem 使用 java 8 流重构的解决方案:
public void loadHibernateMetadata() throws ClassNotFoundException {
Map<String, ClassMetadata> hibernateMetadata = sessionFactory.getAllClassMetadata();
hibernateMetadata.values()
.stream()
.filter(metadata -> metadata != null && metadata instanceof AbstractEntityPersister)
.map(AbstractEntityPersister.class::cast)
.forEach( persister -> createNewnParam(persister));
;
}
然后createNewParam方法就是:
private void createNewParam(AbstractEntityPersister persister) {
try {
Class<?> $class = Class.forName(persister.getEntityName());
List<String> getterNameRoster = Lists.newArrayList($class.getMethods())
.stream()
.filter( method -> method.getName().startsWith("get") || method.getName().startsWith("is"))
.map(getterName -> getterName.getName())
.collect(toList())
;
List<String> setterNameRoster = Lists.newArrayList($class.getMethods())
.stream()
.filter( method -> method.getName().startsWith("set") )
.map(setterName -> setterName.getName())
.collect(toList())
;
Iterable<AttributeDefinition> attrs = persister.getAttributes();
attrs.forEach(a -> {
String columnName = persister.getPropertyColumnNames(a.getName())[0];
org.hibernate.type.Type hibernateType =persister.getPropertyType(a.getName());
Optional<String> optionalGetter = getterNameRoster.stream()
.filter(getterStr -> getterStr.equalsIgnoreCase( String.format("get%s", a.getName()) ) ||
getterStr.equalsIgnoreCase( String.format("is%s", a.getName())) )
.findFirst()
;
String getterName = optionalGetter.isPresent() ? optionalGetter.get() : new String("");
Optional<String> optionalSetter = setterNameRoster.stream()
.filter(setterStr -> setterStr.equalsIgnoreCase( String.format("set%s", a.getName()) ))
.findFirst()
;
String setterName = optionalSetter.isPresent() ? optionalSetter.get() : new String("");
Param param = new Param(persister.getEntityName(),
persister.getTableName().replaceAll("\"", "").toUpperCase(),
columnName.replaceAll("\"", "").toUpperCase(),
a.getName(),
getterName,
setterName,
hibernateType.getName(),
capitalizeFirstLetter(splitCamelCase(a.getName()))
);
hibernateParamList.add(param);
logger.debug(param.toString());
});
} catch (ClassNotFoundException e) {
logger.error(String.format("error occured generating the params %s" , e));
}
}
和两个 String 辅助方法来生成漂亮的标签,这可能与这篇文章无关
private String splitCamelCase(String s) {
return s.replaceAll(
String.format("%s|%s|%s",
"(?<=[A-Z])(?=[A-Z][a-z])",
"(?<=[^A-Z])(?=[A-Z])",
"(?<=[A-Za-z])(?=[^A-Za-z])"
),
" "
);
}
private String capitalizeFirstLetter(String s) {
return Character.toUpperCase(s.charAt(0)) + s.substring(1);
}
当然,在我的 WebAppConfig.class 中,我得到了会话工厂
public SessionFactory sessionFactory() {
LocalSessionFactoryBuilder builder =
new LocalSessionFactoryBuilder(dataSource());
builder.addProperties(hibernateProperties());
builder.scanPackages(new String[] { "com....model" });
SessionFactory sessionFactory = builder.buildSessionFactory();
return sessionFactory;
}
也许我们可以进一步优化流,但对我来说这非常快速和容易。