zoukankan      html  css  js  c++  java
  • JDBC数据源(DataSource)数据源技术是Java操作数据库的一个很关键技术,流行的持久化框架都离不开数据源的应用。

    JDBC数据源(DataSource)的简单实现
     
    数据源技术是Java操作数据库的一个很关键技术,流行的持久化框架都离不开数据源的应用。
    2.数据源提供了一种简单获取数据库连接的方式,并能在内部通过一个池的机制来复用数据库连接,这样就大大减少创建数据库连接的次数,提高了系统性能。
    3.对于数据源的应用,一般都选择实用开源的数据源或数据库连接池来使用,比如,常见的有DBCP、C3P0、Proxool等等。
     
    下面自己手动实现个精简的数据源,代码如下:
     
    package com.lavasoft.simpledatesource; 

    import org.apache.commons.logging.Log; 
    import org.apache.commons.logging.LogFactory; 

    import javax.sql.DataSource; 
    import java.util.Collections; 
    import java.util.LinkedList; 
    import java.sql.Connection; 
    import java.sql.SQLException; 
    import java.sql.DriverManager; 
    import java.io.PrintWriter; 

    /** 
    * 一个简单的DataSource实现 

    * @author leizhimin 2010-1-14 0:03:17 
    */
     
    public class SimpleDateSource implements DataSource { 
            private static Log log = LogFactory.getLog(SimpleDateSource.class); 
            private static final String dirverClassName = "com.mysql.jdbc.Driver"
            private static final String url = "jdbc:mysql://127.0.0.1:3306/testdb"; 
            private static final String user = "root"
            private static final String pswd = "leizhimin"
            //连接池 
            private static LinkedList<Connection> pool = (LinkedList<Connection>) Collections.synchronizedList(new LinkedList<Connection>()); 
            private static SimpleDateSource instance = new SimpleDateSource(); 

            static { 
                    try { 
                            Class.forName(dirverClassName); 
                    } catch (ClassNotFoundException e) { 
                            log.error("找不到驱动类!", e); 
                    } 
            } 

            private SimpleDateSource() { 
            } 

            /** 
             * 获取数据源单例 
             * 
             * @return 数据源单例 
             */
     
            public SimpleDateSource instance() { 
                    if (instance == null) instance = new SimpleDateSource(); 
                    return instance; 
            } 

            /** 
             * 获取一个数据库连接 
             * 
             * @return 一个数据库连接 
             * @throws SQLException 
             */
     
            public Connection getConnection() throws SQLException { 
                    synchronized (pool) { 
                            if (pool.size() > 0) return pool.removeFirst(); 
                            else return makeConnection(); 
                    } 
            } 

            /** 
             * 连接归池 
             * 
             * @param conn 
             */
     
            public static void freeConnection(Connection conn) { 
                    pool.addLast(conn); 
            } 

            private Connection makeConnection() throws SQLException { 
                    return DriverManager.getConnection(url, user, pswd); 
            } 

            public Connection getConnection(String username, String password) throws SQLException { 
                    return DriverManager.getConnection(url, username, password); 
            } 

            public PrintWriter getLogWriter() throws SQLException { 
                    return null
            } 

            public void setLogWriter(PrintWriter out) throws SQLException { 

            } 

            public void setLoginTimeout(int seconds) throws SQLException { 

            } 

            public int getLoginTimeout() throws SQLException { 
                    return 0; 
            } 

            public <T> T unwrap(Class<T> iface) throws SQLException { 
                    return null
            } 

            public boolean isWrapperFor(Class<?> iface) throws SQLException { 
                    return false
            } 
    }
     
    这个数据源的实现虽然很简陋,总代码量不到百行,却基本上实现了数据源的所有功能,达到了提高Connection复用的目的。
     
    如果你想做的更复杂些,做个配置文件,
    配置数据库连接信息
    写个后台线程监控连接池的Connection超时、被强制关闭、池的尺寸、当前大小等等。
    再完善下数据源的log相关方法的实现。
     

    DataSource接口(javax.sql.DataSource)替代DriverManager获取Connection的方法,有以下好处:

    • 可以在部署时灵活更换Connection实现;
    • 可以更好的屏蔽数据库的相关性。

    以下以Oracle为例说明。

    使用厂商DataSource

    数据库厂商在提高JDBC2.0和以上版本的JDBC驱动中应该包含厂商的DataSource实现。

    OracleDataSource ods = new OracleDataSource();
    ods.setUser(“my_user”);
    ods.setPassword(“my_password”);
    ods.setURL(“jdbc:oracle:thin:@<database>”);
    Connection conn = ods.getConnection();

    第三方DataSource

    第三方厂商也可提供DataSource实现,比如免费开源的有DBCP,C3P0和proxool等,中间件厂商比如ibm的websphere,bea的weblogic等也都有实现。

    以下是DBCP的示例:

    BasicDataSource basicDataSource = new BasicDataSource(); basicDataSource.setDriverClassName(“oracle.jdbc.OracleDriver”); basicDataSource.setUrl(“jdbc:oracle:thin:@<database>”); basicDataSource.setUsername(“user”);basicDataSource.setPassword(“password”); Connection connection=basicDataSource.getConnection();

    结合JNDI的DataSource

    以tomcat为例,将数据库驱动库复制到{tomcat}/commmon/lib目录下。

    配置{tomcat}/conf/context.xml文件,加入:

    <Resource name=”jdbc/demo” auth=”Container” type=”javax.sql.DataSource”
            driverClassName=”org.apache.derby.jdbc.ClientDriver”
            url=”jdbc:derby://localhost:1527/demo”
            username=”test”
            password=”test”
            maxActive=”2″
            maxIdle=”1″
            removeAbandoned=”true”
            maxWait=”300″ />

    在程序中访问DataSource:

    Context initContext = new InitialContext();

    // 注意: 以下写法只适用于tomcat(Java:/comp/env).
    Context envContext = (Context) initContext.lookup(“java:/comp/env”);
    dataSource = (DataSource) envContext.lookup(“jdbc/demo”);

    配置内容也可以加到webapp/META-INF/context.xml文件中,这样更便于打包部署。

    <%@page import="java.sql.*, javax.sql.*, javax.naming.*"%>
    <html>
    <head>
    <title>Using a DataSource</title>
    </head>
    <body>
    <h1>Using a DataSource</h1>
    <%
        DataSource ds = null;
        Connection conn = null;
        ResultSet result = null;
        Statement stmt = null;
        ResultSetMetaData rsmd = null;
        try{
          Context context = new InitialContext();
          Context envCtx = (Context) context.lookup("java:comp/env");
          ds =  (DataSource)envCtx.lookup("jdbc/address");
          if (ds != null) {
            conn = ds.getConnection();
            stmt = conn.createStatement();
            result = stmt.executeQuery("SELECT * FROM AddressList");
           }
         }
         catch (SQLException e) {
            System.out.println("Error occurred " + e);
          }
          int columns=0;
          try {
            rsmd = result.getMetaData();
            columns = rsmd.getColumnCount();
          }
          catch (SQLException e) {
             System.out.println("Error occurred " + e);
          }
     %>
     <table width="90%" border="1">
       <tr>
       <% // write out the header cells containing the column labels
          try {
             for (int i=1; i<=columns; i++) {
                  out.write("<th>" + rsmd.getColumnLabel(i) + "</th>");
             }
       %>
       </tr>
       <% // now write out one row for each entry in the database table
             while (result.next()) {
                out.write("<tr>");
                for (int i=1; i<=columns; i++) {
                  out.write("<td>" + result.getString(i) + "</td>");
                }
                out.write("</tr>");
             }
     
             // close the connection, resultset, and the statement
             result.close();
             stmt.close();
             conn.close();
          } // end of the try block
          catch (SQLException e) {
             System.out.println("Error " + e);
          }
          // ensure everything is closed
        finally {
         try {
           if (stmt != null)
            stmt.close();
           }  catch (SQLException e) {}
           try {
            if (conn != null)
             conn.close();
            } catch (SQLException e) {}
        }
     
        %>
    </table>
    </body>
    </html>

  • 相关阅读:
    将vue文件script代码抽取到单独的js文件
    git pull 提示错误:Your local changes to the following files would be overwritten by merge
    vue和uniapp 配置项目基础路径
    XAMPP Access forbidden! Access to the requested directory is only available from the local network.
    postman与newman集成
    postman生成代码段
    Curl命令
    POST方法的Content-type类型
    Selenium Grid 并行的Web测试
    pytorch转ONNX以及TnesorRT的坑
  • 原文地址:https://www.cnblogs.com/panxuejun/p/7264103.html
Copyright © 2011-2022 走看看