#1 2014-05-11 07:56:47

Titou
Member
Registered: 2014-05-11
Posts: 12

Mustache rendering. What's the issue?

Hello,
I tried to use mustache to render html output. Below the code and the tries (I'm a beginner with mORMot, all reviews concerning the code are welcome).

The code :

procedure TSQLCarpeRestServerDB.Users(Ctxt: TSQLRestServerURIContext);
var
  Rec: TSQLUser;
  aUser: TSQLUser;
  JSON: TStringStream;
  OutputFormat: RawUTF8;
  oFormat: TOutputFormat;
  Mustache: TSynMustache;
  Html: TStringList;
  s: RawUTF8;
begin
  oFormat := ofHtml;
  if UrlDecodeNeedParameters(Ctxt.Parameters, 'FORMAT') then
    if Ctxt.Parameters <> nil then
    begin
      UrlDecodeValue(Ctxt.Parameters, 'FORMAT=', OutputFormat);
      oFormat := TOutputFormat(GetEnumValue(TypeInfo(TOutputFormat), 'of' + OutputFormat));
    end;

  aUser := TSQLUser.CreateAndFillPrepare(Self, '', []);
  try
    case oFormat of
      ofHtml, ofJson:
        begin
          JSON := TStringStream.Create;
          try
            while aUser.FillOne do
            begin
              JSON.Clear;
              aUser.GetJSONValues(JSON, True, True, soSelect);
              JSON.Seek(0, soBeginning);
              if Length(s) > 0 then
                s := s + ',' + JSON.ReadString(MaxInt)
              else
                s := JSON.ReadString(MaxInt)
            end;
            s := '{"users":[' + s + ']}';

            if oFormat = ofHtml then
            begin
              Html := TStringList.Create;
              try
                Html.LoadFromFile(ResourcePath + 'Users.html');
                mustache := TSynMustache.Parse(Html.Text);
                Ctxt.Returns(mustache.RenderJSON(s), HTML_SUCCESS, HTML_CONTENT_TYPE_HEADER);
              finally
                Html.Free;
              end;
            end
            else
              Ctxt.Returns(s, HTML_SUCCESS, JSON_CONTENT_TYPE_HEADER);
          finally
            JSON.Free;
          end;
        end;

      ofText:
        begin
          try
            while aUser.FillOne do
              s := s + aUser.FirstName + #9 + aUser.Name + IIFStr(aUser.Connected, #9'Connected', '') + #10;
            Ctxt.Returns(s, HTML_SUCCESS, TEXT_CONTENT_TYPE_HEADER);
          finally
            JSON.Free;
          end;
        end;
    end;
  finally
    aUser.Free;
  end;
end;

The JSON output (http://localhost:8080/Carpe/Users?format=json)

{
"users":
[
{"RowID":1,"Login":"safr","Firstname":"Frodon","Name":"Sacquet","Alias":"safr","Connected":true,"Resto":0},
{"RowID":2,"Login":"saga","Firstname":"Samsagace","Name":"Gamegie","Alias":"saga","Connected":false,"Resto":0},
{"RowID":3,"Login":"peto","Firstname":"Peregrin","Name":"Touque","Alias":"peto","Connected":false,"Resto":0},
{"RowID":4,"Login":"mebr","Firstname":"Meriadoc","Name":"Brandebouc","Alias":"mebr","Connected":true,"Resto":0}
]
}

As we can see, there are two connected users.



First I use the html model below (http://localhost:8080/Carpe/Users?format=html)

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<HTML>
<HEAD>
	<META HTTP-EQUIV="CONTENT-TYPE" CONTENT="text/html; charset=utf-8">
	<TITLE>Carpe - Users</TITLE>
</HEAD>
<BODY LANG="fr-FR" BGCOLOR="#ffffcc" DIR="LTR">
<P STYLE="font-weight: normal">
<FONT FACE="Arial, sans-serif" SIZE=4 COLOR="#663300">
{{#users}}
- {{Name}} {{Firstname}} ({{Connected}})<BR>
{{/users}}
</FONT>
</P>
</BODY>
</HTML>

The result :

- Sacquet Frodon (true)
- Gamegie Samsagace (false)
- Touque Peregrin (false)
- Brandebouc Meriadoc (true)

All right.


Second try with this html model :

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<HTML>
<HEAD>
	<META HTTP-EQUIV="CONTENT-TYPE" CONTENT="text/html; charset=utf-8">
	<TITLE>Carpe - Users</TITLE>
</HEAD>
<BODY LANG="fr-FR" BGCOLOR="#ffffcc" DIR="LTR">
<P STYLE="font-weight: normal">
<FONT FACE="Arial, sans-serif" SIZE=4 COLOR="#663300">
{{#users}}
{{#Connected}}
- {{Name}} {{Firstname}} ({{Connected}})<BR>
{{/Connected}}
{{/users}}
</FONT>
</P>
</BODY>
</HTML>

The result:

- Sacquet Frodon (true)

Only the first user is rendered.




Actually, when I try the example from the SAD document § 7.3.2.2. I have the result :

Colors

red
The list is empty.

Instead of :

Colors

red
green
blue
The list is empty.

An explanation? Is there an error in the code, the HTML, the JSON?
Thanks in advance for the help.

Last edited by Titou (2014-05-11 08:54:54)

Offline

#2 2014-05-11 16:15:07

ab
Administrator
From: France
Registered: 2010-06-21
Posts: 14,659
Website

Re: Mustache rendering. What's the issue?

Oups...
There was an obvious issue with the current code implementation, and it sounds like if the official Mustache specification tests were not enough!

Now the code is much easier to follow and maintain.

Should be fixed by http://synopse.info/fossil/info/a077950bca

Offline

#3 2014-05-12 06:16:16

Titou
Member
Registered: 2014-05-11
Posts: 12

Re: Mustache rendering. What's the issue?

Thank you for the fast correction.
It's better. But ...

This HTML/mustache

{{#users}}
{{#Connected}}
- {{Name}} {{Firstname}} ({{Connected}})<BR>
{{/Connected}}
{{/users}}

Renders:

- Sacquet Frodon (true)
- Brandebouc Meriadoc (true)

But this HTML/mustache (inverted section)

{{#users}}
{{^Connected}}
- {{Name}} {{Firstname}} ({{Connected}})<BR>
{{/Connected}}
{{/users}}

Renders nothing.

Offline

#4 2014-05-12 08:12:45

ab
Administrator
From: France
Registered: 2010-06-21
Posts: 14,659
Website

Re: Mustache rendering. What's the issue?

I've just fixed a problem with inverted sections not rendered as expected...
See http://synopse.info/fossil/info/219e086d96

Sounds better now.
Thanks for the feedback.

Offline

#5 2014-05-12 09:46:02

Titou
Member
Registered: 2014-05-11
Posts: 12

Re: Mustache rendering. What's the issue?

Perfect. It works fine now. Thanks a lot.

For example the final version of my HTML/mustache below.
This code displays the connected and not connected users with different colors.

<BODY LANG="fr-FR" BGCOLOR="#ffffdd" DIR="LTR">
<P STYLE="font-weight: normal">
<FONT FACE="Arial, sans-serif" SIZE=4">
{{#users}}
{{#Connected}}<FONT COLOR="#663300">{{/Connected}}
{{^Connected}}<FONT COLOR="#ccccaa">{{/Connected}}
- {{Name}} {{Firstname}}<BR>
<FONT>
{{/users}}
</FONT>
</P>
</BODY>

Offline

Board footer

Powered by FluxBB