Class JDBCStorageService
java.lang.Object
net.shibboleth.shared.component.AbstractInitializableComponent
net.shibboleth.shared.component.AbstractIdentifiedInitializableComponent
net.shibboleth.shared.component.AbstractIdentifiableInitializableComponent
org.opensaml.storage.AbstractStorageService
net.shibboleth.plugin.storage.jdbc.impl.JDBCStorageService
- All Implemented Interfaces:
Component,DestructableComponent,IdentifiableComponent,IdentifiedComponent,InitializableComponent,EnumeratableStorageService,StorageCapabilities,StorageService
public final class JDBCStorageService
extends AbstractStorageService
implements StorageCapabilities, EnumeratableStorageService
Implementation of
StorageService that uses native JDBC to persist to a database.-
Nested Class Summary
Nested ClassesModifier and TypeClassDescriptionprivate classA Class to encapsulate aConnectionprotected by an optional read/write lock. -
Field Summary
FieldsModifier and TypeFieldDescriptionprivate StringThe SQL to create a new record (transactional withpreCreateQuerySQL.private StringThe SQL to update an expired record as part of a create (transactional withpreCreateQuerySQL.private DataSourceThe Data Source.(package private) static final StringThe SQL to create a new record.(package private) static final StringThe SQL to update an expired record as part of a create.(package private) static final StringThe SQL to delete all records by specified context and expiration.(package private) static final StringThe SQL to delete a given context.(package private) static final StringThe SQL to delete all records by specified expiration.(package private) static final StringThe SQL to delete a record.(package private) static final StringThe SQL to fetch the keys in a context.(package private) static final StringThe SQL to fetch matching keys in a context.(package private) static final StringThe SQL to get check whether this record already exists and is unexpired prior to a create.(package private) static final StringThe SQL to check whether a record exists prior to deleting it.(package private) static final StringThe SQL to check whether a record exists prior to updating it.(package private) static final StringThe SQL to get all the records for a specific context.(package private) static final StringThe SQL to get all the records.(package private) static final StringThe SQL to get all the contexts.(package private) static final StringThe SQL to read a single record.(package private) static final StringThe SQL to update the expiration for a given context.(package private) static final StringThe SQL to update a record.private StringThe SQL to delete expired record with specified context.private StringThe SQL to to delete a given context.private StringThe SQL to delete expired record.private StringThe SQL to delete a record.private StringThe SQL to fetch the keys in a context.private StringThe SQL to fetch the keys in a context with a prefix.private final org.slf4j.LoggerClass logger.private StringThe SQL to get check whether this record already exists and is unexpired prior to a create.private StringThe SQL to check whether a record exists prior to deleting it.private StringThe SQL to check whether a record exists prior to updating it.private DurationTimeout of SQL queries.private StringThe SQL to get all the records for a specific context.private StringThe SQL to get all the records.private StringThe SQL to get all the contexts.private StringThe SQL to read a single record.private ReadWriteLockIf non-null we doing local locking.private Collection<String>Error messages that signal a transaction should be retried.private intWhat transaction isolation do we want?private intHow many times do we try an operation before giving up?private StringThe SQL to update the expiration of a given context.private StringThe SQL to update a record.private booleanAre we verifying the database during initialize?(package private) static final StringThe context, key and value we test the database with. -
Constructor Summary
Constructors -
Method Summary
Modifier and TypeMethodDescriptionbooleanbooleanvoiddeleteContext(String context) protected voiddeleteImpl(Long expiration) Deletes every record with an expiration before the supplied expiration.protected booleandeleteImpl(Long version, String context, String key) Deletes the record matching the supplied parameters.booleandeleteWithVersion(long version, String context, String key) protected voidprotected TimerTaskgetContextKeys(String context, String prefix) private static LonggetExpires(ResultSet results, int columm) Return the value of expires in the supplied column of the suppliedResultSet.booleanboolean<T> StorageRecord<T><T> Pair<Long,StorageRecord<T>> protected List<?>readAll()Returns all records from the store (for testing only).protected List<?>Returns all records from the store for the supplied context (for testing only).Returns all contexts from the store (for testing only).protected <T> Pair<Long,StorageRecord<T>> Reads the record matching the supplied parameters.voidvoidSet the SQL to create a new record (transactional withpreCreateQuerySQL.voidSet the SQL to update an expired record as part of a create (transactional withpreCreateQuerySQL.voidsetDataSource(DataSource source) Set theDataSource.voidSet the SQL to delete expired record with specified context.voidsetDeleteByContextSQL(String what) Set the SQL to Delete a specified Context.voidsetDeleteByExpiredSQL(String what) Set the SQL to delete expired record.voidsetDeleteRecordSQL(String what) Set the SQL to delete a record.private static voidsetExpires(PreparedStatement stmnt, int column, Long expires) Set the value of expiration into the prepared statement at the suppiled column converting java nulls into SQL nulls.voidsetGetContextKeysSQL(String what) Set the SQL to fetch the keys in a specified context.voidsetLocalLocking(boolean what) Will we do thread level locking or delegate to the Database?voidsetPreCreateQuerySQL(String what) Set the SQL to get check whether this record already exists and is unexpired prior to a create.voidsetPreDeleteQuerySQL(String what) Set the SQL to check whether a record exists prior to deleting it.voidsetPreUpdateQuerySQL(String what) Set the SQL to get check whether this record already exists and is unexpired prior to an update.voidsetReadAllByContextSQL(String what) SQL to read all contexts.voidsetReadAllSQL(String what) SQL to read all contexts.voidsetReadContextsSQL(String what) SQL to read contexts.voidsetReadRecordSQL(String what) Set the SQL to read a single record.voidsetRetryableErrors(List<String> errors) What errors do we retry?voidsetTransactionIsolation(int what) Set the parameter that will be passed toConnection.setTransactionIsolation(int).voidsetTransactionRetries(int count) settransactionRetries.voidSet the SQL to update the expiration of a record specified by context.voidsetUpdateRecordSQL(String what) Set the SQL to update a record.voidsetVerify(boolean what) Set whether we are to verify the database during initialize.booleanvoidupdateContextExpiration(String context, Long expires) booleanupdateExpiration(String context, String key, Long expiration) protected LongUpdates the record matching the supplied parameters.updateWithVersion(long version, String context, String key, String value, Long expiration) private voidCheck the database and the presence of a uniqueness constraint.Methods inherited from class org.opensaml.storage.AbstractStorageService
create, create, delete, deleteWithVersion, doDestroy, getCapabilities, getCleanupInterval, getCleanupTaskTimer, getContextSize, getKeySize, getValueSize, read, setCleanupInterval, setCleanupTaskTimer, setContextSize, setKeySize, setValueSize, update, update, updateExpiration, updateWithVersion, updateWithVersionMethods inherited from class net.shibboleth.shared.component.AbstractIdentifiableInitializableComponent
setIdMethods inherited from class net.shibboleth.shared.component.AbstractIdentifiedInitializableComponent
ensureId, getId, ifDestroyedThrowDestroyedComponentException, ifInitializedThrowUnmodifiabledComponentException, ifNotInitializedThrowUninitializedComponentExceptionMethods inherited from class net.shibboleth.shared.component.AbstractInitializableComponent
checkComponentActive, checkSetterPreconditions, destroy, initialize, isDestroyed, isInitializedMethods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, waitMethods inherited from interface net.shibboleth.shared.component.IdentifiedComponent
getIdMethods inherited from interface org.opensaml.storage.StorageCapabilities
getContextSize, getKeySize, getValueSizeMethods inherited from interface org.opensaml.storage.StorageService
create, create, delete, deleteWithVersion, getCapabilities, read, update, update, updateExpiration, updateWithVersion, updateWithVersion
-
Field Details
-
VERIFY_STRING
The context, key and value we test the database with.- See Also:
-
DEFAULT_READ_CONTEXTS_SQL
The SQL to get all the contexts.- See Also:
-
DEFAULT_READ_ALL_SQL
The SQL to get all the records.- See Also:
-
DEFAULT_READ_ALL_BY_CONTEXT_SQL
The SQL to get all the records for a specific context.- See Also:
-
DEFAULT_PRE_CREATE_QUERY_SQL
The SQL to get check whether this record already exists and is unexpired prior to a create.- See Also:
-
DEFAULT_CREATE_CREATE_RECORD_SQL
The SQL to create a new record.- See Also:
-
DEFAULT_CREATE_UPDATE_RECORD_SQL
The SQL to update an expired record as part of a create.- See Also:
-
DEFAULT_READ_RECORD_SQL
The SQL to read a single record.- See Also:
-
DEFAULT_PRE_UPDATE_QUERY_SQL
The SQL to check whether a record exists prior to updating it.- See Also:
-
DEFAULT_UPDATE_RECORD_SQL
The SQL to update a record.- See Also:
-
DEFAULT_PRE_DELETE_QUERY_SQL
The SQL to check whether a record exists prior to deleting it.- See Also:
-
DEFAULT_DELETE_RECORD_SQL
The SQL to delete a record.- See Also:
-
DEFAULT_DELETE_BY_EXPIRED_SQL
The SQL to delete all records by specified expiration.- See Also:
-
DEFAULT_DELETE_BY_CONTEXT_EXPIRED_SQL
The SQL to delete all records by specified context and expiration.- See Also:
-
DEFAULT_UPDATE_EXPIRES_BY_CONTEXT_SQL
The SQL to update the expiration for a given context.- See Also:
-
DEFAULT_DELETE_BY_CONTEXT_SQL
The SQL to delete a given context.- See Also:
-
DEFAULT_GET_CONTEXT_KEYS_SQL
The SQL to fetch the keys in a context.- See Also:
-
DEFAULT_GET_CONTEXT_KEYS_WITH_PREFIX_SQL
The SQL to fetch matching keys in a context.- See Also:
-
log
@Nonnull private final org.slf4j.Logger logClass logger. -
queryTimeout
Timeout of SQL queries. -
transactionRetries
private int transactionRetriesHow many times do we try an operation before giving up? -
transactionIsolation
private int transactionIsolationWhat transaction isolation do we want? -
readWriteLock
If non-null we doing local locking. -
verify
private boolean verifyAre we verifying the database during initialize? -
retryableErrors
Error messages that signal a transaction should be retried. -
dataSource
The Data Source. -
readContextsSQL
The SQL to get all the contexts. Default: "SELECT context FROM StorageRecords". -
readAllSQL
The SQL to get all the records. Default: "SELECT context, id, expires, value, version FROM StorageRecords". -
readAllByContextSQL
The SQL to get all the records for a specific context. Default: "SELECT id, expires, value, version FROM StorageRecords WHERE context=?" -
preCreateQuerySQL
The SQL to get check whether this record already exists and is unexpired prior to a create. Default: "SELECT expires FROM StorageRecords WHERE context=? AND id=?" -
createCreateRecordSQL
The SQL to create a new record (transactional withpreCreateQuerySQL. Default: "INSERT INTO StorageRecords(context, id, expires, value, version) VALUES (?, ?, ?, ?, 1)" -
createUpdateRecordSQL
The SQL to update an expired record as part of a create (transactional withpreCreateQuerySQL. Default: "UPDATE StorageRecords SET value=?, version=1, expires=? WHERE context=? AND id=?" -
readRecordSQL
The SQL to read a single record. Default: "SELECT version, expires, value FROM StorageRecords WHERE context=? AND id=?" -
preUpdateQuerySQL
The SQL to check whether a record exists prior to updating it. Default: "SELECT version, expires, value FROM StorageRecords WHERE context=? AND id=?" -
updateRecordSQL
The SQL to update a record. Transactional withpreUpdateQuerySQL. Default: "UPDATE StorageRecords SET value=?, version=?, expires=? WHERE context=? AND id=?" -
preDeleteQuerySQL
The SQL to check whether a record exists prior to deleting it. Default: "SELECT version FROM StorageRecords WHERE context=? AND id=?" -
deleteRecordSQL
The SQL to delete a record. Transactional withpreDeleteQuerySQLDefault: "DELETE FROM StorageRecords WHERE context=? AND id=?" -
deleteByExpiredSQL
The SQL to delete expired record. Used as part of thegetCleanupTask(). Default: "DELETE FROM StorageRecords WHERE expires <= ? " -
deleteByContextExpiredSQL
The SQL to delete expired record with specified context. Used as part ofreap(String). Default: "DELETE FROM StorageRecords WHERE context = ? AND expires <= ?" -
updateExpiresByContextSQL
The SQL to update the expiration of a given context. Default: "UPDATE StorageRecords SET expires=? WHERE context = ? AND expires > ?" -
deleteByContextSQL
The SQL to to delete a given context. Default: "DELETE FROM StorageRecords WHERE context=?" -
getContextKeysSQL
The SQL to fetch the keys in a context. Default: "SELECT id FROM StorageRecords WHERE context=? AND (expires IS NULL OR expires > ?)" -
getContextKeysWithPrefixSQL
The SQL to fetch the keys in a context with a prefix. Default: "SELECT id FROM StorageRecords WHERE context=? AND id like ? AND (expires IS NULL OR expires > ?)"
-
-
Constructor Details
-
JDBCStorageService
public JDBCStorageService()Constructor. Set the defaults so that they can be over-ridden by Spring.
-
-
Method Details
-
setTransactionRetries
settransactionRetries.- Parameters:
count- how many time to try before we bail.
-
setLocalLocking
public void setLocalLocking(boolean what) Will we do thread level locking or delegate to the Database?- Parameters:
what- do we want to lock locally?
-
setVerify
public void setVerify(boolean what) Set whether we are to verify the database during initialize.- Parameters:
what- the value to set
-
setTransactionIsolation
public void setTransactionIsolation(int what) Set the parameter that will be passed toConnection.setTransactionIsolation(int).- Parameters:
what- the value to set
-
setDataSource
Set theDataSource.- Parameters:
source- what to set.
-
setRetryableErrors
What errors do we retry?- Parameters:
errors- what to set.
-
setReadContextsSQL
SQL to read contexts.- Parameters:
what- the SQL to set.
-
setReadAllByContextSQL
SQL to read all contexts.- Parameters:
what- the SQL to set.
-
setReadAllSQL
SQL to read all contexts.- Parameters:
what- the SQL to set.
-
setPreCreateQuerySQL
Set the SQL to get check whether this record already exists and is unexpired prior to a create. This starts a transaction which will be completed after either the SQL increateCreateRecordSQLorcreateUpdateRecordSQL.- Parameters:
what- the SQL to set.
-
setCreateCreateRecordSQL
Set the SQL to create a new record (transactional withpreCreateQuerySQL.- Parameters:
what- the SQl to set.
-
setCreateUpdateRecordSQL
Set the SQL to update an expired record as part of a create (transactional withpreCreateQuerySQL.- Parameters:
what- the SQL to set.
-
setReadRecordSQL
Set the SQL to read a single record.- Parameters:
what- what to set.
-
setPreUpdateQuerySQL
Set the SQL to get check whether this record already exists and is unexpired prior to an update.- Parameters:
what- The preUpdateQuerySQL to set.
-
setUpdateRecordSQL
Set the SQL to update a record. Transactional withpreUpdateQuerySQL- Parameters:
what- The updateQuerySQL to set.
-
setPreDeleteQuerySQL
Set the SQL to check whether a record exists prior to deleting it.- Parameters:
what- The SQL to set.
-
setDeleteRecordSQL
Set the SQL to delete a record. Transactional withpreDeleteQuerySQL.- Parameters:
what- The SQL to set.
-
setDeleteByExpiredSQL
Set the SQL to delete expired record. Used as part of thegetCleanupTask().- Parameters:
what- The SQL to set.
-
setDeleteByContextExpiredSQL
Set the SQL to delete expired record with specified context. Used as part ofreap(String).- Parameters:
what- The SQL to set.
-
setUpdateExpiresByContextSQL
Set the SQL to update the expiration of a record specified by context.- Parameters:
what- The SQL to set.
-
setDeleteByContextSQL
Set the SQL to Delete a specified Context.- Parameters:
what- The SQL to set.
-
setGetContextKeysSQL
Set the SQL to fetch the keys in a specified context.- Parameters:
what- the SQL to set- Since:
- 2.0.0
-
doInitialize
- Overrides:
doInitializein classAbstractStorageService- Throws:
ComponentInitializationException
-
readContexts
Returns all contexts from the store (for testing only).- Returns:
- all contexts or an empty list
- Throws:
IOException- if errors occur in the read process
-
readAll
Returns all records from the store (for testing only).- Returns:
- all records or an empty list
- Throws:
IOException- if errors occur in the read process
-
readAll
@Nonnull @NonnullElements protected List<?> readAll(@Nonnull @NotEmpty String context) throws IOException Returns all records from the store for the supplied context (for testing only).- Parameters:
context- a storage context label- Returns:
- all records in the context or an empty list
- Throws:
IOException- if errors occur in the read process
-
create
public boolean create(@Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key, @Nonnull @NotEmpty String value, @Nullable @Positive Long expiration) throws IOException - Specified by:
createin interfaceStorageService- Throws:
IOException
-
read
@Nullable public <T> StorageRecord<T> read(@Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key) throws IOException - Specified by:
readin interfaceStorageService- Throws:
IOException
-
read
@Nonnull public <T> Pair<Long,StorageRecord<T>> read(@Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key, @Positive long version) throws IOException - Specified by:
readin interfaceStorageService- Throws:
IOException
-
readImpl
@Nonnull protected <T> Pair<Long,StorageRecord<T>> readImpl(@Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key, @Positive @Nullable Long version) throws IOException Reads the record matching the supplied parameters. Returns an empty pair if the record cannot be found or is expired.- Type Parameters:
T- type of object- Parameters:
context- to search forkey- to search forversion- to match- Returns:
- pair of version and storage record
- Throws:
IOException- if errors occur in the read process
-
update
public boolean update(@Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key, @Nonnull @NotEmpty String value, @Nullable @Positive Long expiration) throws IOException - Specified by:
updatein interfaceStorageService- Throws:
IOException
-
updateWithVersion
@Nullable public Long updateWithVersion(@Positive long version, @Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key, @Nonnull @NotEmpty String value, @Nullable @Positive Long expiration) throws IOException, VersionMismatchException - Specified by:
updateWithVersionin interfaceStorageService- Throws:
IOExceptionVersionMismatchException
-
updateExpiration
public boolean updateExpiration(@Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key, @Nullable @Positive Long expiration) throws IOException - Specified by:
updateExpirationin interfaceStorageService- Throws:
IOException
-
updateImpl
@Nullable protected Long updateImpl(@Nullable Long version, @Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key, @Nullable String value, @Nullable @Positive Long expires) throws IOException, VersionMismatchException Updates the record matching the supplied parameters. Returns null if the record cannot be found or is expired.- Parameters:
version- to checkcontext- to search forkey- to search forvalue- to updateexpires- to update- Returns:
- the version of the record after update, null if no record exists
- Throws:
IOException- if errors occur in the update processVersionMismatchException- if the record found contains a version that does not match the parameter
-
deleteWithVersion
public boolean deleteWithVersion(@Positive long version, @Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key) throws IOException, VersionMismatchException - Specified by:
deleteWithVersionin interfaceStorageService- Throws:
IOExceptionVersionMismatchException
-
delete
public boolean delete(@Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key) throws IOException - Specified by:
deletein interfaceStorageService- Throws:
IOException
-
deleteImpl
protected boolean deleteImpl(@Nullable @Positive Long version, @Nonnull @NotEmpty String context, @Nonnull @NotEmpty String key) throws IOException, VersionMismatchException Deletes the record matching the supplied parameters.- Parameters:
version- to checkcontext- to search forkey- to search for- Returns:
- whether the record was deleted
- Throws:
IOException- if errors occur in the delete processVersionMismatchException- if the record found contains a version that does not match the parameter
-
deleteImpl
Deletes every record with an expiration before the supplied expiration.- Parameters:
expiration- of records to delete- Throws:
IOException- if errors occur in the cleanup process
-
reap
- Specified by:
reapin interfaceStorageService- Throws:
IOException
-
updateContextExpiration
public void updateContextExpiration(@Nonnull @NotEmpty String context, @Nullable Long expires) throws IOException - Specified by:
updateContextExpirationin interfaceStorageService- Throws:
IOException
-
deleteContext
- Specified by:
deleteContextin interfaceStorageService- Throws:
IOException
-
getContextKeys
@Nonnull public Iterable<String> getContextKeys(@Nonnull @NotEmpty String context, @Nullable String prefix) throws IOException - Specified by:
getContextKeysin interfaceEnumeratableStorageService- Throws:
IOException
-
verifyDatabase
Check the database and the presence of a uniqueness constraint. - Create a record and give it 10 minutes life - Read it back - Delete it- Throws:
IOException- if our methods failComponentInitializationException- if no record was inserted or the wrong value came back
-
getExpires
@Nullable private static Long getExpires(@Nonnull ResultSet results, int columm) throws SQLException Return the value of expires in the supplied column of the suppliedResultSet.- Parameters:
results- the results whose current row we want to inspectcolumm- the column- Returns:
- the expiration (converting an SQL null into a null)
- Throws:
SQLException- if the results interrogation fails
-
setExpires
private static void setExpires(@Nonnull PreparedStatement stmnt, int column, @Nullable Long expires) throws SQLException Set the value of expiration into the prepared statement at the suppiled column converting java nulls into SQL nulls.- Parameters:
stmnt- where to put itcolumn- which column to put it inexpires- what to set it to- Throws:
SQLException- if thePreparedStatementthrows one.
-
isServerSide
public boolean isServerSide()- Specified by:
isServerSidein interfaceStorageCapabilities
-
isClustered
public boolean isClustered()- Specified by:
isClusteredin interfaceStorageCapabilities
-
getCleanupTask
- Overrides:
getCleanupTaskin classAbstractStorageService
-