001/* 002 * HA-JDBC: High-Availability JDBC 003 * Copyright (c) 2004-2008 Paul Ferraro 004 * 005 * This library is free software; you can redistribute it and/or modify it 006 * under the terms of the GNU Lesser General Public License as published by the 007 * Free Software Foundation; either version 2.1 of the License, or (at your 008 * option) any later version. 009 * 010 * This library is distributed in the hope that it will be useful, but WITHOUT 011 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 012 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License 013 * for more details. 014 * 015 * You should have received a copy of the GNU Lesser General Public License 016 * along with this library; if not, write to the Free Software Foundation, 017 * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 018 * 019 * Contact: ferraro@users.sourceforge.net 020 */ 021package net.sf.hajdbc.sql; 022 023import java.lang.reflect.InvocationHandler; 024import java.sql.SQLException; 025import java.util.Hashtable; 026 027import javax.naming.Context; 028import javax.naming.Name; 029import javax.naming.RefAddr; 030import javax.naming.Reference; 031import javax.naming.spi.ObjectFactory; 032 033import net.sf.hajdbc.DatabaseCluster; 034import net.sf.hajdbc.util.reflect.ProxyFactory; 035 036/** 037 * @author Paul Ferraro 038 * 039 * @param <D> 040 */ 041public abstract class CommonDataSourceObjectFactory<D> implements ObjectFactory, CommonDataSourceFactory<D> 042{ 043 private Class<D> targetClass; 044 045 /** 046 * @param targetClass 047 */ 048 protected CommonDataSourceObjectFactory(Class<D> targetClass) 049 { 050 this.targetClass = targetClass; 051 } 052 053 /** 054 * @see javax.naming.spi.ObjectFactory#getObjectInstance(java.lang.Object, javax.naming.Name, javax.naming.Context, java.util.Hashtable) 055 */ 056 @Override 057 public Object getObjectInstance(Object object, Name name, Context context, Hashtable<?,?> environment) throws Exception 058 { 059 if ((object == null) || !(object instanceof Reference)) return null; 060 061 Reference reference = (Reference) object; 062 063 String className = reference.getClassName(); 064 065 if ((className == null) || !className.equals(this.targetClass.getName())) return null; 066 067 RefAddr idAddr = reference.get(CommonDataSourceReference.CLUSTER); 068 069 if (idAddr == null) return null; 070 071 Object idAddrContent = idAddr.getContent(); 072 073 if ((idAddrContent == null) || !(idAddrContent instanceof String)) return null; 074 075 String id = (String) idAddrContent; 076 077 RefAddr configAddr = reference.get(CommonDataSourceReference.CONFIG); 078 079 String config = null; 080 081 if (configAddr != null) 082 { 083 Object configAddrContent = configAddr.getContent(); 084 085 if ((configAddrContent != null) && (configAddrContent instanceof String)) 086 { 087 config = (String) configAddrContent; 088 } 089 } 090 091 return this.createProxy(id, config); 092 } 093 094 /** 095 * @see net.sf.hajdbc.sql.CommonDataSourceFactory#createProxy(java.lang.String, java.lang.String) 096 */ 097 public D createProxy(String id, String config) throws SQLException 098 { 099 DatabaseCluster<D> cluster = this.getDatabaseCluster(id, config); 100 101 if (cluster == null) return null; 102 103 return ProxyFactory.createProxy(this.targetClass, this.getInvocationHandler(cluster)); 104 } 105 106 /** 107 * @param id 108 * @param config 109 * @return the appropriate database cluster 110 * @throws SQLException 111 */ 112 protected abstract DatabaseCluster<D> getDatabaseCluster(String id, String config) throws SQLException; 113 114 /** 115 * @param cluster 116 * @return the appropriate proxy invocation handler for this datasource 117 */ 118 protected abstract InvocationHandler getInvocationHandler(DatabaseCluster<D> cluster); 119}