DEV Community

Sempare Limited
Sempare Limited

Posted on

Accessing a FireDAC dataset from the Sempare Template Engine for Delphi

The Sempare Template Engine (available at https://github.com/sempare/sempare-delphi-template-engine and GetIt) is a versatile templating system designed specifically for Delphi developers to streamline the creation and management of dynamic HTML, text, or any other text-based output formats. Whether you are building web applications, reports, or email templates, the Sempare Template Engine offers a powerful yet straightforward solution that integrates with minimal boilerplate into Delphi projects. The template engine has been around since 2019 and has many features for you to explore.

In this article, we will explore how a FireDAC TDataSet can be enumerated from a Sempare Template Engine template.

The code for this tutorial is available at https://github.com/sempare/sempare-devto-examples/tree/dev/FireDACInMemory

Creating a mock dataset

We normally get a TDataSet back from a database query. In this tutorial, I'll construct a TFDMemTable which we can use later in a template.

function CreateMockUsersTable(): TFDMemTable; 

    procedure AddPerson(const AName: string; const AAge, AWeight: integer);
    begin
      result.Append;
      result.FieldByName('name').value := AName;
      result.FieldByName('age').value := AAge;
      result.FieldByName('weight').value := AWeight;
      result.Post;
    end;

begin
  result := TFDMemTable.Create(nil);
  result.FieldDefs.Add('name', ftWideString, 20);
  result.FieldDefs.Add('age', ftInteger);
  result.FieldDefs.Add('weight', ftFloat);
  result.CreateDataSet;
  AddPerson('joe', 20, 67);
  AddPerson('pete', 19, 87);
  AddPerson('jane', 23, 47); 
end; 
Enter fullscreen mode Exit fullscreen mode

In the function above, we create a TFDMemTable containing 3 users. We first define the fields and then add the users.

templates/users.tpl

<h1>Users</h1>
<% for idx in Users %>
      <tr>
         <td><% idx %></td>
         <td><% Users.name %></td>
         <td><% Users.age %></td>
         <td><% Users.weight %></td>
      </tr>
  <% onbegin %>
    <table>
      <tr>
         <th>No</th>
         <th>Name</th>
         <th>Age</th>
         <th>Width</th>
      </tr>
  <% onend %>
    </table>
  <% onempty %>
    <div>There are no users</div>
<% end %>
Enter fullscreen mode Exit fullscreen mode

In the above template, we use some of the additional 'events' on loops to control various aspects around when the header, body and footer is created, as well as what to output when there is no data. During each iteration, the the loop will dereference the various fields from the dataset, as we see with 'Users.name' as an example.

Now to pull it all together:

program FireDACInMemoryExample;

uses
  Data.DB,
  FireDAC.Comp.Client,
  System.SysUtils,
  Sempare.Template;

function CreateMockUsersTable(): TFDMemTable; 
begin 
  // code from above
end;

type
  TTemplateData = record
    Users: TDataSet;
  end;

var
  LTemplateData : TTemplateData;
begin
  LTemplateData.Users := CreateMockUsersTable;
  try
    writeln(Template.Resolve('users.tpl', LTemplateData)); 
  finally
    LTemplateData.Users.Free;
  end;
end.
Enter fullscreen mode Exit fullscreen mode

This will give us a simple HTML table:

    <h1>Users</h1>
    <table>
      <tr>
         <th>No</th>
         <th>Name</th>
         <th>Age</th>
         <th>Width</th>
      </tr>
      <tr>
         <td>1</td>
         <td>joe</td>
         <td>20</td>
         <td>67</td>
      </tr>
      <tr>
         <td>2</td>
         <td>pete</td>
         <td>19</td>
         <td>87</td>
      </tr>
      <tr>
         <td>3</td>
         <td>jane</td>
         <td>23</td>
         <td>47</td>
      </tr>
    </table>
Enter fullscreen mode Exit fullscreen mode

Gotchas

Something to be aware of. When enumerating using the for statement, the index variable returns an offset into the data set, starting from 1.

We dereference fields directory off the dataset as shown above. If there are spaces in the field name, you can use array dereferencing style. e.g. In the above Users.name and Users['name'] are equivalent.

Conclusion

The above example has illustrated how a simple HTML report can be generated with an in memory FireDAC table.

The Sempare Template Engine is very flexible, configurable and extensible, allowing for a good seperation of concerns between your business logic that will access data, and the templating engine that will render/present your data as required.

The template engine is available on https://github.com/sempare/sempare-delphi-template-engine and via Embarcadero GetIt.

Sponsorship Required

Please help us maintain the project by supporting Sempare via GitHub sponsors (https://github.com/sponsors/sempare) or via our payment link (https://buy.stripe.com/aEU7t61N88pffQIdQQ). Sponsors can obtain access to our integrated IDE wizard for RAD Studio.

Top comments (0)