Add Persistence to an Existing Hierarchy: Session-less Persistent Objects
- 5 minutes to read
Using Session-less persistent objects implies that the corresponding class definitions have no session-specific constructors, compared to the other option of adding persistence to an existing class hierarchy which is discussed in the Add Persistence to an Existing Hierarchy: Change the Base Inheritance topic. Because of this, all persistent operations on the objects can be performed directly via the Session object by calling the corresponding methods.
In the most basic instance of using this technique, all that needs to be done to add persistence to an object is to mark the corresponding class with the PersistentAttribute and provide a key field or property (if there isn’t one already defined in the class) which will be used to specify an identity value for a specific object’s state. After that, the object can be persisted by calling the Session.Save method and passing the object as a parameter. The default mapping in XPO allows you to persist objects at this early stage but generally, you’ll be required to override the default mapping to map to custom tables (views) and columns.
Below are step-by-step instructions on what you need to do.
Adding the Persistent Attribute and Customizing the Default Mapping
By adding persistence to an object you also need to determine which properties or fields of the object are to be stored and the mapping and format options that should be applied. With XPO, this can be carried out by marking the required classes, properties and fields with the following attributes:
- PersistentAttribute. Use this attribute to specify whether a class, property or field should be stored. By default, XPO automatically designates database tables (views) and column names for the objects being persisted. You can pass the relevant name as a parameter to this attribute to override the default mapping.
- PersistentAliasAttribute. Use this attribute to specify the association between a field and a property. The property’s value is stored by persisting the corresponding field.
- NonPersistentAttribute. Mark a property or field with this attribute to prevent it from being persisted.
- SizeAttribute. Mark a property or field with this attribute to specify the format size of the database column which will be created for it.
The following code example demonstrates how persistence options can be specified.
[Persistent("Contact")]
public class SessionLessObject: SuperObject {
string firstName = "";
// The FirstName property is not persisted
[NonPersistent]
public string FirstName {
get { return firstName; }
set { firstName = value; }
}
//The lastName field values are stored in the LastName database column of the string type with max length 254.
[Persistent("LastName"), Size(254)]
string lastName = "";
// The LastName property is associated with the lastName field which will be persisted.
[PersistentAlias(nameof(lastName))]
public string LastName {
get { return lastName; }
set { lastName = value; }
}
// The FullName readonly property values are stored
// in the FullName database column of the string type with max length 254
[Persistent("FullName"), Size(254)]
public string FullName { get { return String.Format("{0}, {1}", lastName, firstName); }}
}
Implementing an Object Identity Value
To distinguish the states of persistent objects stored in a database, an object identity value should be used. It is used to address a specific object’s state. In the following code example one possible implementation of identity values is shown. In a database it will be represented by an auto-generated key field of the integer type.
[Persistent("Contact")]
public class SessionLessObject: SuperObject {
// ...
int persistentID;
[Key(AutoGenerate = true)]
public int Oid {
get { return persistentID; }
set {
persistentID = value;
OnChanged(nameof(Oid));
}
}
}
Manipulating Session-less Persistent Objects
A session-less persistent object represents a standard persistent object in regard to the functionality. The only exception is that it doesn’t implement the IXPSimpleObject interface, thus all the persistent operations such as saving, reloading and deletion can be initiated only by the Session object or the default session as shown in the following code snippet.
SessionLessObject contact = new SessionLessObject();
contact.FirstName = "John";
contact.LastName = "Doe";
Session.DefaultSession.Save(contact);
// ...
Session.DefaultSession.Reload(contact);
// ...
Session.DefaultSession.Delete(contact);