Delphi Rest Server Code First?

Hi there,
I have to build a RestServer using Delphi 10.4.1 with RO 10.0.0.1481 . Looking at some snippets and searching various topics here did not bring me to a succesful try. Could you possibly create a very simple example with a get or/and post function with a parameter which could be called by postman? I would really very appreciate it and i’m sure it would also help others.

Hi,

I’ll log s feature request. Unfortunately,y the person best suited for this is current off sick, so I’m afraid it might be a tuple weeks before we can get to it. In the mean time, if tie have any more concrete questions or could let us know what went wrong, hopefully we can help you out.

thanx,
marc

Thanks, logged as bugs://84994

Hello

Did you check this article?

It is quite easy to achieve what you need:

  1. Add the TROHttpApiDispatcher dispatcher. This component will read incoming requests and call corresponding service methods.
  2. Decorate service methods with corresponding attributes to let the dispatcher know how exactly to translate requests (see the article for details)

Do not forget to set the content type header to application/json for requests that contain JSON body

Regards

1 Like

Honestly - no. I did not find that one so far. Thanks. I’ll give it a try!

This sample works so far. But i’m not able to create a more complex function to work. I’ve attached the project also. If one get to run this maybe someone else could benefit as well from it. RestServer.zip (5.3 KB)

  • swagger complains a structural error (see swagger screenshot below)
  • how can i force swagger to use http instead of https?
  • how do i have to add an object item in swagger?

I have this objects:

type
  TPlateInfo = class(TROComplexType)
  private
    FLicencePlate: ROUTF8String;
    FParkingBayName: ROUTF8String;
    FParkingBayId: Integer;
    FBuildingId: Integer;
  published
    {$IFDEF RO_RTTI_Support} [ROSerializeAsUTF8String] {$ENDIF}
    property LicencePlate: ROUTF8String read FLicencePlate write FLicencePlate;
    {$IFDEF RO_RTTI_Support} [ROSerializeAsUTF8String] {$ENDIF}
    property ParkingBayName: ROUTF8String read FParkingBayName write FParkingBayName;
    property ParkingBayId: Integer read FParkingBayId write FParkingBayId;
    property BuildingId: Integer read FBuildingId write FBuildingId;
  end;

  TPlateResult = class(TROComplexType)
  private
    FParkingBayId: Integer;
    FPlateExists: Boolean;
  published
    property ParkingBayId: Integer read FParkingBayId write FParkingBayId;
    property PlateExists: Boolean read FPlateExists write FPlateExists;
  end;

Method Definition:

  public
    [ROServiceMethod]
    [ROCustom('HttpApiPath','PlateUpdate')]
    [ROCustom('HttpApiMethod','GET')]
    function PlateUpdate([ROCustom('HttpApiQueryParameter','1')] PlateInfo: TROArray<TPlateInfo>): TROArray<TPlateResult>;
  end;

Method:

function TEPPUEVService.PlateUpdate(PlateInfo: TROArray<TPlateInfo>): TROArray<TPlateResult>;
var
  i: Integer;
  Res: TPlateResult;
begin
  Result:= TROArray<TPlateResult>.Create;
  for i := 0 to PlateInfo.Count - 1 do
  begin
    Res:= Result.Add;
    Res.FParkingBayId:= PlateInfo[i].ParkingBayId;
    Res.FPlateExists:= True;
  end;
end;

When i past the json from http://localhost:8099/api to swagger it will result in some yaml code:

Hello

Ad the following entry below the basePath entry:

schemes:
  - http

So your swagger definition should look like

...
info:
  version: 1.0.0
  title: ROServer6
basePath: /api
schemes:
  - http
consumes:
  - application/json
produces:
  - application/json
...

Your service method definition is not correct (in terms of REST):

  1. You should NEVER use GET method for any requests that update data server-side.
  2. Only primitive types (like string, int32, boolean etc) can be used in query parameters (this is standard limitation). Also please bear in mind that length of Url is limited and this also limits amount of data that can be passed via query parameters
  3. Complex data types (arrays, complex objects) should be passed via request body

Unce you fix the server method definition issues the Swagger will show you JSON sample for the service method calls:

2020-09-30_13-47-57_msedge

Regards

Thanks Anton, i should have known this. It was my mistake. Everything fine now.

That was not actually a mistake - it was just not following some REST conventions by Swagger.

Formally it is still possible to pass a complex object or array via query parameter, still it is highly not recommended to do this (request result can be cached by browser, Url length is limited etc).

All 4 supported Http methods (GET, POST, PUT, DELETE) have their own (recommended) meaning in terms of REST. F.e. it is expected that DELETE call actually deletes something server-side

I guess your problem is solved & my input may not be helpful, but in case it helps someone:

Before I discovered WASM & RO, for my Application I built a Web Server using Delphi WebBroker compiled to an ISAPI dll which is about the fastest running Web Server. I used a MS Server but understand an ISAPI dll can be added to Linux/Apache. My primary client was HTML/CSS/JS (which I hate!) but also included a standard desktop Windows Client which accessed my Web Server. Anything can access a Web Server knowing the API.

WebBroker looks easier to me than the solns provided, but then I’ve never seen TROHttpApiDispatcher before & never heard of swagger.

In my case I used an ISAPI dll for math/engineering-type programming which is not easy in HTML/CSS/JS which I hate for desktop-type but on-line Ap programming vs publishing for which HTML/CSS was intended. Java Applets were the thing for desktop-type on-line Aps which I did use till the Web Gods got rid of Java Applets rather than improving it. HTML/CSS/JS is a programming Kludge!

WASM & RO TO THE RESCUE! I discovered AutoCAD on-line is written in WASM so I determined I could do my math-heavy task in the browser rather than relying on the complexity of Client/Server. I replaced the whole thing with RO’s WASM, so all the work is done in the browser & all the server does is download the WASM files.

New work also in RO WASM. Love it!

1 Like

Hi tampatex

thank you very much for your info!

For WASM do you use the RemObjects platform?

I’m starting to use Blazor with .NET Core 5 (RC) and I love it!

If you use it too what do you think?

Thank you very much!

Just in case - Remoting SDK and Data Abstract can be used in Blazor too

1 Like

Yes, I use RO’s WASM (Water, Oxygene).

If you read my stuff, ya know I got “hates” in programming. C# is a much better language than C++ which is so freaky that yrs ago some programming rag had a C++ puzzle every issue of 1 or very few lines of C++ asking what it did – and never obvious.

I’m an old guy & never had a programming course, so keep that in mind. I’ve used quite a few self-learned languages starting with several assemblers (different CPUs, micros to mainframes), Fortran, COBOL, C, Java, Pascal, et al. The basics of all are variables (& constants), in-line instructions, sub-routines, loops, IF, etc. That is how I think, in the basics, not in the language to express it. Having no formal programming background, I’d flunk any programming test with all the acronyms in use.

The first Windows GUI programs I wrote used Borland’s Turbo Pascal. At the time C++ had “Foundation Classes” rather than GUI controls to place, i.e. all text. A VC told me Gates was furious with his team that Borland did & MS did not have that. MS came out later with Visual Basic. Soon after release an excited math friend called & told me I had to come see the new VB GUI & how great it was. I went. He demo’d it with a few simple controls . . . it crashed! Borland’s worked.

I heard that MS “eventually gets it right” & over the years kept up with MS tools & almost converted to C# but found it incomplete. I studied Silverlight, installed it & played with it. I observed that MS seemed not to care about obsoleting tools nor compatibility between tool versions. Whether VB or C# MS made changes requiring reprogramming previous work & throwing out tools people had spent months & $’s using. The only major rewrite I’ve ever had with Pascal (Delphi) was the conversion to Unicode. My current WASM project ran in all browsers including Apple & iPad, but not MS Edge until a new version came out approx in April. For business I’ve got MS Teams – the Calendar doesn’t work – a Calendar!!! What is wrong with MS??? Whatever it is, this is a too long explanation of MS being among my “hates.” I don’t trust ‘em. Weeks & months of work may need redoing & MS stuff is not reliable. So, this an even longer answer to your Blazor .NET query: “Not much! I got’s me Delphi & RO’s WASM & happily using CentOS 8 for free.” I may use C to develop a front-end filter for my server to let the good guys in & keep the bad guys out & a few other things.

I hope I’ve not bored you as an old guy who doesn’t even know all your modern lingo. As a hammer to a nail, to me, programming is just math & logic (which is math).

1 Like

I find the opposite. Beyond version 3, anything MS does resolves into a huge mess. e.g. .NET: 1.x and 2.0 was very clean, well designed and comprehensible. With 3.5, things started to fall apart, with MSBuild “magic” and every-increasing complexity in the tool chain. .NET Core is going the same way (if it ever was “simple”)…

:wink:

:raised_hands:t3:

1 Like

The “eventually gets it right” was from several years ago. Probably from a MS guy.

1 Like