📄 log.java
字号:
/* Copyright (c) 1995-2000, The Hypersonic SQL Group. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * Redistributions of source code must retain the above copyright notice, this * list of conditions and the following disclaimer. * * Redistributions in binary form must reproduce the above copyright notice, * this list of conditions and the following disclaimer in the documentation * and/or other materials provided with the distribution. * * Neither the name of the Hypersonic SQL Group nor the names of its * contributors may be used to endorse or promote products derived from this * software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE HYPERSONIC SQL GROUP, * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * * This software consists of voluntary contributions made by many individuals * on behalf of the Hypersonic SQL Group. * * * For work added by the HSQL Development Group: * * Copyright (c) 2001-2005, The HSQL Development Group * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * Redistributions of source code must retain the above copyright notice, this * list of conditions and the following disclaimer. * * Redistributions in binary form must reproduce the above copyright notice, * this list of conditions and the following disclaimer in the documentation * and/or other materials provided with the distribution. * * Neither the name of the HSQL Development Group nor the names of its * contributors may be used to endorse or promote products derived from this * software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL HSQL DEVELOPMENT GROUP, HSQLDB.ORG, * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */package org.hsqldb.persist;import java.io.File;import java.io.IOException;import org.hsqldb.Database;import org.hsqldb.HsqlException;import org.hsqldb.NumberSequence;import org.hsqldb.Session;import org.hsqldb.Table;import org.hsqldb.Trace;import org.hsqldb.lib.FileAccess;import org.hsqldb.lib.HashMap;import org.hsqldb.lib.Iterator;import org.hsqldb.lib.SimpleLog;import org.hsqldb.lib.ZipUnzipFile;import org.hsqldb.scriptio.ScriptReaderBase;import org.hsqldb.scriptio.ScriptWriterBase;// fredt@users 20020215 - patch 1.7.0 by fredt// to move operations on the database.properties files to new// class HsqlDatabaseProperties// fredt@users 20020220 - patch 488200 by xclayl@users - throw exception// throw addded to all methods relying on file io// fredt@users 20020221 - patch 513005 by sqlbob@users (RMP)// fredt@users 20020405 - patch 1.7.0 by fredt - no change in db location// because important information about the database is now stored in the// *.properties file, all database files should be in the same folder as the// *.properties file// tony_lai@users 20020820 - export hsqldb.log_size to .properties file// tony_lai@users 20020820 - changes to shutdown compact to save memory// fredt@users 20020910 - patch 1.7.1 by Nitin Chauhan - code improvements// fredt@users 20021208 - ongoing revamp// fredt@users 20021212 - do not rewrite the *.backup file if the *.data// file has not been updated in the current session.// boucherb@users 20030510 - patch 1.7.2 consolidated all periodic database// tasks in one timed task queue// fredt@users - 20050102 patch 1.8.0 - refactoring and clearer separation of concerns/** * This class is responsible for managing the database files. An HSQLDB database * consists of a .properties file, a .script file (contains an SQL script), * a .data file (contains data of cached tables) a .backup file * and a .log file.<p> * When using TEXT tables, a data source for each table is also present.<p> * * Notes on OpenOffice.org integration. * * A Storage API is used when HSQLDB is integrated into OpenOffice.org. All * file operations on the 4 main files are performed by OOo, which integrates * the contents of these files into its database file. The script format is * always TEXT in this case. * * Extensively rewritten and extended in successive versions of HSQLDB. * * @author Thomas Mueller (Hypersonic SQL Group) * @author fredt@users. * @version 1.8.0 * @since Hypersonic SQL */public class Log { private HsqlDatabaseProperties properties; private String fileName; private Database database; private FileAccess fa; private ScriptWriterBase dbLogWriter; private String scriptFileName; private String logFileName; private boolean filesReadOnly; private long maxLogSize; private int writeDelay; private int scriptFormat; private DataFileCache cache; Log(Database db) throws HsqlException { database = db; fa = db.getFileAccess(); fileName = db.getPath(); properties = db.getProperties(); } void initParams() { // Allows the user to set log size in the properties file. int logMegas = properties.getIntegerProperty( HsqlDatabaseProperties.hsqldb_log_size, 0); maxLogSize = logMegas * 1024 * 1024; scriptFormat = properties.getIntegerProperty( HsqlDatabaseProperties.hsqldb_script_format, ScriptWriterBase.SCRIPT_TEXT_170); writeDelay = properties.getDefaultWriteDelay(); filesReadOnly = database.isFilesReadOnly(); scriptFileName = fileName + ".script"; logFileName = fileName + ".log"; } /** * When opening a database, the hsqldb.compatible_version property is * used to determine if this version of the engine is equal to or greater * than the earliest version of the engine capable of opening that * database.<p> * * @throws HsqlException */ void open() throws HsqlException { initParams(); int state = properties.getDBModified(); switch (state) { case HsqlDatabaseProperties.FILES_MODIFIED : deleteNewAndOldFiles(); restoreBackup(); processScript(); processDataFile(); processLog(); close(false); if (cache != null) { cache.open(filesReadOnly); } reopenAllTextCaches(); break; case HsqlDatabaseProperties.FILES_NEW : try { deleteBackup(); backupData(); renameNewBackup(); renameNewScript(); deleteLog(); properties.setDBModified( HsqlDatabaseProperties.FILES_NOT_MODIFIED); } catch (IOException e) { database.logger.appLog.logContext(e, null); } // continue as non-modified files case HsqlDatabaseProperties.FILES_NOT_MODIFIED : /** * if startup is after a SHUTDOWN SCRIPT and there are CACHED * or TEXT tables, perform a checkpoint so that the .script * file no longer contains CACHED or TEXT table rows. */ processScript(); if (isAnyCacheModified()) { properties.setDBModified( HsqlDatabaseProperties.FILES_MODIFIED); close(false); if (cache != null) { cache.open(filesReadOnly); } reopenAllTextCaches(); } break; } openLog(); if (!filesReadOnly) { properties.setDBModified(HsqlDatabaseProperties.FILES_MODIFIED); } } /** * Close all the database files. If script argument is true, no .data * or .backup file will remain and the .script file will contain all the * data of the cached tables as well as memory tables. * * This is not used for filesReadOnly databases which use shutdown. */ void close(boolean script) throws HsqlException { closeLog(); deleteNewAndOldFiles(); writeScript(script); closeAllTextCaches(script); if (cache != null) { cache.close(true); } properties.setProperty(HsqlDatabaseProperties.db_version, HsqlDatabaseProperties.THIS_VERSION); properties.setProperty( HsqlDatabaseProperties.hsqldb_compatible_version, HsqlDatabaseProperties.FIRST_COMPATIBLE_VERSION); // set this one last to save the props properties.setDBModified(HsqlDatabaseProperties.FILES_NEW); deleteLog(); if (script) { deleteBackup(); deleteData(); } else { try { backupData(); renameNewBackup(); } catch (IOException e) {} } renameNewScript(); properties.setDBModified(HsqlDatabaseProperties.FILES_NOT_MODIFIED); } /** * Fast counterpart to close(). Does not perform a checkpoint or a backup * of the .data file. */ void shutdown() throws HsqlException { synchLog(); if (cache != null) { cache.close(false); } closeAllTextCaches(false); closeLog(); } /** * Deletes the leftovers from any previous unfinished operations. */ void deleteNewAndOldFiles() { fa.removeElement(fileName + ".data" + ".old"); fa.removeElement(fileName + ".data" + ".new"); fa.removeElement(fileName + ".backup" + ".new"); fa.removeElement(scriptFileName + ".new"); } void deleteBackup() { fa.removeElement(fileName + ".backup"); } void deleteData() { fa.removeElement(fileName + ".data"); } void backupData() throws IOException { if (fa.isStreamElement(fileName + ".data")) { ZipUnzipFile.compressFile(fileName + ".data", fileName + ".backup.new", database.getFileAccess()); } } void renameNewBackup() { if (fa.isStreamElement(fileName + ".backup.new")) { fa.renameElement(fileName + ".backup.new", fileName + ".backup"); } } void renameNewScript() { if (fa.isStreamElement(scriptFileName + ".new")) { fa.renameElement(scriptFileName + ".new", scriptFileName); } } void deleteNewScript() { fa.removeElement(scriptFileName + ".new"); } void deleteNewBackup() { fa.removeElement(scriptFileName + ".backup.new"); } void deleteLog() { fa.removeElement(logFileName); } /** * Checks all the caches and returns true if the modified flag is set for any */ boolean isAnyCacheModified() { if (cache != null && cache.isFileModified()) { return true; } return isAnyTextCacheModified(); } /** * Performs checkpoint including pre and post operations. Returns to the * same state as before the checkpoint. */ void checkpoint(boolean defrag) throws HsqlException { if (filesReadOnly) { return; } database.logger.appLog.logContext(SimpleLog.LOG_NORMAL, "start"); deleteNewAndOldFiles(); if (cache != null) { if (forceDefrag()) { defrag = true; } if (defrag) { try { cache.defrag(); } catch (Exception e) {} } else { cache.close(true); try { cache.backupFile(); } catch (IOException e1) { deleteNewBackup(); cache.open(false); return; } cache.open(false); } } writeScript(false); properties.setDBModified(HsqlDatabaseProperties.FILES_NEW); closeLog(); deleteLog(); renameNewScript(); renameNewBackup(); properties.setDBModified(HsqlDatabaseProperties.FILES_MODIFIED); if (dbLogWriter == null) { return; } openLog();
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -