hibernate涂鸦(1)——cfg配置 Hibernate配置管理XMLJPASecurity
org.hibernate.cfg.SettingsFactory: 工厂的工厂,根据properties创建一系列setting和factory,会在Configuration 的无参构造函数里被new出来,并设置给Configuration 的settingsFactory
-- protected SettingsFactory() 空构造函数。
org.hibernate.cfg.EJB3DTDEntityResolver extends DTDEntityResolver: 根据xml文件的publicId和systemId创建并返回SAX的InputSource,其中systemId会包含具体的xsd或者 dtd(dtd由父类处理)的文件名字,classpath路径固定为org/hibernate/ejb/xxx.xsd或者org /hibernate/xxx.dtd
-- entityResolver 静态自身对象,默认创建,但它没有用private*构造函数,所以不是单例模式。
org.hibernate.util.xml.OriginImpl: 描述xml配置文件的来源
-- String type
-- String name
org.hibernate.util.xml.XmlDocumentImpl: 描述xml doc本身
-- documentTree: dom4j的文档结构
-- origin: 来源对象
org.hibernate.util.xml.MappingReader: 饥渴单例,帮助类,单个public方法,通过resolver和inputSource来生成xmlDocument。
-- public XmlDocument readMappingDocument(EntityResolver, InputSource, Origin): 根据resolver来做xml校验,并生成document
org.hibernate.event.EventListeners: 一个所有listener的超级容器类,包含了所有listener类型的数组,会在Configuration 的reset 方法里被new出来,并设置给Configuration 的eventListeners
-- eventInterfaceFromType: 一个将listener类型的Class对象按event类型分类存放的Map。
-- public Class getListenerClassFor(String): 根据传入的event type值从上面的map里得到Class对象
org.hibernate.secure.JACCConfiguration: EJB JACC配置的抽象,JACC对象应该是受JavaEE容器管理的;有一个以contextId为参数的构造函数,会在Configuration 的doConfig 方法中解析到配置了"security"子节点时被new出来。
-- policyConfiguration: 在构造函数中通过PolicyConfigurationFactory(参见JACC API) 得到
-- public JACCConfiguration(String contextId) throws HibernateException: 唯一的一个构造函数,会将在取得policyConfiguration时捕获的异常转化成HibernateException 抛出
-- public void addPermission(String role, String entityName, String action): 用传入的实体名字和动作构成EJBMethodPermission (参见JACC API) 对象后授权给role参数指定的角色。
org.hibernate.cfg.Configuration.MappingsImpl: 内部类,默认构造函数,会在Configuration 的addPackage 方法中被new出来传给AnnotationBinder .bindPackage方法
-- String schemaName: 默认schema配置 @QUESTION赋值时间
-- String catalogName: 默认catalog配置 @QUESTION 赋值时间
-- Boolean useNewGeneratorMappings: 是否用新版的Id生成机制
-- public ReflectionManager getReflectionManager(): 取外部类Configuration 的reflectionManager
-- public TypeResolver getTypeResolver(): 取外部类Configuration 的typeResolver
-- public Properties getConfigurationProperties(): 取外部类Configuration 的properties
-- public boolean useNewGeneratorMappings(): 返回useNewGeneratorMappings 的值,如果useNewGeneratorMappings 为空,则用getConfigurationProperties() 里的"hibernate.id.new_generator_mappings" 属性值来初始化useNewGeneratorMappings
-- public void addGenerator(IdGenerator): 如果defaultNamedGenerators 集合里还没有包括传入的idGenetator的name,则把name作为key,对象本身作为value放入namedGenerators ,旧的key-value会被覆盖掉并记录log。
-- public void addSecondPass(SecondPass): ② addSecondPass( 传入的SecondPass , false)
-- public void addSecondPass(SecondPass, boolean onTopOfTheQueue): 将传入的 SecondPass对象放入secondPasses 列表中,如果 onTopOfTheQueue是true则放入第0个,else放入最后一个。
-- public void addFilterDefinition(FilterDefinition): 把传入的filterDefinition的name作为key,对象本身作为value放入filterDefinitions
-- public void addDefaultQuery(String, NamedQueryDefinition): 把传入的name作为key,对象本身作为value放入namedQueries ,然后在defaultNamedQueryNames 集合里加入name,修改之前如果namedQueries 或者namedSqlQueries 之一已经有这个name了,则停止修改并抛出DuplicateMappingException ,该类为MappingException 的子类。
-- public void addDefaultSQLQuery(String, NamedSQLQueryDefinition): 把传入的name作为key,对象本身作为value放入namedSqlQueries ,然后在defaultNamedNativeQueryNames 集合里加入name,修改之前如果namedQueries 或者namedSqlQueries 之一已经有这个name了,则停止修改并抛出DuplicateMappingException ,该类为MappingException 的子类。
-- public void addQuery(String, NamedQueryDefinition) throws DuplicateMappingException: 如果defaultNamedQueryNames 集合里还没有包括传入的name参数,则把name作为key,对象本身作为value放入namedQueries ,修改之前如果namedQueries 或者namedSqlQueries 之一已经有这个name了,则停止修改并抛出DuplicateMappingException ,该类为MappingException 的子类。
-- public void addSQLQuery(String, NamedSQLQueryDefinition) throws DuplicateMappingException: 如果defaultNamedNativeQueryNames 集合里还没有包括传入的name参数,则把name作为key,对象本身作为value放入namedSqlQueries ,修改之前如果namedQueries 或者namedSqlQueries 之一已经有这个name了,则停止修改并抛出DuplicateMappingException ,该类为MappingException 的子类。
-- public void addTypeDef(String, String, Properties): 拿传入的typeClass和properties构造一个TypeDef 对象,然后 把传入的typeName作为key,TypeDef 对象作为value放入typeDefs
-- public void addAnyMetaDef(AnyMetaDef) throws AnnotationException: 如果anyMetaDefs 的key集合里已经包括了传入annotation的name参数值,则抛出AnnotationException,否则把 把传入的annotation的name参数值作为key,annotation本身作为value放入anyMetaDefs。
org.hibernate.cfg.Configuration.MetadataSourceQueue: 内部类,默认构造函数,会在Configuration 的reset 方法中被new出来,并设置给metadataSourceQueue
-- annotatedClasses: List<XClass>,transient,存放所有实体的XClass,包括H-cfg配置文件里定义的"class"以及JAP-orm声明的"entity"/"mapped-superclass"/"embeddable"节点下的"class"和"listener"。
-- hbmMetadataByEntityNameXRef: Map<String, XmlDocument>,从映射实体的标识符找hbm doc。
-- hbmMetadataToEntityNamesMap: LinkedHashMap<XmlDocument, Set<String>>,从hbm doc文档找映射实体标识符集合。
-- public void add(XClass): 将传入的XClass放入annotatedClasses
-- public void add(XmlDocument): 传入这个方法的doc都应该是hbm,递归的查找hbm中声明的所有"
class"
/
"
subclass"
/
"
joined-subclass"
/
"
union-subclass"子节点上定义的被映射实体的唯一标识符
,唯一标识符通常为这些子节点的"entity-name"属性值,如果
"entity-name"属性值不存在,则使用"name"属性值,如果"name"属性值不是class的全限定名,则在"name"属性值之前加上"package"属性值(定义在root节点"hibernate-mapping"上);对每一个标识符:将这些标识符作为key,hbm doc作为value放入到hbmMetadataByEntityNameXRef
中;将hbm doc作为key,所有标识符组成的Set作为value放入hbmMetadataToEntityNamesMap
中。
org.hibernate.cfg.Configuration.CacheHolder: 内部类,对Cache配置的描述,全属性参数构造函数, 会在Configuration 的reset 方法中建立出一个该对象的空List,并设置给caches
-- String role: 对谁使用缓存,一般为实体类的名字
-- String usage: 缓存对象的并发策略(read-only|read-write|nonstrict-read-write|transactional四选一
)
-- String region: 缓存在哪里
-- boolean isClass: 是否是实体类级别的缓存
-- boolean cacheLazy: 是否lazy
org.hibernate.cfg.Configuration: 配置核心类,很多配置方法都返回this,使得这些方法可以在单个语句中被连续调用
。
-- settingsFactory: 在reset 中被new出来
-- XMLHelper: transient,在reset 中被new出来,提供SAXReader,DOMReader
-- entityResolver: 有public的accessor方法,在reset 中使用new EJB3DTDEntityResolver 赋值
-- typeResolver: 有public的get方法,在变量声明时直接使用new TypeResolver 赋值
-- properties: 属性库
-- reflectionManager: transient,有public的get方法,在reset 中使用new JavaReflectionManager 赋值
-- secondPasses: List<SecondPass >: 需要第二次处理的所有对象列表
-- inSecondPass : 默认false,只有在secondPassCompile()方法中才会被置成true,在方法退出之前被置回false。@QUESTION
-- metadataSourceQueue: 元数据队列 ,在reset 中使用new MetadataSourceQueue 赋值
-- caches: List<CacheHolder >
-- eventListeners: 有public的get方法,在reset 中使用new EventListeners 赋值
-- defaultNamedGenerators: Set<String>,IdGenerator 的名字组成的集合
-- namedGenerators: Map<String, IdGenerator>,名字找IdGenerator 对象
-- defaultNamedQueryNames: Set<String>,NamedQueryDefinition 的名字组成的集合
-- namedQueries: Map<String, NamedQueryDefinition>,名字找NamedQueryDefinition 对象
-- defaultNamedNativeQueryNames: Set<String>,NamedSQLQueryDefinition 的名字组成的集合
-- namedSqlQueries: Map<String, NamedSQLQueryDefinition>,名字找NamedSQLQueryDefinition 对象
-- filterDefinitions: Map<String, FilterDefinition>,名字找FilterDefinition 对象
-- typeDefs: Map<String, TypeDef>,名字找TypeDef 对象
-- anyMetaDefs: Map<String, AnyMetaDef>,名字找@AnyMetaDef 对象
-- public Configuration(): 公开构造函数,new一个SettingsFactory后作为参数调用包内构造函数。
-- protected Configuration(SettingsFactory): 赋值settingsFactory
,调用reset
方法。
-- protected void reset(): 只在包内构造函数中调用一次,初始化。
-- public Configuration configure() throws HibernateException
: 默认使用"/hibernate.cfg.xml"调用configure(String)
方法。
-- public Configuration configure(File) throws HibernateException : 根据文件类建立InputStream,作为参数和文件toString调用① doConfigure 方法。File找不到错误会被包装成HibernateException 抛出。
-- public Configuration configure(org.w3c.dom.Document) throws HibernateExceptio : 把w3c的dom结构转化为dom4j的dom结构,作为参数调用② doConfigure 方法。
-- public Configuration configure(String) throws HibernateException : 根据文件路径建立InputStream,作为参数和String本身调用① doConfigure 方法,空的InputStream会导致一个HibernateException 的抛出。
-- public Configuration configure(URL) throws HibernateException : ① doConfigure(url.openStream(), url.toString()) ,url的io错误会被包装成HibernateException 抛出
-- protected Configuration doConfigure(InputStream, String) throws HibernateException : 以entityResolver 为参数调用XMLHelper 建立SAXReader后读取InputStream生成dom4j的dom结构,作为参数调用② doConfigure 方法,解析InputStream失败会抛出MappingException ,该类为HibernateException 的子类。
-- protected Configuration doConfigure(Document) throws HibernateException : 最终使用的配置方法:
- 如果"session-factory"节点存在"name"属性,则properties .setProperty("hibernate.session_factory_name", "name"属性的值) ;
- 调用 addProperties("session-factory"节点 ) 方法:遍历"session-factory"节点下的所有"property"节点,调用setProperty("name"属性值, tag body值) ;如果其中有"name"属性值不是以"hibernate"开头,则调用setProperty("hibernate." +"name"属性值, tag body值) ,遍历完毕后调用Environment .verifyProperties(properties ) 做校验,看是否使用了过期的property名字;
-
调用
parseSessionFactory(
"session-factory"节点,
"name"属性的值
)
方法:解析"session-factory"的子节点:
- 如果是"mapping"子节点,调用parseMappingElement("mapping"子节点
,
"name"属性的值
)
解析该节点的属性,其中name属性的值只在log中使用:
- 如果是"resource"属性,调用① addResource("resource"属性值 )
- 如果是"file"属性,调用①addFile ("file"属性值 )
- 如果是"jar"属性,调用addJar(通过"jar"属性值建立的File对象 )
- 如果是"package"属性,调用addPackage( "package"属性值 )
- 如果是"class"属性,调用addAnnotatedClass(使用当前线程的CL加载"class"属性值指定的类名得到的Class对象) ,Class找不到错误会被包装成MappingException 抛出。
- 如果什么属性都没有,则抛出MappingException
- 如果是"class-cache"子节点:调用③ setCacheConcurrencyStrategy ("class"属性值, "usage"属性值(read-only|read-write|nonstrict-read-write|transactional四选一), "region"属性值(没有region的话直接"class"属性值), "include"属性值(布尔变量,是否lazy))
- 如果是"collection-cache"子节点:调用② setCollectionCacheConcurrencyStrategy("collection"属性值, "usage"属性值(read-only|read-write|nonstrict-read-write|transactional四选一), "region"属性值(没有region的话直接"collection "属性值))
- 如果是"listener"子节点:调用 parseListener("listener "子节点 ) 解析该节点的属性:调用③ setListeners(" type"属性值 , new String[]{"class"属性值}) ,如果"type"属性值如果为空,则抛出MappingException。其中type可选值为(auto-flush|merge|create|create-onflush|delete|dirty-check|evict|flush|flush-entity|load|load-collection|lock|refresh|replicate|save-update|save|update|pre-load|pre-update|pre-insert|pre-delete|pre-collection-recreate|pre-collection-remove|pre-collection-update|post-load|post-update|post-insert|post-delete|post-collection-recreate|post-collection-remove|post-collection-update|post-commit-update|post-commit-insert|post-commit-delete)
- 如果是"event"子节点:调用parseEvent ("event "子节点 ) 解析该节点的属性:调用③ setListeners(" type"属性值 , 由"event"的所有listener子节点的"class"属性值组成的String数组 ) 。type值同上。
- 如果是"mapping"子节点,调用parseMappingElement("mapping"子节点
,
"name"属性的值
)
解析该节点的属性,其中name属性的值只在log中使用:
- 如果root节点下存在"security"节点,则调用parseSecurity("security"节点)
:
- setProperty("hibernate.jacc_context_id", "context"属性的值 );
- 用 "context"属性的值new一个JACCConfiguration 对象jcfg,遍历 "security"节点下的子节点,对所有"grant"子节点调用jcfg.addPermission("role"属性值,"entity-name"属性值,"actions"属性值)。其中"actions"属性是以逗号分隔的字符串,也可以是通配符*代表"insert,read,update,delete"
-- public Configuration addResource(String) throws MappingException : ① add(由传入的mapping全文件名得到的InputStream, "resource", mapping全文件名) ,读取InputStream的ClassLoader优先选择当前线程的CL,其次使用加载Environment类的CL;空的InputStream会导致一个MappingNotFoundException 的抛出,该类为MappingException 的子类。
-- public Configuration addResource(String, ClassLoader) throws MappingException : ① add(由传入的mapping文件名得到的InputStream, "resource", mapping文件名) ,和上面方法的区别是只能通过指定的ClassLoader来读取InputStream,同样空的InputStream会导致一个MappingNotFoundException 的抛出,该类为MappingException 的子类。
-- public Configuration addClass(Class) throws MappingException : 直接把Class的全名称的点替换为除号后再加上.hbm.xml,和该Class的CL作为参数调用② addResource 方法。
-- public Configuration addFile(String) throws MappingException: 通过文件名建立File对象,然后调用② addFile (File对象 )
-- public Configuration addFile(File) throws MappingException: ② add(由传入的File得到的InputSource, "file", File的AbsolutePath) ,File找不到错误导致一个MappingNotFoundException 的抛出,该类为MappingException 的子类。
-- public Configuration addJar(File) throws MappingException: 对jar包中每一个以".hbm.xml"结尾的文件调用addInputStream(文件的InputStream), IO错误会被包装成InvalidMappingException 抛出,该类为MappingException 的子类。
-- public Configuration addInputStream(InputStream) throws MappingException: ① add(传入的InputStream , "input stream", null)
-- public Configuration addPackage(String) throws MappingException: AnnotationBinder .bindPackage(传入的package名字, new出一个内部类MappingImp对象),对catch到的 MappingException 记录日志后再抛出 。
-- public Configuration addAnnotatedClass(Class): 通过reflectionManager .toXClass(Class) 将传入的Class对象转化成JavaXClass对象,然后调用metadataSourceQueue .add(XClass )。
-- private XmlDocument add(InputStream, String, String): ② add(由传入的 InputStream 得到的InputSource, originType, originName)
-- private XmlDocument add(InputSource, String, String): ③ add( inputSource, 根据originType和originName建立的OriginImpl 对象)
-- private XmlDocument add(InputSource, Origin): 将InputSource参数和entityResolver属性传给MappingReader 来生成XmlDocumentImpl 的实例,然后作为参数调用add(xmlDocument) ,最后return这个实例。
-- public void add(XmlDocument): 如果是inSecondPass或者不是JPA的orm.xml,则调用metadataSourceQueue .add( xmlDocument ) ;else,则通过 reflectionManager.jpaMetadataProvider.xmlContext.addDocument(Document) 将doc文档中的dom4j结构解析成XMLContext对象,并且将返回的一个className的List中的所有Class(包括JPA orm中所有"entity"/"mapped-superclass"/"embeddable"定义的class和listener)都通过 reflectionManager.classForName(className, 当前Configuration对象的Class对象) 转化成XClass对象,然后调用 metadataSourceQueue .add(XClass ),在根据className找class的过程中如果出现类找不到错误则包装成AnnotationException 抛出 ,该类为MappingException 的子类。
-- public Configuration setCacheConcurrencyStrategy(String, String): ②setCacheConcurrencyStrategy (传入的 entityName , 传入的concurrencyStrategy, 传入的 entityName)。
-- public Configuration setCacheConcurrencyStrategy(String, String , String): ③setCacheConcurrencyStrategy(传入的 entityName , 传入的concurrencyStrategy, 传入的region, true )。
-- public void setCacheConcurrencyStrategy(String, String, String, boolean cacheLazyProperty) throws MappingException: 用传入的4个参数再加上指示isClass的true值构造一个CacheHolder 对象放入caches 列表中。
-- public Configuration setCollectionCacheConcurrencyStrategy(String, String): ②setCollectionCacheConcurrencyStrategy(传入的 collectionName , 传入的concurrencyStrategy, 传入的collectionName )。
-- public void setCollectionCacheConcurrencyStrategy(String, String, String): 用传入的3个参数再加上指示isClass的false值和指示lazy的false值构造一个CacheHolder 对象放入caches 列表中。
-- public void setListener(String, String): ③ setListeners(传入的type, new String[]{ 传入的listener名字 } )
-- public void setListener(String, Object): ④ setListeners(传入的type, new Object[]{ 传入的listener对象 } ),其中 Object数组是由特定类型的数组cast而来的,具体类型通过 eventListeners . getListenerClassFor( 传入的type ) 得到,所以当传入的Object对象不属于这个类型时,会发生ArrayStoreException,该错误并没有得到捕获
-- public void setListeners(String, String[]): ④ setListeners(传入的type, new Object []{ 根据传入的listeners的ClassName构造的多个对象 } ) ,其中 Object数组是由特定类型的数组cast而来的,具体类型通过 eventListeners . getListenerClassFor( 传入的type ) 得到 ,所以当传入的 listeners 中有一个ClassName不属于这个类型时,会发生ArrayStoreException,该异常以及类找不到异常会被转换成 MappingException 抛出。
-- public void setListeners(String, Object[]): 根据传入的type,分别 修改eventListeners 里存的对应的 listener数组:如果传入的listeners是null,则使用空数组修改;else则使用listener赋值。如果传入的type不符合所有预定于的event type,在抛出 MappingException。
-- public Configuration setProperties(Properties): 直接赋值整个properties。
-- public Configuration setProperty(String, String): 对properties里的单个property进行赋值。
-- public Configuration addProperties(Properties): 增加或者替换额外的properties。
org.hibernate.cfg.AnnotationBinder: 静态帮助类,使用private*构造函数。
-- public static void bindPackage(String, Mappings): 通过mapping参数拿到它外部Configuration 类的reflectionManager ,调用packageForName(传入的pkg名字参数)得到一个XPackage的对象,然后:
- 如果该pkg上声明了javax.persistence. @SequenceGenerator 这个ann并且mapping.useNewGeneratorMappings() 返回true,则使用ann的name属性值作为name ,SequenceStyleGenerator .class.getName()作为identifierGeneratorStrategy ,ann的其他属性值包括catalog(会先从mappings的schemaName 先拿个默认值),schema(会先从mappings的catalogName 先拿个默认值),sequence_name:sequenceName,increment_size:allocationSize,initial_value:initialValue 作为params 建立IdGenerator 的一个对象,作为参数调用mapping.addGenerator(IdGenerator)。
- 如果该pkg上声明了javax.persistence. @SequenceGenerator 这个ann并且mapping.useNewGeneratorMappings() 返回false,则使用ann的name属性值作为name ,"seqhilo"作为identifierGeneratorStrategy ,ann的其他属性值包括sequence:sequenceName,max_lo:allocationSize作为params 建立IdGenerator 的一个对象,作为参数调用mapping.addGenerator(IdGenerator)。
- 如果该pkg上声明了javax.persistence. @TableGenerator 这个ann并且mapping.useNewGeneratorMappings() 返回true,则使用ann的name属性值作为name ,org.hibernate.id.enhanced.TableGenerator. class.getName()作为identifierGeneratorStrategy ,ann的其他属性值包括prefer_entity_table_as_segment_value:"true",catalog(会先从mappings的schemaName 先拿个默认值),schema(会先从mappings的catalogName 先拿个默认值), table_name:table,segment_column_name:pkColumnName,segment_value:pkColumnValue,value_column_name:valueColumnName, increment_size:allocationSize,initial_value:initialValue 作为params 建立IdGenerator 的一个对象,作为参数调用mapping.addGenerator(IdGenerator)。
- 如果该pkg上声明了javax.persistence. @TableGenerator 这个ann并且mapping.useNewGeneratorMappings() 返回false,则使用ann的name属性值作为name ,MultipleHiLoPerTableGenerator. class.getName()作为identifierGeneratorStrategy ,ann的其他属性值包括catalog(会先从mappings的schemaName 先拿个默认值),schema(会先从mappings的catalogName 先拿个默认值),table,primary_key_column:pkColumnName, primary_key_value:pkColumnValue,value_column:valueColumnName,max_lo:allocationSize 作为params 建立IdGenerator 的一个对象,作为参数调用mapping.addGenerator(IdGenerator)。对于3/4, @TableGenerator的uniqueConstraints属性在Hibernate中未实现
- 调用 bindGenericGenerators(XAnnotatedElement pkg, Mappings)方法: 如果该pkg上声明了org.hibernate.annotations. @GenericGenerator/GenericGenerators 这2个ann,则使用ann的name属性值作为name ,ann的strategy属性作为identifierGeneratorStrategy ,ann的parameters属性值作为params 建立IdGenerator 的一个对象,作为参数调用mapping.addGenerator(IdGenerator)。
- 调用 bindQueries (XAnnotatedElement pkg, Mappings)方法: 如果该pkg上声明了javax.persistence. @SqlResultSetMapping/SqlResultSetMappings 这2个ann,则调用QueryBinder .bindSqlResultsetMapping(单独的ann或者遍历后的每个ann, mappings, false) ;如果该pkg上声明了javax.persistence. @NamedQuery/NamedQueries 这2个ann,则分别调用QueryBinder .bindQuery(ann, mappings, false) 和QueryBinder .bindQueries(ann, mappings, false); 如果该pkg上声明了org.hibernate.annotations. @NamedQuery/NamedQueries 这2个ann,则分别调用QueryBinder .bindQuery(ann, mappings) 和QueryBinder .bindQueries(ann, mappings); 如果该pkg上声明了javax.persistence. @NamedNativeQuery/NamedNativeQueries 这2个ann,则分别调用QueryBinder .bindNativeQuery(ann, mappings, false) 和QueryBinder .bindNativeQueries(ann, mappings, false); 如果该pkg上声明了org.hibernate.annotations. @ NamedNativeQuery / NamedNativeQueries 这2个ann,则分别调用QueryBinder .bindNativeQuery(ann, mappings) 和QueryBinder .bindNativeQueries(ann, mappings);
- 调用 bindFilterDefs (XAnnotatedElement pkg, Mappings)方法: 如果该pkg上声明了org.hibernate.annotations. @FilterDef/FilterDefs 这2个ann,则遍历ann的parameters属性并构造一个Map<String, org.hibernate.type.Type>,将每个parameter的name属性作为key,type属性经过typeResolver. heuristicType方法转化成一个Hibernate的Type后作为value,放入map中; 然后使用ann的name属性,ann的defaultCondition属性和map对象建立FilterDefinition 的一个对象,作为参数调用mapping.addFilterDefinition(FilterDefinition )。
-
调用
bindTypeDefs
(XAnnotatedElement pkg, Mappings)方法:
如果该pkg上声明了org.hibernate.annotations.
@TypeDef/TypeDefs
这2个ann,则用ann的parameters属性构造出一个Properties对象,然后:
- 如果ann上的name属性为空并且没定义defaultForType属性,则抛出AnnotationException;
- 如果ann上定义了非空name属性,则调用mapping.addTypeDef(ann的name属性, ann的typeClass属性的name属性, Properties对象 ) ;
- 如果ann上定义了defaultForType属性,则调用mapping.addTypeDef(ann的 defaultForType属性的 name属性, ann的typeClass属性的name属性, Properties对象 ) ;
- 调用 bindFetchProfiles (XAnnotatedElement pkg, Mappings)方法: 如果该pkg上声明了org.hibernate.annotations. @FetchProfile/FetchProfiles 这2个ann,遍历fetchOverrides子注解,对每一个FetchOverride判断mode属性是不是JOIN,是的话就是拿FetchProfile的name属性和 F etchOverride以及mapping建立VerifyFetchProfileReferenceSecondPass对象,然后调用 mapping.addSecondPass( SecondPass );如果遍历过程中有一个mode属性不是JOIN,在抛出 MappingException并且遍历终止。
- 调用 BinderHelper .bindAnyMetaDefs( XAnnotatedElement pkg, Mappings ) 方法: 如果该pkg上声明了org.hibernate.annotations. @AnyMetaDef/AnyMetaDefs 这2个ann,调用 mapping.addAnyMetaDef( AnyMetaDef类型的ann );如果ann的name属性为空,则会抛出AnnotationException。
-
参考其他涂鸦:
org.hibernate.cfg.annotations.reflection.XMLContext : 描述整个xml配置的环境,会在JPAMetadataProvider 的xmlContext 属性初始化时被new出来。
org.hibernate.cfg.annotations.reflection.JPAMetadataProvider : 默认构造函数,在Configuration 的reset 方法中被new出来,并设置给JavaReflectionManager 的metadataProvider
org.hibernate.annotations.common.reflection.java.JavaReflectionManager : static初始块里log一下annotation的版本,在Configuration 的reset 方法中被new出来,并设置给Configuration 的reflectionManager
org.hibernate.type.TypeResolver : 默认构造函数,在Configuration 的typeResolver 属性初始化时被new出来。
org.hibernate.mapping.IdGenerator : 对id生成机制的抽象,会在AnnotationBinder 的bindPackage 方法里对声明了 javax.persistence. @SequenceGenerator或者 javax.persistence. @TableGenerator 或者 org.hibernate.annotations. @GenericGenerator/GenericGenerators 的pkg new出一些idGenerator放入mapping对象中。
org.hibernate.cfg.annotations.ResultsetMappingSecondPass : 对ResultsetMapping的抽象,会在AnnotationBinder 的bindPackage 方法里对声明了 javax.persistence. @SqlResultSetMapping/SqlResultSetMappings 的pkg new出一些 ResultsetMappingSecondPass放入mapping对象中。
org.hibernate.engine.NamedQueryDefinition : 对对象查询语句的抽象,会在AnnotationBinder 的bindPackage 方法里对声明了javax.persistence. @NamedQuery/NamedQueries 或者 org.hibernate.annotations. @NamedQuery/NamedQueries 的pkg new出一些 NamedQueryDefinition放入mapping对象中。
org.hibernate.engine.NamedSQLQueryDefinition : 对SQL查询语句的抽象,重用了对象查询语句的所有属性,会在AnnotationBinder 的bindPackage 方法里对声明了javax.persistence. @ NamedNativeQuery / NamedNativeQueries 或者 org.hibernate.annotations. @ NamedNativeQuery / NamedNativeQueries 的pkg new出一些 NamedSQLQueryDefinition放入mapping对象中。
org.hibernate.engine.FilterDefinition : 对查询过滤器的抽象,会在AnnotationBinder 的bindPackage 方法里对声明了 org.hibernate.annotations. @FilterDef/FilterDefs 的pkg new出一些 FilterDefinition 放入mapping对象中。
org.hibernate.mapping.TypeDef : 对类型定义的抽象,会在Configuration 的MappingsImpl 内部类的addTypeDef 方法里new出来,该方法其实是被AnnotationBinder 的bindPackage 方法里处理声明了 org.hibernate.annotations. @TypeDef/TypeDefs 的pkg时调用的。
org.hibernate.cfg. VerifyFetchProfileReferenceSecondPass : @QUESTION ,会在AnnotationBinder 的bindPackage 方法里对声明了 org.hibernate.annotations. @FetchProfile/FetchProfiles 的pkg new出一些 VerifyFetchProfileReferenceSecondPass放入mapping对象中。
org.hibernate.cfg.annotations.QueryBinder : 抽象静态帮助类