Table of Contents

Storing and reading objects

With a connection open and a model registered, the database exposes a small set of asynchronous operations to persist and retrieve your objects. Each call returns immediately and reports completion through a matching On... event whose ARequestResult indicates success. This chapter covers inserting objects, reading them back as typed instances, and deleting objects or creating new table nodes.

Inserting objects

Create a model instance, set its published properties, and pass it to InsertObject. The component serializes the published properties and writes the record; the result arrives in OnInsertData. The database does not take ownership of the instance you pass, so free it after the call (or keep it if you still need it locally).

procedure TForm1.AddContact(const AName, AEmail: string);
var
  Contact: TContact;
begin
  Contact := TContact.Create;
  try
    Contact.Name := AName;
    Contact.Email := AEmail;
    Contact.Friend := True;
    FDatabase.InsertObject(Contact); // serialized and sent; result arrives in OnInsertData
  finally
    Contact.Free; // the database does not take ownership of the passed instance
  end;
end;

Reading the stored objects

ReadList fetches every object in the current table into a TTMSFNCCloudGoogleFireBaseObjectList, raising OnReadDataList with the reconstructed instances. Because a table can hold more than one model type, test each entry's class with is before casting. This example combines the model from Defining a data model with the database read, reconstructing each TContact from the result list.

procedure TForm1.LoadContacts;
begin
  FObjects.Clear;
  FDatabase.ReadList(FObjects); // result arrives in OnReadDataList
end;

procedure TForm1.DatabaseReadDataList(Sender: TObject;
  const AList: TObjectList<TTMSFNCCloudGoogleFireBaseObject>;
  const ARequestResult: TTMSFNCCloudBaseRequestResult);
var
  Obj: TTMSFNCCloudGoogleFireBaseObject;
  Contact: TContact;
begin
  if not ARequestResult.Success then
    Exit;

  ListBox1.Clear;
  // Each entry is reconstructed as its registered class; test the type before use.
  for Obj in AList do
    if Obj is TContact then
    begin
      Contact := TContact(Obj);
      ListBox1.Items.AddObject(Contact.Name, Contact);
    end;
end;

Deleting objects and creating tables

Remove a stored object by passing it to DeleteObject (OnDeleteData confirms the removal). Create a new table node under the database with CreateObject, passing the node name (OnCreateObject confirms it). Refresh your list in the completion event rather than immediately after the call.

procedure TForm1.RemoveSelectedContact;
var
  Obj: TObject;
begin
  if ListBox1.ItemIndex < 0 then
    Exit;
  Obj := ListBox1.Items.Objects[ListBox1.ItemIndex];
  FDatabase.DeleteObject(TTMSFNCCloudGoogleFireBaseObject(Obj)); // result arrives in OnDeleteData
end;

procedure TForm1.AddTable(const ATableName: string);
begin
  // Create a new node under the database; result arrives in OnCreateObject.
  FDatabase.CreateObject(ATableName);
end;

Pitfalls

  • Act on results in the completion event. The operations are asynchronous; the object list and a new record's ID are only guaranteed once the matching On... event fires.
  • Free the instance passed to InsertObject. The database copies the data; it does not adopt your object.
  • Type-test entries from ReadList. A table may contain several model types, and only registered classes are reconstructed.

See also