머리말
이 기사는 주로 Spring이 사물을 지원하는 방법과 Spring이 mybatis를 결합 할 때 단순히 데이터베이스의 기능을 구현할 수있는 방법을 기록합니다. 아래에 대해 많이 말하지 않을 것입니다. 자세한 소개를 함께 살펴 보겠습니다.
CASE1 : 두 테이블의 상황을 지원합니다
먼저 두 개의 테이블, 하나의 사용자 테이블 및 1 개의 스토리 테이블을 준비하고 구조는 다음과 같습니다.
테이블`user` (`id` int (11) unull auto_increment,`name` varchar (20) not null default ''not not not not not not not not not not not not not not not not not not not not not not not not not not not not not not not not not not not not not not nont 'varchar (26)`pwd` varchar (26) null default' '댓글'비밀번호 ',`isdeleted` tinyint (1) 0'0 '0'0 ',```````0' ' `updated` varchar (13) NULL DEFAULT '0', 기본 키 (`ID`), 키`name` ( 'name`)) 엔진 = innodb 기본값 기본적 charset = utf8mb4;`story'(`id` int (11) signed null auto_increment,`userid` int ', null default'0 'null default'0 'null default'0 'inull' 'emuled'0. Varchar (20) NOL NOT NOT DEFAULT ''COMMING 'AUTHOR',`TITILE 'VARCHAR (26) NULL DEFAULT' 'COMMING'PASSOATH ',`스토리`텍스트 댓글'스토리 내용 ','isdeleted` tinyint (1) NOL NULL DEFAULT '0',`VARCHAR (13) 0 '0'0 ', VARCHAR (13), ky ky (13), kay (13) `userId` (`userID`
우리의 상황은 사용자가 이름을 수정하면 두 테이블의 이름을 함께 수정해야하며 불일치가 허용되지 않는다는 것입니다.
CASE2 : 단일 테이블이 지원합니다
송금, 한 사용자는 돈을 줄이고 다른 사용자는 돈을 늘립니다.
CREATE TABLE `money` ( `id` int(11) unsigned NOT NULL AUTO_INCREMENT, `name` varchar(20) NOT NULL DEFAULT '' COMMENT 'Username', `money` int(26) NOT NULL DEFAULT '0' COMMENT 'money', `isDeleted` tinyint(1) NOT NULL DEFAULT '0', `created` varchar(13) NOT NULL DEFAULT '0', `updated` varchar (13) NULL DEFAULT '0', 기본 키 (`ID`), 키`name` ( 'name`)) Engine = innodb 기본 charset = utf8mb4;
위의 경우와 비교할 때 이것은 더 간단합니다. 다음 예제는 주로이를 기반으로 설명됩니다. CASE1은 확장되어야합니다.
먼저 해당 DAO 및 엔티티를 구현하십시오
@Datapublic Class MoneyEntity는 시리얼화할 수있는 {private static final long serialversionuid = -70747888842783160025L; 개인 int ID; 개인 문자열 이름; 개인 int 자금; 개인 INT ISDELETED; 생성 된 개인 int; private int 업데이트;} public interface moneydao {Moneyentity QueryMoney (@param ( "id") int userId); // 돈을 추가하면, 부정적인 경우, 그것은 돈을 줄이는 것을 의미합니다 int excrementmoney (@param ( "id") int userId, @param ( "addmoney") int addmonney);}해당 매퍼 파일은입니다
<? xml version = "1.0"encoding = "utf-8"?> <! doctype mapper public "-// mybatis.org//dtd Mapper 3.0 // en" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <<1mapper 네임 스페이스 = "com.git.hui.demo.mybatis.mapper.moneydao"> <sql id = "moneyentity"> id,`name`,`money`,`isdeleted`,`created` resulttype = "com.git.hui.demo.mybatis.entity.moneyentity"> select <refid = "moneyentity"/> includ refid = "moneyentity"/> id =#{id} </select> <update id = "incrementmoney"> update money = money +#{addmoney} id =#{id} </mapper> </mapper>MyBatis 연결 데이터 소스의 해당 구성
<bean> <property name = "locations"> <value> classpath*: jdbc.properties </value> </property> </bean> <bean id = "dataSource"init-method = "init"close "> <property name ="driverClassName "value ="$ {driver} "/> <value"$ {url ""url ""url ""url " 이름 = "username"value = "$ {username}"/> <속성 이름 = "password"value = "$ {password}"/> <속성 이름 = "필터"value = "stat"/> <property name = "maxActive"value = "20"/> <property name = "inititize"value = "1"/> <maxwait "value ="60000 "/>>>>>>. value = "1"/> <속성 이름 = "timebetweenevictionRunsmillis"value = "60000"/> <property name = "minevictabledletimemillis"value = "300000"/> <propertyquery "value ="select 'x' "/> <property name ="value ""value "/> <testonbormor 이름 = "testonborring"value = "false"/> <property name = "testonreturn"value = "false"/> <property name = "poolpreparedStatements"value = "true"/> <property name = "maxpoolpreparedStatementperConnections"value = "50"/> </bean> <bean id = "sqlsessionfactory"> ref = "dataSource"/> <!-맵퍼 파일을 지정-> <속성 이름 = "mapperlocations"value = "classPath*: mapper/*. xml"/> </bean> <!-Scan dao-> <ean> <property name = "value"value = "com.git.hui.demo.mybatis"/bean>.온라인 쿼리를 통해 스프링을 관리하는 네 가지 방법이 있습니다. 다음은 시연이 하나씩 있습니다. 각 방법을 재생하는 방법, 실제 프로젝트에서 선택하는 방법을 확인하십시오.
TransactionTemplate를 통해 여러 DB 운영의 관리를 실현하는 프로그래밍 제품 관리
에이. 구현
그런 다음 전송 케이스를 다음과 같이 구현할 수 있습니다
@RepositoryPublic Class CodeDemo1 {@autowired private moneydao moneydao; @autowired Private TransactionTemplate TransactionTemplate; / ** * 전송 * * @param inuserid * @param untuserid * @param paymoney * @param status 0 정상 전송을 나타냅니다. 1 예외는 내부적으로 던져 졌음을 나타냅니다. 2는 새로운 스레드를 나타냅니다. 새로운 스레드 + 200, 3은 새로운 스레드의 돈을 수정하고, Outuserid + 200 */ Public void의 돈을 수정합니다. 상태) {transactionTemplate.Execute (새로운 TransactionCallbackwithOUtResult () {Protected void dointransactionWithoutResult (transactionStatus transactionStatus) {Moneyentity Entity = MoneyDao.queryMoney (untity.getMoney ()> PAYMONE) Moneydao.incrementmoney (Outuserid, -paymoney) (Inuserid, Outuserid); } // 다음은 모든 관련 테스트 케이스 개인 무효 테스트 케이스 (최종 int inuserid, 최종 int outuserid, 최종 int 상태) {if (status == 1) {throw new new OregalArgumentException ( "전송 예외 !!!"); } else if (status == 2) {addmoney (inuserid); try {thread.sleep (3000); } catch (InterruptedException e) {e.printstacktrace (); }} else if (status == 3) {addmoney (outuserid); try {thread.sleep (3000); } catch (InterruptedException e) {e.printstacktrace (); }}} public void addmoney (Final int userId) {System.out.printf ( "내부 addmoney :" + system.currenttimeMillis ()); new Thread (new Runnable () {public void run () {mondedao.incrementmoney (userId, 200); System.out.println ( "sub modify success! now :" + system.currenttimeMillis ()). start (); }}주로 위의 변환 방법을 살펴 봅니다. 사물의 캡슐화는 내부적으로 TransactionTemplate을 통해 실현됩니다. 내부적으로 3 개의 DB 작업, 1 개의 쿼리 및 2 개의 업데이트가 있습니다. 특정 분석은 나중에 설명됩니다.
위의 코드는 비교적 간단합니다. 주의를 기울여야 할 유일한 것은 TransactionTemplate Bean이 정의되는 방법입니다. XML 파일과 이전 파일을 붙여 넣지 않으면 키 코드를 붙여 넣으십시오. 하나는 DataSource를 기반으로 생성 된 TransactionManager이고 다른 하나는 TransactionManager를 기반으로 작성된 TransactionTemplate입니다.
<!-프로그래밍-> <bean id = "transactionManager"> <property name = "dataSource"ref = "dataSource"/> </bean> <bean id = "transactionTemplate"> <property name = "transactionManager"ref = "transactionManager"/</bean>
비. 테스트 사례
정상적인 데모 상황, 데모에는 예외가 없으며 동시성 상황이 고려되지 않습니다.
@RunWith (SpringJunit4classRunner.class) @contextConfiguration ({ "ClassPath*: spring/service.xml", "classPath*: test-datasource1.xml"}) 공개 클래스 CodeDemo1test {@autowired private codedemo1 codeDemo1; @autowired private moneydao moneydao; @test public void testtransfor () {system.out.println ( "------------------------------------------------------------ System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ()); CodedEmo1.transfor (1, 2, 10, 0); System.out.println ( "------------------------------------------- System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ()); }}출력은 다음과 같습니다. 두 계정의 돈에는 아무런 문제가 없습니다.
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10000
ID : 2 Money = 50000
전송이 완료되었습니다! 지금 : 1526130394266
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
이적 과정에서 비정상이 발생합니다. 특히 양도인이 돈을 공제하고 수령인이 돈을받지 못했을 때, 즉 사건의 상태가 1 인 상황입니다.
// @TestPublic void testRansforexception () {system.out.println ( "---------------------"); System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ()); try {codedemo1.transfor (1, 2, 10, 1); } catch (예외 e) {e.printstacktrace (); } system.out.println ( "------------------------------------------------------------------ System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ());}이와 관련하여, 우리는 양도인에게서 돈을 반환하고 다음과 같이 그것을 출력하기를 희망합니다. 우리는 돈 중 어느 것도 바뀌지 않았다는 것을 알았습니다.
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
java.lang.illegalargumentexception : 전송 예외 !!!
... // 예외 정보를 생략합니다
ID : 2 Money = 49990
상태가 2 인 경우, 이체의 돈이 공제되었고 수취인의 돈이받지 못했다는 것을 의미합니다. 현재 MySQL의 잠금 장치에 따르면, 다른 사람의 양도는 즉시 수령해야하며 (수취인의 계정이 잠겨 있지 않기 때문에) 금액에 아무런 문제가 없어야합니다.
출력 결과는 다음과 같습니다.
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
## 오른쪽에는 주석이 있습니다 : 이전 과정에서 돈이 즉시 입금되었으며 돈이 추가되지 않았습니다. 1526130827480
서브 수정 성공! 지금 : 1526130827500
## 돈을 절약 한 후 이전이 완료됩니다! 지금 : 1526130830488
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10220
ID : 2 Money = 49980
지위가 3 인 경우, 이식 자의 돈이 공제되었고 수취인의 돈이 접수되지 않았으며 누군가가 200을 양도인으로 이체했음을 의미합니다. 이 시점에서, 이전자의 기록과 Write Lock이 추가되기 때문에, 그는 +200 성공 전에 이적을 성공하기 위해 양도를 제출할 때만 기다릴 수 있습니다. 물론 최종 금액도 동일해야합니다.
출력 결과는 다음과 같습니다
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10220
ID : 2 Money = 49980
## 오른쪽은 메모입니다 : 내부적으로 돈을 절약했지만 즉시 성공하지 못했습니다.
## 전송이 완료 될 때까지 즉시 성공할 수 있습니다. 두 개의 타임 스탬프에 돈을 추가하는 데주의를 기울이십시오 : 1526131101046
전송이 완료되었습니다! 지금 : 1526131104051
서브 수정 성공! 지금 : 1526131104053
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10230
ID : 2 Money = 50170
기음. 요약
지금까지 프로그래밍은 예에서 시연되었습니다. 위의 과정에서 사람들은 SQL과 관련된 것들을 쓰는 것과 같은 느낌을줍니다.
트랜잭션 시작;
- 이것은 TransactionTemplate#Execute 메소드 내의 논리입니다
- 즉, 물건을 관리 해야하는 SQL 세트저지르다;
다음 세 가지는 선언적 사물 관리입니다. 각 사물 관리 클래스는 트랜잭션 ProxyFactoryBean에 추가해야하기 때문에 덜 사용됩니다.
에이. 구현
트랜잭션 템플릿을 죽이고 내부 SQL 로직을 제거하는 것 외에도 이전의 논리와 비교하여 기본적으로 차이가 없다는 것을 알았습니다.
공개 클래스 FactoryBeendemo2 {@autowired private moneydao moneydao; / ** * 전송 * * @param inuserid * @param untuserid * @param paymoney * @param 상태 0 정상 전송을 나타냅니다. 1 예외가 내부적으로 던져 졌음을 나타냅니다. 2는 새로운 스레드를 나타냅니다. 새로운 스레드 + 200의 돈을 수정하고, 새로운 스레드의 돈을 수정하고, Outserid + 200 */ Public void 송금의 돈을 수정합니다. 상태) {MoneyEntity Entity = Moneydao.QueryMoney (OutuserId); if (entity.getMoney ()> paymoney) {// 돈을 송금 할 수 있습니다. // 돈을 줄일 수 있습니다. 먼저 moneydao.incrementmoney (OutuserId, -paymoney); 테스트 케이스 (Inuserid, OutuserId, 상태); // moneydao.incrementmoney (inuserid, paymoney)에 돈을 추가합니다. System.out.println ( "전송이 완료되었습니다! 지금 :" + system.currenttimeMillis ()); }} private void testcase (최종 int inuserid, 최종 int outuserid, final int status) {if (status == 1) {throw new new OrgalArgumentException ( "전송 예외 !!!"); } else if (status == 2) {addmoney (inuserid); try {thread.sleep (3000); } catch (InterruptedException e) {e.printstacktrace (); }} else if (status == 3) {addmoney (outuserid); try {thread.sleep (3000); } catch (InterruptedException e) {e.printstacktrace (); }}} public void addmoney (Final int userId) {System.out.println ( "내부 추가 비용 :" + System.CurrentTimeMillis ()); new Thread (new Runnable () {public void run () {mondedao.incrementmoney (userId, 200); System.out.println ( "sub modify success! now :" + system.currenttimeMillis ()). start (); }}핵심 요점은 트랜잭션 프록시 비안을 구성해야한다는 것입니다. 우리는 Beanfactory가 우리 자신이 콩을 만들 수있는 수단이라는 것을 알고 있습니다. 관련 XML 구성은 다음과 같습니다
<!-> <bean id = "transactionManager"> <property name = "dataSource"ref = "dataSource"/> </bean> <bean id = "factoryBeandemo2"/> <!-비즈니스 계층에 대한 프록시를 구성-> <bean id = "ancatorybeandemoproxy">-<PropertoryBeanDemoProxy ">-<propertorybeandemoproxy"> < "" "" "" "" "" "" "" "" " ref = "factorybeandemo2" /> <!-트랜잭션 관리자-> <속성 이름 = "transactionManager"ref = "TransactionManager" /> <!-트랜잭션의 속성을 주입-> <속성 이름 = "transactionattributes"> <spects> <! <! <propgation aciboction : transatomation readation foreation : transactionation readation fore : transactionation forection : transationation hation : transationation forection : transationation hatiption : transaction format : <props> <props> <! 예외 롤백 트랜잭션* +예외 : 어떤 예외는 트랜잭션을 롤백하지 않는 예외-> <!-이 키는 대상 클래스의 메소드-> <prop key = "transfor"> propagation_required </prop> <!-<prop key = "송신"> propagation_required, readonly </prop> --> <!-<prop </procired, </procired, </prop ". <!-<prop key = "transfer"> propagation_required,+java.lang.arithmeticexception </prop>-> </props> </propert> </bean>
위의 구성을 통해 TransactionProxyFactoryBean이 FactoryBeendEmo2의 프록시 클래스를 생성한다는 것을 대략 이해할 수 있습니다. 이 프록시 클래스는 내부의 좋은 것과 관련된 논리를 캡슐화하며, 이는 이전 프로그래밍의 간단한 일반적인 추상화로 간주 될 수 있습니다.
비. 시험
테스트 코드는 기본적으로 이전과 동일합니다. 유일한 차이점은 FactoryBeendEmo2를 직접 사용하지 않고 위의 콩별로 생성 된 콩을 사용해야한다는 것입니다.
일반 데모 케이스 :
@RunWith (SpringJunit4classRunner.class) @contextConfiguration ({ "ClassPath*: Spring/Service.xml", "ClassPath*: test-datasource2.xml"}) 공개 클래스 FactoryBeanDemo1test {@Resource (이름 = ""FactoryBeanDemoProxy "))) @autowired private moneydao moneydao; @test public void testtransfor () {system.out.println ( "------------------------------------------------------ System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ()); FactoryBeendemo2.transfor (1, 2, 10, 0); System.out.println ( "--------------------------------------------------- System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ()); }}산출
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10000
ID : 2 Money = 50000
전송이 완료되었습니다! 지금 : 1526132058886
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
상태가 1이고 내부 예외가 발생하지 않으면 돈에 아무런 문제가 없기를 바랍니다.
@testpublic void testtransforexception () {system.out.println ( "------------------------------------------------------------------------------ System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ()); try {factorybeandemo2.transfor (1, 2, 10, 1); } catch (예외 e) {System.out.println (e.getMessage ()) ;; } system.out.println ( "--------------------------------------------- System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ());}출력은입니다
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
비정상을 옮기십시오 !!!
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
상태가 2 인 경우 분석 결과는 위와 동일하고 출력은 다음과 같습니다.
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49950
내부 자금 : 1526133325376
서브 수정 성공! 지금 : 1526133325387
전송이 완료되었습니다! 지금 : 1526133328381
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10220
ID : 2 Money = 49940
상태가 3 인 경우 출력
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10220
ID : 2 Money = 49940
내부 자금 : 1526133373466
전송이 완료되었습니다! 지금 : 1526133376476
서브 수정 성공! 지금 : 152613376480
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10230
ID : 2 Money = 50130
기음. 요약
TransactionProxyFactoryBean의 아이디어는 프록시 모드를 사용하여 사물 관리를 구현하고, 프록시 클래스를 생성하고, 대상 방법을 가로 채며, 일련의 SQL 작업을 사물로 캡슐화하는 것입니다. 하드 코드와 비교하여 비 침습적이며 유연한 구성 방법을 지원합니다.
단점도 분명합니다. 각각 구성해야합니다. 이는 매우 복잡합니다.
Spring은 IOC와 AOP의 두 가지 주요 특성을 가지고 있습니다. 이런 일을 위해 AOP를 사용하여 수행 할 수 있습니까?
전원을 켜고, 인터셉트하고, 실행하기 전에 물건을 시작하고, 실행 후 물건을 제출하고, 예외가 발생할 때 롤백 해야하는 방법의 경우.
이러한 관점에서 볼 때, 그것은 매우 유망한 느낌이 들며, 다음 두 가지 자세는 이런 식으로 재생되므로 측면의 의존성이 필요합니다.
<pectionency> <groupId> org.aspectj </groupid> <artifactid> 종면 jweaver </artifactid> <bersion> 1.8.7 </version> </fectionency>
에이. 구현
Java 클래스는 두 번째 유형과 정확히 동일하며 XML 만 변경됩니다.
<!-먼저 네임 스페이스를 추가합니다-> xmlns : tx = "http://www.springframework.org/schema/tx"xmlns : aop = "http://www.springframework.org/schema/aop"xsi : schemalocation = "..."... " http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd"<- Transaction-Manager = "TransactionManager"> <TX : Attributes> <!-전파 : 전파 : 트랜잭션 전파 동작 격리 : 트랜잭션 격리 수준 읽기 전용 : 읽기 전용 롤백 : 어떤 예외가 발생했는지 : 롤백 타임 아웃 : 어떤 예외가 발생한 예외가 발생했는지-> <tx : "transfor" "/> </tx : attributes> </tx : 조언> <!-구성 섹션-> <aop : config> <!-구성점-절단-> <aop : pointcut expression = "execution (* com.git.hui.demo.mybatis.repository.xmldemo3. <AOP : Advisor Advice-Ref = "TXADVICE"PointCut-Ref = "PointCut1"/> </aop : config>
위의 구성을 관찰하고 두 번째 방법에 대해 생각하십시오. 아이디어는 거의 동일하지만이 방법은 분명히 더 일반적입니다. 섹션과 절단 지점을 통해 많은 수의 구성을 줄일 수 있습니다.
비. 시험
@RunWith (SpringJunit4classRunner.class) @contextConfiguration ({ "ClassPath*: spring/service.xml", "classPath*: test-datasource3.xml"}) public class xmlbeantest {@autowired private xmldemo3 xmldemo; @autowired private moneydao moneydao; @test public void testtransfor () {system.out.println ( "-------------------------"); System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ()); xmldemo.transfor (1, 2, 10, 0); System.out.println ( "-------------------------"; System.out.println ( "id : 1 money =" + moneydao.querymoney (1) .getmoney ()); System.out.println ( "id : 2 money =" + moneydao.querymoney (2) .getmoney ()); }}이 테스트는 일반적인 작문 방법과 다르지 않으며 두 번째 공장의 주사 방법보다 간단합니다.
정상 출력
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10000
ID : 2 Money = 50000
전송이 완료되었습니다! 지금 : 1526135301273
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
상태 = 1 예외가 발생하면 출력이 있습니다
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
비정상을 옮기십시오 !!!
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
상태 = 2 전송 프로세스 중에 돈을 절약하는 시나리오, 출력은 이전의 기대와 일치합니다.
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10010
ID : 2 Money = 49990
내부 자금 : 1526135438403
서브 수정 성공! 지금 : 1526135438421
전송이 완료되었습니다! 지금 : 1526135441410
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10220
ID : 2 Money = 49980
상태 = 3의 출력은 이전 기대치와 일치합니다.
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10220
ID : 2 Money = 49980
내부 자금 : 1526135464341
전송이 완료되었습니다! 지금 : 1526135467349
서브 수정 성공! 지금 : 1526135467352
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------.
ID : 1 Money = 10230
ID : 2 Money = 50170
이는 XML을 제거하고 주석을 사용하여 이전 XML의 구성을 @transactional 주석으로 바꾸는 것입니다.
에이. 구현
@repositorypublic 클래스 annodemo4 {@autowired private moneydao moneydao; /** * 전송 * * @param inuserid * @param untuserid * @param paymoney * @param status 0은 정상 전송을 나타냅니다. 1 예외는 내부적으로 던져 졌음을 나타냅니다. ReadOnly : Read Only* Rollbackfor : Norollbackfor : 롤백에 대한 예외가 발생한 예외*/ @transactional (propagation = propagation.Required, dispault.default, readonly = false)에 따른 롤백* rollback rollback에 대한 예외가 발생했습니다. MoneyEntity Entity = Moneydao.QueryMoney (OutuserId); if (entity.getMoney ()> paymoney) {// 돈을 송금 할 수 있습니다. // 돈을 줄일 수 있습니다. 먼저 moneydao.incrementmoney (OutuserId, -paymoney); 테스트 케이스 (Inuserid, OutuserId, 상태); // moneydao.incrementmoney (inuserid, paymoney)에 돈을 추가합니다. System.out.println ( "전송이 완료되었습니다! 지금 :" + system.currenttimeMillis ()); }} private void testcase (최종 int inuserid, 최종 int outuserid, final int status) {if (status == 1) {throw new new OrgalArgumentException ( "전송 예외 !!!"); } else if (status == 2) {addmoney (inuserid); try {thread.sleep (3000); } catch (InterruptedException e) {e.printstacktrace (); }} else if (status == 3) {addmoney (outuserid); try {thread.sleep (3000); } catch (InterruptedException e) {e.printstacktrace (); }}} private void addmoney (final int userId) {system.out.println ( "내부 추가 비용 :" + system.currenttimeMillis ()); new Thread (new Runnable () {public void run () {mondedao.incrementmoney (userId, 200); System.out.println ( "sub modify success! now :" + system.currenttimeMillis ()). start (); }}따라서 사물의 주석을 활성화하려면 XML로 구성해야합니다.
<!-프로그래밍-> <bean id = "transactionManager"> <property name = "dataSource"ref = "dataSource"/> </bean> <tx : 주석 구동 트랜잭션-매너 = "TransactionManager"/>
이것은 더 명확하게 만듭니다. 실제 프로젝트에서 XML 및 주석 방법은 가장 일반적으로 사용되는 시나리오입니다.
비. 테스트 케이스
세 번째 테스트 케이스와 정확히 동일하며 출력 결과가 동일하며 직접 생략됩니다.
위의 것은 봄에 사물을 사용하는 네 가지 방법에 대해 이야기합니다. 그중에서도 하드 코딩 된 방법은 최상의 이해 일 수 있으며, 이는 SQL의 물건을 해당 Java 코드로 직접 사용하는 방법을 직접 변환하는 것과 같습니다. 그리고 공장의 방법은 사물의 기능을 향상시키기 위해 특별한 상황을 치료하고 프록시 클래스로 각각을 처리하는 것과 같습니다. 후자의 두 원칙은 AP (Attinification)를 사용하여 거의 구현되어 접선 지점 및 관련 정보를 정의합니다.
프로그램 작성:
transactionTemplate#execute 메소드에 사물을 사용하는 논리를 캡슐화하십시오프록시 빈칸 :
XML 구성 :
주석 방법 :
tx:annotation-driven transaction-manager="transactionManager"/>문서
봄 거래 관리의 네 가지 방법
소스 코드
위는이 기사의 전체 내용입니다. 이 기사의 내용에 모든 사람의 연구 나 작업에 대한 특정 참조 가치가 있기를 바랍니다. 궁금한 점이 있으면 의사 소통을 위해 메시지를 남길 수 있습니다. Wulin.com을 지원 해주셔서 감사합니다.