Doctrine Transaction Unexpected Nesting Level Increasing

작업 환경


PHP5.3 + Fuel 1.8.1 + Doctrine

문제.


업무상 한 거래에서 아래의 Pseudo 코드의 느낌으로 처리를 집행하고 마지막으로 정리하고 제출한다.
$em = \Fuel\Doctrine::manager("default");
$em->getConnection()->beginTransaction();
…
DB登録処理呼び出し関数1($em);
DBクエリ処理呼び出し関数1($em);
繰り返し処理{
…
    DB登録処理呼び出し関数2($em);
    DB更新処理呼び出し関数1($em);
…
}
…
DB更新処理呼び出し関数2($em);
$em->commit();
하지만 커미션이 아무리 해도 성공하지 못해 사흘을 고민했다.

경과를 조사하다


우연히 Doctine 거래 관리의 Nesting 수준을 보고 싶어요.
Doctine 트랜잭션 공식 참조↑https://www.doctrine-project...
DB 변경 및 로그인 함수 실행 전후 붙여넣기 결과는 놀랍습니다.echo "TransactionNestingLevel Before Insert :".$em->getConnection()->getTransactionNestingLevel()."\n";반복 처리 중 네스팅 레벨의 수치가 계속 상승!!!
TransactionNestingLevel Before Insert :11
TransactionNestingLevel After Insert :11
TransactionNestingLevel Before Insert :41
TransactionNestingLevel After Insert :41
TransactionNestingLevel Before Insert :215
TransactionNestingLevel After Insert :215
TransactionNestingLevel Before Insert :301
TransactionNestingLevel After Insert :301
TransactionNestingLevel Before Insert :345
TransactionNestingLevel After Insert :345
TransactionNestingLevel Before Insert :395
TransactionNestingLevel After Insert :395
TransactionNestingLevel Before Insert :461
TransactionNestingLevel After Insert :461
Are you kidding me!! なんじゃと
거래 수준이 461층에 이르다
トランザクション階層1
    トランザクション階層2
        トランザクション階層3
                    …
                                        トランザクション階層461
변경 사항을 DB에 반영하기 위해 460회$em->commit();!!그래서 제출하면 안 돼요!

잠깐만!이번 조작 대상 데이터는 230건이다.마지막 461건이 230의 2배 늘었잖아요?편리한 수치에 단서가 있는 것 같아!!
여러 실험을 거쳐 다음 느낌의 코드를 실행하면 고장난 곳을 확인할 수 있다.
$em = \Fuel\Doctrine::manager("default");
$em->getConnection()->beginTransaction();
echo "TransactionNestingLevel beginTransaction:".$em->getConnection()->getTransactionNestingLevel()."\n";
$info = array();
$info[0] = array(
    "Sequence"=>5
    …
);
$info[1] = array(
    "Sequence"=>6
    …
);
echo "TransactionNestingLevel After Setting array :".$em->getConnection()->getTransactionNestingLevel()."\n";
결과:
TransactionNestingLevel beginTransaction :1
TransactionNestingLevel After Setting array :3

결론


Doctine의 거래 Nesting 레벨이 1Plus인 것을 한 번에 그룹 대입 처리합니다.그러니까!이는 상위 230건의 2배 플러스로, 등록 함수가 호출되기 전 데이터를 배열별로 전달하기 위해 2차례 배열대입 처리가 이뤄졌기 때문이다.
왜 그런지 모르겠어!!!!!

대책


네!회피 전략으로 중복 처리 중인 DB 변경 처리를 모두 외부로 출력하고 $em->getConnection()->setAutoCommit(false);에서는 중복 처리 중 플러스에 의해 트랜잭션 등급을 1로 되돌려줍니다.
$em = \Fuel\Doctrine::manager("default");
$em->getConnection()->beginTransaction();
…
DB登録処理呼び出し関数1($em);
DBクエリ処理呼び出し関数1($em);
繰り返し処理{
…
…
}
…
$em->getConnection()->setAutoCommit(false);
DB登録処理呼び出し関数2($em);
DB更新処理呼び出し関数1($em);
…
DB更新処理呼び出し関数2($em);
$em->commit();
이렇게 심심한 일 때문에 3일 동안 증발했어!!!

좋은 웹페이지 즐겨찾기