El marco de Spring se crea debido a la complejidad del desarrollo de software. Spring usa javabeans básicos para hacer cosas que anteriormente solo era posible por EJB. Sin embargo, el propósito de Spring no se limita al desarrollo del lado del servidor. Desde la perspectiva de la simplicidad, la capacidad de prueba y el acoplamiento suelto, la mayoría de las aplicaciones Java pueden beneficiarse de la primavera. Spring es una inversión de control liviana (COI) y marco de contenedores orientado a la sección (AOP).
◆ Propósito: resolver la complejidad del desarrollo de aplicaciones empresariales
◆ Función: use Javabean básico en lugar de EJB y proporciona más funciones de aplicación empresarial
◆ Alcance: cualquier aplicación Java
La inversión de control (COI en abreviatura inglesa) da el derecho de crear objetos al marco, que es una característica importante del marco y no es un término especial para la programación orientada a objetos. Incluye inyección de dependencia y búsqueda de dependencia. En la capa comercial tradicional, cuando se necesitan recursos, se encuentran nuevos recursos en la capa comercial, de modo que el acoplamiento (interdependencia y correlación entre programas) sea mayor. Ahora entregue la nueva parte para la primavera para lograr una alta cohesión y un bajo acoplamiento. En resumen: originalmente, cada vez que se llamaba a la capa DAO o al método de la capa de servicio, la aplicación usaría NUEVO, y ahora los nuevos derechos se entregaron a la primavera, ¡y qué recursos se necesitaban se obtuvieron de la primavera!
1. Descargue el paquete JAR de dependencia requerido para el marco
El sitio web oficial de Spring es: http://spring.io/
Descargue el paquete jar: http://repo.springsource.org/libs-release-local/org/springframework/spring
2. Importe el paquete de jar básico
De hecho, los frascos básicos de núcleo incluyen frijoles; contexto; núcleo; paquetes de expresión y otros dependen de los registros log4j. Por supuesto, los frascos de primavera son más que eso, se agregan lentamente en la etapa posterior.
3. Configurar el archivo de configuración LOG4J
El archivo de registro se define en el directorio SRC
### Mensajes de registro directo a stdout ### log4j.appender.stdout = org.apache.log4j.consoleppenderlog4j.appender.stdout.toRget = system.errlog4j.appender.stdout.layout = org.apache.log4j.patternlayoutlog4j.appender.stdout.conversionpattern = %d @ { %c {1}: %l - %m %n ### Mensajes directos para presentar mylog.log ##. %C {1}: %l - %m %n ### Establecer niveles de registro - Para un cambio de registro más detallado 'Info' a 'Debug' ### log4j.rootlogger = info, stdout4. Pruebe si el archivo de registro se implementa correctamente
paquete com.clj.demo1; importar org.apache.log4j.logger; import org.junit.test;/** * uso de registro de demo * @author administrador * */public class Demo1 {// Crea Log Clase private Logger log = logger.getLogger (Demo1.classs); @Test public void run1 () {// Cambie la información en el atributo log4j.rootlogger a OFF, y log.info ("ejecutar"); }}5. Defina una interfaz e implementa la clase
interfaz:
paquete com.clj.demo2; interfaz pública UserService {public void sayshello ();}Clase de implementación
paquete com.clj.demo2; public class UserServiceImpl implementa UserService {Nombre de cadena privada; public String getName () {nombre de retorno; } public void setName (nombre de cadena) {this.name = name; } public void init () {System.out.println ("Inicializar .."); } public void sayshello () {System.out.println ("Hello Spring"+"/t"+nombre); } public void Destory () {System.out.println ("destruir .."); }}6. Definir archivos de configuración específicos de Spring
Defina el nombre de ApplicationContext.xml, la ubicación es SRC, el mismo directorio que el archivo de registro, importe las restricciones correspondientes e inyecte la clase de implementación en el archivo de configuración. Comience con el principio, use restricciones de frijoles
<? xml versión = "1.0" encoding = "utf-8"?> <beans xmlns = "http://www.springframework.org/schema/beans" xmlns: xsi = "http://www.w3.org/2001/xmlschema-instance" "" "" xmlns: p = "http://www.springframework.org/schema/p" xsi: schemalocation = "http://www.springframework.org/schema/beans http:/www.springframework.org/schema/Beans/spring-beansding- bean tag 1. The id value is unique (must write) 2. Note: class is the implementation classpath, not an interface (must write) 3. Initialization work before the core method is executed (select write) 4. Initialization work after the core method is executed (select write) --> <bean id="userService" init-method="init" destroy-method="destory"> <property name="name" value="Jaxiansen"></property> </bean> </beans>
7. Prueba
public class Demo1 { /*** Way original* /@test public void run () {// Crear clase de implementación UserServiceImpl S = New UserServiceImpl (); S.SetName ("Jaxiansen"); S.Sayhello (); } / *** Versión de fábrica antigua BeanFactory* Old Factory no creará objetos de archivo de configuración* / @test public void run2 () {beanFactory factory = new XMLBeanFactory (new ClassPathResource ("ApplicationContext.xml")); UserService US = (UserService) Factory.getBean ("UserService"); US.SayHello (); } /*** Use el método Spring Framework IOC* Cree un servidor de inicio en la nueva versión de Factory para crear un objeto de archivo de configuración, y no es necesario cargar la fábrica al llamar nuevamente* /@Test public void run3 () {// Crear la fábrica y cargar el archivo de configuración central (classPathXMLApPlicationContex. ClasspathxmLapplicationContext ("ApplicationContext.xml"); // Obtenga el objeto del valor de fábrica (valor de identificación en el archivo de configuración, el polimorfismo se usa aquí) UserService usi = (UserService) ac.getBean ("UserService"); // llamando al método del objeto para ejecutar usi.sayhello (); } /*** Método de Destrución Destration* El método de destrucción de frijoles no se ejecutará automáticamente* a menos que se llame automáticamente en scope = singleton o en un contenedor web, la función principal o el caso de prueba debe llamarse manualmente (debe usar el método Close () de classpathxmlaPplicationContext)* /@Test public public run4 () {// Crear una fábrica y cargar la configuración de la núcleo de la núcleo (ClassPathXMLApPlicationContext se encuentra en src) classpathxmlaPlaPlicationContext ac = new ClassPathXMLApPlicationContext ("ApplicationContext.xml"); // Obtenga el objeto del valor de fábrica (valor de identificación en el archivo de configuración, el polimorfismo se usa aquí) UserService usi = (UserService) ac.getBean ("UserService"); // llamando al método del objeto para ejecutar usi.sayhello (); // La clase de implementación de AplicationContext proporciona un método de cierre, y la fábrica puede cerrarse y el método Destory-Method se puede ejecutar. }}La diferencia entre las antiguas fábricas y las nuevas fábricas
* Diferencia entre BeanFactory y ApplicationContext
* BeanFactory - BeanFactory toma una carga perezosa, y el frijol se inicializará solo cuando obtenga la primera vez
* ApplicationContext: al cargar ApplicationContext.xml, se creará una instancia específica del objeto Bean, y se proporcionan algunas otras funciones.
* Entrega de eventos
* Asamblea automática de frijoles
* Implementaciones de contexto de varias capas de aplicación
Resumen: Esta es la demostración más básica, que configura la clase de implementación en el archivo de configuración de Spring. Cada vez que se inicie el servidor, se cargará el archivo de configuración, instanciando así la clase de implementación.
1. ¿Qué es la inyección de dependencia?
La primavera puede organizar efectivamente objetos de los niveles de aplicación J2EE. Ya sea el objeto de acción de la capa de control, el objeto de servicio de la capa comercial o el objeto DAO de la capa de persistencia, puede coordinarse y ejecutarse orgánicamente bajo la gestión de Spring. Spring organiza objetos de cada capa juntos de una manera libremente acoplada. Los objetos de acción no necesitan preocuparse por la implementación específica de objetos de servicio, los objetos de servicio no necesitan preocuparse por la implementación específica de objetos de capa persistentes, y las llamadas a cada objeto de capa están completamente orientadas a la interfaz. Cuando el sistema necesita ser refactorizado, la cantidad de reescritura de código se reducirá considerablemente. La inyección de dependencia hace que el frijol y el frijol se organicen en los archivos de configuración, en lugar de ser codificados. Comprender la inyección de dependencia
La inyección de dependencia y la inversión de control son el mismo concepto. El significado específico es: cuando un rol (tal vez una instancia de Java, la persona que llama) necesita la ayuda de otro rol (otra instancia de Java, persona que llama), en el proceso de programación tradicional, la persona que llama generalmente es creada por la persona que llama. Pero en la primavera, el trabajo de crear el Callee ya no lo realiza la persona que llama, por lo que se llama inversión de control; El trabajo de crear la instancia de Callee generalmente lo realiza el contenedor de resorte y luego se inyecta en la persona que llama, por lo que también se llama inyección de dependencia.
Ya sea que se trate de inyección de dependencia o inversión de control, significa que Spring adopta una forma dinámica y flexible de administrar varios objetos. Las implementaciones específicas entre objetos son transparentes entre sí.
2. El concepto de COI y DI
* COI - Inverso del control, inversión de control, ¡Invierta el derecho de creación del objeto a Spring! !
* DI: inyección de dependencia, inyección de dependencia, cuando el marco de resorte es responsable de crear objetos de frijoles, inyectando dinámicamente objetos de dependencia en el componente de frijoles. !
3. Demo
Para las variables miembros de la clase, hay dos métodos de inyección comunes.
Inyección del método del conjunto de propiedades y inyección del método del constructor
Primero demuestre el primer tipo: inyección de método de conjunto de propiedades
1) Capa persistente
paquete com.clj.demo3; public class CustomerDaoImpl {public void save () {System.out.println ("Soy Dao de la capa de persistencia"); }}2) Capa comercial
Nota: En este momento, quiero inyectar la capa de persistencia en la capa de negocios y entregar el derecho de crear la instancia de la capa de persistencia al marco, la condición es que la capa comercial debe proporcionar los atributos del miembro y establecer métodos de la capa de persistencia.
El paquete com.clj.demo3;/** * La inyección de dependencia inyecta la capa DAO en la capa de servicio * @Author Administrator * */public ClasserServiceImpl {// Proporcione el miembro Zodiac, proporcione el método establecido CustomerDaoImpl CustomerDao; public void setCustomerDao (CustomerDaoImpl CustomerDao) {this.customerdao = customerDao; } public void save () {System.out.println ("Yo soy el servicio ..."); // 1. Método original // nuevo CustomerDaoImpl (). Save (); //2.Spring IOC Method CustomerDao.save (); }}3) Configuración del archivo de configuración
<
4) Prueba
/** * Método de inyección de dependencia de primavera * Inyectar la capa DAO en la capa de servicio */@Test public void run2 () {// Cree la fábrica, cargue el archivo de configuración, y se crea el servicio de clientes, creando así customerdao applicationContext context = new ClassPathxMlaPplicationContext ("ApplicationContext.xml");; CustomerServiceImpl CSI = (CustomerServiceImpl) context.getBean ("CustomerService"); csi.save (); }El segundo tipo: inyección del método de construcción
1) Clase POJO y proporcionar métodos de constructor
paquete com.clj.demo4;/** * El método de inyección de demostración * @author administrador * */public class Car1 {private String cname; precio doble privado; Public Car1 (String Cname, Double Price) {super (); this.cname = cname; this.price = precio; } @Override public string toString () {return "car1 [cname =" + cname + ", precio =" + precio + "]"; }}2) Configuración del archivo de configuración
< value = "400000"/> </bean>
3) Prueba
@Test public void run1 () {applicationContext AC = new ClassPathXMLApPlicationContext ("ApplicationContext.xml"); Car1 Car = (CAR1) AC.GetBean ("Car1"); System.out.println (CAR); }Extensión: la construcción del método inyecta un objeto en otro
1) Clase POJO: Propósito: Inyecte el automóvil en la columna anterior en humanos y conviértalo en uno de los atributos. En esta clase, se deben proporcionar los atributos miembros del automóvil y se deben proporcionar métodos de construcción parametrizados.
paquete com.clj.demo4; persona de clase pública {nombre de cadena privada; auto privado1 coche1; Persona pública (nombre de cadena, Car1 Car1) {super (); this.name = name; this.car1 = car1; } @Override public String toString () {return "persona [name =" + name + ", car1 =" + car1 + "]"; }}2) Archivo de configuración
<
4. Cómo inyectar una matriz de colección
1) Defina la clase POJO
paquete com.clj.demo4; import java.util.arrays; import java.util.list; import java.util.map; import java.util.properties; import java.util.set;/** * Demuestre la forma de establecer inyección * @author administrador * */usuario de clase pública {cadena privada [] Arrrs; Lista de lista privada <String>; Conjunto privado <String> sets; mapa privado <string, string> map; Propiedades privadas Pro; public void setPro (Properties Pro) {this.pro = pro; } public void setsets (set <string> sets) {this.sets = sets; } public void setMap (map <string, string> map) {this.map = map; } public void setList (list <string> list) {this.list = list; } public void setarrrs (string [] arrrs) {this.arrs = arrrs; } @Override public string toString () {return "user [arrs =" + arrays.toString (arrs) + ", list =" + list + ", sets =" + sets + ", map =" + map + ", pro =" + pro + "]"; }}2) Archivo de configuración
< </property> <!-set set-> <property name = "sets"> <set> <value> jaja </value> <value> jaja </valor> </set> </propiety> <!-map set-> <Property name = "map"> <s map> <entry key = "aa" value = "Rainbow"/> <Entry Key = "BB" Value = "Hellowvenus"/> <</mapser <Property name = "pro"> <props> <prot key = "username"> root </prop> <proping key = "contraseña"> 123 </prop> </props> </propianas> </bean>
3) Prueba
/ *** PRUEBA DE LA COLECCIÓN DE INYECCIÓN*/ @TEST public void run3 () {ApplicationContext AC = new ClassPathXMLApPlicationContext ("ApplicationContext.xml"); Usuario user = (usuario) ac.getBean ("usuario"); System.out.println (usuario); }5. Cómo desarrollarse en módulos
Agregue la etiqueta <import> al archivo de configuración principal (suponga que, un archivo de configuración applicationContext2.xml se define en el paquete com.clj.test)
<!-Introducción de otros archivos de configuración por desarrollo del módulo-> <importe resource = "com/clj/test/applicationContext2.xml"/>
1. Comenzando
1). Paquete de jarra de Import
Además de los 6 paquetes anteriores, también necesita un paquete Spring-AOP para reproducir la anotación.
2). Capa de persistencia y capa de implementación (las interfaces se ignoran aquí)
Capa persistente
paquete com.clj.demo1; import org.springframework.context.annotation.scope; import org.springframework.stereotype.component; import org.springframework.stereotype.repository;/** * Contenedor administración de contenedores entregada por userDaoImpl to ioc * @aAutor Administrator * * */public Class userments Userements Userments Userdao {@Override public void save () {System.out.println ("Guardar el cliente .."); }}Capa comercial
paquete com.clj.demo1; import javax.annotation.postConstruct; import org.springframework.beans.factory.annotation.aUtowired; importar org.springframework.beans.factory.annotation.qualifier; import og.springframework.beans.factory.annotation.value; import org.springframework.stereotype.component; public class UserServiceImpl implementa UserService {@Override public void Sayshello () {System.out.println ("Hello Spring"); }}3). Definir el archivo de configuración
En este momento, las restricciones deben agregar restricciones de contexto y agregar escaneo de componentes
<? xml versión = "1.0" encoding = "utf-8"?> <beans xmlns = "http://www.springframework.org/schema/beans" xmlns: xsi = "http://www.w3.org/2001/xmlschema-instance" "" "" xmlns: context = "http://www.springframework.org/schema/context" xsi: schemalocation = "http://www.springframework.org/schema/beans http:/www.springframework.org/schema/scoans/spring-ste http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd "> <!-Bean Definiciones aquí-> < Base-Package = "com.clj.demo1"/> </beans>
4) Agregar anotaciones a la clase de implementación
/*** Anotación de componentes, que se puede usar para marcar la clase actual* similar a <bean id = "userService">* valor significa dar un alias para la clase*/@componente (value = "userservice") Public Class UserServiceImpl implementa UserService {// omitido}5) Escribir pruebas
/ *** Método de anotación*/ @test public void run2 () {applicationContext AC = new ClassPathXMLApPlicationContext ("ApplicationContext.xml"); UserService US = (UserService) AC.GetBean ("UserService"); US.SayHello (); }2. Acerca de los atributos comunes de gestión de frijoles
1. @Component: componente. (actuó en la clase) La anotación más primitiva, está bien escribir esto para todas las clases que necesitan anotación, es general
2. Tres anotaciones derivadas de @Component se proporcionan en primavera: (las funciones son actualmente consistentes)
* @Controller - funciona en la capa web
* @Service - actúa a nivel comercial
* @Repository - actuando sobre la capa de persistencia
* Nota: Estas tres anotaciones están destinadas a aclarar el propósito de la clase de anotación, y la primavera lo mejorará en versiones posteriores.
3. Anotaciones para la inyección de atributos (nota: Cuando se usa la inyección de anotaciones, no necesita proporcionar un método establecido)
* Si se trata de un tipo normal de inyección, puede usar la anotación de valor
* @Value - para inyectar tipos normales
* Si el tipo de objeto inyectado, use la siguiente anotación
* @AUtowired: de forma predeterminada, el tipo se ensambla automáticamente por tipo, y no tiene nada que ver con el nombre de clase de la clase inyectada.
* Si quieres inyectar por nombre
* @Qualifier: el uso forzado de la inyección de nombre debe usarse con autowired, especificar el nombre de la clase y relacionado con el nombre de la clase inyectado
* @Resource - equivalente a @aUtowired y @qualifier
* Enfatizar: anotaciones proporcionadas por Java
* El atributo usa el atributo de nombre
4. Anotación del alcance del frijol
* Anotado como @scope (valor = "prototipo"), que se usa en la clase. Los valores son los siguientes:
* Singleton - Singleton, valor predeterminado
* Prototipo - múltiples casos
5. Configuración del ciclo de vida del frijol (comprender)
* La anotación es la siguiente:
* @PostConstruct-equivalente al método inicial
* @Predestroy-equivalente a destruir el método
1. Demuestre anotación de objetos de atributo
Condición: Atributos de inyección (nombre) y objeto (userDaoImpl) en la capa comercial mediante escaneo.
1) Abra la capa de persistencia para escanear la anotación
//@componente (valor = "userdao") Universal Class Annotation@Repository (value = "UD") Public Class UserDaoMpl implementa UserDao {@Override public void save () {System.Println ("Guardar el cliente ..."); }}2) La capa comercial proporciona anotaciones para atributos y objetos
paquete com.clj.demo1; import javax.annotation.postConstruct; import org.springframework.beans.factory.annotation.aUtowired; importar org.springframework.beans.factory.annotation.qualifier; import og.springframework.beans.factory.annotation.value; import org.springframework.stereotype.component;/** * Anotación de componentes, se puede usar para marcar la clase actual * similar a <bean id = "userService"> * valor significa dar un alias a la clase * /// @@cope (valor = "grototipo") múltiples columnas (columna SingTletipo es una columna única) @Component (value = "UsserService") Public ClassSeSEnseSEnseSEmentSeSEmentSeSEmentSeSEmentSeMils // Anotación de atributos: es equivalente a inyectar la cadena especificada en el atributo de nombre. El método SetName se puede omitir sin escribir @Value (value = "Jaxiansen") Nombre de cadena privada; /** * Método de inyección de referencia 1: Autowired () * Método de inyección de referencia 2: Autowired () + Calificador * Método de inyección de referencia 3: @Resource (name = "userdao") Método Java, identificar inyección por nombre * // Autowired () está automáticamente ensamblado y inyectado por tipo (Desvasas (porque coincide con Tipo, por lo que no es muy accesible) @auted) @Ayectado automáticamente). @Qualifier (valor = "UD") // Inyección por nombre, debe usarse con Autowired. Ambos pueden especificar la clase de usuarios privados de usuarios de usuarios; // Tenga en cuenta que el valor en el calificador es el nombre de anotación en la parte superior del nombre de la clase userDaoMpl, o puede especificar el nombre de ID del bean en el archivo de configuración/*public void setName (nombre de cadena) {this.name = name; }*/ @Override public void sayshello () {System.out.println ("Hello Spring"+nombre); userdao.save (); } // @PostConstruct Annotation para la inicialización en Action Lifecycle @PostConstruct public void init () {System.out.println ("Inicializar ..."); }}3) El archivo de configuración solo debe habilitarse para escanear todos los archivos de configuración
<? xml versión = "1.0" encoding = "utf-8"?> <beans xmlns = "http://www.springframework.org/schema/beans" xmlns: xsi = "http://www.w3.org/2001/xmlschema-instance" "" "" xmlns: context = "http://www.springframework.org/schema/context" xsi: schemalocation = "http://www.springframework.org/schema/beans http:/www.springframework.org/schema/scoans/spring-ste http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd "> <!-Bean Definiciones aquí-> < Base-Package = "com.clj.demo1"/> </beans>
Nota: En cuanto a las colecciones, se recomienda usar archivos de configuración
2. Spring Framework integra las pruebas de unidades JUNIT
1) Agregue el paquete de dependencia requerido Test Spring.Jar
Nota: Myeclipes viene con su propio entorno Junit, pero a veces debido a problemas de versión, puede ser necesario un nuevo entorno JUnit. Aquí he descargado un nuevo paquete JUNIT-4.9 JAR en línea. Si Myeclipes es más nuevo, no necesita considerarlo.
2) Escriba una clase de prueba y agregue las anotaciones correspondientes
@Runwith y @ContextConfiguration (esto se utiliza para cargar el archivo de configuración, porque la ruta predeterminada desde Webroot es un directorio de primer nivel, además de determinar que SRC es un directorio de primer nivel)
paquete com.clj.demo2; import javax.annotation.resource; import org.junit.test; import org.junit.runner.runwith; import og.springframework.test.context.contextconfiguration; importar org.springframework.test.context.junit4.springjunit4clunner; import com.clj.demo1.userservice; @runwith (springjunit4classrunner.class) @contextconfiguration ("classpath: applicationContext.xml") clase pública Demo2 {@resource (name = "Userservice") UserService de usuarios privados; @Test public void run1 () {Userservice.sayhello (); }}6. AOP del marco de primavera
1. Que es AOP
* En la industria del software, AOP es la abreviatura de la programación orientada a los aspectos, lo que significa: programación de facetas, modularidad funcional
* AOP es un paradigma de programación, afiliado a la categoría de trabajo suave, guiando a los desarrolladores cómo organizar las estructuras del programa
* AOP fue propuesto por primera vez por la Organización AOP Alliance y formuló un conjunto de normas. Spring introdujo las ideas de AOP en el marco y debe cumplir con las especificaciones de AOP Alliance.
* Una tecnología para lograr el mantenimiento unificado de las funciones del programa a través de la precompilación y los agentes dinámicos durante el tiempo de ejecución
* AOP es una continuación de OOP, un tema candente en el desarrollo de software, una parte importante del marco de primavera y un paradigma derivado de la programación funcional.
* Usando AOP, se pueden aislar varias partes de la lógica comercial, reduciendo así el acoplamiento entre las partes de la lógica comercial, mejorando la reutilización del programa y mejorando la eficiencia del desarrollo.
AOP adopta un mecanismo de extracción horizontal, reemplazando el código repetitivo del sistema tradicional de herencia vertical (monitoreo del rendimiento, gestión de transacciones, inspección de seguridad, almacenamiento en caché)
2. Por qué estudiar AOP
* ¡El programa se puede mejorar sin modificar el código fuente! ! (Cree un proxy para un método fijo. Antes de acceder al método, ingrese primero el proxy. En el proxy, puede escribir más funciones para que el método sea más potente y mejorar el programa)
AOP: programación orientada, modulariza todo, cada módulo es relativamente independiente, los módulos se pueden compartir (igual) y diferentes están particularmente personalizados. Use esto en lugar de la programación vertical tradicional para mejorar la reutilización del programa
3. Implementación de AOP (principio de implementación)
La implementación de AOP incluye dos métodos proxy <1> para implementar interfaces de clase: use JDK Dynamic Proxy <2> No implementadas interfaces de clase: use CGLIB Dynamic Proxy
1. Implementar el proxy dinámico JDK
1) Defina la clase de implementación de la interfaz de la capa de persistencia
paquete com.clj.demo3; interfaz pública userdao {public void save (); Public void Update ();} paquete com.clj.demo3; public class UserDaoImpl implementa UserDao {@Override public void save () {System.out.println ("Guardar usuario"); } @Override public void Update () {System.out.println ("Modificar usuario"); }}2) Defina la clase de herramienta proxy dinámica JDK
Esta clase de herramienta agrega algunas funciones al ejecutar el método de guardado de la capa de persistencia, y en el desarrollo, es necesario mejorar un cierto método sin cambiar el código fuente
paquete com.clj.demo3; import java.lang.reflect.invocationHandler; import java.lang.reflect.method; import java.lang.reflect.proxy;/** * Genere objetos proxy en JDK (Demostrar los principios AOP) * @Author Administrator * */public Class MyProxyutils {Usuarios públicos STAT Userdao dao) {// use la clase proxy para generar objetos proxy userdao proxy = (userDao) proxy.newproxyInstance (dao.getclass (). GetClassLoader (), dao.getClass (). Getinterfaces (), nuevo invocationHanler () {// como el objeto de proxy se ejecutará, el objeto se ejecutará, se ejecutará, se ejecutará, el metod de Invede, lo que se ejecutará, se ejecutará el objeto de Inveded, lo que se ejecutará, el Meté. Invoke (Object Proxy, Método, Object [] args) lanza Throwable {// proxy representa el objeto de proxy actual // método del método ejecutado por el objeto actual // args parámetros encapsulados // deja que la clase guarde o actualice el método ejecutarse normalmente si ("guardar" .equals (método.getName ())) {System.out.Println ("Guardar ejecutado"); método.invoke (Dao, args); Return proxy; }}3) Prueba
paquete com.clj.demo3; import org.junit.test; public class Demo1 {@test public void run1 () {// Obtenga el objeto de destino UserDao Dao = new UserDaImpl (); dao.save (); dao.update (); System.out.println ("=================================================================== =============================================================================================================================================== Use la clase de herramientas para obtener el objeto proxy userDao2. Implementar la tecnología CGLIB
1) Defina la capa de persistencia, no hay interfaz en este momento
paquete com.clj.demo4; public class bookdaoImpl {public void save () {System.out.println ("Save Book"); } public void Update () {System.out.println ("Modify Book"); }}2) Escribir clases de herramientas
paquete com.clj.demo4; import java.lang.reflect.method; import org.springframework.cglib.proxy.enhancer; import org.springframework.cglib.proxy.methodinterceptor; import og.springframework.cglib.proxy.methodproxy;/** ** principas de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementación de la implementation. Método proxy * @Author Administrator * */public class MyCGlibutils {/** * Genere el objeto proxy usando el método CGLIB * @return */public static bookdaoImpl getProxy () {mejor mejor potencador = nuevo mejor (); // Establecer el potencador de clase principal.setsuperClass (bookdaoImpl.class); // Establezca la función de devolución de llamada mejor.setCallback (nuevo MethodInterceptor () {@Override Public Object Intercept (Object obj, Method Method, Object [] objs, MethodProxy MethodProxy) lanza showeable {if (método.getName (). EQUALS ("Guardar")) {System.PrintlnN ("guardado"); System.Println (prota } return MethodProxy.Invokesuper (obj, objs); // es el método ejecutado}}); // Generar el objeto proxy bookdaoImpl proxy = (bookdaoImpl) pothancer.create (); Return proxy; }}3) Escribir clases de prueba
paquete com.clj.demo4; import org.junit.test; public class Demo1 {@test public void run1 () {// Object Target bookDaoImpl dao = new BookDaImpl (); dao.save (); dao.update (); System.out.println ("==============================); bookdaoImpl proxy = mycglibutils.getProxy (); proxy.save (); proxy.Update ();}}3. Desarrollo de AOP de Spring basado en SUPSJ (método de archivo de configuración)
1) Implemente el entorno e importe el paquete JAR correspondiente
2) Crear archivos de configuración e introducir restricciones AOP
<Beans xmlns = "http://www.springframework.org/schema/beans" xmlns: xsi = "http://www.w3.org/2001/xmlschemainstance" xmlns: aop = "http://wwww.springfframe xsi: schemalocation = "http://www.springframework.org/schema/beans http://www.springframework.org/schema/aop http://www.springframework.org/ http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd ">
3) Crear interfaces e implementar clases
paquete com.clj.demo5; interfaz pública customerdao {public void save (); Public void Update ();} paquete com.clj.demo5;/** * Use el archivo de configuración para interpretar AOP * @author Administrator * */public classDaoMpl implementa CustomerDao {@Override public void save () {// simuló excepción // int a = 10/0; System.out.println ("Guardar al cliente"); } @Override public void Update () {// TODO Auto Generado Método stub System.out.println ("actualizado al cliente"); }}4) Defina la clase faceta
paquete com.clj.demo5; import org.aspectj.lang.procedingjoinpoint;/** * FACET CLASS: Punto de entrada + notificación * @author administrador * */public class myAspectXMl {/** * Notificación (mejora específica) */public void log () {System.out.Println ("log log"); } / ** * El método se ejecuta correctamente o las excepciones se ejecutarán * / public void después () {System.out.println ("Notificación final"); } /*** Después de ejecutar el método, se ejecuta la notificación posterior. Si se produce una excepción en el programa, la notificación posterior no se ejecutará */ public void afterReturn () {System.out.println ("Post Notificación"); } / ** * Después de ejecutar el método, si hay una excepción, la notificación de excepción se ejecutará * / public void Afterthrowing () {System.out.println ("Notificación de excepción"); } /*** Notificación envolvente: la notificación se realiza antes y después de ejecutar el método. * De forma predeterminada, el método del objeto de destino no se puede ejecutar, y el objeto de destino debe ejecutarse manualmente */ public void alrededor (procedimiento de punto de unión) {System.out.println ("Wrap Notification 1"); // deja que el método del objeto de destino ejecute intente {unkepoint.proced (); } Catch (Throwable E) {// TODO Auto Generado Bloque E.PrintStackTrace (); } System.out.println ("Wrap Notification 2"); }}5) Inyectar clases de implementación y clases de facetas
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd"> <!-- bean definitions here --> <!-- 配置客户的dao --> <bean id="customerDao"/> <!-- 编写切面类配置好--> <bean id="myAspectXml"/> <!-- 配置AOP --> <aop:config> <!-- 配置切面类:切入点+通知(类型)--> <aop:aspect ref="myAspectXml"> <!-- 配置前置通知,save方法执行之前,增强方法会执行--> <!-- 切入点表达式:execution(public void com.clj.demo5.CustomerDaoImpl.save()) --> <!-- 切入点表达式: 1.execution()固定的,必写2.public可以省略不写3.返回值必写,严格根据切入点方法而定,否则增强方法不会执行,可以用*代替,表示任意的返回值4.包名必写,可以用*代替(如:*..*(默认所有包); com.clj.*) 5.类名必写,可以部分用*(如*DaoImpl表示以'DaoImpl'结尾的持久层实现类),但不建议用*代替整个类名6.方法必写,可以部分用*(如save*表示以'save'开头的方法),但不建议用*代替整个类名7.方法参数根据实际方法而定,可以用'..'表示有0或者多个参数--> <!-- <aop:before method="log" pointcut="execution(public void com.clj.*.CustomerDaoImpl.save(..))"/> --> <aop:before method="log" pointcut="execution(* *..*.*DaoImpl.save*(..))"/> </aop:aspect> </aop:config></beans>
6)测试
package com.clj.demo5;import javax.annotation.Resource;import org.junit.Test;import org.junit.runner.RunWith;import org.springframework.test.context.ContextConfiguration;import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;@RunWith(SpringJUnit4ClassRunner.class)@ContextConfiguration("classpath:applicationContext.xml")public class Demo1 { @Resource(name="customerDao") private CustomerDao customerDao; @Test public void run(){ customerDao.save(); customerDao.update(); }}扩展:切面类升级
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd"> <!-- bean definitions here --> <bean id="myAspectXml"/> <aop:config> <aop:aspect ref="myAspectXml"> <!-- 配置最终通知<aop:after method="after" pointcut="execution(* *..*.*DaoImpl.save*(..))"/>--> <!-- 配置后置通知<aop:after-returning method="afterReturn" pointcut="execution(* *..*.*DaoImpl.save*(..))"/>--> <!-- 配置异常通知<aop:after-throwing method="afterThrowing" pointcut="execution(* *..*.*DaoImpl.save*(..))"/>--> <aop:around method="around" pointcut="execution(* *..*.*DaoImpl.update*(..))"/> </aop:aspect> </aop:config></beans>
4、Spring框架AOP之注解方式
1)创建接口和实现类
package com.clj.demo1;public interface CustomerDao { public void save(); public void update();} package com.clj.demo1;public class CustomerDaoImpl implements CustomerDao{ @Override public void save() { // TODO Auto-generated method stub System.out.println("Save customer.."); } @Override public void update() { // TODO Auto-generated method stub System.out.println("Update customer"); }}2)定义切面类
package com.clj.demo1;import org.aspectj.lang.ProceedingJoinPoint;import org.aspectj.lang.annotation.After;import org.aspectj.lang.annotation.Around;import org.aspectj.lang.annotation.Aspect;import org.aspectj.lang.annotation.Before;import org.aspectj.lang.annotation.Pointcut;/** * 注解方式的切面类* @Aspect表示定义为切面类*/@Aspectpublic class MyAspectAnno { //通知类型:@Before前置通知(切入点的表达式) @Before(value="execution(public * com.clj.demo1.CustomerDaoImpl.save())") public void log(){ System.out.println("记录日志。。"); } //引入切入点@After(value="MyAspectAnno.fun()") public void after(){ System.out.println("执行之后"); } @Around(value="MyAspectAnno.fun()") public void around(ProceedingJoinPoint joinPoint){ System.out.println("环绕通知1"); try { //让目标对象执行joinPoint.proceed(); } catch (Throwable e) { // TODO Auto-generated catch block e.printStackTrace(); } System.out.println("环绕通知2"); } //自定义切入点@Pointcut(value="execution(public * com.clj.demo1.CustomerDaoImpl.save())") public void fun(){ }}3)配置切面类和实现类,并开启自动代理
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd"> <!-- 开启自动注解代理--> <aop:aspectj-autoproxy/> <!-- 配置目标对象--> <bean id="customerDao"/> <!-- 配置切面类--> <bean id="myAspectAnno"/></beans>
spring提供了JDBC模板:JdbcTemplate类
1.快速搭建
1)部署环境
这里在原有的jar包基础上,还要添加关乎jdbc的jar包,这里使用的是mysql驱动
2)配置内置连接池,将连接数据库程序交给框架管理,并配置Jdbc模板类
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd"> <!-- 先配置连接池(内置) --> <bean id="dataSource"> <property name="driverClassName" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="username" value="root"/> <property name="password" value="root"/> </bean> <!-- 配置JDBC的模板类--> <bean id="jdbcTemplate"> <property name="dataSource" ref="dataSource"/> </bean></beans>
3) Prueba
package com.clj.demo2;import java.sql.ResultSet;import java.sql.SQLException;import java.util.List;import javax.annotation.Resource;import org.apache.commons.dbcp.BasicDataSource;import org.junit.Test;import org.junit.runner.RunWith;import org.springframework.cglib.beans.BeanMap;import org.springframework.jdbc.core.JdbcTemplate;import org.springframework.jdbc.core.RowMapper;import org.springframework.test.context.ContextConfiguration;import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;/** * 测试JDBC的模板类,使用IOC的方式* @author Administrator * */@RunWith(SpringJUnit4ClassRunner.class)@ContextConfiguration("classpath:applicationContext.xml")public class Demo2 { @Resource(name="jdbcTemplate") private JdbcTemplate jdbcTemplate; /** * 插入*/ @Test public void run1(){ String sql="insert into t_account values(null,?,?)"; jdbcTemplate.update(sql,"李钇林",10000); } /** * 更新*/ @Test public void run2(){ String sql="update t_account set name=? where id=?"; jdbcTemplate.update(sql,"李钇林",1); } /** * 删除*/ @Test public void run3(){ String sql="delete from t_account where id=?"; jdbcTemplate.update(sql,4); } /** * 测试查询,通过主键来查询一条记录*/ @Test public void run4(){ String sql="select * from t_account where id=?"; Account ac=jdbcTemplate.queryForObject(sql, new BeanMapper(),1); System.out.println(ac); } /** * 查询所有*/ @Test public void run5(){ String sql="select * from t_account"; List<Account> ac=jdbcTemplate.query(sql,new BeanMapper()); System.out.println(ac); }}/** * 定义内部类(手动封装数据(一行一行封装数据,用于查询所有) * @author Administrator * */class BeanMapper implements RowMapper<Account>{ @Override public Account mapRow(ResultSet rs, int rowNum) throws SQLException { Account ac=new Account(); ac.setId(rs.getInt("id")); ac.setName(rs.getString("name")); ac.setMoney(rs.getDouble("money")); return ac; } }2、配置开源连接池
一般现在企业都是用一些主流的连接池,如c3p0和dbcp
首先配置dbcp
1)导入dbcp依赖jar包
2)编写配置文件
<!-- 配置DBCP开源连接池--> <bean id="dataSource"> <property name="driverClassName" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="username" value="root"/> <property name="password" value="root"/> </bean>
将模板类中引入的内置类datasource改为开源连接池的
3)编写测试类
配置c3p0
1)导入c3p0依赖jar包
2)配置c3p0
<!-- 配置C3P0开源连接池--> <bean id="dataSource"> <property name="driverClass" value="com.mysql.jdbc.Driver"/> <property name="jdbcUrl" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="user" value="root"/> <property name="password" value="root"/> </bean>
将模板类中引入的内置类datasource改为开源连接池的
3)编写测试类
1、什么是事务
数据库事务(Database Transaction) ,是指作为单个逻辑工作单元执行的一系列操作,要么完全地执行,要么完全地不执行。 事务处理可以确保除非事务性单元内的所有操作都成功完成,否则不会永久更新面向数据的资源。通过将一组相关操作组合为一个要么全部成功要么全部失败的单元,可以简化错误恢复并使应用程序更加可靠。一个逻辑工作单元要成为事务,必须满足所谓的ACID(原子性、一致性、隔离性和持久性)属性。事务是数据库运行中的逻辑工作单位,由DBMS中的事务管理子系统负责事务的处理。
2、怎么解决事务安全性问题
读问题解决,设置数据库隔离级别;写问题解决可以使用悲观锁和乐观锁的方式解决
3、快速开发
方式一:调用模板类,将模板注入持久层
1)编写相对应的持久层和也外层,这里省略接口
package com.clj.demo3;import org.springframework.jdbc.core.JdbcTemplate;import org.springframework.jdbc.core.support.JdbcDaoSupport;public class AccountDaoImpl extends JdbcDaoSupport implements AccountDao{ // Method 1: Inject the jdbc template class into the configuration file and write the template class private in the persistence layer JdbcTemplate jdbcTemplate; public void setJdbcTemplate(JdbcTemplate jdbcTemplate) { this.jdbcTemplate = jdbcTemplate; } public void outMoney(String out, double money) { String sql="update t_account set money=money-? where name=?"; jdbcTemplate().update(sql,money,out); } public void inMoney(String in, double money) { String sql="update t_account set money=money+? where name=?"; jdbcTemplate().update(sql,money,in); }} package com.clj.demo4;import org.springframework.transaction.TransactionStatus;import org.springframework.transaction.support.TransactionCallbackWithoutResult;import org.springframework.transaction.support.TransactionTemplate;public class AccountServiceImpl implements AccountService{ //It uses configuration file injection method, and the set method must be provided private AccountDao accountDao; public void setAccountDao(AccountDao accountDao) { this.accountDao = accountDao; } @Override public void pay(String out, String in, double money) { // TODO Auto-generated method stub accountDao.outMoney(out, money); int a=10/0; accountDao.inMoney(in, money); }}2)配置相对应的配置文件
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd"><!-- 配置C3P0开源连接池--> <bean id="dataSource"> <property name="driverClass" value="com.mysql.jdbc.Driver"/> <property name="jdbcUrl" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="user" value="root"/> <property name="password" value="root"/> </bean><!-- 配置JDBC的模板类--> <bean id="jdbcTemplate"> <property name="dataSource" ref="dataSource"/> </bean><!-- 配置业务层和持久层--> <bean id="accountService"> <property name="accountDao" ref="accountDao"/> </bean><bean id="accountDao"> <!-- 注入模板类--> <property name="jdbcTemplate" ref="jdbcTemplate"/> <property name="dataSource" ref="dataSource"/> </bean></beans>
3)测试类
package com.clj.demo3;import javax.annotation.Resource;import org.junit.Test;import org.junit.runner.RunWith;import org.springframework.test.context.ContextConfiguration;import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;@RunWith(SpringJUnit4ClassRunner.class)@ContextConfiguration("classpath:applicationContext.xml")public class Demo1 { @Resource(name="accountService") private AccountService accountService; @Test public void Demo1(){ //Call the payment method accountService.pay("Jia Xiansen","Li Yilin",100); }}方式二:持久层继承JdbcDaoSupport接口,此接口封装了模板类jdbcTemplate
1)编写配置文件
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd"> <!-- 配置C3P0开源连接池--> <bean id="dataSource"> <property name="driverClass" value="com.mysql.jdbc.Driver"/> <property name="jdbcUrl" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="user" value="root"/> <property name="password" value="root"/> </bean> <!-- 配置业务层和持久层--> <bean id="accountService"> <property name="accountDao" ref="accountDao"/> </bean> <bean id="accountDao"> <property name="dataSource" ref="dataSource"/> </bean></beans>
2)更改持久层
package com.clj.demo3;import org.springframework.jdbc.core.JdbcTemplate;import org.springframework.jdbc.core.support.JdbcDaoSupport;public class AccountDaoImpl extends JdbcDaoSupport implements AccountDao{ //Method 1: Inject the jdbc template class into the configuration file and write the template class directly in the persistence layer// private JdbcTemplate jdbcTemplate;// public void setJdbcTemplate(JdbcTemplate jdbcTemplate) {// this.jdbcTemplate = jdbcTemplate;// } // Method 2: The persistence layer inherits JdbcDaoSupport, which encloses the template class. The persistence layer of the configuration file does not need to inject the template class, nor does it need to configure the template class public void outMoney(String out, double money) { //jdbcTemplate.update(psc); String sql="update t_account set money=money-? where name=?"; this.getJdbcTemplate().update(sql,money,out); } public void inMoney(String in, double money) { String sql="update t_account set money=money+? where name=?"; this.getJdbcTemplate().update(sql,money,in); }}3)更改业务层
package com.clj.demo4;import org.springframework.transaction.TransactionStatus;import org.springframework.transaction.support.TransactionCallbackWithoutResult;import org.springframework.transaction.support.TransactionTemplate;public class AccountServiceImpl implements AccountService{ //It uses configuration file injection method, and the set method must be provided private AccountDao accountDao; public void setAccountDao(AccountDao accountDao) { this.accountDao = accountDao; } @Override public void pay(String out, String in, double money) { // TODO Auto-generated method stub accountDao.outMoney(out, money); int a=10/0; accountDao.inMoney(in, money); }}4)测试类和上述一样
4、spring事务管理
In order to simplify transaction management code, Spring provides a template class TransactionTemplate, which can be manually programmed to manage transactions. You only need to use this template class! !
1、手动编程方式事务(了解原理)
1)快速部署,搭建配置文件,配置事务管理和事务管理模板,并在持久层注入事务管理模板
配置事务管理器
<!-- 配置平台事务管理器--> <bean id="transactionManager"> <property name="dataSource" ref="dataSource"/> </bean>
配置事务管理模板
<bean id="transactionTemplate"> <property name="transactionManager" ref="transactionManager"/></bean>
将管理模板注入业务层
<bean id="accountService"> <property name="accountDao" ref="accountDao"/> <property name="transactionTemplate" ref="transactionTemplate"/></bean>
全部代码:
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd"> <!-- 配置C3P0开源连接池--> <bean id="dataSource"> <property name="driverClass" value="com.mysql.jdbc.Driver"/> <property name="jdbcUrl" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="user" value="root"/> <property name="password" value="root"/> </bean> <!-- 配置业务层和持久层--> <bean id="accountService"> <property name="accountDao" ref="accountDao"/> <property name="transactionTemplate" ref="transactionTemplate"/> </bean> <bean id="accountDao"> <property name="dataSource" ref="dataSource"/> </bean> <!-- 配置平台事务管理器--> <bean id="transactionManager"> <property name="dataSource" ref="dataSource"/> </bean> <!-- 手动编码方式,提供了模板类,使用该类管理事务比较简单--> <bean id="transactionTemplate"> <property name="transactionManager" ref="transactionManager"/> </bean></beans>
2)在业务层使用模板事务管理
package com.clj.demo3;import org.springframework.transaction.TransactionStatus;import org.springframework.transaction.support.TransactionCallbackWithoutResult;import org.springframework.transaction.support.TransactionTemplate;public class AccountServiceImpl implements AccountService{ //Usage configuration file injection method, set method must be provided private AccountDao accountDao; //Inject transaction template class private TransactionTemplate transactionTemplate; public void setAccountDao(AccountDao accountDao) { this.accountDao = accountDao; } public void setTransactionTemplate(TransactionTemplate transactionTemplate) { this.transactionTemplate = transactionTemplate; } /** * Method of transfer*/ public void pay(final String out,final String in, final double money) { transactionTemplate.execute(new TransactionCallbackWithoutResult() { //The execution of the transaction, if there is no problem, submit, if Chu Xiang is exception, roll back protected void doInTransactionWithoutResult(TransactionStatus arg0) { // TODO Auto-generated method stub accountDao.outMoney(out, money); int a=10/0; accountDao.inMoney(in, money); } }); }}3)测试类和上一致
package com.clj.demo4;import javax.annotation.Resource;import org.junit.Test;import org.junit.runner.RunWith;import org.springframework.test.context.ContextConfiguration;import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;@RunWith(SpringJUnit4ClassRunner.class)@ContextConfiguration("classpath:applicationContext2.xml")public class Demo2 { @Resource(name="accountService") private AccountService accountService; @Test public void Demo1(){ //Call the payment method accountService.pay("Jia Xiansen","Li Yilin",100); }}申明式事务有两种方式:基于AspectJ的XML方式;基于AspectJ的注解方式
1、XML方式
1)配置配置文件
需要配置平台事务管理
<!-- 配置C3P0开源连接池--> <bean id="dataSource"> <property name="driverClass" value="com.mysql.jdbc.Driver"/> <property name="jdbcUrl" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="user" value="root"/> <property name="password" value="root"/> </bean> <!-- 配置平台事务管理器--> <bean id="transactionManager"> <property name="dataSource" ref="dataSource"/> </bean>
配置事务增强
<tx:advice id="myAdvice" transaction-manager="transactionManager"> <tx:attributes> <!-- 给方法设置数据库属性(隔离级别,传播行为) --> <!--propagation事务隔离级别:一般采用默认形式:tx:method可以设置多个--> <tx:method name="pay" propagation="REQUIRED"/> </tx:attributes> </tx:advice>
aop切面类
<aop:config> <!-- aop:advisor,是spring框架提供的通知--> <aop:advisor advice-ref="myAdvice" pointcut="execution(public * com.clj.demo4.AccountServiceImpl.pay(..))"/> </aop:config>
Todos los códigos
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd"> <!-- 配置C3P0开源连接池--> <bean id="dataSource"> <property name="driverClass" value="com.mysql.jdbc.Driver"/> <property name="jdbcUrl" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="user" value="root"/> <property name="password" value="root"/> </bean> <!-- 配置平台事务管理器--> <bean id="transactionManager"> <property name="dataSource" ref="dataSource"/> </bean> <!-- 申明式事务(采用XML文件的方式) --> <!-- 先配置通知--> <tx:advice id="myAdvice" transaction-manager="transactionManager"> <tx:attributes> <!-- 给方法设置数据库属性(隔离级别,传播行为) --> <!--propagation事务隔离级别:一般采用默认形式:tx:method可以设置多个--> <tx:method name="pay" propagation="REQUIRED"/> </tx:attributes> </tx:advice> <!-- 配置AOP:如果是自己编写的AOP,使用aop:aspect配置,使用的是Spring框架提供的通知--> <aop:config> <!-- aop:advisor,是spring框架提供的通知--> <aop:advisor advice-ref="myAdvice" pointcut="execution(public * com.clj.demo4.AccountServiceImpl.pay(..))"/> </aop:config> <!-- 配置业务层和持久层--> <bean id="accountService"> <property name="accountDao" ref="accountDao"/> </bean> <bean id="accountDao"> <property name="dataSource" ref="dataSource"/> </bean></beans>
2)编写持久层和业务层(省略接口)
package com.clj.demo5;import org.springframework.jdbc.core.JdbcTemplate;import org.springframework.jdbc.core.support.JdbcDaoSupport;public class AccountDaoImpl extends JdbcDaoSupport implements AccountDao{ //Method 1: Inject the jdbc template class into the configuration file and write the template class directly in the persistence layer// private JdbcTemplate jdbcTemplate;// public void setJdbcTemplate(JdbcTemplate jdbcTemplate) {// this.jdbcTemplate = jdbcTemplate;// } // Method 2: The persistence layer inherits JdbcDaoSupport, which encloses the template class. The persistence layer of the configuration file does not need to inject the template class, nor does it need to configure the template class public void outMoney(String out, double money) { //jdbcTemplate.update(psc); String sql="update t_account set money=money-? where name=?"; this.getJdbcTemplate().update(sql,money,out); } public void inMoney(String in, double money) { String sql="update t_account set money=money+? where name=?"; this.getJdbcTemplate().update(sql,money,in); }} package com.clj.demo5;import org.springframework.transaction.TransactionStatus;import org.springframework.transaction.annotation.Transactional;import org.springframework.transaction.support.TransactionCallbackWithoutResult;import org.springframework.transaction.support.TransactionTemplate;public class AccountServiceImpl implements AccountService{ //It uses configuration file injection method, and the set method must be provided private AccountDao accountDao; public void setAccountDao(AccountDao accountDao) { this.accountDao = accountDao; } @Override public void pay(String out, String in, double money) { // TODO Auto-generated method stub accountDao.outMoney(out, money); int a=10/0; accountDao.inMoney(in, money); }}3)测试类
package com.clj.demo4;import javax.annotation.Resource;import org.junit.Test;import org.junit.runner.RunWith;import org.springframework.test.context.ContextConfiguration;import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;@RunWith(SpringJUnit4ClassRunner.class)@ContextConfiguration("classpath:applicationContext2.xml")public class Demo2 { @Resource(name="accountService") private AccountService accountService; @Test public void Demo1(){ //Call the payment method accountService.pay("Jia Xiansen","Li Yilin",100); }}2、注解方式
1)配置配置文件
配置事务管理
<bean id="dataSource"> <property name="driverClass" value="com.mysql.jdbc.Driver"/> <property name="jdbcUrl" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="user" value="root"/> <property name="password" value="root"/> </bean> <bean id="transactionManager"> <property name="dataSource" ref="dataSource"/> </bean>
开启注释事务
<!-- 开启事务的注解--> <tx:annotation-driven transaction-manager="transactionManager"/>
Todos los códigos
<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd"> <!-- 配置C3P0开源连接池--> <bean id="dataSource"> <property name="driverClass" value="com.mysql.jdbc.Driver"/> <property name="jdbcUrl" value="jdbc:mysql://192.168.174.130:3306/SSH"/> <property name="user" value="root"/> <property name="password" value="root"/> </bean> <!-- 配置平台事务管理器--> <bean id="transactionManager"> <property name="dataSource" ref="dataSource"/> </bean> <!-- 开启事务的注解--> <tx:annotation-driven transaction-manager="transactionManager"/> <!-- 配置业务层和持久层--> <bean id="accountService"> <property name="accountDao" ref="accountDao"/> </bean> <bean id="accountDao"> <property name="dataSource" ref="dataSource"/> </bean></beans>
2)业务层增加@Transactional
package com.clj.demo5;import org.springframework.transaction.TransactionStatus;import org.springframework.transaction.annotation.Transactional;import org.springframework.transaction.support.TransactionCallbackWithoutResult;import org.springframework.transaction.support.TransactionTemplate;//Add this annotation in the current class means that all the current class has transactions @Transactionalpublic class AccountServiceImpl implements AccountService{ //Using configuration file injection method, the set method must be provided private AccountDao accountDao; public void setAccountDao(AccountDao accountDao) { this.accountDao = accountDao; } @Override public void pay(String out, String in, double money) { // TODO Auto-generated method stub accountDao.outMoney(out, money); int a=10/0; accountDao.inMoney(in, money); }}3)持久层不变
package com.clj.demo5;import org.springframework.jdbc.core.JdbcTemplate;import org.springframework.jdbc.core.support.JdbcDaoSupport;public class AccountDaoImpl extends JdbcDaoSupport implements AccountDao{ //Method 1: Inject the jdbc template class into the configuration file and write the template class directly in the persistence layer// private JdbcTemplate jdbcTemplate;// public void setJdbcTemplate(JdbcTemplate jdbcTemplate) {// this.jdbcTemplate = jdbcTemplate;// } // Method 2: The persistence layer inherits JdbcDaoSupport, which encloses the template class. The persistence layer of the configuration file does not need to inject the template class, nor does it need to configure the template class public void outMoney(String out, double money) { //jdbcTemplate.update(psc); String sql="update t_account set money=money-? where name=?"; this.getJdbcTemplate().update(sql,money,out); } public void inMoney(String in, double money) { String sql="update t_account set money=money+? where name=?"; this.getJdbcTemplate().update(sql,money,in); }}4)测试类
package com.clj.demo5;import javax.annotation.Resource;import org.junit.Test;import org.junit.runner.RunWith;import org.springframework.test.context.ContextConfiguration;import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;@RunWith(SpringJUnit4ClassRunner.class)@ContextConfiguration("classpath:applicationContext3.xml")public class Demo3 { @Resource(name="accountService") private AccountService accountService; @Test public void Demo1(){ //Call the payment method accountService.pay("Jia Xiansen","Li Yilin",100); }}Lo anterior es todo el contenido de este artículo. Espero que sea útil para el aprendizaje de todos y espero que todos apoyen más a Wulin.com.