|
|
Dark Planet Development Platform |
|
| Return value | Method | Function |
|---|---|---|
| Capsuleer | loadCharacter(int keyID) | Load the persisted Capsuleer instance corresponding to the given key ID. |
| Corporation | loadCorporation(int keyID) | Load the persisted Corporation instance corresponding to the given corporation ID. |
| void | saveCharacter(Capsuleer c) | Persist the given Capsuleer instance. |
| void | saveCorporation(Corporation c) | Persist the given Corporation instance. |
| Collection<Integer> | getCharacterKeys() | Return a list of key IDs corresponding to characters stored by this persistence factory. |
| Collection<Integer> | getCorporationKeys() | Return a list of key IDs corresponding to corporations stored by this persistence factory. |
The "save" and "load" methods provide the basic mechanism for storing and later retrieving data model information. Data model objects are designed to be persisted via Java serialization. However, persistence API implementations are free to store data model instances however they like. The "get" methods allow for discovering all available persisted data model information.
The second group of methods in the persistence API provide methods for working with Hibernate stored data, of which we only show a subset here:
| Return value | Method | Function |
|---|---|---|
| SessionFactory | getGenericDataSessionFactory() | Retrieve a Hibernate Session factory which may be used to access generic information tables, for example external market data. |
| SessionFactory | getKeySessionFactory(int keyID) | Retrieve a Hibernate Session factory which may be used to access tables associated with the specified key ID. |
| IWalletJournalRecord | getNewJournalRecord(...) | Instantiate a new WalletJournalRecord ready for population and eventual storage in a Hibernate table. |
| ... other record factory methods ... | ||
Working with Hibernate stored data requires a Session which is normally provided by a SessionFactory. In DPS there are two distinct groups of Hibernate tables:
The two "get...SessionFactory" methods provide a means to get an appropriate factory for working with each type of data. We distinguish the two types of data to allow more flexibility in storage.
A "record" represents a data object stored (or intended to be stored) in a Hibernate table. Most of the methods in the persistence API are factory methods which allow the construction of new records. The arguments to a factory method are always the key columns of the table in which the record will be stored. For example, the full specification of the "getNewJournalRecord" methods is:
IWalletJournalRecord getNewJournalRecord(int keyID, long charOrCorpID, int accountKey, long refID);
This means that the key columns of the "wallet journal" table are:
Record key columns are chosen to allow as much flexibility as possible in the persistence API implementation. For example, since "keyID" is a key column, you can choose to store all records in a single common table shared across all characters or corporations. Or, for performance reasons, you may wish to store character and corporation data in completely separate tables.
// Create a Capsuleer
int keyID = ... you keyID ...;
IEveDataModel dataModel = ... reference to your data model ...;
IModelFactory factory = dataModel.getModelFactory();
Capsuleer myCharacter = factory.makeCharacter(keyID, vCode, characterID);
// Save our capsuleer
IEvePersistenceFactory pFactory = ... reference to your persistence factory ...;
pFactory.saveCharacter(myCharacter);
// Verify that we can find it again
Collection charKeys = pFactory.getCharacterKeys();
assert charKeys.contains(keyID);
// Reload
Capsuleer loadedChar = pFactory.loadCharacter(keyID);
The store and load methods throw predictable exceptions for failures.
For example, load and store throw IOException if an
error occurs while reading or storing data. Load methods will
throw NoSuchCharacterException
or NoSuchCorporationException if a request is made for
an unknown character or corporation. Finally, load methods may
throw a ClassNotFoundException while attempting to
restore character or corporation data. This can happen when
attempting to restore persisted data from an incompatible version
of DPS.
There are five steps to inserting data into a Hibernate table:
@Override
public IWalletJournalRecord getNewJournalRecord(int keyID, long entityID,
int accountKey, long refID) {
WalletJournalRecordImpl newEntry = new WalletJournalRecordImpl();
newEntry.setKeyID(keyID);
newEntry.setEntityID(entityID);
newEntry.setAccountKey(accountKey);
newEntry.setRefID(refID);
return newEntry;
}
The class WalletJournalRecordImpl implements IWalletJournalRecord. The code here just ensures that the fields representing the key columns are always populated. It's up to the caller to populate everything else.
Beyond object construction, you can use the Hibernate API methods directly if needed to insert new records. Here's the code for the five step process we described above assuming we want to insert a new wallet journal record (using the persistence API to obtain a Session):
// Create record to insert
IEvePersistenceFactory persistFactory = ...get persist reference...;
IWalletJournalRecord newRecord = persistFactory.getNewJournalRecord(keyID, entityID, accountKey, refID);
... populate other journal record fields ...;
// Obtain session
Session txn = persistFactory.getKeySessionFactory(keyID).openSession();
try {
// Start transaction
txn.begin();
// Store record
txn.merge(newRecord);
// Commit
txn.commit();
} catch (HibernateException e) {
// Commit failed, rollback
txn.rollback();
}
In terms of storing your new record, there are at least choices:
Records are retrieved from a Hibernate table in five steps:
// Obtain session
IEvePersistenceFactory persistFactory = ...get persist reference...;
Session txn = persistFactory.getKeySessionFactory(keyID).openSession();
// Assume we know the refID of the record we want
long refID = ... refID we want ...;
// This variable will store the results
List results;
try {
// Start transaction
txn.begin();
// Construct a query
Query select = txn.createQuery("from org.dps.core.persist.IWalletJournalRecord where refID = :refID");
select.setLong("refID", refID);
// Execute the query
results = select.list();
// Commit
txn.commit();
} catch (HibernateException e) {
// Commit failed, rollback
txn.rollback();
}
If the transaction commits, then "results" will hold all the journal
records which matched our query (if any). The syntax for queries
is any legal query in the Hibernate Query Language (HQL). Note
that the "name" of the table against which the query is made is
the fully qualified class name of the record interface type.
While the DPS API provides many helper functions for inserting records, there are very few factory-type methods for performing queries. This is because the type of query needed will vary widely among different applications. Instead, DPS provides a few simple methods to make it easier to manage Session objects (see the discussion of the HibernateCachedData type here). It is largely up to user to construct their own queries.
For more details on query construction, see the Hibernate documentation here.