Simple Data Operations sample (console) (Delphi)

The Simple Data Operations sample uses a console based program to demonstrate the most common interactions you will make to an instance of Relativity Server. It shows how to:

  • connect to the server
  • retrieve a table from the server
  • add a row to the retrieved table and apply that change to the server
  • update/change the contents of a row and apply that change to the server
  • delete a row from the table and apply that change to the server

Getting Started

The sample is located in C:\Users\Public\Documents\RemObjects Samples\Data Abstract for Delphi\SimpleDataOperations (Console).

To build it, you will need a version of Delphi RAD Studio, and like all the samples provided with Data Abstract for Delphi you will need to be running Relativity Server with the DASamples Domain and the Simple Schema available.

Included with the sample is a uLogSupport class which has a LogTable procedure that takes an instance of TDADataTable and creates a nicely formatted string representation of the table that it then prints to the Console which can be useful for debugging purposes. (An example of its output can be seen at the end of this document)

Running the Sample

When run the sample sets up a connection to an instance of Relativity Server and logs in (Step 1). It then retrieves the "Deps" table and prints the table to the console (Step 2). It then inserts a new row with a department name ("DepName") of "Security" and phone number ("DepPhone") of "(873)000-00-00" before applying those changes to the original data on the server (Step 3). The phone number is then updated to a new value (Step 4) before the new row is then deleted from the table (Step 5).

Examining the Code

All of the code can be found in the uSimpleDataOperations.pas source file. The Deps schema table used in this sample has three fields:

  • DepId is the primary key and use an AutoInc data type.
  • DepName is a string of up to 50 characters and is required for each new row
  • DepPhone is also a string of up to 50 characters, the field is optional.

Setting up a Connection (Step 1)

You can think of setting up a connection to an instance of Relativity Server as requiring two stages.

In the first stage we create and configure an instance of TDARemoteDataAdapter which will be used to exchange data between the client program and the server. In this sample beyond the initial configuration all interaction with the TDARemoteDataAdapter is handled internally by the TDAMemDataTable class. Working directly with the TDARemoteDataAdapter can bring additional flexibility when interacting with the server, but that is not covered in this sample.

To configure the TDARemoteDataAdapter you need to assign values to the following properties:

  • DataServiceName this is the name of the server's data service, typically this is simply "DataService".
  • LoginServiceName this is the name of the server's login service, typically this is "LoginService".
  • LoginString this is the string that will be passed to the server when a login attempt is made. It is comprised of 4 parts:
    • User Id the username to attempt to login with
    • Password the password to use
    • Domain the name of the domain that the schema is located in
    • Schema the name of the schema we wish to use
  • TargetURL this is the address of the server that the sample will attempt to connect to.
  • DynamicSelect this is an optional property that defines whether the data adapter should use Dynamic Select when performing queries.

An empty data table, an instance of TDAMemDataTable, is created and the newly configured TDARemoteDataAdapter is assigned to its RemoteDataAdapter property. The table will now use the data adapter for any operations that require interacting with the server.

Log(':Simple Data Operations sample has been started.');
Log('Target URL is %s',[ServerURL]);

lRemoteDataAdapter := TDARemoteDataAdapter.Create(nil);
lRemoteDataAdapter.DataServiceName := 'DataService';
lRemoteDataAdapter.LoginServiceName := 'LoginService';
lRemoteDataAdapter.LoginString := connString;
lRemoteDataAdapter.TargetURL := ServerURL;
lRemoteDataAdapter.DynamicSelect:=True;

lTable := TDAMemDataTable.Create(nil);

lTable.RemoteDataAdapter := lRemoteDataAdapter;

The next stage is to actually log into the server, this is done using the Login method of TDARemoteDataAdapter. Internally it passes the previously assigned login string to the server and returns the results. If successful then the sample carries on, otherwise the sample ends.

Log('STEP 1: Login to DataService');
Log;
Log('Connecting to Relativity server: %s',[ServerURL]);
Log('Login string is :');
Log('  %s',[connstring]);

  if lRemoteDataAdapter.Login then begin
    Log('Login has been successfull. Going further...');
  end
  else begin
    Log('Unsuccessful login. Please check your login and password. Exiting...');
    Exit;
  end;

At this point the sample has a working connection to the server and is now logged in.

Retrieving a Table (Step 2)

To retrieve a data table from a schema, we need to first assign the name of the table we want to retrieve to the previously created TDAMemDataTable object. This is done using the LogicalName property.

Then all that is required is to call the Open method which will open the dataset and prepare it for fetching the records from the database using the TDARemoteDataAdapter object that was previously assigned to the RemoteDataAdapter property. When the method returns it will have retrieved the table data.

NOTE Passing an invalid table name to the LogicalName property will result in an exception being thrown when the Open method is called.

lTable := TDAMemDataTable.Create(nil);
lTable.RemoteDataAdapter := lRemoteDataAdapter;
... skipped code ...
Log('STEP 2. Select the data (List of departments) ...');
Log();
lTable.LogicalName := 'Deps';
lTable.Open;

Inserting a Row (Step 3)

To add/insert a new record into a TDAMemDataTable object it must be first be put into append mode using the Append method.

This adds a new record to the table and makes it the current record. You can now set the values for the required fields by using the FieldByName method to retrieve the field you wish to set, and then assign the value to it. Fields that are defined as AutoInc in the schema shouldn't be set, they will automatically be given a value of -1 (or lower) until the changes have been applied to the server at which point a proper value will be assigned and returned to program.

The results of this are particularly observable in this sample when the new row is added. Initially the new row has a DepId of "-1" (see the sample output below in Step 3), once the changes have be applied to the server that DepId is updated to reflect what the actual id is on the server (sample output below in Step 4).

When you have finished adding the required fields for the record you must call the Post method to save the changes to the table. Note that the changes are only saved to the local table, you need to use the ApplyUpdates method to apply them to the server.

Log('STEP 3. Insert a new row (Security department) ...');
Log();
lTable.Append;
ltable.FieldByName('DepName').AsString := 'Security';
ltable.FieldByName('DepPhone').AsString := '(873)000-00-00';
lTable.Post;

Updating a Row (Step 4)

To change the value in a particular field/column of a row you must first locate the appropriate row in the TDAMemDataTable. There are two methods available in TDAMemDataTable to do it, the first LocateByIndex takes the index of the desire record and makes it the current record.

The alternative method, which is used in this sample, is Locate. It takes three arguments, the first is a list of the field or fields in the dataset that must be matched against when the lookup occurs. The second is an array of one or more values that are used to find appropriate row, these are provided in the order of the fields in the first argument. The last argument is an array of optional options to affect the search; for instance whether the search should be case insensitive.

After the record has been found, the table must be first put into editing mode using the Edit method. When editing is finished the Post method must be called to save the changes to the table. Note that the changes are only saved to the local table, you need to use the ApplyUpdates method to apply them to the server.

To change the value of a particular field use the FieldByName method to retrieve the field you wish to update, and then assign the new value to it.

Log('STEP 4. Modify row (Change phone for added department) ...');
Log();

if not lTable.Locate('DepName;DepPhone',VarArrayOf(['Security','(873)000-00-00']),[]) then begin
  Log('Added record is not found. Exiting...');
  Exit;
end;

ltable.Edit;
ltable.FieldByName('DepPhone').AsString := '(873)456-77-77';
ltable.Post;

Deleting a Row (Step 5)

To remove or delete a row from a TDAMemDataTable you need to use the Delete method after having first used the Locate method to find the row you are interested in.

Remember that unless the local changes are applied back to the server using the ApplyUpdates method the changes will be lost when the program exits.

Log('STEP 5. Delete row (Remove added department)...');
Log();
if not lTable.Locate('DepName;DepPhone',VarArrayOf(['Security','(873)456-77-77']),[]) then begin
  Log('Modified record is not found. Exiting...');
  Exit;
end;
lTable.Delete;

Example Output

This is an example of the output you will see when the sample is run. In Step 2 you can see there are 2 rows in the Deps table, in Step 3 there are now 3 rows and that in Step 4 the phone number for the Security department has changed. Lastly in Step 5 there are once again only 2 rows.

:Simple Data Operations sample has been started.
Target URL is http://localhost:7099/bin
RO DataAbstract layer is configured.

STEP 1: Login to DataService

Connecting to Relativity server: http://localhost:7099/bin
Login string is :
  User Id="simple";Password="simple";Domain="DASamples";Schema="Simple"
Login has been successfull. Going further...

STEP 2. Select the data (List of departments) ...

Table: Deps (2 rows from 2)
-----------------------------------------------------------------------
| DepId       | DepName                   | DepPhone                  |
-----------------------------------------------------------------------
| 1           | Sales                     | (873)456-78-99            |
| 2           | Incomes                   | (873)456-78-88            |
-----------------------------------------------------------------------

STEP 3. Insert a new row (Security department) ...

Table: Deps (3 rows from 3)
-----------------------------------------------------------------------
| DepId       | DepName                   | DepPhone                  |
-----------------------------------------------------------------------
| 1           | Sales                     | (873)456-78-99            |
| 2           | Incomes                   | (873)456-78-88            |
| -1          | Security                  | (873)000-00-00            |
-----------------------------------------------------------------------

Apply changes ...
Table: Deps (3 rows from 3)
-----------------------------------------------------------------------
| DepId       | DepName                   | DepPhone                  |
-----------------------------------------------------------------------
| 1           | Sales                     | (873)456-78-99            |
| 2           | Incomes                   | (873)456-78-88            |
| 4           | Security                  | (873)000-00-00            |
-----------------------------------------------------------------------

STEP 4. Modify row (Change phone for added department) ...

Apply changes ...
Table: Deps (3 rows from 3)
-----------------------------------------------------------------------
| DepId       | DepName                   | DepPhone                  |
-----------------------------------------------------------------------
| 1           | Sales                     | (873)456-78-99            |
| 2           | Incomes                   | (873)456-78-88            |
| 4           | Security                  | (873)456-77-77            |
-----------------------------------------------------------------------

STEP 5. Delete row (Remove added department)...

Apply changes ...
Table: Deps (2 rows from 2)
-----------------------------------------------------------------------
| DepId       | DepName                   | DepPhone                  |
-----------------------------------------------------------------------
| 1           | Sales                     | (873)456-78-99            |
| 2           | Incomes                   | (873)456-78-88            |
-----------------------------------------------------------------------

Done!
Cleanup!

Press Return to exit...