-
-
Save lzva/4756328024ea8cde7de1110105f11601 to your computer and use it in GitHub Desktop.
Testing ways of sending variable inputs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
program TestCallInBody; | |
{$APPTYPE CONSOLE} | |
uses | |
Windows, | |
mormot.core.variants, | |
mormot.core.interfaces, | |
mormot.rest.core, | |
mormot.rest.memserver, | |
mormot.rest.http.server, | |
mormot.rest.server, | |
mormot.soa.core, | |
mormot.core.json, | |
mormot.core.os, | |
mormot.core.data, | |
mormot.net.client | |
; | |
type | |
ITest = interface(IInvokable) | |
['{20B99698-D35A-43DD-A993-3A57AB40C302}'] | |
function A(const Vars: Variant): TServiceCustomAnswer; | |
function B(const Idee, Udoo: Integer): TServiceCustomAnswer; | |
function C(const _AllInputAs: Variant): TServiceCustomAnswer; | |
end; | |
TTest = class(TInterfacedObject, ITest) | |
public | |
function A(const Vars: Variant): TServiceCustomAnswer; | |
function B(const Idee, Udoo: Integer): TServiceCustomAnswer; | |
function C(const _AllInputAs: Variant): TServiceCustomAnswer; | |
end; | |
THandlerContainer = class | |
function HandleBeforeURI(Ctxt: TRestServerURIContext): Boolean; | |
end; | |
var | |
U_InBody: String; | |
function GetInputParams: UTF8String; | |
begin | |
// outgoing Json variant must be retained by callee, otherwise DV will point | |
// to invalid data because variant gets auto-freed | |
if ServiceRunningRequest.Method = mPOST | |
then Result := _Json(U_InBody, [dvoIsObject]) | |
else Result := ServiceRunningRequest.GetInputAsTDocVariant([], nil); | |
end; | |
function TTest.A(const Vars: Variant): TServiceCustomAnswer; | |
var | |
DV: TDocVariantData; | |
LIdx: Integer; | |
begin | |
DV := _DV(Vars); | |
Writeln(' Vars = ' + string(Vars)); | |
if not DV.IsArray then | |
for LIdx := 0 to DV.Count - 1 do | |
Writeln(' ' + String(DV.Names[LIdx]) + ' = ' + String(DV.Value[LIdx])); | |
Result.Status := 200; | |
Result.Header := TEXT_CONTENT_TYPE_HEADER; | |
Result.Content := _Json(Vars, [dvoIsObject]) | |
end; | |
function TTest.B(const Idee, Udoo: Integer): TServiceCustomAnswer; | |
begin | |
Result.Status := 200; | |
Result.Header := TEXT_CONTENT_TYPE_HEADER; | |
Result.Content := GetInputParams; | |
end; | |
function TTest.C(const _AllInputAs: Variant): TServiceCustomAnswer; | |
var | |
DV: TDocVariantData; | |
LIdx: Integer; | |
begin | |
DV := _DV(_AllInputAs); | |
Writeln(' _AllInputAs = ' + string(_AllInputAs)); | |
for LIdx := 0 to DV.Count - 1 do | |
Writeln(' ' + String(DV.Names[LIdx]) + ' = ' + String(DV.Value[LIdx])); | |
Result.Status := 200; | |
Result.Header := TEXT_CONTENT_TYPE_HEADER; | |
Result.Content := _AllInputAs; | |
end; | |
function THandlerContainer.HandleBeforeURI(Ctxt: TRestServerURIContext): Boolean; | |
begin | |
Result := True; | |
if Ctxt.Method = mPOST then | |
begin | |
// because ServiceRunningRequest.Call.InBody is consumed | |
U_InBody := Ctxt.call.InBody; | |
UniqueString(U_InBody); | |
end; | |
end; | |
procedure Check(const Put, Expect, Got: String); | |
begin | |
WriteLn(' Put: ' + Put); | |
WriteLn(' Got: ' + Got); | |
if Expect <> Got | |
then WriteLn('= unexpected') | |
else WriteLn('= OK, as expected'); | |
end; | |
var | |
LWebServer: TRestHttpServer; | |
LRestServer: TRestServerFullMemory; | |
LContainer: THandlerContainer; | |
const | |
CJSON_DOTTED = '{"Vars":{"Abc":123,"Def":321}}'; | |
CJSON_DOTTED_REPLY = '{"Abc":123,"Def":321}'; | |
CJSON_DOTTED_URI = 'Vars={Abc=123,Def=321}'; | |
CJSON = '{"Idee":123,"Idoo":321,"Icee":775}'; | |
CJSON_URI = 'Idee=123&Idoo=321&Icee=775'; | |
CJSON3 = '{"Idee":{"Abc":123,"Def":222},"Idoo":321}'; | |
begin | |
TInterfaceFactory.RegisterInterfaces([TypeInfo(ITest)]); | |
LContainer := THandlerContainer.Create; | |
LRestServer := TRestServerFullMemory.Create('API'); | |
LRestServer.ServicesRouting := TRestServerRoutingRest; | |
LRestServer.OnBeforeURI := LContainer.HandleBeforeURI; | |
LRestServer.ServiceDefine(TTest, [ITest], sicShared); | |
LWebServer := TRestHttpServer.Create('8080', [LRestServer], '+', useHttpSocket, 1); | |
{$message 'this works but dont like having to use vars object'} | |
WriteLn; WriteLn('> function A(const Vars: Variant): TServiceCustomAnswer;'); | |
WriteLn('> Post params as sub-properies'); | |
Check(CJSON_DOTTED, CJSON_DOTTED_REPLY, TWinHttp.Post('http://localhost:8080/API/Test.A', CJSON_DOTTED)); | |
WriteLn; WriteLn('> Get params as sub-properies'); | |
Check(CJSON_DOTTED_URI, CJSON_DOTTED_REPLY, TWinHttp.Get('http://localhost:8080/API/Test.A?' + CJSON_DOTTED_URI)); | |
WriteLn; | |
{$message 'this also works and is easy with overriding but doesnt express intent'} | |
WriteLn; WriteLn('> function B(const Idee, Udoo: Integer): TServiceCustomAnswer;'); | |
WriteLn('> Post params via copy of call.InBody'); | |
Check(CJSON, CJSON, TWinHttp.Post('http://localhost:8080/API/Test.B', CJSON)); | |
WriteLn; WriteLn('> Get params via ServiceRunningRequest.GetInputAsTDocVariant'); | |
Check(CJSON_DOTTED_URI, CJSON_DOTTED, TWinHttp.Get('http://localhost:8080/API/Test.B?' + CJSON_DOTTED_URI)); | |
WriteLn; | |
{$message 'proposed new way to define unknown params'} | |
// procedure Abc(const _AllInputAs: Variant); -- _AllInputAs contains docvariant with parsed inputs for both GET and POST | |
// procedure Abc(const _AllInputAs: UTF8String); -- _AllInputAs would contain post body or uri params as text | |
WriteLn; WriteLn('> function C(const _AllInputAs: Variant): TServiceCustomAnswer;'); | |
WriteLn('> Post to interface with magic param name _AllInputAs'); | |
Check(CJSON3, CJSON3, TWinHttp.Post('http://localhost:8080/API/Test.C', CJSON3)); | |
WriteLn; WriteLn('> Get from interface with magic param name _AllInputAs'); | |
Check(CJSON_URI, CJSON, TWinHttp.Get('http://localhost:8080/API/Test.C?' + CJSON_URI)); | |
LWebServer.Free; | |
LRestServer.Free; | |
LContainer.Free; | |
WriteLn; WriteLn; WriteLn('Sqeeze a key when done'); | |
Readln; | |
end. |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment