• 动态代理实现dataSource ConnectionPool


    编写连接池需实现java.sql.DataSource接口,
    DataSource接口中定义了两个重载的getConnection方法:
    Connection getConnection()
    Connection getConnection(String username, String password)


    没有close或release方法那么怎么 释放到池中呢?
    所以通过动态代理实现
    代码如下

    
    public class JdbcPool implements DataSource {
    
    	private static String driver;
    	private static String url;
    	private static  String username;
    	private static String password;
    
    	static{
    		try {
    			
    			Properties prop = new Properties();
    			InputStream in = JdbcUtil.class.getClassLoader().getResourceAsStream("db.properties");
    			prop.load(in);
    			driver = prop.getProperty("driver");
    			url = prop.getProperty("url");
    			username = prop.getProperty("username");
    			password = prop.getProperty("password");
    			Class.forName(driver);
    		} catch (Exception e) {
    			throw new ExceptionInInitializerError(e);
    		}
    	}
    	
    	private static LinkedList<Connection> pool = new LinkedList<Connection>();
    	private static int poolsize = 10;
    	//问题:每次newJdbcPoll都会建立10个链接,可使用单态设计模式解决此类问题
    	public JdbcPool(){
    	
    		for(int i=0;i<poolsize;i++){
    			try {
    				Connection conn = DriverManager.getConnection(url,username,password);
    				pool.add(conn);
    				System.out.println(conn + "被加到池里面了!!!");
    			} catch (SQLException e) {
    				// TODO Auto-generated catch block
    				e.printStackTrace();
    			}
    		}
    	}
    	
    	
    	/*
    	 * 这里使用动态代理技术返回一个假的Connection,当dao调用假connection的任何方法时,该方法体内会调用InvocationHandler.invoke方法
    	 * 在invoke方法体内,发现dao调用的是close方法,则把链接还到池里,否则,调用真connection的对应方法。
    	 * (non-Javadoc)
    	 * @see javax.sql.DataSource#getConnection()
    	 */
    	public Connection getConnection() throws SQLException { //spring aop
    		if(pool.size()>0){
    			final Connection conn = pool.removeFirst();
    			System.out.println(conn + "从池里面取出去了!!!");
    			return (Connection) Proxy.newProxyInstance(JdbcPool.class.getClassLoader(),conn.getClass().getInterfaces(), new InvocationHandler(){
    					//proxy为代理对象 method为要调用的方法 args为方法的参数
    				public Object invoke(Object proxy, Method method, Object[] args)
    						throws Throwable {
    					if(method.getName().equals("close")){
    						pool.addFirst(conn);
    						System.out.println(conn + "被还到池里面了!!");
    						return null;
    					}else{
    						return method.invoke(conn, args);
    					}
    				}
    			});
    			
    		}
    		throw new RuntimeException("对不起,池里没有资源了!!!");
    	}
    
    	public Connection getConnection(String arg0, String arg1)
    			throws SQLException {
    		// TODO Auto-generated method stub
    		return null;
    	}
    
    	public PrintWriter getLogWriter() throws SQLException {
    		// TODO Auto-generated method stub
    		return null;
    	}
    
    	public int getLoginTimeout() throws SQLException {
    		// TODO Auto-generated method stub
    		return 0;
    	}
    
    	public void setLogWriter(PrintWriter arg0) throws SQLException {
    		// TODO Auto-generated method stub
    		
    	}
    
    	public void setLoginTimeout(int arg0) throws SQLException {
    		// TODO Auto-generated method stub
    		
    	}
    
    	//public Jdbcpool
    	
    }
    
  • 相关阅读:
    linux下文件的复制、移动与删除
    031_spark架构原理
    Scala基础篇-05求值策略
    Ceph pg分裂流程及可行性分析
    Ceph中的序列化
    奔跑吧,OpenStack现场分享:超融合架构如何抹平物理硬件差异?
    Ceph中Bufferlist的设计与使用
    IaaS中的统一存储:从设计到实现
    关于Ceph现状与未来的一些思考
    解析Ceph: 数据的端到端正确性和 Scrub 机制
  • 原文地址:https://www.cnblogs.com/hiaming/p/8967808.html
Copyright © 2020-2023  润新知