1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.mybatis.spring;
17
18 import java.sql.SQLException;
19 import java.util.function.Supplier;
20
21 import javax.sql.DataSource;
22
23 import org.apache.ibatis.exceptions.PersistenceException;
24 import org.springframework.dao.DataAccessException;
25 import org.springframework.dao.support.PersistenceExceptionTranslator;
26 import org.springframework.jdbc.UncategorizedSQLException;
27 import org.springframework.jdbc.support.SQLErrorCodeSQLExceptionTranslator;
28 import org.springframework.jdbc.support.SQLExceptionTranslator;
29 import org.springframework.transaction.TransactionException;
30
31
32
33
34
35
36
37
38
39
40 public class MyBatisExceptionTranslator implements PersistenceExceptionTranslator {
41
42 private final Supplier<SQLExceptionTranslator> exceptionTranslatorSupplier;
43 private SQLExceptionTranslator exceptionTranslator;
44
45
46
47
48
49
50
51
52
53
54 public MyBatisExceptionTranslator(DataSource dataSource, boolean exceptionTranslatorLazyInit) {
55 this(() -> new SQLErrorCodeSQLExceptionTranslator(dataSource), exceptionTranslatorLazyInit);
56 }
57
58
59
60
61
62
63
64
65
66
67
68
69 public MyBatisExceptionTranslator(Supplier<SQLExceptionTranslator> exceptionTranslatorSupplier,
70 boolean exceptionTranslatorLazyInit) {
71 this.exceptionTranslatorSupplier = exceptionTranslatorSupplier;
72 if (!exceptionTranslatorLazyInit) {
73 this.initExceptionTranslator();
74 }
75 }
76
77
78
79
80 @Override
81 public DataAccessException translateExceptionIfPossible(RuntimeException e) {
82 if (e instanceof PersistenceException) {
83
84
85 String msg = e.getMessage();
86 if (e.getCause() instanceof PersistenceException) {
87 e = (PersistenceException) e.getCause();
88 if (msg == null) {
89 msg = e.getMessage();
90 }
91 }
92 if (e.getCause() instanceof SQLException) {
93 this.initExceptionTranslator();
94 String task = e.getMessage() + "\n";
95 SQLException se = (SQLException) e.getCause();
96 DataAccessException dae = this.exceptionTranslator.translate(task, null, se);
97 return dae != null ? dae : new UncategorizedSQLException(task, null, se);
98 } else if (e.getCause() instanceof TransactionException) {
99 throw (TransactionException) e.getCause();
100 }
101 return new MyBatisSystemException(msg, e);
102 }
103 return null;
104 }
105
106
107
108
109 private synchronized void initExceptionTranslator() {
110 if (this.exceptionTranslator == null) {
111 this.exceptionTranslator = exceptionTranslatorSupplier.get();
112 }
113 }
114
115 }