<!--开启aop切面代理 -->
<aop:aspectj-autoproxy/>
通过配置织入@Aspectj切面,通过aop命名空间的<aop:aspectj-autoproxy/>声明自动为spring容器中那些配置@aspectJ切面的bean创建代理,织入切面。当然,spring在内部依旧采用AnnotationAwareAspectJAutoProxyCreator进行自动代理的创建工作,但具体实现的细节已经被<aop:aspectj-autoproxy/>隐藏起来了
<!--开启注解 -->
<context:annotation-config/>
并且为后面编程式事务的@Transaction提供支持
<!-- 开启自动扫描后,不需配置注解,该选项包内含开启注解 -->
<context:component-scanbase-package="com.idomov"/>
扫描指定包下的全部的标有@Component的类,并注册成bean.也就是@Component的子注解@Service,@Reposity等
<!--########################################### sessionFactory管理 ########################################### -->
<!--引入外部的properties文件 -->
<context:property-placeholderlocation="classpath*:jdbc.properties"/>
<!--DataSource配置 -->
<beanid="myDataSource"class="com.jolbox.bonecp.BoneCPDataSource"
destroy-method="close">
<propertyname="driverClass"value="${jdbc.driver}"/>
<propertyname="jdbcUrl"value="${jdbc.url}"/>
<propertyname="username"value="${jdbc.username}"/>
<propertyname="password"value="${jdbc.password}"/>
<!--检查数据库连接池中空闲连接的间隔时间,单位是分,默认值:240,如果要取消则设置为0 -->
<propertyname="idleConnectionTestPeriod"value="${boncp.idleConnectionTestPeriod}"/>
<!--连接池中未使用的链接最大存活时间,单位是分,默认值:60,如果要永远存活设置为0 -->
<propertyname="idleMaxAge"value="${boncp.idleMaxAge}"/>
<!--分区数,默认值2,最小1,推荐3-4,视应用而定-->
<propertyname="partitionCount"value="${boncp.partitionCount}"/>
<!--每个分区最小的连接数 -->
<propertyname="minConnectionsPerPartition"value="${boncp.minConnectionsPerPartition}"/>
<!--每个分区最大的连接数 -->
<propertyname="maxConnectionsPerPartition"value="${boncp.maxConnectionsPerPartition}"/>
<!--创建之后最大存活时间单位秒 -->
<propertyname="maxConnectionAge"value="${boncp.maxConnectionAge}"/>
</bean>
<!--###########################################jpa entityManagerFactory
###########################################-->
<!--对标注@PersistenceContext的类经行增强,引入代理后的EntityManager实例 -->
<bean
class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor"/>
<!--对标注@Repository的类经行增强,将EntityManager异常转换为SpringDAO体系的异常 -->
<bean class="org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor"/>
<beanid="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<propertyname="dataSource"ref="myDataSource"/>
<propertyname="persistenceXmlLocation"value="classpath:META-INF/persistence.xml"/>
<propertyname="persistenceUnitName"value="idomov"/>
<propertyname="jpaVendorAdapter">
<beanclass="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<propertyname="database"value="MYSQL"/>
<propertyname="showSql"value="true"/>
<propertyname="generateDdl"value="true"/>
<propertyname="databasePlatform"value="org.hibernate.dialect.MySQL5InnoDBDialect"/>
</bean>
</property>
<propertyname="jpaProperties">
<props>
<propkey="hibernate.show_sql">false</prop>
<prop key="hibernate.format_sql">true</prop>
<propkey="hibernate.dialect">${hibernate.dialect}</prop>
<propkey="hibernate.jdbc.batch_size">${hibernate.jdbc.batch_size}</prop>
<propkey="hibernate.jdbc.fetch_size">${hibernate.jdbc.fetch_size}</prop>
<propkey="hibernate.hbm2ddl.auto">${hibernate.hbm2ddl.auto}</prop>
</props>
</property>
</bean>
<!-- JPA事务管理 -->
<beanid="transactionManager"class="org.springframework.orm.jpa.JpaTransactionManager">
<propertyname="entityManagerFactory"ref="entityManagerFactory"></property>
</bean>
在service类前加上@Transactional,声明这个service所有方法需要事务管理。每一个业务方法开始时都会打开一个事务。
<tx:annotation-driventransaction-manager="transactionManager"/>
声明使用注解让Spring管理事务,注解的方式是一种编程式事务
声明式事务有三种方式实现:第一种,使用tx标签方式;第二种,使用代理方式;第三种,使用拦截器
<!--###########################################jbpmentityManagerFactory########################################### -->
<!--配置 sessionFactory -->
<beanid="sessionFactory"
class="org.springframework.orm.hibernate3.LocalSessionFactoryBean">
可见生成的是LocalSessionFactoryBean而非SessionFactory。从LocalSessionFactoryBean的实现上看
LocalSessionFactoryBean extends AbstractSessionFactoryBean implements BeanClassLoaderAware
在AbstractSessionFactoryBeanimplements FactoryBean<SessionFactory>中有
private SessionFactory sessionFactory;
public Object getObject(); {
return this.sessionFactory;
}
顺藤摸瓜,AbstractSessionFactoryBeanextends HibernateExceptionTranslator
implements FactoryBean<SessionFactory>,InitializingBean, DisposableBean
而FactoryBean的代码为:
publicinterface FactoryBean<T> {
T getObject() throws Exception;
Class<?> getObjectType();
boolean isSingleton();
}
可见Spring在装配的时候如果发现实现了FactoryBean接口就会使用FactoryBean的getObject()方法返回对象的装配。当使用LocalSessionFactoryBean,比如applicationContext.getBean(“SessionFactory”)时,Spring返回的不是LocalSessionFactoryBean本身,他会自动调用getObject()方法,把真正的sessionFactory返回。所以不需要显式地创建一个sessionFactory,直接引用LocalSessionFactoryBean就可以
<propertyname="dataSource"ref="myDataSource"/>
<propertyname="configLocation">
<value>classpath:hibernate.cfg.xml</value>
</property>
<propertyname="mappingResources">
<list>
<!-- <value>config/hibernate/hbm/WorkFlow.hbm.xml</value>-->
</list>
</property>
<propertyname="hibernateProperties">
<value>
hibernate.dialect=${hibernate.dialect}
<!-- hibernate.hbm2ddl.auto=update
hibernate.show_sql=${hibernate.show_sql}
hibernate.format_sql= ${hibernate.format_sql} -->
hibernate.jdbc.batch_size=${hibernate.jdbc.batch_size}
hibernate.jdbc.fetch_size=${hibernate.jdbc.fetch_size}
</value>
</property>
</bean>
<!--###########################################缓存管理########################################### -->
<!--缓存定义 -->
<beanid="defaultCacheManager"
class="org.springframework.cache.ehcache.EhCacheManagerFactoryBean">
<propertyname="configLocation"value="classpath:ehcache.xml">
</property>
</bean>
<!--注解实现缓存ehcache -->
<!--<ehcache:annotation-driven cache-manager="defaultCacheManager"/> -->
</beans>
1.Hibernate一级缓存又称为“Session的缓存”。
Session内置不能被卸载,Session的缓存是事务范围的缓存(Session对象的生命周期通常对应一个数据库事务或者一个应用事务)。
一级缓存中,持久化类的每个实例都具有唯一的OID。
2.Hibernate二级缓存又称为“SessionFactory的缓存”。
由于SessionFactory对象的生命周期和应用程序的整个过程对应,因此Hibernate二级缓存是进程范围或者集群范围的缓存,有可能出现并发问题,因此需要采用适当的并发访问策略,该策略为被缓存的数据提供了事务隔离级别。
第二级缓存是可选的,是一个可配置的插件,默认下SessionFactory不会启用这个插件。
Hibernate查找对象如何应用缓存?
当Hibernate根据ID访问数据对象的时候,首先从Session一级缓存中查;
查不到,如果配置了二级缓存,那么从二级缓存中查;
如果都查不到,再查询数据库,把结果按照ID放入到缓存删除、更新、增加数据的时候,同时更新缓存。
.二级缓存的管理:
evict(Class arg0, Serializable arg1)将某个类的指定ID的持久化对象从二级缓存中清除,释放对象所占用的资源。
sessionFactory.evict(Customer.class, new Integer(1));
evict(Class arg0) 将指定类的所有持久化对象从二级缓存中清除,释放其占用的内存资源。
sessionFactory.evict(Customer.class);
evictCollection(String arg0) 将指定类的所有持久化对象的指定集合从二级缓存中清除,释放其占用的内存资源。
sessionFactory.evictCollection("Customer.orders");
//--------------------------
JPA和Hibernate之间的关系,可以简单的理解为JPA是标准接口,Hibernate是实现。Hibernate主要是通过三个组件来实现的,及hibernate-annotation、hibernate-entitymanager和hibernate-core。
hibernate-annotation是Hibernate支持annotation方式配置的基础,它包括了标准的JPA annotation以及Hibernate自身特殊功能的annotation。
hibernate-core是Hibernate的核心实现,提供了Hibernate所有的核心功能。
hibernate-entitymanager实现了标准的JPA,可以把它看成hibernate-core和JPA之间的适配器,它并不直接提供ORM的功能,而是对hibernate-core进行封装,使得Hibernate符合JPA的规范。
EntityManagerFactory对象的实现是EntityManagerFactoryImpl类,这个类有一个最重要的private属性就是Hibernate的核心对象之一SessionFactory。这个类最重要的方法是createEntityManager,来返回EntityMnagaer对象,而sessionFactory属性也传入了该方法。
EntityManager对象的实现是EntityManagerImpl类,这个类继承自AbstractEntityManagerImpl类,在AbstractEntityManager类中有一个抽象方法getSession来获得Hibernate的Session对象,正是在这个Session对象的实际支持下,EntityManagerImpl类实现了JPA的EntityManager接口的所有方法,并完成实际的ORM操作。
此外,hibernate-entitymanager 包中还有QueryImpl类利用EntityManagerImpl的支持实现了JPA的Query接口;TransactionImpl利用EntityManagerImpl的支持实现了JPA的EntityTransaction接口。
至此,Hibernate通过hibernate-entitymanager包完成了对于JPA的全部支持工作。
//--------------------------
hibernate 简介:
hibernate是一个开源框架,它是对象关联关系映射的框架,它对JDBC做了轻量级的封装,而我们java程序员可以使用面向对象的思想来操纵数据库。
hibernate核心接口
session:负责被持久化对象CRUD操作
sessionFactory:负责初始化hibernate,创建session对象
configuration:负责配置并启动hibernate,创建SessionFactory
Transaction:负责事物相关的操作
Query和Criteria接口:负责执行各种数据库查询
hibernate工作原理:
1.通过Configuration config = new Configuration().configure();//读取并解析hibernate.cfg.xml配置文件
2.由hibernate.cfg.xml中的<mapping resource="com/xx/User.hbm.xml"/>读取并解析映射信息
3.通过SessionFactory sf = config.buildSessionFactory();//创建SessionFactory
4.Session session = sf.openSession();//打开Sesssion
5.Transaction tx = session.beginTransaction();//创建并启动事务Transation
6.persistent operate操作数据,持久化操作
7.tx.commit();//提交事务
8.关闭Session
9.关闭SesstionFactory
如何优化Hibernate?
1.使用双向一对多关联,不使用单向一对多
2.灵活使用单向一对多关联
3.不用一对一,用多对一取代
4.配置对象缓存,不使用集合缓存
5.一对多集合使用Bag,多对多集合使用Set
6. 继承类使用显式多态
7. 表字段要少,表关联不要怕多,有二级缓存撑腰