001/* 002 * HA-JDBC: High-Availability JDBC 003 * Copyright (C) 2012 Paul Ferraro 004 * 005 * This program is free software: you can redistribute it and/or modify 006 * it under the terms of the GNU Lesser General Public License as published by 007 * the Free Software Foundation, either version 3 of the License, or 008 * (at your option) any later version. 009 * 010 * This program is distributed in the hope that it will be useful, 011 * but WITHOUT ANY WARRANTY; without even the implied warranty of 012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 013 * GNU Lesser General Public License for more details. 014 * 015 * You should have received a copy of the GNU Lesser General Public License 016 * along with this program. If not, see <http://www.gnu.org/licenses/>. 017 */ 018package net.sf.hajdbc.sql; 019 020import java.lang.reflect.Method; 021import java.sql.CallableStatement; 022import java.sql.PreparedStatement; 023import java.sql.SQLException; 024import java.util.Set; 025 026import net.sf.hajdbc.Database; 027import net.sf.hajdbc.invocation.InvocationStrategies; 028import net.sf.hajdbc.invocation.InvocationStrategy; 029import net.sf.hajdbc.util.reflect.Methods; 030 031/** 032 * @author Paul Ferraro 033 * @param <D> 034 */ 035@SuppressWarnings("nls") 036public class CallableStatementInvocationHandler<Z, D extends Database<Z>> extends AbstractPreparedStatementInvocationHandler<Z, D, CallableStatement, CallableStatementProxyFactory<Z, D>> 037{ 038 private static final Set<Method> registerOutParameterMethods = Methods.findMethods(CallableStatement.class, "registerOutParameter"); 039 private static final Set<Method> setMethods = Methods.findMethods(CallableStatement.class, "set\\w+"); 040 private static final Set<Method> driverReadMethods = Methods.findMethods(CallableStatement.class, "get\\w+", "wasNull"); 041 { 042 driverReadMethods.removeAll(Methods.findMethods(PreparedStatement.class, "get\\w+")); 043 } 044 045 public CallableStatementInvocationHandler(CallableStatementProxyFactory<Z, D> proxyFactory) 046 { 047 super(CallableStatement.class, proxyFactory, setMethods); 048 } 049 050 /** 051 * @see net.sf.hajdbc.sql.AbstractStatementInvocationHandler#getInvocationStrategy(java.sql.Statement, java.lang.reflect.Method, java.lang.Object[]) 052 */ 053 @Override 054 protected InvocationStrategy getInvocationStrategy(CallableStatement statement, Method method, Object... parameters) throws SQLException 055 { 056 if (registerOutParameterMethods.contains(method)) 057 { 058 return InvocationStrategies.INVOKE_ON_EXISTING; 059 } 060 061 if (driverReadMethods.contains(method)) 062 { 063 return InvocationStrategies.INVOKE_ON_ANY; 064 } 065 066 return super.getInvocationStrategy(statement, method, parameters); 067 } 068 069 /** 070 * @see net.sf.hajdbc.sql.AbstractPreparedStatementInvocationHandler#isBatchMethod(java.lang.reflect.Method) 071 */ 072 @Override 073 protected boolean isBatchMethod(Method method) 074 { 075 return registerOutParameterMethods.contains(method) || super.isBatchMethod(method); 076 } 077 078 /** 079 * @see net.sf.hajdbc.sql.AbstractPreparedStatementInvocationHandler#isIndexType(java.lang.Class) 080 */ 081 @Override 082 protected boolean isIndexType(Class<?> type) 083 { 084 return super.isIndexType(type) || type.equals(String.class); 085 } 086}