📄 driverrdb.java
字号:
/*
(c) Copyright 2003, 2004, 2005, 2006, 2007 Hewlett-Packard Development Company, LP
[See end of file]
*/
package com.hp.hpl.jena.db.impl;
import java.sql.*;
import java.util.*;
import java.util.zip.CRC32;
import java.io.UnsupportedEncodingException;
import java.lang.Thread;
import com.hp.hpl.jena.datatypes.RDFDatatype;
import com.hp.hpl.jena.datatypes.TypeMapper;
import com.hp.hpl.jena.db.GraphRDB;
import com.hp.hpl.jena.db.IDBConnection;
import com.hp.hpl.jena.db.RDFRDBException;
import com.hp.hpl.jena.graph.*;
import com.hp.hpl.jena.graph.query.ExpressionFunctionURIs;
import com.hp.hpl.jena.rdf.model.AnonId;
import com.hp.hpl.jena.shared.*;
import com.hp.hpl.jena.vocabulary.RDF;
import com.hp.hpl.jena.vocabulary.DB;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.xerces.util.XMLChar;
//=======================================================================
/**
* Base database driver for implementing SpecializedGraphs.
* Different drivers are needed for different databases and different
* layout schemes.
* <p>
* This driver is a base implemention from which database-specific
* drivers can inherit. It is not generic in the sense that it will work
* on any minimal SQL store and so should be treated as if it were
* an abstract class.
* <p>The SQL statements which implement each of the functions are
* loaded in a separate file etc/[layout]_[database].sql from the classpath.
*
* @author hkuno modification of Jena1 code by Dave Reynolds (der)
* @version $Revision: 1.68 $ on $Date: 2007/06/28 12:46:53 $
*/
public abstract class DriverRDB implements IRDBDriver {
//=======================================================================
// Cutomization variables
// =======================================================================
/**
* This Graph's db properties
*/
protected DBPropDatabase m_dbProps;
/**
* Name of this class's PSet_TripleStore_XXX class
*/
protected String m_psetClassName;
/**
* Name of this class's PSet_TripleStore_XXX class
*/
protected String m_psetReifierClassName;
/**
* Cached name of this class's SpecializedGraph_XXX class
*/
protected String m_lsetClassName;
/**
* Cached name of this class's SpecializedGraphReifer_XXX class
*/
protected String m_lsetReifierClassName;
/** The class name of the database driver (e.g. jdbc.sql.class)*/
protected String DRIVER_NAME;
// Dummy - needs replacing when instantiated?
/** The name of the database type this driver supports */
protected String DATABASE_TYPE;
/** The maximum size of index key (or a component of a key) */
protected int INDEX_KEY_LENGTH;
/** The maximum possible value for INDEX_KEY_LENGTH (db-dependent) */
protected int INDEX_KEY_LENGTH_MAX;
/** true if graphs using this database instance supports transactions.
* this is a user settable parameter. the underlying db engine may support
* transactions but an application may prefer to run without transactions
* for better performance. this can only be set before the db is formatted.
*/
protected boolean IS_XACT_DB;
protected boolean STRINGS_TRIMMED;
/** true if the database engine will trim trailing spaces in strings. to
* prevent this, append EOS to strings that should not be trimmed.
*/
protected String EOS = "";
protected char EOS_CHAR = ':';
protected int EOS_LEN = 0;
/** EOS is appended to most RDB strings to deal with string trimming. if
* STRINGS_TRIMMED is false, EOS is null. otherwise, EOS is EOS_CHAR.
* EOS_LEN is the length of EOS (0 or 1).
*/
protected char QUOTE_CHAR = '\"';
/** the quote character used to delimit characters and strings.
*/
/**
* Indicates whether search pattern used to select system objects by name should be upper-case.
*/
protected boolean DB_NAMES_TO_UPPER = false;
/** true if URI's are to be compressed by storing prefixes (an approximation
* of a namespace) in the JENA_PREFIX table. note that "short" prefixes are
* not stored, i.e., the prefix length not more than URI_COMPRESS_LENGTH.
*/
protected boolean URI_COMPRESS;
protected int URI_COMPRESS_LENGTH = 100;
/** if URI_COMPRESS is true, compress prefixes that are longer than this.
/** The maximum size of an object that can be stored in a Statement table */
protected int LONG_OBJECT_LENGTH;
/** The maximum possible value for LONG_OBJECT_LENGTH (db-dependent) */
protected int LONG_OBJECT_LENGTH_MAX;
/** The SQL type to use for storing ids (compatible with wrapDBID) */
protected String ID_SQL_TYPE;
/** Set to true if the insert operations already check for duplications */
protected boolean SKIP_DUPLICATE_CHECK;
/** Set to true if IDs are allocated prior to insert */
protected boolean PRE_ALLOCATE_ID;
/** The name of the sql definition file for this database/layout combo */
protected String SQL_FILE;
/** The name of the sql definition file for this database/layout combo */
protected String DEFAULT_SQL_FILE = "etc/generic_generic.sql";
// =======================================================================
// Common variables
// =======================================================================
/**
* Holds prefix for names of Jena database tables.
*/
protected String TABLE_NAME_PREFIX = "jena_";
/**
* Holds maximum length of table and index names in database.
*/
protected int TABLE_NAME_LENGTH_MAX;
/** Suffixes for asserted and reified table names. */
protected String STMT_TABLE_NAME_SUFFIX = "_stmt";
protected String REIF_TABLE_NAME_SUFFIX = "_reif";
/** Maximum number of index columns. can be changed. */
protected int MAXIMUM_INDEX_COLUMNS = 3;
/** Number of required system tables. */
protected int SYSTEM_TABLE_CNT = 0;
/** Names of jena system tables. */
public String [] SYSTEM_TABLE_NAME;
/** Set to true to enable cache of pre-prepared statements */
protected boolean CACHE_PREPARED_STATEMENTS = true;
/** The name of the layout type this driver supports */
protected String LAYOUT_TYPE = "TripleStore";
/** Default name of the table that holds system property graph asserted statements **/
protected String SYSTEM_STMT_TABLE;
/** Name of the long literal table **/
protected String LONG_LIT_TABLE;
/** Name of the long URI table **/
protected String LONG_URI_TABLE;
/** Name of the prefix table **/
protected String PREFIX_TABLE;
/** Name of the graph table **/
protected String GRAPH_TABLE;
/** Name of the mutex table **/
protected String MUTEX_TABLE;
/** If not null, newly-created graphs share tables with the identified graph **/
protected String STORE_WITH_MODEL = null;
/** Name of the graph holding default properties (the one's that a newly-created
* graph will have by default **/
protected final String DEFAULT_PROPS = "JENA_DEFAULT_GRAPH_PROPERTIES";
/** Unique numeric identifier of the graph holding default properties **/
protected final int DEFAULT_ID = 0;
/** Driver version number */
protected final String VERSION = "2.0alpha";
/** Database layout version */
protected String LAYOUT_VERSION = "2.0";
protected static Log logger = LogFactory.getLog( DriverRDB.class );
// =======================================================================
// Instance variables
// =======================================================================
/**
* Instance of SQLCache used by Driver for hard-coded db commands
*/
protected SQLCache m_sql = null;
/** Cache a reference to the system property graph (java) **/
protected SpecializedGraph m_sysProperties = null;
protected IDBConnection m_dbcon = null;
protected LRUCache prefixCache = null;
public static final int PREFIX_CACHE_SIZE = 50;
//===================================
// for transaction support
//===================================
// caches whether or not underlying connection supports transactions
private Boolean m_transactionsSupported;
/** flag to indicate that there is a transaction active on the associated connection */
private boolean inTransaction = false;
// =======================================================================
// Constructor
// =======================================================================
/**
* Create a bare instance of the driver. It is not functional until a
* database connection has been supplied via setConnection.
*/
public DriverRDB() {
}
// =======================================================================
// Methods
// =======================================================================
/**
* Return the connection
*/
public IDBConnection getConnection() {
return m_dbcon;
}
/**
* Return the specialized graph used to store system properties.
* (Constuct a new one if necessary). if the database is not
* properly formatted, then if doInit is true, the database will
* be formatted, else null is returned and the (unformatted
* database is unchanged).
*/
public SpecializedGraph getSystemSpecializedGraph(boolean doInit) {
SpecializedGraph res = null;
if (m_sysProperties != null) {
return m_sysProperties;
}
if (!isDBFormatOK()) {
// another thread could be formatting database
// so get the mutex and try again
lockDB();
if (!isDBFormatOK()) {
if (doInit) {
try {
// Format the DB
// throw new JenaException("The database is not
// formatted.\n");
doCleanDB(false);
prefixCache = new LRUCache(PREFIX_CACHE_SIZE);
res = formatAndConstructSystemSpecializedGraph();
} catch (Exception e) {
unlockDB();
// We see an error during format testing, might be
// a dead connection rather than an unformated
// database so abort
throw new JenaException(
"The database appears to be unformatted or corrupted and\n"
+ "an attempt to automatically format the database has failed\n", e);
}
}
unlockDB();
return res;
}
// after second try, DB is found to be correctly formatted.
unlockDB();
}
prefixCache = new LRUCache(PREFIX_CACHE_SIZE);
getDbInitTablesParams(); //this call is a hack. it's needed because
// it has the side effect of initializing some vars (e.g., EOS).
IPSet pSet = createIPSetInstanceFromName(m_psetClassName,
SYSTEM_STMT_TABLE);
m_sysProperties = createLSetInstanceFromName(m_lsetClassName, pSet,
DEFAULT_ID);
m_dbProps = new DBPropDatabase(m_sysProperties);
// need to get initial values for encoding parameters
String longObjLen = m_dbProps.getInitLongObjectLength();
String indexKeyLen = m_dbProps.getInitIndexKeyLength();
String compURI = m_dbProps.getInitDoCompressURI();
String compURILen = m_dbProps.getInitCompressURILength();
if (longObjLen == null)
throwBadFormat("long object length");
else
LONG_OBJECT_LENGTH = Integer.parseInt(longObjLen);
if (indexKeyLen == null)
throwBadFormat("index key length");
else
INDEX_KEY_LENGTH = Integer.parseInt(indexKeyLen);
if (compURI == null)
throwBadFormat("compress URIs");
else
URI_COMPRESS = Boolean.valueOf(compURI).booleanValue();
if (compURILen == null)
throwBadFormat("URI compress length");
else
URI_COMPRESS_LENGTH = Integer.parseInt(compURILen);
// now reset the configuration parameters
checkEngine(m_dbProps);
checkDriverVersion(m_dbProps);
checkLayoutVersion(m_dbProps);
String val = null;
val = m_dbProps.getIsTransactionDb();
if (val == null)
throwBadFormat("database supports transactions");
else
IS_XACT_DB = Boolean.valueOf(val).booleanValue();
val = m_dbProps.getTableNamePrefix();
if (val == null)
throwBadFormat("table name prefix");
else
TABLE_NAME_PREFIX = val;
return m_sysProperties;
}
private void checkEngine ( DBProp dbProps ) {
String dbtype = m_dbProps.getEngineType();
if ( dbtype == null ) throwBadFormat("database type");
if ( !dbtype.equals(DATABASE_TYPE) ) {
throw new JenaException(
"Database created with incompatible database type for this version of Jena: "
+ dbtype);
}
}
private void checkDriverVersion ( DBProp dbProps ) {
String vers = m_dbProps.getDriverVersion();
if ( vers == null ) throwBadFormat("database version");
if ( !vers.equals(VERSION) ) {
throw new JenaException(
"Models in the database were created with an incompatible version of Jena: "
+ vers);
}
}
private void checkLayoutVersion ( DBProp dbProps ) {
String layout = m_dbProps.getLayoutVersion();
if ( layout == null ) throwBadFormat("database layout");
if ( !layout.equals(LAYOUT_VERSION) ) {
throw new JenaException(
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -