简体   繁体   English

如何在Java应用程序中运行SQLite VACUUM命令?

[英]How can I run the SQLite VACUUM command within a Java application?

Question: I want to allow my Java application to manually run the SQLite VACUUM command? 问:我想允许我的Java应用程序手动运行SQLite VACUUM命令吗? I include a code snippet below. 我在下面包含一个代码段。 I have tried as a PreparedStatement and as a straight Statement. 我已经尝试过作为PreparedStatement和直接声明。 I have also done an extensive web search for a solution and have found no relevant examples. 我也进行了广泛的网络搜索以寻找解决方案,但没有找到相关的示例。

What Happens? 怎么了? When I run my code, the system pauses. 当我运行代码时,系统暂停。 Looking at the directory, the file size does not decrease when executing my code. 查看目录,执行我的代码时文件大小不会减小。 RecordSet returns false as well. RecordSet也返回false。

But, if I run SQLiteManager via Firefox and run Compact Database, the database does compact. 但是,如果我通过Firefox运行SQLiteManager并运行“压缩数据库”,则数据库确实会压缩。 NOTE: I make a copy of the DB before compacting so I can see the difference in size. 注意:在压缩之前,我会复制数据库,以便可以看到大小的差异。

Sanity Checks --I make sure the DB is closed by all other applications (including SQLiteManager). 完整性检查 -我确保所有其他应用程序(包括SQLiteManager)都已关闭数据库。 --No known transactions running. -没有已知的交易正在运行。 --No exceptions thrown. -没有抛出异常。

Code Snippet: I kept my test code inside. 代码段:我将测试代码保留在其中。 This is NOT production code so error handling etc is available but minimal. 这不是生产代码,因此可以进行错误处理等,但是错误最少。

try {
    Connection conn = db.getConnection() ;
    StringBuilder sql = new StringBuilder() ;
    sql.append("VACUUM");

    //PreparedStatement prep = conn.prepareStatement(sql.toString()) ;
    Statement stat = conn.createStatement() ;
    boolean rs = stat.execute(sql.toString()) ;

    System.out.println("Executed vacuum " + rs ) ;     

    //Testing code--preparedstatement attempts
    //conn.setAutoCommit(false);
    //boolean rs = prep.execute() ;
    //conn.setAutoCommit(true);

    } catch (Exception e) {
       //Edited back in after posting to StackOverflow
        System.out.println(
                ".SQLiteVacuum :: exception " + 
                e.getMessage() + " " + e.getClass().getName() );
        e.printStackTrace() ;
    }

Cross References Java 1.6+ SQLite 3+ Xerial JDBC Driver 交叉引用 Java 1.6+ SQLite 3+ Xerial JDBC驱动程序

Addendum 附录

private final String dbJDBCdriverclassname = "org.sqlite.JDBC" ;
private final String dbJDBCpreconnectionstring = "jdbc:sqlite:" ;
        // Setup the driver reference
        Class.forName(dbJDBCdriverclassname) ; //"org.sqlite.JDBC"

        // Create the connection string
        String connstring = dbJDBCpreconnectionstring + this.getDBConnectionFullFileName() ;

        // create the connection
        dbconnection = 
                DriverManager.getConnection(connstring) ; // "jdbc:sqlite:test.db"

I know that this is quite old but if everyone needs here it goes. 我知道这已经很老了,但是如果每个人都需要它,那就去吧。

Statement stmt = null;
ResultSet rs = null;
try {
    Connection conn = DBConnection.getConnection();//something to get a connection
    stmt = conn.createStatement();
    stmt.executeUpdate("VACUUM");
} catch (SQLException ex) {
    //Something if you like, or not you're the boss!
} finally {
    DBConnection.closeResources(rs, stmt);//something to close all the resources
}

With something like this snippet, I got 63KB of savings in a test DataBase of 185KB. 有了这样的代码片段,我在185KB的测试数据库中节省了63KB。

Are you using the correct driver in your data source? 您是否在数据源中使用了正确的驱动程序? Are you configuring it properly? 您是否配置正确? That's the part of the code (or configuration) that we're not seeing. 那是我们没有看到的代码(或配置)的一部分。

Also, print a stack trace or something, as the above user said, so that we know whether an exception is being thrown. 另外,如上述用户所述,打印堆栈跟踪或其他内容,以便我们知道是否引发了异常。 And it would be nice to know whether Statement's execute method returns true or false. 很高兴知道Statement的execute方法返回true还是false。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM