`

hsqldb源码分析启动调试

 
阅读更多

  

 hsqldb是java版的简化数据库,代码量比较少,对于学习数据库的设计是一个比较好的选择,

对于derby代码量比较大,mysql c++更复杂,所以就通过学习hsqldb来学习数据库的设计。

在这里可以下载到源码http://hsqldb.org/,源码包下org.hsqldb.test有很多的测试类,大家可以从这里开始调试学习hsqldb。

 

HyperSQL 数据库叫catalog,根据数据库存储方式不同分为几种:

• mem: stored entirely in RAM - without any persistence beyond the JVM process's life
• file: stored in filesystem files

• res: stored in a Java resource, such as a Jar and always read-only

 

客户端可以通过连接串不同指定不同的存储格式

 

 Connection c = DriverManager.getConnection("jdbc:hsqldb:file:testdb", "SA", "");
Connection c = DriverManager.getConnection("jdbc:hsqldb:file:/opt/db/testdb", "SA", "");file:数据保存在文件
 Connection c = DriverManager.getConnection("jdbc:hsqldb:mem:mymemdb", "SA", "");mem表示数据库只保存在内存
  Connection c = DriverManager.getConnection("jdbc:hsqldb:res:org.my.path.resdb", "SA", ""); res表示压缩保存classpath java或者zip包中,内存解压使用

 

启动hyperSQL的服务器模式
HyperSQL HSQL Server  可以使用参数--help查看参数选项,下面是打开mydb数据文件作为数据库别名为xdb,客户端就可以使用xdb数据库来连接服务器使用了。
java -cp ../lib/hsqldb.jar org.hsqldb.server.Server --database.0 file:mydb --dbname.0 xdb
 HyperSQL HTTP Server http协议的服务器模式
java -cp ../lib/hsqldb.jar org.hsqldb.server.WebServer --database.0 file:mydb --dbname.0 xdb
 servlet容器启动服务器HyperSQL HTTP Servlet
需要在web.xml配置org/hsqldb/server/Servlet.java 这个servlet,这种模式只能支持一个数据库。
客户端连接到hsql server:
 try {
      Class.forName("org.hsqldb.jdbc.JDBCDriver" );
  } catch (Exception e) {
      System.err.println("ERROR: failed to load HSQLDB JDBC driver.");
      e.printStackTrace();
      return;
  }
 
 Connection c = DriverManager.getConnection("jdbc:hsqldb:hsql://localhost/xdb", "SA", "");
如果是hsql服务器模式则用:hsql:,http则用http://
  Connection c = DriverManager.getConnection("jdbc:hsqldb:http://localhost/xdb", "SA", "");

使用ssl连接到hsql和 http 服务器
 Connection c = DriverManager.getConnection("jdbc:hsqldb:hsqls://localhost/xdb", "SA", "");
 Connection c = DriverManager.getConnection("jdbc:hsqldb:https://localhost/xdb", "SA", "");
 
关闭服务器:使用参数shutdown=true,最后一个连接处理完了需要关闭服务器,会对内存数据进行处理(如果是文件的,则flush到文件),这个在测试场景下用得比较多。
  Connection c = DriverManager.getConnection(
          "jdbc:hsqldb:file:/opt/db/testdb;shutdown=true", "SA", "");

如果要重用已有的数据库,则用参数ifexists=true,如果数据库不存在,则抛异常。
Connection c = DriverManager.getConnection(
        "jdbc:hsqldb:file:/opt/db/testdb;ifexists=true", "SA", "");
 
代码分析:
  org.hsqldb.server类的run方法处理输入,打开数据库,建立服务器socket或者http连接,监听socket连接,每次accept一个socket连接,则使用public void handleConnection(Socket s)方法来处理该连接,每个客户端连接服务端都会生产一个线程来处理,然后在每个ServerConnection或者WebServerConnection处理每个sql的处理,后面再进一步分析sql的访问协议,以后sql语法分析,语义分析等后续逻辑。 这段代码比较简单,大家可以直接查看server类。
  关键部分开始如下:
 public void handleConnection(Socket s) {


        Thread   t;
        Runnable r;
        String   ctn;


        printWithThread("handleConnection(" + s + ") entered");


        if (!allowConnection(s)) {
            try {
                s.close();
            } catch (Exception e) {}


            printWithThread("allowConnection(): connection refused");
            printWithThread("handleConnection() exited");


            return;
        }


        // Maybe set up socket options, SSL
        // Session tracing/callbacks, etc.
        if (socketFactory != null) {
            socketFactory.configureSocket(s);
        }


        if (serverProtocol == ServerConstants.SC_PROTOCOL_HSQL) {
            r   = new ServerConnection(s, this);
            ctn = ((ServerConnection) r).getConnectionThreadName();
        } else {
            r   = new WebServerConnection(s, (WebServer) this);
            ctn = ((WebServerConnection) r).getConnectionThreadName();
        }


        t = new Thread(serverConnectionThreadGroup, r, ctn);


        t.start();
        printWithThread("handleConnection() exited");
    }
 

 从server的main函数输出参数中主要有几个:maxConnections 最大连接数限制, isSilent是否显示所有query,isRemoteOpen是否支持远程打开,不支持,isDaemon是否守护模式,acl指定访问控制权限文件路径,指定ip地址的黑白名单。acl文件格式参考http://hsqldb.org/doc/2.0/guide/listeners-chapt.html#N15C79

 * +-----------------+-------------+----------+------------------------------+
 * |    OPTION       |    TYPE     | DEFAULT  |         DESCRIPTION          |
 * +-----------------+-------------+----------+------------------------------|
 * | --help          |             |          | prints this message          |
 * | --address       | name|number | any      | server inet address          |
 * | --port          | number      | 9001/544 | port at which server listens |
 * | --database.i    | [type]spec  | 0=test   | path of database i           |
 * | --dbname.i      | alias       |          | url alias for database i     |
 * | --silent        | true|false  | true     | false => display all queries |
 * | --trace         | true|false  | false    | display JDBC trace messages  |
 * | --tls           | true|false  | false    | TLS/SSL (secure) sockets     |
 * | --no_system_exit| true|false  | false    | do not issue System.exit()   |
 * | --remote_open   | true|false  | false    | can open databases remotely  |
 * | --props         | filepath    |          | file path of properties file |
 * +-----------------+-------------+----------+------------------------------+

 

    maxConnections = serverProperties.getIntegerProperty(
            ServerProperties.sc_key_max_connections, 16);

        JavaSystem.setLogToSystem(isTrace());

        isSilent =
            serverProperties.isPropertyTrue(ServerProperties.sc_key_silent);
        isRemoteOpen = serverProperties.isPropertyTrue(
            ServerProperties.sc_key_remote_open_db);
        isDaemon =
            serverProperties.isPropertyTrue(ServerProperties.sc_key_daemon);

 当然openDatabase里面就是根据参数指定的database文件打开对应的数据库。

在database类的reopen方法中有几个对象,就是数据库操作相关的对象,无非就是数据库对象名称管理,权限管理,用户管理,shema管理,session管理,事务管理,日志管理,检查点管理,后续一个一个分析。

  /**
     * Opens this database.  The database should be opened after construction.
     * or reopened by the close(int closemode) method during a
     * "shutdown compact". Closes the log if there is an error.
     */
    void reopen() {

        boolean isNew = false;

        setState(DATABASE_OPENING);

        try {
            nameManager    = new HsqlNameManager(this);
            granteeManager = new GranteeManager(this);
            userManager    = new UserManager(this);
            schemaManager  = new SchemaManager(this);
            persistentStoreCollection =
                new PersistentStoreCollectionDatabase();
            isReferentialIntegrity = true;
            sessionManager         = new SessionManager(this);
            collation              = collation.newDatabaseInstance();
            dbInfo = DatabaseInformation.newDatabaseInformation(this);
            txManager              = new TransactionManager2PL(this);

            lobManager.createSchema();
            sessionManager.getSysLobSession().setSchema(
                SqlInvariants.LOBS_SCHEMA);
            schemaManager.setSchemaChangeTimestamp();
            schemaManager.createSystemTables();

            // completed metadata
            logger.openPersistence();

            isNew = logger.isNewDatabase;

            if (isNew) {
                String username = urlProperties.getProperty("user", "SA");
                String password = urlProperties.getProperty("password", "");

                userManager.createFirstUser(username, password);
                schemaManager.createPublicSchema();
                lobManager.initialiseLobSpace();
                logger.checkpoint(false);
            }

            lobManager.open();
            dbInfo.setWithContent(true);

            checkpointRunner = new CheckpointRunner();
        } catch (Throwable e) {
            logger.closePersistence(Database.CLOSEMODE_IMMEDIATELY);
            logger.releaseLock();
            setState(DATABASE_SHUTDOWN);
            clearStructures();
            DatabaseManager.removeDatabase(this);

            if (!(e instanceof HsqlException)) {
                e = Error.error(ErrorCode.GENERAL_ERROR, e);
            }

            logger.logSevereEvent("could not reopen database", e);

            throw (HsqlException) e;
        }

        setState(DATABASE_ONLINE);
    }

 

下一节分析handleConnection的处理

分享到:
评论

相关推荐

    Hsqldb的缓存分析及调试步骤

    以下是对HSQLDB的缓存分析和调试步骤的详细解释。 ### 一、实验环境 在进行HSQLDB的分析之前,我们需要一个合适的实验环境。这通常包括安装Java Development Kit (JDK),配置好环境变量,以及下载并设置HSQLDB的...

    hsqldb随tomcat启动

    标签“源码”和“工具”暗示这篇博客可能还涉及了代码示例以及HSQLDB作为开发工具的使用。 在提供的压缩包文件`hsqlDemo`中,可能包含了示例代码、数据库脚本或者其他相关资源,帮助读者更好地理解和实践这个过程。...

    hsqldb使用(转载)

    例如,启动名为`test`的数据库,命令为`java -cp hsqldb.jar org.hsqldb.Server -database.0 ./db/test -dbname.0 test`。通过JDBC,我们可以使用`jdbc:hsqldb:hsql://localhost:9002/test`连接到服务器。 - **In-...

    HSQLDB

    源码分析** 由于HSQLDB是开源的,开发者可以深入研究其源码,理解数据库的内部工作原理,如查询解析、执行计划生成、事务管理等,这对提升数据库相关的技术能力非常有帮助。 总之,HSQLDB作为一个轻量级、高性能...

    HSQLDB-Research:HSQLDB数据库源代码学习研究(包括代码注释,文档,用于代码分析的测试用例)

    src:HSQLDB数据库的最新源代码,在源代码中附加了轻松分析理解代码的注释 把代码引入Eclipse 运行mvn eclipse:eclipse生成Eclipse项目,打开Eclipse,选择File-> Import-> Existing Projects into Workspace 运行...

    开源数据库软件hsqldb

    然而,HSQldb的开源特性使其在学习和调试方面具有便利性,开发者可以直接查看源码,了解其内部工作原理。 四、HSQldb的应用场景 HSQldb广泛应用于软件开发的原型设计、单元测试、小型Web应用、移动应用等场景。...

    HSQLDB快速连接数据库

    - **约束和索引**:详细阐述了如何在HSQLDB中定义和使用主键、唯一性约束、唯一性索引以及外键约束,并分析了这些约束和索引如何影响查询性能。 - **类型和算术操作**:介绍了HSQLDB支持的各种数据类型,包括整型、...

    hsqldb 2.25

    HSQldb因其小巧、高效以及对Java应用的良好支持,常被用于开发、测试和部署阶段,尤其是对于那些对数据存储需求不高但又需快速启动的项目。 在本压缩包中,提供的HSQldb版本为2.25,特别之处在于它是针对JDK 1.5...

    <转>HSQLDB 安装与使用

    ### 源码分析 HSQLDB是用纯Java编写的,因此对于开发者来说,查看源码可以深入了解其工作原理。主要的类包括`org.hsqldb.Server`(服务器进程)、`org.hsqldb.jdbc.JDBCConnection`(JDBC连接)以及`org.hsqldb....

    hsqldb-2.5.0.jar

    hsqldb数据库下载,很好用,简易的内存数据库,特别适合初学者。

    hsqldb-2.2.8数据库

    **HSQldb 2.2.8 数据库详解** HSQldb(HyperSQL Database)是一款高效、轻量级且开源的Java数据库管理系统,它在IT领域中被广泛应用于开发、测试以及小型应用环境。HSQldb完全用Java编写,因此具有良好的跨平台性,...

    HSQLDB的使用

    **源码分析** HSQLDB是用Java编写的,因此其源码可读性较高,对于学习数据库原理和实现有很高的价值。通过阅读源码,开发者可以深入理解SQL的执行流程、事务管理、索引构建等核心概念。 **工具支持** HSQLDB提供...

    hsqldb学习包括数据库创建启动配置等

    在本文中,我们将深入探讨HSQldb的学习,包括数据库的创建、启动、配置以及管理工具和SQLTool的使用。 首先,获取HSQldb的最新稳定版本,可以从官方网址http://www.hsqldb.org/下载。解压缩后,文档目录下的`index....

    hsqldb-lib.zip

    5. 其他工具:HSQldb可能包含一些用于数据导入/导出、数据库管理或性能分析的工具,这些工具可能依赖于额外的JAR文件。 使用这些额外的JAR文件时,我们需要确保它们与HSQldb的核心库以及其他依赖库兼容。通常,我们...

    hsqldb的最新版本

    HSQldb,全称HyperSQL Database,是一款开源的、轻量级的关系型数据库管理系统,尤其适合于嵌入式应用和开发测试环境。HSQldb完全用Java编写,因此具有跨平台性,能在任何支持Java的环境中运行,包括Windows操作系统...

    hsqldb快速入门

    HSQldb在启动时,如果指定的数据库文件不存在,会自动创建。数据库文件的位置可以通过启动参数`-database.n`来指定,`dbname.n`则是访问数据库的别名。 **HSQldb启动模式** HSQldb提供了三种主要的启动模式: 1. *...

    hsqldb demo

    6. **网络服务器模式**:如果示例包含网络服务器模式,将展示如何启动HSQldb 服务器,并通过网络连接进行数据库操作。 **应用场景** HSQldb 常用于以下场合: - **开发和测试**:开发人员可以快速搭建数据库环境...

Global site tag (gtag.js) - Google Analytics