1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.apache.ibatis.executor.statement;
17
18 import java.sql.Connection;
19 import java.sql.SQLException;
20 import java.sql.Statement;
21
22 import org.apache.ibatis.executor.ErrorContext;
23 import org.apache.ibatis.executor.Executor;
24 import org.apache.ibatis.executor.ExecutorException;
25 import org.apache.ibatis.executor.keygen.KeyGenerator;
26 import org.apache.ibatis.executor.parameter.ParameterHandler;
27 import org.apache.ibatis.executor.resultset.ResultSetHandler;
28 import org.apache.ibatis.mapping.BoundSql;
29 import org.apache.ibatis.mapping.MappedStatement;
30 import org.apache.ibatis.reflection.factory.ObjectFactory;
31 import org.apache.ibatis.session.Configuration;
32 import org.apache.ibatis.session.ResultHandler;
33 import org.apache.ibatis.session.RowBounds;
34 import org.apache.ibatis.type.TypeHandlerRegistry;
35
36
37
38
39 public abstract class BaseStatementHandler implements StatementHandler {
40
41 protected final Configuration configuration;
42 protected final ObjectFactory objectFactory;
43 protected final TypeHandlerRegistry typeHandlerRegistry;
44 protected final ResultSetHandler resultSetHandler;
45 protected final ParameterHandler parameterHandler;
46
47 protected final Executor executor;
48 protected final MappedStatement mappedStatement;
49 protected final RowBounds rowBounds;
50
51 protected BoundSql boundSql;
52
53 protected BaseStatementHandler(Executor executor, MappedStatement mappedStatement, Object parameterObject, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql) {
54 this.configuration = mappedStatement.getConfiguration();
55 this.executor = executor;
56 this.mappedStatement = mappedStatement;
57 this.rowBounds = rowBounds;
58
59 this.typeHandlerRegistry = configuration.getTypeHandlerRegistry();
60 this.objectFactory = configuration.getObjectFactory();
61
62 if (boundSql == null) {
63 generateKeys(parameterObject);
64 boundSql = mappedStatement.getBoundSql(parameterObject);
65 }
66
67 this.boundSql = boundSql;
68
69 this.parameterHandler = configuration.newParameterHandler(mappedStatement, parameterObject, boundSql);
70 this.resultSetHandler = configuration.newResultSetHandler(executor, mappedStatement, rowBounds, parameterHandler, resultHandler, boundSql);
71 }
72
73 @Override
74 public BoundSql getBoundSql() {
75 return boundSql;
76 }
77
78 @Override
79 public ParameterHandler getParameterHandler() {
80 return parameterHandler;
81 }
82
83 @Override
84 public Statement prepare(Connection connection) throws SQLException {
85 ErrorContext.instance().sql(boundSql.getSql());
86 Statement statement = null;
87 try {
88 statement = instantiateStatement(connection);
89 setStatementTimeout(statement);
90 setFetchSize(statement);
91 return statement;
92 } catch (SQLException e) {
93 closeStatement(statement);
94 throw e;
95 } catch (Exception e) {
96 closeStatement(statement);
97 throw new ExecutorException("Error preparing statement. Cause: " + e, e);
98 }
99 }
100
101 protected abstract Statement instantiateStatement(Connection connection) throws SQLException;
102
103 protected void setStatementTimeout(Statement stmt) throws SQLException {
104 Integer timeout = mappedStatement.getTimeout();
105 if (timeout != null) {
106 stmt.setQueryTimeout(timeout);
107 return;
108 }
109 Integer defaultTimeout = configuration.getDefaultStatementTimeout();
110 if (defaultTimeout != null) {
111 stmt.setQueryTimeout(defaultTimeout);
112 }
113 }
114
115 protected void setFetchSize(Statement stmt) throws SQLException {
116 Integer fetchSize = mappedStatement.getFetchSize();
117 if (fetchSize != null) {
118 stmt.setFetchSize(fetchSize);
119 return;
120 }
121 Integer defaultFetchSize = configuration.getDefaultFetchSize();
122 if (defaultFetchSize != null) {
123 stmt.setFetchSize(defaultFetchSize);
124 }
125 }
126
127 protected void closeStatement(Statement statement) {
128 try {
129 if (statement != null) {
130 statement.close();
131 }
132 } catch (SQLException e) {
133
134 }
135 }
136
137 protected void generateKeys(Object parameter) {
138 KeyGenerator keyGenerator = mappedStatement.getKeyGenerator();
139 ErrorContext.instance().store();
140 keyGenerator.processBefore(executor, mappedStatement, null, parameter);
141 ErrorContext.instance().recall();
142 }
143
144 }