Dal - STARIONGROUP/COMET-SDK-Community-Edition GitHub Wiki
The IDal interface and Dal class define the abstract Data Access Layer that is used to connect to a an Annex-C data-source. An IDal is used to perform CRUD (Create, Read, Update and Delete) operations on a data-source.
CDP4-COMET-SDK users should not need to interact with the [Dal] implementations directly. the Session class provides a layer of abstraction for the
IDal
interface that exposes the methods that can be used to Create, Read, Update and Delete objects from an Annex C data-source.
The IDal
interface defines the following methods:
Task<IEnumerable<Thing>> Open(Credentials credentials, CancellationToken cancellationToken);
Before any of the methods to write/read data to and from a Dal can be used, a connection to the underlying data-source must be opened. The Open method returns a Task<IEnumerable<Thing>>
, which means this method can be used in asynchronous manner using await
. Implementations of the IDal interface should query the data-source for sufficient data to be able to select an EngineeringModel and Iteration, or a SiteReferenceDataLibrary to read. This is achieved by querying the SiteDirectory including its complete containment tree, using the extent=deep
query parameter.
The Credentials class captures the username, password and Uri of the data-source that is being opened. Currently there are 2 kinds of data-sources available: REST based abd File based.
The following code-snippet demonstrates how to open a Dal. The CdpServicesDal is used as concrete class in the example.
var cancelationTokenSource = new CancellationTokenSource();
var uri = new Uri("https://cdp4services-test.cdp4.org");
var credentials = new Credentials("admin", "pass", uri);
var dal = new CdpServicesDal();
var dtos = await dal.Open(credentials, cancelationTokenSource.Token);
var siteDirectory = dtos.Single(x => x.ClassKind == ClassKind.SiteDirectory);
The return value is an IEnumerable of DTO objects including the SiteDirectory. A side-effect of the Open
method, provided it was succesfull, is that the Credentials
property of the Dal
is set to the provided credentials instance.
void Close();
The Close
method is called to close a Dal, a closed Dal can no longer be used to write/read to and from the previously connected data-source.
The IDal
interface exposes 2 Read methods. The Read methods are used to read DTO objects from the connected data-source.
Task<IEnumerable<Thing>> Read<T>(T thing, CancellationToken cancellationToken, IQueryAttributes attributes = null) where T : Thing;
Task<IEnumerable<Thing>> Read(Iteration iteration, CancellationToken cancellationToken, IQueryAttributes attributes = null);
The generic Read<T>
method is used read any DTO from the data-source. An Annex-C data-source can only be queried along the COMET Data Model containment tree. In order to query a DTO it is required to know its complete containment hierarchy.
The following code-snippet demonstrates how to read a specific email from a data-source. The unique identifiers of the email address and its container objects must be known.
// open a connection to the cdp4services-test webservices instance
var cancelationTokenSource = new CancellationTokenSource();
var uri = new Uri("https://cdp4services-test.cdp4.org");
var credentials = new Credentials("admin", "pass", uri);
var dal = new CdpServicesDal();
var dtos = await dal.Open(credentials, cancelationTokenSource.Token);
// construct the email address object to read
var email = new Email(Guid.Parse("325620cd-4354-4ddb-9c66-e75550da643a"), 1);
email.AddContainer(ClassKind.Person, Guid.Parse("77791b12-4c2c-4499-93fa-869df3692d22"));
email.AddContainer(ClassKind.SiteDitectory, Guid.Parse("f13de6f8-b03a-46e7-a492-53b2f260f294"));
// read the email address from the data-source
dtos = dal.Read(email, cancelationTokenSource.Token);
The second read method is a convenience method to read all the data of an Iteration.
The IDal
interface exposes 2 Write methods. The Write methods are used to Create, Update and Delete DTO objects in one operation or transaction in a connected data-source.
Task<IEnumerable<Thing>> Write(OperationContainer operationContainer, IEnumerable<string> files = null);
Task<IEnumerable<Thing>> Write(IEnumerable<OperationContainer> operationContainers, IEnumerable<string> files = null);
The following code-snippet demonstrates how to use an OperationContainer to create, update and delete objects. The example shows how to add, update and delete items from the SiteDirectory. Adding or deletings items in Annex-C always include an update on the container of the Thing that is being added or deleted. When using the IDal directly it is up to the developer to reflect these changes on the DTO objects.
API developers should make use of the the Session class, it provides a layer of abstraction for the
IDal
interface that exposes the methods that can be used to Create, Read, Update and Delete objects from an Annex C data-source.
// open a connection to the cdp4services-test webservices instance
var cancelationTokenSource = new CancellationTokenSource();
var uri = new Uri("https://cdp4services-test.cdp4.org");
var credentials = new Credentials("admin", "pass", uri);
var dal = new CdpServicesDal();
var dtos = await dal.Open(credentials, cancelationTokenSource.Token);
// get the SiteDirectory object
var siteDirectory = dtos.Single(x => x.ClassKind == ClassKind.SiteDirectory);
// create an OperationContainer, the context is set to the siteDirectory that was retrieved from the Dal
var context = siteDirectory.Route;
var operationContainer = new OperationContainer(context, siteDirectory.RevisionNumber);
// retrieve an existing email address from the dtos and update the "value" property
var emailAddress = dtos.Single(x => x.Iid == Guid.Parse("325620cd-4354-4ddb-9c66-e75550da643a"));
var clonedEmailAddress = emailAddress.DeepClone<EmailAddress>();
clonedEmailAddress.Value = "[email protected]";
var operation_1 = new Operation(emailAddress, clonedEmailAddress, OperationKind.Update);
operationContainer.AddOperation(operation_1);
// create a new email address
var newemail = new EmailAddress(Guid.Parse("c8b98e0f-ded5-42b1-885e-3b0d0feb210d", 1));
newemail.VcardType = VcardEmailAddressKind.WORK;
newemail.Value = "[email protected]";
var operation_2 = new Operation(null, newemail, OperationKind.Create);
operationContainer.AddOperation(operation_2);
// update the existing person EmailAddress property
var person = dtos.Single(x => x.Iid == Guid.Parse("77791b12-4c2c-4499-93fa-869df3692d22"));
var clonedPerson = person.DeepClone<Person>();
clonedPerson.EmailAddress.Add(newemail.Iid);
var operation_3 = new Operation(person, clonedPerson, OperationKind.Update);
operationContainer.AddOperation(operation_3);
// retrieve the Domain to Delete from the SiteDirectory
var domainGroup = dtos.Single(x => x.Iid == Guid.Parse("86992db5-8ce2-4431-8ff5-6fe794d14687"));
var operation_4 = new Operation(domainGroup, domainGroup, OperationKind.Delete);
operationContainer.AddOperation(operation_4);
// Write the operation container using the Dal
var updates = dal.Write(operationContainer);
The Create method is used to create a new DTO.
The Create method is not supported. The Annex-C protocol does not suppert the direct creation of objects. Objects can only be created as part of a write, which is a compounded write operation in which multiple objects can be created, updated and deleted.
The Update method is used to update an existing DTO.
The Update method is not supported. The Annex-C protocol does not suppert the direct updates of objects. Objects can only be created as part of an write, which is a compounded write operation in which multiple objects can be created, updated and deleted.
The Delete method is used to update an existing DTO.
The Delete method is not supported. The Annex-C protocol does not suppert the direct deletions of objects. Objects can only be created as part of an write, which is a compounded write operation in which multiple objects can be created, updated and deleted.