#1 2023-06-19 08:23:18

yanchung
Member
Registered: 2023-06-13
Posts: 10

Error: 400 when trying to execute 'RetrieveList'?

Hello mormot,

My Server based on Mormot 2, and Client (cross-platform) using Mormot 1.

Model := TSQLModel.Create([TNote],'root');
  DB := TSQLRestServerDB.Create(Model,ChangeFileExt(paramstr(0),'.db3'),true);//enable auth.
  DB.DB.LockingMode:=lmExclusive;
  DB.DB.Synchronous:=smOff;
  DB.CreateMissingTables;
  Server := TSQLHttpServer.Create('8080',[DB],'+',useHttpApiRegisteringURI);
  Server.AccessControlAllowOrigin := '*'; // allow cross-site AJAX queries

When I try to get one record it works and when I want to get a list (all of records for example) I got error 400 !

procedure TForm1.Button1Click(Sender: TObject);
var
  Model:TSQLModel;
  Client:TSQLRestClientHTTP;
  rec : TNote;
  aList:TObjectList;
  x:TObjectList<TNote>;
begin
 Model:=TSQLModel.Create([TNote],'root');
 Client:=TSQLRestClientHTTP.Create('x.x.x.x',8080,Model,false);
 if not Client.SetUser(TSQLRestServerAuthenticationDefault,'Admin','synopse',false) then
 begin
   //.......
 end;
 if (not Client.Connect) or (Client.ServerTimeStamp=0) then
 begin
  //......
 end
 //get one record works
 rec := TNote.Create (Client,1);
 //this also works
 Client.Retrieve(1,rec);
 x:=Client.RetrieveList<TNote>('id,body','',[]);
 x.count <--- zero
end;

Error 400 is the status of the request as I debug it here (syncrossplatfromrest.pas):

Call.Init(Model.Root+UrlEncode(['sql',sql]),'GET','');
  URI(Call);
  if Call.OutStatus=HTTP_SUCCESS then begin//<--- here
........

Any idea :-)

Last edited by yanchung (2023-06-19 08:24:31)

Offline

#2 2023-06-19 09:07:14

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

Re: Error: 400 when trying to execute 'RetrieveList'?

Try to debug a little bit on the server side to see what happens.

What is the URI generated? What is the input content and verb?

The entry point is the TRestServer.Uri method of mormot.rest.server.pas.
It should dispatch the query up to TRestServerUriContext.ExecuteOrmGet and make the query.

Offline

#3 2023-06-20 09:21:12

yanchung
Member
Registered: 2023-06-13
Posts: 10

Re: Error: 400 when trying to execute 'RetrieveList'?

Hi @AB

Trying to get a few records (for test)

Client:

aList:=Client.RetrieveList(TNote,'body','id<?',[5]);

[image]https://imgtr.ee/images/2023/06/20/ZYD8n.png[/image]

Last edited by yanchung (2023-06-20 09:28:02)

Offline

#4 2023-06-20 09:30:37

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

Re: Error: 400 when trying to execute 'RetrieveList'?

So what happens in TRestServer.Uri ?

Offline

#5 2023-06-20 09:37:42

yanchung
Member
Registered: 2023-06-13
Posts: 10

Re: Error: 400 when trying to execute 'RetrieveList'?

The inBody is empty:

[image]https://imgtr.ee/images/2023/06/20/ZYN3X.png[/image]

And access rights has [reSQL]


....
           // GET with a sql statement sent as UTF-8 body (not 100% HTTP compatible)
              sql := fCall^.InBody;
            if sql <> '' then//<-------sql is empty
            begin
              sqlisselect := IsSelect(pointer(sql), @sqlselect);
              if sqlisselect or
                 (reSql in fCall^.RestAccessRights^.AllowRemoteExecute) then
              begin
                fStaticOrm := nil;
....

Last edited by yanchung (2023-06-20 09:50:02)

Offline

#6 2023-06-20 09:56:53

yanchung
Member
Registered: 2023-06-13
Posts: 10

Re: Error: 400 when trying to execute 'RetrieveList'?

@AB:

I changes this line (mormot.rest.server line#3514):

sql := fCall^.InBody; 

TO:

sql:='select id from note';

and it works, Do have an idea what to do?

And I checked that in (mormot.rest.core) When I try to send a request by the client the Call.InBody is empty !!

constructor TRestUriContext.Create(const aCall: TRestUriParams);
begin
  fCall := @aCall;
  fMethod := ToMethod(aCall.Method);
  if aCall.InBody <> '' then //<---- empty !!!!
    aCall.InBodyType(fInputContentType, {guessjsonifnone=}false);
end;

Last edited by yanchung (2023-06-20 10:05:35)

Offline

#7 2023-06-20 10:07:33

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

Re: Error: 400 when trying to execute 'RetrieveList'?

It should go inside

            if (fCall^.InBody = '') and
               (params <> nil) and
               (reUrlEncodedSql in fCall^.RestAccessRights^.AllowRemoteExecute) then
            begin
              // GET with a sql statement sent in URI, as sql=....
              while not UrlDecodeValue(params, 'sql=', sql, @params) do
                if params = nil then
                  break;
            end

and extract the sql value from the URI.

Is reUrlEncodedSql part of the AllowRemoteExecute rights?
Or is there a bug in the "while not UrlDecodeValue" loop?

Note: I could debug it myself, but I don't have much time now, and it is better to let users find out how to debug and make a PR.

Offline

#8 2023-06-20 12:25:19

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

Re: Error: 400 when trying to execute 'RetrieveList'?

Offline

#9 2023-06-20 20:00:39

yanchung
Member
Registered: 2023-06-13
Posts: 10

Re: Error: 400 when trying to execute 'RetrieveList'?

Hi @AB

I updated Mormot, Now works as expected.

Great thanks to you and good day

Offline

Board footer

Powered by FluxBB