logo.png
mORMot2 API Reference

mormot.rest.server.pas unit

Purpose: REpresentation State Tranfer (REST) Types and Classes on Server Side
- this unit is a part of the Open Source Synopse mORMot framework 2, licensed under a MPL/GPL/LGPL three license - see LICENSE.md

1.1. Units used in the mormot.rest.server unit

Unit NameDescription
mormot.core.baseFramework Core Shared Types and RTL-like Functions
mormot.core.buffersFramework Core Low-Level Memory Buffer Process
mormot.core.dataFramework Core Low-Level Data Processing Functions
mormot.core.datetimeFramework Core Low-Level Date and Time Support
mormot.core.interfacesFramework Core Low-Level Interface/SOLID Processing
mormot.core.jsonFramework Core Low-Level JSON Processing
mormot.core.logFramework Core Logging
mormot.core.osFramework Core Low-Level Wrappers to the Operating-System API
mormot.core.perfFramework Core Performance and Monitoring Classes
mormot.core.rttiFramework Core Low-Level Cross-Compiler RTTI Definitions
mormot.core.textFramework Core Low-Level Text Processing
mormot.core.threadsFramework Core Multi-Threading Support
mormot.core.unicodeFramework Core Low-Level Unicode UTF-8 UTF-16 Ansi Conversion
mormot.core.variantsFramework Core Low-Level Variants / TDocVariant process
mormot.crypt.coreFramework Core Cryptographic Process (Hashing and Cypher)
mormot.crypt.jwtFramework Core JSON Web Tokens (JWT) Support
mormot.crypt.secureFramework Core Authentication and Security Features
mormot.db.coreDatabase Framework Core Types and Classes
mormot.lib.gssapiLow-level access to the GssApi on Linux/POSIX
mormot.lib.sspiLow-level access to the SSPI/SChannel API for Win32/Win64
mormot.orm.baseObject-Relational-Mapping (ORM) Low-Level Process
mormot.orm.coreObject-Relational-Mapping (ORM) Main Types and Classes
mormot.orm.restObject-Relational-Mapping (ORM) Abstract REST Implementation
mormot.orm.serverORM Types and Classes for the Server side
mormot.orm.storageORM Types and Classes for the Server side JSON/Binary Storage
mormot.rest.clientREpresentation State Tranfer (REST) Types and Classes on Client side
mormot.rest.coreREpresentation State Tranfer (REST) Core Types and Classes
mormot.soa.coreInterface-based SOA Process Core Types and Classes
mormot.soa.serverInterface-based SOA Process Types and Classes for Server-Side

1.2. mormot.rest.server class hierarchy

TSynPersistentWithPasswordTRestHttpServerDefinitionTSynPersistentTRestRouterTAuthSessionParentTAuthSessionTSynMonitorUsageTSynMonitorUsageRestTSynMonitorServerTRestServerMonitorTRestServerAuthenticationSignedUriTRestServerAuthenticationSspiTRestServerAuthenticationDefaultTRestServerAuthenticationUriTRestServerAuthenticationNoneTRestServerAuthenticationTRestServerAuthenticationHttpAbstractTRestServerAuthenticationHttpBasicTSynLockedTRestServerUriContextTRestServerRoutingRestTRestServerRoutingJsonRpcTRestUriContextTRestTRestServerTRadixTreeNodeParamsTRestTreeNodeTOrmNoCaseExtendedTOrmMonitorUsageESynExceptionESecurityExceptionEParsingExceptionERadixTreeERestTree
mormot.rest.server class hierarchy

1.3. Objects implemented in the mormot.rest.server unit

ObjectsDescription
EParsingExceptionException raised in case of unexpected parsing error
ERestTreeException class raised during TRestTree URI parsing
ESecurityExceptionException raised when security authorization/authentication failed
TAuthSessionClass used to maintain in-memory sessions
TAuthSessionParentUsed for efficient TAuthSession.IDCardinal comparison
TOrmMonitorUsageORM table used to store TSynMonitorUsage information in TSynMonitorUsageRest
TRestHttpServerDefinitionParameters supplied to publish a TRestServer via HTTP
TRestRouterEfficient server-side URI routing for TRestServer
TRestServerAbstract REpresentational State Transfer (REST) server
TRestServerAuthenticationAbstract class used to implement server-side authentication in TRestServer
TRestServerAuthenticationDefaultMORMot secure RESTful authentication scheme on Server
TRestServerAuthenticationHttpAbstractAbstract class for implementing HTTP authentication
TRestServerAuthenticationHttpBasicAuthentication using HTTP Basic scheme
TRestServerAuthenticationNoneMORMot weak RESTful authentication scheme
TRestServerAuthenticationSignedUriSecure authentication scheme using URL-level digital signature
TRestServerAuthenticationSspiAuthentication of the current logged user using Windows Security Support Provider Interface (SSPI) or the GSSAPI library on Linux
TRestServerAuthenticationUriWeak authentication scheme using URL-level parameter
TRestServerMethodDescription of a method-based service
TRestServerMonitorUsed for high-level statistics in TRestServer.Uri()
TRestServerRoutingJsonRpcCalling context for a TOnRestServerCallBack using JSON/RPC for interface-based services
TRestServerRoutingRestCalling context for a TOnRestServerCallBack using our default simple REST routing for interface-based services
TRestServerUriContextAbstract calling context for a TOnRestServerCallBack event handler
TRestServerUriPagingParametersStructure used to specify custom request paging parameters for TRestServer
TRestTreeNodeImplement a Radix Tree node to hold one URI registration
TRestTreeNodeDataREST-specific context information, as stored in TRestTreeNode
TServiceRunningContextWill identify the currently running service on the server side
TSynMonitorUsageRestWill store TSynMonitorUsage information in TOrmMonitorUsage ORM tables

1.3.1. EParsingException

EParsingException = class(ESynException)

Exception raised in case of unexpected parsing error


1.3.2. ESecurityException

ESecurityException = class(ESynException)

Exception raised when security authorization/authentication failed


1.3.3. TServiceRunningContext

TServiceRunningContext = record

Will identify the currently running service on the server side
- is the type of the ServiceRunningContext per-thread function
- to access the current TRestServer instance (and e.g. its ORM/CRUD or SOA methods), use Request.Server and not Factory.Server, which may not be available e.g. if you run the service from the server side (so no factory is involved)
- note that the safest (and slightly faster) access to the TRestServer instance associated with a service is to inherit your implementation class from TInjectableObjectRest
- should map TPerThreadRunningContext private version in mormot.core.interfaces.pas


Factory: TServiceFactory;

The currently running TServiceFactoryServer instance
- it can be used within server-side implementation to retrieve the associated TRestServer instance
- note that TServiceFactoryServer.Get() won't override this value, when called within another service (i.e. if Factory is not nil)


Request: TRestServerUriContext;

The currently runnning context which launched the method
- low-level RESTful context is also available in its Call member
- Request.Server is the safe access point to the underlying TRestServer, unless the service is implemented via TInjectableObjectRest, so the TInjectableObjectRest.Server property is preferred
- make available e.g. current session or authentication parameters (including e.g. user details via Request.Server.SessionGetUser)


RunningThread: TThread;

The thread which launched the request
- is set by TRestServer.BeginCurrentThread from multi-thread server handlers - e.g. TRestHttpServer


1.3.4. TRestServerUriContext

TRestServerUriContext = class(TRestUriContext)

Abstract calling context for a TOnRestServerCallBack event handler
- having a dedicated class avoid changing the implementation methods signature if the framework add some parameters or behavior to it
- see TOnRestServerCallBack for general code use
- most of the internal methods are declared as virtual, so it allows any kind of custom routing or execution scheme
- instantiated by the TRestServer.Uri() method using its ServicesRouting property
- see TRestServerRoutingRest and TRestServerRoutingJsonRpc for workable classes - this abstract class will be rejected for TRest.ServicesRouting
- on client side, see TRestClientRouting reciprocal class hierarchy and the ClientRouting class method - as defined in mormot.rest.client.pas


destructor Destroy; override;

Finalize the execution context


function AuthenticationBearerToken: RawUtf8; override;

Method overriden to support rsoAuthenticationUriDisable option
- i.e. as an alternative, a non-standard and slightly less safe way of token transmission may be to encode its value as ?authenticationbearer=.... URI parameter (may be convenient when embedding resources in HTML DOM - but note that the URI is usually part of the web server logs, so it may be unsafe to use it on production - but may be handy e.g. for debugging or if you can't tweak the HTTP headers - as with websockets on JavaScript)


function AuthenticationCheck(jwt: TJwtAbstract): boolean; override;

Validate "Authorization: Bearer <JWT>" content from incoming HTTP headers
- overriden to support TRestServer.JwtForUnauthenticatedRequestWhiteIP()


function CanExecuteOrmWrite(Method: TUriMethod; Table: TOrmClass; TableIndex: integer; const TableID: TID; const Rights: TOrmAccessRights): boolean;

Validate mPOST/mPUT/mDELETE action against current session access rights
- used by TRestServerUriContext.ExecuteOrmWrite and TRestServer.EngineBatchSend methods for proper security checks


function ClientOrmOptions: TOrmWriterOptions;

Identify if the request is about a Table containing nested objects or arrays, which could be serialized as JSON objects or arrays, instead of plain JSON string (as stored in the database)
- will idenfity ClientKind=ckAjax, or check for rsoGetAsJsonNotAsString in TRestServer.Options


class function ClientRouting: TRestClientRoutingClass; virtual;

The associated routing class on the client side


function GetInputAsTDocVariant(const Options: TDocVariantOptions; InterfaceMethod: PInterfaceMethod): variant;

Retrieve all input parameters from URI as a variant JSON object
- returns Unassigned if no parameter was defined
- returns a JSON object with input parameters encoded as

 {"name1":value1,"name2":value2...}

- optionally with a PInterfaceMethod information about the actual values types
- if the parameters were encoded as multipart, the JSON object will be encoded with its textual values, or with nested objects, if the data was supplied as binary:

 {"name1":{"data":..,"filename":...,"contenttype":...},"name2":...}

since name1.data will be Base64 encoded, so you should better use the InputAsMultiPart() method instead when working with binary


function InputEnum(const ParamName: RawUtf8; EnumType: PRttiInfo; out ValueEnum; DefaultEnumOrd: integer = 0): boolean;

Retrieve one input parameter from its URI name as an enumeration
- will expect the value to be specified as integer, or as the textual representation of the enumerate, ignoring any optional lowercase prefix as featured by TEnumType.GetEnumNameValue()
- returns TRUE and set ValueEnum if the parameter is found and correct
- returns FALSE and set ValueEnum to first item (i.e. DefaultEnumOrd) if the parameter is not found, or not containing a correct value


function InputOrError(const ParamName: RawUtf8; out Value: variant; const ErrorMessageForMissingParameter: string): boolean;

Retrieve one input parameter from its URI name as variant
- returns FALSE and call Error(ErrorMessageForMissingParameter) - which may be a resourcestring - if the parameter is not found
- returns TRUE and set Value if the parameter is found
- if the parameter value is text, it is stored in the variant as a RawUtf8: so before Delphi 2009, you won't loose any Unicode character, but you should convert its value to AnsiString using Utf8ToString()


function InputUtf8OrDefault(const ParamName, DefaultValue: RawUtf8): RawUtf8;

Retrieve one input parameter from its URI name as RawUtf8
- returns supplied DefaultValue if the parameter is not found


function InputUtf8OrError(const ParamName: RawUtf8; out Value: RawUtf8; const ErrorMessageForMissingParameter: string = ''): boolean;

Retrieve one input parameter from its URI name as RawUtf8
- returns FALSE and call Error(ErrorMessageForMissingParameter) - which may be a resourcestring - if the parameter is not found; if ErrorMessageForMissingParameter is not set, a default message is used
- returns TRUE and set Value if the parameter is found


function IsRemoteAdministrationExecute: boolean;

True if called from TRestServer.AdministrationExecute


function UriWithoutInlinedParams: shortstring;

Same as Call^.Uri, but without the ?... ending
- will compute it from Call^.Url and fParameters
- since used for logging, return a shortstring and not a RawUtf8 to avoid memory allocation


function UriWithoutRoot: RawUtf8;

Same as Call^.Uri, after the 'root/' prefix, including '?' params
- will compute it from Call^.Url and Server.Model.RootLen


function UriWithoutSignature: RawUtf8;

Same as Call^.Uri, but without the &session_signature=... ending
- will compute it from Call^.Url and UriSessionSignaturePos


procedure AuthenticationFailed(Reason: TOnAuthenticationFailedReason); virtual;

Method called in case of authentication failure
- the failure origin is stated by the Reason parameter
- this default implementation will just set OutStatus := HTTP_FORBIDDEN and call TRestServer.OnAuthenticationFailed event (if any)
- is used internally


procedure ConfigurationRestMethod(SettingsStorage: TObject);

Implements a method-based service for live update of some settings
- should be called from a method-based service, e.g. Configuration()
- the settings are expected to be stored e.g. in a TSynAutoCreateFields instance, potentially with nested objects
- accept the following REST methods to read and write the settings:

 GET http://server:888/root/configuration
 GET http://server:888/root/configuration/propname
 GET http://server:888/root/configuration/propname?value=propvalue

- could be used e.g. as such:

 procedure TMyRestServerMethods.Configuration(Ctxt: TRestServerUriContext);
 begin //  http://server:888/myrestserver/configuration/name?value=newValue
   Ctxt.ConfigurationRestMethod(fSettings);
 end;

procedure Error(const ErrorMessage: RawUtf8 = ''; Status: integer = HTTP_BADREQUEST; CacheControlMaxAgeSec: integer = 0); override;

Use this method to send back an error to the caller
- overriden method with additional logging


procedure ExecuteCallback(var Ctxt: TJsonParserContext; ParamInterfaceInfo: TRttiJson; out Obj); virtual;

Event raised by ExecuteMethod() for interface parameters
- match TInterfaceMethodInternalExecuteCallback signature
- redirect to TServiceContainerServer.GetFakeCallback


procedure FillInput(const LogInputIdent: RawUtf8 = '');

Extract the input parameters from its URI (up to 512 params)
- you should not have to call this method directly, but rather all the InputInt/InputDouble/InputUtf8/InputExists/... properties
- may be useful if you want to access directly to InputPairs[] with no prior knowledge of the input parameter names
- you can specify a title text to optionally log the input array


procedure LogFromContext;

Low-level logging after service execution


procedure OutHeadFromCookie; override;

Low-level HTTP header merge of the OutSetCookie value
- this overriden method will handle rsoCookieIncludeRootPath option


procedure Prepare(aServer: TRestServer; const aCall: TRestUriParams); virtual;

Initialize the execution context
- this method could have been declared as protected, since it should never be called outside the TRestServer.Uri() method workflow
- should set Call, and Method members


procedure ReturnFileFromFolder(const FolderName: TFileName; Handle304NotModified: boolean = true; const DefaultFileName: TFileName = 'index.html'; const Error404Redirect: RawUtf8 = ''; CacheControlMaxAgeSec: integer = 0); override;

Use this method to send back a file from a local folder to the caller
- UriMethodPath value, as parsed from the URI, will contain the expected file name in the local folder, using DefaultFileName if the URI is void, and redirecting to Error404Redirect if the file is not found


procedure ServiceResult(const Name, JsonValue: RawUtf8);

Low-level process of the JSON result for a service execution


procedure ServiceResultEnd(WR: TJsonWriter; ID: TID); virtual;

Low-level closure of the JSON result for a service execution


procedure ServiceResultStart(WR: TJsonWriter); virtual;

Low-level preparation of the JSON result for a service execution


procedure StatsFromContext(Stats: TSynMonitorInputOutput; MicroSec: Int64);

Low-level statistics merge during service execution


property AuthSession: TAuthSession read fAuthSession write fAuthSession;

Low-level access to the associated Session
- may be nil depending on the context: you should NOT use it, but the safe Session, SessionGroup, SessionUser, SessionUserName fields instead
- is used internally


property Command: TRestServerUriContextCommand read fCommand;

The current execution command


property CustomErrorMsg: RawUtf8 read fCustomErrorMsg;

Optional error message which will be transmitted as JSON error (if set)
- contains e.g. TOnAuthenticationFailedReason text during TRestServer.OnAuthenticationFailed event call, or the reason of a TRestServer.RecordCanBeUpdated failure


property ForceServiceResultAsJsonObject: boolean read fForceServiceResultAsJsonObject;

Force the interface-based service methods to return a JSON object
- default behavior is to follow Service.ResultAsJsonObject property value (which own default is to return a more convenient JSON array)
- if set to TRUE, this execution context will FORCE the method to return a JSON object, even if Service.ResultAsJsonObject=false: this may be handy when the method is executed from a JavaScript content


property ForceServiceResultAsJsonObjectWithoutResult: boolean read fForceServiceResultAsJsonObjectWithoutResult;

Force the interface-based service methods to return a plain JSON object
- i.e. '{....}' instead of '{"result":{....}}'
- only set if ForceServiceResultAsJsonObject=TRUE and if no ID is about to be returned
- could be used e.g. for stateless interaction with a (non mORMot) stateless JSON REST Server


property ForceServiceResultAsXMLObject: boolean read fForceServiceResultAsXMLObject;

Force the interface-based service methods to return a XML object
- default behavior is to follow Service.ResultAsJsonObject property value (which own default is to return a more convenient JSON array)
- if set to TRUE, this execution context will FORCE the method to return a XML object, by setting ForceServiceResultAsJsonObject then converting the resulting JSON object into the corresponding XML via JsonBufferToXML()
- TRestServerUriContext.InternalExecuteSoaByInterface will inspect the Accept HTTP header to check if the answer should be XML rather than JSON


property ForceServiceResultAsXMLObjectNameSpace: RawUtf8 read fForceServiceResultAsXMLObjectNameSpace;

Specify a custom name space content when returning a XML object
- default behavior is to follow Service.ResultAsXMLObjectNameSpace property (which is void by default)
- service may set e.g. XMLUTF8_NAMESPACE, which will append <content ...> </content> around the generated XML data, to avoid validation problems or set a particular XML name space, depending on the application


property Input[const ParamName: RawUtf8]: variant read GetInput;

Retrieve one input parameter from its URI name as variant
- if the parameter value is text, it is stored in the variant as a RTL string content: so before Delphi 2009, you may loose some characters at decoding from UTF-8 input buffer
- raise an EParsingException if the parameter is not found


property InputAllowDouble: boolean read fInputAllowDouble write fInputAllowDouble;

If Input[] InputOrVoid[] InputOrError() variants could be double


property InputDouble[const ParamName: RawUtf8]: double read GetInputDouble;

Retrieve one input parameter from its URI name as double
- raise an EParsingException if the parameter is not found


property InputDoubleOrVoid[const ParamName: RawUtf8]: double read GetInputDoubleOrVoid;

Retrieve one input parameter from its URI name as double
- returns 0 if the parameter is not found


property InputExists[const ParamName: RawUtf8]: boolean read GetInputExists;

Return TRUE if the input parameter is available at URI
- even if InputUtf8['param']='', there may be '..?param=&another=2'


property InputHexaOrVoid[const ParamName: RawUtf8]: cardinal read GetInputHexaOrVoid;

Retrieve one hexadecimal input parameter from its URI name as cardinal
- returns 0 if the parameter is not found


property InputInt[const ParamName: RawUtf8]: Int64 read GetInputInt;

Retrieve one input parameter from its URI name as Int64
- raise an EParsingException if the parameter is not found


property InputIntOrVoid[const ParamName: RawUtf8]: Int64 read GetInputIntOrVoid;

Retrieve one input parameter from its URI name as Int64
- returns 0 if the parameter is not found


property InputOrVoid[const ParamName: RawUtf8]: variant read GetInputOrVoid;

Retrieve one input parameter from its URI name as variant
- if the parameter value is text, it is stored in the variant as a RawUtf8: so before Delphi 2009, you won't loose any Unicode character, but you should convert its value to AnsiString using Utf8ToString()
- returns Unassigned if the parameter is not found


property InputPairs: TRawUtf8DynArray read fInput;

Low-level access to the input parameters, stored as pairs of UTF-8
- even items are parameter names, odd are values
- Input*[] properties should have been called previously to fill the internal array, or by calling FillInput if you do not know the input parameters which may appear


property InputString[const ParamName: RawUtf8]: string read GetInputString;

Retrieve one input parameter from its URI name as a RTL string
- raise an EParsingException if the parameter is not found
- prior to Delphi 2009, some Unicode characters may be missing in the returned AnsiString value


property InputStringOrVoid[const ParamName: RawUtf8]: string read GetInputStringOrVoid;

Retrieve one input parameter from its URI name as a RTL string
- returns '' if the parameter is not found
- prior to Delphi 2009, some Unicode characters may be missing in the returned AnsiString value


property InputUtf8[const ParamName: RawUtf8]: RawUtf8 read GetInputUtf8;

Retrieve one input parameter from its URI name as RawUtf8
- raise an EParsingException if the parameter is not found


property InputUtf8OrVoid[const ParamName: RawUtf8]: RawUtf8 read GetInputUtf8OrVoid;

Retrieve one input parameter from its URI name as RawUtf8
- returns '' if the parameter is not found


property Log: TSynLog read fLog;

Associated logging instance for the current thread on the server
- you can use it to log some process on the server side


property MethodIndex: integer read fMethodIndex;

The index of the callback published method within the internal class list


property MicroSecondsElapsed: QWord read fMicroSecondsElapsed;

High-resolution timimg of the execution command, in micro-seconds
- only set when TRestServer.Uri finished, available e.g. for OnAfterUri


property MicroSecondsStart: Int64 read fMicroSecondsStart;

High-resolution start of the execution command, in micro-seconds


property Parameters: PUtf8Char read fParameters;

URI inlined parameters position within Call^.Url, just after trailing '?'
- use UrlDecodeValue*() functions to retrieve the values
- for mPOST requests, will also be filled from a WEB form body, i.e.

 application/x-www-form-urlencoded

- use InputAsMultiPart() for multipart/form-data decoding


property ResourceFileName: TFileName read GetResourceFileName;

Compute the file name corresponding to the URI
- e.g. '/root/methodname/toto/index.html' will return 'toto\index.html'


property Server: TRestServer read fServer;

The associated TRestServer instance which executes its URI method


property Service: TServiceFactory read fService write fService;

The service identified by an interface-based URI
- is in fact a TServiceFactoryServer instance


property ServiceExecution: PServiceFactoryExecution read fServiceExecution write fServiceExecution;

The current execution context of an interface-based service
- maps to

 Service.fExecution[ServiceMethodIndex - SERVICE_PSEUDO_METHOD_COUNT]

property ServiceExecutionOptions: TInterfaceMethodOptions read fServiceExecutionOptions write fServiceExecutionOptions;

The current execution options of an interface-based service
- contains a local copy of ServiceExecution.Options, adding eventual optNoLogInput/optNoLogOutput for TInterfaceFactory.RegisterUnsafeSpiType


property ServiceInstanceID: TID read fServiceInstanceID write fServiceInstanceID;

The instance ID for interface-based services instance
- can be e.g. the sicPerSession session ID, the sicPerThread thread ID, or the sicClientDriven field as decoded by UriDecodeSoaByInterface


property ServiceMethod: PInterfaceMethod read fServiceMethod write fServiceMethod;

Access to the raw information of an interface-based URI
- equals nil if ServiceMethodIndex is within 0..3 (pseudo-methods)


property ServiceMethodIndex: integer read fServiceMethodIndex write fServiceMethodIndex;

The method index for an interface-based service
- filled if Service is not nil
- as retrieved by Service.ServiceMethodIndex(), i.e. 0..3 as internal _free_/_contract_/_signature_/_instance_ pseudo-methods or in InterfaceFactory.Methods[ServiceMethodIndex-SERVICE_PSEUDO_METHOD_COUNT]


property ServiceParameters: PUtf8Char read fServiceParameters write fServiceParameters;

The JSON array of parameters for an the interface-based service
- Service member has already be retrieved from URI (so is not nil)


property Session: cardinal read fSession write fSession;

The corresponding session TAuthSession.IDCardinal value
- equals 0 (CONST_AUTHENTICATION_SESSION_NOT_STARTED) if the session is not started yet - i.e. if still in handshaking phase
- equals 1 (CONST_AUTHENTICATION_NOT_USED) if authentication mode is not enabled - i.e. if TRestServer.HandleAuthentication = FALSE


property SessionGroup: TID read fSessionGroup write fSessionGroup;

The corresponding TAuthSession.User.GroupRights.ID value
- is undefined if Session is 0 or 1 (no authentication running)


property SessionOS: TOperatingSystemVersion read fSessionOS write fSessionOS;

The corresponding TAuthSession.RemoteOsVersion
- is undefined if Session is 0 or 1 (no authentication running) or if the client was not using TRestClientAuthenticationDefault scheme


property SessionUser: TID read fSessionUser write fSessionUser;

The corresponding TAuthSession.User.ID value
- is undefined if Session is 0 or 1 (no authentication running)


property SessionUserName: RawUtf8 read fSessionUserName write fSessionUserName;

The corresponding TAuthSession.User.LogonName value
- is undefined if Session is 0 or 1 (no authentication running)


property StaticKind: TRestServerKind read fStaticKind;

The kind of static instance corresponding to the associated Table (if any)


property StaticOrm: TRestOrm read fStaticOrm;

The static instance corresponding to the associated Table (if any)


property Table: TOrmClass read fTable;

The Table as specified at the URI level (if any)


property TableEngine: TRestOrm read fTableEngine;

The RESTful instance implementing the Table specified at the URI level (if any)
- equals the Server field most of the time, but may be an TRestStorage for any in-memory/MongoDB/virtual instance


property TableID: TID read fTableID;

The associated TOrm.ID, as decoded from URI scheme
- this property will be set from incoming URI, even if RESTful authentication is not enabled


property TableIndex: integer read fTableIndex;

The index in the Model of the Table specified at the URI level (if any)


property TableModelProps: TOrmModelProperties read fTableModelProps;

The RTTI properties of the Table specified at the URI level (if any)


property ThreadServer: PServiceRunningContext read fThreadServer;

Just a wrapper over ServiceRunningContext function result
- avoid a call to the threadvar resolution


property UriBlobFieldName: RawUtf8 read fUriMethodPath;

May be used in old method-based service callbacks


property UriMethodPath: RawUtf8 read fUriMethodPath;

The URI after the method service name, excluding the '?' parameters
- as set by TRestTreeNode.LookupParam from <path:fulluri> place holder


property UriSessionSignaturePos: integer read fUriSessionSignaturePos;

Position of the &session_signature=... text in Call^.Url string


1.3.5. TRestServerMethod

TRestServerMethod = record

Description of a method-based service


ByPassAuthentication: boolean;

Set to TRUE disable Authentication check for this method
- use TRestServer.ServiceMethodByPassAuthentication() method


CallBack: TOnRestServerCallBack;

The event which will be executed for this method


Methods: TUriMethods;

The allowed HTTP methods on this service


Name: RawUtf8;

The method name


Stats: TSynMonitorInputOutput;

Detailed statistics associated with this method


1.3.6. TRestServerRoutingJsonRpc

TRestServerRoutingJsonRpc = class(TRestServerUriContext)

Calling context for a TOnRestServerCallBack using JSON/RPC for interface-based services
- see also TRestClientRoutingRest alternative (and default) class
- in this routing scheme, the URI will define the interface, then the method name will be inlined with parameters, e.g.

 POST /root/Calculator
 (...)
 {"method":"Add","params":[1,2]}

or, for a sicClientDriven mode service:

 POST /root/ComplexNumber
 (...)
 {"method":"Add","params":[20,30],"id":1234}

class function ClientRouting: TRestClientRoutingClass; override;

The associated routing class on the client side
- this overriden method returns TRestClientRoutingJsonRpc


1.3.7. TRestServerRoutingRest

TRestServerRoutingRest = class(TRestServerUriContext)

Calling context for a TOnRestServerCallBack using our default simple REST routing for interface-based services
- see also TRestClientRoutingJsonRpc alternative class
- this class will use RESTful routing for interface-based services: method name will be identified within the URI, as

 /Model/Interface.Method[/ClientDrivenID]

e.g. for ICalculator.Add:

 POST /root/Calculator.Add
 (...)
 [1,2]

or, for a sicClientDriven mode service:

 POST /root/ComplexNumber.Add/1234
 (...)
 [20,30]

in this case, the sent content will be a JSON array of [parameters...]
- as an alternative, input parameters may be encoded at URI level (with a size limit depending on the HTTP routers, whereas there is no such limitation when they are transmitted as message body)
- one benefit of having .../ClientDrivenID encoded at URI is that it will be more secured in our RESTful authentication scheme: each method and even client driven session will be signed individualy


class function ClientRouting: TRestClientRoutingClass; override;

The associated routing class on the client side
- this overriden method returns TRestClientRoutingRest


1.3.8. TAuthSessionParent

TAuthSessionParent = class(TSynPersistent)

Used for efficient TAuthSession.IDCardinal comparison


1.3.9. TAuthSession

TAuthSession = class(TAuthSessionParent)

Class used to maintain in-memory sessions
- this is not a TOrm table so won't be remotely accessible, for performance and security reasons
- the User field is a true instance, copy of the corresponding database content (for better speed)
- you can inherit from this class, to add custom session process


constructor Create(aCtxt: TRestServerUriContext; aUser: TAuthUser); reintroduce; virtual;

Initialize a session instance with the supplied TAuthUser instance
- this aUser instance will be handled by the class until Destroy
- raise an exception on any error
- on success, will also retrieve the aUser.Data BLOB field content


constructor CreateFrom(var Read: TFastReader; Server: TRestServer; tix: Int64); virtual;

Initialize a session instance from some persisted buffer
- following the TRestServer.SessionsSaveToFile binary layout


destructor Destroy; override;

Will release the User and User.GroupRights instances


procedure NotifyInterfaces(aCtxt: TRestServerUriContext; aElapsed: Int64);

Update the Interfaces[] statistics


property AccessRights: TOrmAccessRights read fAccessRights;

Copy of the associated user access rights
- extracted from User.TAuthGroup.OrmAccessRights


property ConnectionID: TRestConnectionID read fConnectionID;

The low-level ConnectionID of the connection initiating this session


property GroupID: TID read GetGroupID;

The associated Group ID, as in User.GroupRights.ID


property ID: cardinal read fID;

The session ID number, as numerical value
- never equals to 1 (CONST_AUTHENTICATION_NOT_USED, i.e. authentication mode is not enabled), nor 0 (CONST_AUTHENTICATION_SESSION_NOT_STARTED, i.e. session still in handshaking phase)


property Interfaces: TSynMonitorInputOutputObjArray read fInterfaces write fInterfaces;

Per-session statistics about interface-based services
- Interfaces[] follows TRestServer.Services.fListInterfaceMethod[] array
- is initialized and maintained only if mlSessions is defined in TRestServer.StatLevels property


property Methods: TSynMonitorInputOutputObjArray read fMethods;

Per-session statistics about method-based services
- Methods[] follows TRestServer.fPublishedMethod[] array
- is initialized and maintained only if mlSessions is defined in TRestServer.StatLevels property


property PrivateKey: RawUtf8 read fPrivateKey;

The hexadecimal private key as returned to the connected client as 'SessionID+PrivateKey'


property RemoteIP: RawUtf8 read fRemoteIP;

The remote IP, if any
- is extracted from SentHeaders properties


property RemoteOS: RawUtf8 read GetRemoteOS;

The client Operating System, if sent from a mORMot 2 client
- is extracted from 'clientnonce' by TRestServerAuthenticationDefault.Auth into RemoteOsVersion 32-bit flags
- returns e.g. 'Windows 11 64-bit 22000' or 'Debian 5.4.0'


property RemoteOsVersion: TOperatingSystemVersion read fRemoteOsVersion;

The Client Operating System
- as extracted from 'clientnonce' by TRestServerAuthenticationDefault.Auth


property SentHeaders: RawUtf8 read fSentHeaders;

The transmitted HTTP headers, if any
- can contain e.g. 'RemoteIp: 127.0.0.1' or 'User-Agent: Mozilla/4.0'


property TimeoutShr10: cardinal read fTimeOutShr10;

The timestamp (in numbers of 1024 ms) until a session is kept alive
- extracted from User.TAuthGroup.SessionTimeout
- is used for fast comparison with GetTickCount64 shr 10


property TimeOutTix: cardinal read fTimeOutTix;

Set by the Access() method to the current GetTickCount64 shr 10 timestamp + TimeoutSecs


property User: TAuthUser read fUser;

The associated User
- this is a true TAuthUser instance, and User.GroupRights will contain also a true TAuthGroup instance


property UserID: TID read GetUserID;

The associated User ID, as in User.ID


property UserName: RawUtf8 read GetUserName;

The associated User Name, as in User.LogonName


1.3.10. TRestServerAuthentication

TRestServerAuthentication = class(TSynLocked)

Abstract class used to implement server-side authentication in TRestServer
- inherit from this class to implement expected authentication scheme
- each TRestServerAuthentication class is associated with a TRestClientAuthentication class from mormot.rest.client.pas


constructor Create(aServer: TRestServer); reintroduce; virtual;

Initialize the authentication method to a specified server
- you can define several authentication schemes for the same server


function Auth(Ctxt: TRestServerUriContext): boolean; virtual; abstract;

Called by the Server to implement the Auth RESTful method
- overridden method shall return TRUE if the request has been handled
- returns FALSE to let the next registered TRestServerAuthentication class to try implementing the content
- Ctxt.Parameters has been tested to contain an UserName=... value
- method execution is protected by TRestServer.Sessions.WriteLock


function RetrieveSession( Ctxt: TRestServerUriContext): TAuthSession; virtual; abstract;

Called by the Server to check if the execution context match a session
- returns a session instance corresponding to the remote request, and fill Ctxt.Session* members according to in-memory session information
- returns nil if this remote request does not match this authentication
- method execution is protected by TRestServer.Sessions.Safe


property Options: TRestServerAuthenticationOptions read fOptions write fOptions;

Allow to tune the authentication process
- default value is [saoUserByLogonOrID]


1.3.11. TRestServerAuthenticationUri

TRestServerAuthenticationUri = class(TRestServerAuthentication)

Weak authentication scheme using URL-level parameter


function RetrieveSession( Ctxt: TRestServerUriContext): TAuthSession; override;

Will check URI-level signature
- retrieve the session ID from 'session_signature=...' parameter
- method execution is protected by TRestServer.Sessions.ReadOnlyLock


1.3.12. TRestServerAuthenticationSignedUri

TRestServerAuthenticationSignedUri = class(TRestServerAuthenticationUri)

Secure authentication scheme using URL-level digital signature
- match TRestClientAuthenticationSignedUri on Client side
- for instance, default suaCRC32 format of session_signature is

Hexa8(SessionID)+
Hexa8(Timestamp)+
Hexa8(crc32('SessionID+HexaSessionPrivateKey'+Sha256('salt'+PassWord)+
            Hexa8(Timestamp)+url))

constructor Create(aServer: TRestServer); override;

Initialize the authentication method to a specified server


function RetrieveSession( Ctxt: TRestServerUriContext): TAuthSession; override;

Will check URI-level signature
- check session_signature=... parameter to be a valid digital signature
- method execution is protected by TRestServer.Sessions.ReadOnlyLock


property Algorithm: TRestAuthenticationSignedUriAlgo write SetAlgorithm;

Customize the session_signature signing algorithm
- you need to set this value on the server side only; those known algorithms will be recognized by TRestClientUri on the client side during the session handshake, to select the matching ComputeSignature function


property ComputeSignature: TOnRestAuthenticationSignedUriComputeSignature read fComputeSignature write fComputeSignature;

Customize the session_signature signing algorithm with a specific function
- the very same function should be set on TRestClientUri
- to select a known hash algorithm, you may change the Algorithm property


property NoTimestampCoherencyCheck: boolean read fNoTimestampCoherencyCheck write SetNoTimestampCoherencyCheck;

Allow any order when creating sessions
- by default, signed sessions are expected to be sequential, and new signed session signature can't be older in time than the last one, with a tolerance of TimestampCoherencySeconds
- but if your client is asynchronous (e.g. for AJAX requests), session may be rejected due to the delay involved on the client side: you can set this property to TRUE to enabled a weaker but more tolerant behavior

 (aServer.AuthenticationRegister(TRestServerAuthenticationDefault) as
   TRestServerAuthenticationSignedUri).NoTimestampCoherencyCheck := true;

property TimestampCoherencySeconds: cardinal read fTimestampCoherencySeconds write SetTimestampCoherencySeconds;

Time tolerance in seconds for the signature timestamps coherency check
- by default, signed sessions are expected to be sequential, and new signed session signature can't be older in time than the last one, with a tolerance time defined by this property
- default value is 5 seconds, which cover most kind of clients (AJAX or WebSockets), even over a slow Internet connection


1.3.13. TRestServerAuthenticationDefault

TRestServerAuthenticationDefault = class(TRestServerAuthenticationSignedUri)

MORMot secure RESTful authentication scheme on Server
- match TRestClientAuthenticationDefault on Client side
- this method will use a password stored via safe SHA-256 hashing in the TAuthUser ORM table


function Auth(Ctxt: TRestServerUriContext): boolean; override;

Will try to handle the Auth RESTful method with mORMot authentication
- to be called in a two pass "challenging" algorithm:

 GET ModelRoot/auth?UserName=...
  -> returns an hexadecimal nonce contents (valid for 5 minutes)
 GET ModelRoot/auth?UserName=...&PassWord=...&ClientNonce=...
 -> if password is OK, will open the corresponding session
    and return 'SessionID+HexaSessionPrivateKey'

The Password parameter as sent for the 2nd request will be computed as

 Sha256(ModelRoot+Nonce+ClientNonce+UserName+Sha256('salt'+PassWord))

- the returned HexaSessionPrivateKey content will identify the current user logged and its corresponding session (the same user may have several sessions opened at once, each with its own private key)
- then the private session key must be added to every query sent to the server as a session_signature=???? parameter, which will be computed as such:

 ModelRoot/url?A=1&B=2&session_signature=012345670123456701234567

were the session_signature= parameter will be computed as such:

 Hexa8(SessionID)+Hexa8(Timestamp)+
 Hexa8(crc32('SessionID+HexaSessionPrivateKey'+Sha256('salt'+PassWord)+
  Hexa8(Timestamp)+url))
 with url='ModelRoot/url?A=1&B=2'

this query authentication uses crc32 for hashing instead of SHA-256 in in order to lower the Server-side CPU consumption; the salted password (i.e. TAuthUser.PasswordHashHexa) and client-side Timestamp are inserted inside the session_signature calculation to prevent naive man-in-the-middle attack (MITM)
- the session ID will be used to retrieve the rights associated with the user which opened the session via a successful call to the Auth service
- when you don't need the session any more (e.g. if the TRestClientUri instance is destroyed), you can call the service as such:

 GET ModelRoot/auth?UserName=...&Session=...

- for a way of computing SHA-256 in JavaScript, see for instance @http://www.webtoolkit.info/javascript-sha256.html


1.3.14. TRestServerAuthenticationNone

TRestServerAuthenticationNone = class(TRestServerAuthenticationUri)

MORMot weak RESTful authentication scheme
- match TRestClientAuthenticationNone on Client side
- this method will authenticate with a given username, but no signature
- on client side, this scheme is not called by TRestClientUri.SetUser() method - so you have to write:

 TRestServerAuthenticationNone.ClientSetUser(Client,'User','');

function Auth(Ctxt: TRestServerUriContext): boolean; override;

Will try to handle the Auth RESTful method with mORMot authentication
- to be called in a weak one pass request:

 GET ModelRoot/auth?UserName=...
 -> if the specified user name exists, will open the corresponding
    session and return 'SessionID+HexaSessionPrivateKey'

1.3.15. TRestServerAuthenticationHttpAbstract

TRestServerAuthenticationHttpAbstract = class(TRestServerAuthentication)

Abstract class for implementing HTTP authentication
- do not use this abstract class, but e.g. TRestServerAuthenticationHttpBasic
- this class will transmit the session_signature as HTTP cookie, not at URI level, so is expected to be used only from browsers or old clients


function RetrieveSession(Ctxt: TRestServerUriContext): TAuthSession; override;

Will check the caller signature
- retrieve the session ID from "Cookie: mORMot_session_signature=..." HTTP header
- method execution is protected by TRestServer.Sessions.ReadOnlyLock


1.3.16. TRestServerAuthenticationHttpBasic

TRestServerAuthenticationHttpBasic = class(TRestServerAuthenticationHttpAbstract)

Authentication using HTTP Basic scheme
- match TRestClientAuthenticationHttpBasic on Client side
- this protocol send both name and password as clear (just Base64 encoded) so should only be used over TLS / HTTPS, or for compatibility reasons
- will rely on TRestServerAuthenticationNone for authorization
- on client side, this scheme is not called by TRestClientUri.SetUser() method - so you have to write:

 TRestServerAuthenticationHttpBasic.ClientSetUser(Client,'User','password');

- for a remote proxy-only authentication (without creating any mORMot session), you can write:

 TRestServerAuthenticationHttpBasic.ClientSetUserHttpOnly(Client,'proxyUser','proxyPass');

function Auth(Ctxt: TRestServerUriContext): boolean; override;

Handle the Auth RESTful method with HTTP Basic
- will first return HTTP_UNAUTHORIZED (401), then expect user and password to be supplied as incoming "Authorization: Basic ...." headers


function RetrieveSession(Ctxt: TRestServerUriContext): TAuthSession; override;

Will check URI-level signature
- retrieve the session ID from 'session_signature=...' parameter
- will also check incoming "Authorization: Basic ...." HTTP header
- method execution should be protected by TRestServer.fSessions.Lock


1.3.17. TRestServerAuthenticationSspi

TRestServerAuthenticationSspi = class(TRestServerAuthenticationSignedUri)

Authentication of the current logged user using Windows Security Support Provider Interface (SSPI) or the GSSAPI library on Linux
- is able to authenticate the currently logged user on the client side, using either NTLM (Windows only) or Kerberos - it will allow to safely authenticate on a mORMot server without prompting the user to enter its password
- if ClientSetUser() receives aUserName as '', aPassword should be either '' if you expect NTLM authentication to take place, or contain the SPN registration (e.g. 'mymormotservice/myserver.mydomain.tld') for Kerberos authentication
- if ClientSetUser() receives aUserName as 'DomainName\UserName', then authentication will take place on the specified domain, with aPassword as plain password value
- this class is not available on some targets (e.g. Android)


constructor Create(aServer: TRestServer); override;

Initialize this SSPI/GSSAPI authentication scheme


destructor Destroy; override;

Finalize internal sspi/gssapi allocated structures


function Auth(Ctxt: TRestServerUriContext): boolean; override;

Will try to handle the RESTful authentication via SSPI/GSSAPI
- to be called in a two pass algorithm, used to cypher the password
- the client-side logged user will be identified as valid, according to a Windows SSPI API secure challenge


1.3.18. TRestServerMonitor

TRestServerMonitor = class(TSynMonitorServer)

Used for high-level statistics in TRestServer.Uri()


constructor Create(aServer: TRestServer); reintroduce;

Initialize the instance


destructor Destroy; override;

Finalize the instance


function NotifyThreadCount(delta: integer): integer;

Update and returns the CurrentThreadCount property
- this method is thread-safe


procedure NotifyOrm(aMethod: TUriMethod);

Update the Created/Read/Updated/Deleted properties
- this method is thread-safe


procedure NotifyOrmTable(TableIndex, DataSize: integer; Write: boolean; const MicroSecondsElapsed: QWord);

Update the per-table statistics
- this method is thread-safe


procedure ProcessSuccess(IsOutcomingFile: boolean);

Should be called when a task successfully ended
- thread-safe method


property Created: TSynMonitorCount64 read fCreated;

How many Create / Add ORM operations did take place


property CurrentThreadCount: TSynMonitorOneCount read fCurrentThreadCount;

Number of current declared threads count
- as registered by BeginCurrentThread/EndCurrentThread


property Deleted: TSynMonitorCount64 read fDeleted;

How many Delete ORM operations did take place


property OutcomingFiles: TSynMonitorCount64 read fOutcomingFiles;

Count of files transmitted directly (not part of Output size property)
- i.e. when the service uses STATICFILE_CONTENT_TYPE/HTTP_RESP_STATICFILE as content type to let the HTTP server directly serve the file content


property Read: TSynMonitorCount64 read fRead;

How many Read / Get ORM operations did take place


property ServiceInterface: TSynMonitorCount64 read fServiceInterface;

Count of the remote interface-based service calls


property ServiceMethod: TSynMonitorCount64 read fServiceMethod;

Count of the remote method-based service calls


property StartDate: RawUtf8 read fStartDate;

When this monitoring instance (therefore the server) was created


property Success: TSynMonitorCount64 read fSuccess;

Number of valid responses
- i.e. which returned status code 200/HTTP_SUCCESS or 201/HTTP_CREATED
- any invalid request will increase the TSynMonitor.Errors property


property Updated: TSynMonitorCount64 read fUpdated;

How many Update ORM operations did take place


1.3.19. TOrmMonitorUsage

TOrmMonitorUsage = class(TOrmNoCaseExtended)

ORM table used to store TSynMonitorUsage information in TSynMonitorUsageRest
- the ID primary field is the TSynMonitorUsageID (accessible from UsageID public property) shifted by 16-bit (by default) to include a TSynUniqueIdentifierProcess value


function UsageID(aProcessIDShift: integer = 16): integer;

Compute the corresponding 23 bit TSynMonitorUsageID.Value time slice
- according to the stored Process field, after bit shift
- allows a custom aProcessIDShift if it is not set as default 16-bit


property Comment: RawUtf8 read fComment write fComment;

A custom text, which may be used e.g. by support or developpers


property Gran: TSynMonitorUsageGranularity read fGran write fGran;

The granularity of the statistics of this entry


property Info: variant read fInfo write fInfo;

The actual statistics information, stored as a TDocVariant JSON object


property Process: Int64 read fProcess write fProcess;

Identify which application is monitored
- match the lower bits of each record ID
- by default, is expected to be a TSynUniqueIdentifierProcess 16-bit value


1.3.20. TSynMonitorUsageRest

TSynMonitorUsageRest = class(TSynMonitorUsage)

Will store TSynMonitorUsage information in TOrmMonitorUsage ORM tables
- TOrm.ID will be the TSynMonitorUsageID shifted by ProcessIDShift bits


constructor Create(const aStorage: IRestOrm; aProcessID: Int64; aStoredClass: TOrmMonitorUsageClass = nil; aProcessIDShift: integer = 16); reintroduce; virtual;

Initialize storage via ORM
- if a 16-bit TSynUniqueIdentifierProcess is supplied, it will be used to identify the generating process by shifting TSynMonitorUsageID values by aProcessIDShift bits (default 16 but you may increase it up to 40 bits)
- will use TOrmMonitorUsage table, unless another one is specified


destructor Destroy; override;

Finalize the process, saving pending changes


property ProcessID: Int64 read fProcessID;

How the information could be stored for several processes
- e.g. when several SOA nodes gather monitoring information in a shared (MongoDB) database
- is by default a TSynUniqueIdentifierProcess value, but may be any integer up to ProcessIDShift bits as set in Create()


property ProcessIDShift: integer read fProcessIDShift;

How process ID are stored within the mORMot TOrm.ID
- equals 16-bit by default, to match TSynUniqueIdentifierProcess resolution


property SaveBatch: TRestBatch read fSaveBatch write fSaveBatch;

You can set an optional Batch instance to speed up DB writing
- when calling the Modified() method


property StoredClass: TOrmMonitorUsageClass read fStoredClass;

The actual ORM class used for persistence


1.3.21. TRestTreeNodeData

TRestTreeNodeData = record

REST-specific context information, as stored in TRestTreeNode


Blob: TOrmPropInfoRttiRawBlob;

The ORM BLOB field definition for rnTableIDBlob


Command: TRestServerUriContextCommand;

The ORM/SOA TRestServer execution context


MethodIndex: SmallInt ;

The index of the associated method (16-bit is enough, -1 for none)
- for rn*Method*, in TRestServer.PublishedMethod[]
- for rnInterface*, in Service.InterfaceFactory.Methods[MethodIndex-4] or 0..3 for internal _free_/_contract_/_signature_/_instance_ pseudo-methods


Node: TRestNode;

Which kind of execution this node is about


Service: TServiceFactoryServerAbstract;

The interface-based service for rnInterface


Table: TOrmModelProperties;

The properties of the ORM class in the server TOrmModel for rnTable*


TableMain: TRestOrm;

The main engine of this Table ORM class - set at runtime


TableStatic: TRestOrm;

The static engine of this Table ORM class - set at runtime


TableStaticKind: TRestServerKind;

The static engine kind of this Table ORM class - set at runtime


1.3.22. TRestTreeNode

TRestTreeNode = class(TRadixTreeNodeParams)

Implement a Radix Tree node to hold one URI registration


Data: TRestTreeNodeData;

REST-specific context information, as cloned by Split()


function Split(const Text: RawUtf8): TRadixTreeNode; override;

Overriden to support the additional Data fields


1.3.23. ERestTree

ERestTree = class(ERadixTree)

Exception class raised during TRestTree URI parsing


1.3.24. TRestRouter

TRestRouter = class(TSynPersistent)

Efficient server-side URI routing for TRestServer


constructor Create(aOwner: TRestServer); reintroduce;

Initialize this URI routine engine


destructor Destroy; override;

Finalize this URI routing engine


function InfoText: RawUtf8;

Used by ComputeRoutes to log the current route registration state


function Lookup(Ctxt: TRestServerUriContext): TRestTreeNode;

Quickly search for the node corresponding to Ctxt.Method and Uri
- should never raise an exception


function Setup(aFrom: TUriMethod; const aUri: RawUtf8; aNode: TRestNode): TRestTreeNode; overload;

Register a given URI to the tree, for a given HTTP method
- 'modelroot/' will be prefixed to the supplied aUri


procedure Setup(aFrom: TUriMethods; const aUri: RawUtf8; aNode: TRestNode; aTable: TOrmModelProperties; aBlob: TOrmPropInfoRttiRawBlob = nil; aMethodIndex: integer = -1; aService: TServiceFactory = nil); overload;

Register a given URI to the tree, for a given HTTP method
- 'modelroot/' will be prefixed to the supplied aUri


property Tree: TRestRouterTree read fTree;

Access to the internal per-method TRestTree instance
- some Tree[] may be nil if the HTTP method has not been registered yet


1.3.25. TRestServerUriPagingParameters

TRestServerUriPagingParameters = record

Structure used to specify custom request paging parameters for TRestServer
- default values are the one used for YUI component paging (i.e. PAGINGPARAMETERS_YAHOO constant, as set by TRestServer.Create)
- warning: using paging can be VERY expensive on Server side, especially when used with external databases (since all data is retrieved before paging, when SQLite3 works in virtual mode)


Dir: RawUtf8;

Parameter name used to specify the request sort direction
- default value is 'DIR='
- note that any custom value should be uppercase and end with a '=' character


Results: RawUtf8;

Parameter name used to specify the request the page size (LIMIT clause)
- default value is 'RESULTS='
- note that any custom value should be uppercase and end with a '=' character


Select: RawUtf8;

Parameter name used to specify the request field names
- default value is 'SELECT='
- note that any custom value should be uppercase and end with a '=' character


SendTotalRowsCountFmt: RawUtf8;

Returned JSON field value of optional total rows count
- default value is '', i.e. no total rows count field
- computing total rows count can be very expensive, depending on the database back-end used (especially for external databases)
- can be set e.g. to ',"totalRows":%' value (note that the initial "," is expected by the produced JSON content, and % will be set with the value)


Sort: RawUtf8;

Parameter name used to specify the request sort order
- default value is 'SORT='
- note that any custom value should be uppercase and end with a '=' character


StartIndex: RawUtf8;

Parameter name used to specify the request starting offset
- default value is 'STARTINDEX='
- note that any custom value should be uppercase and end with a '=' character


Where: RawUtf8;

Parameter name used to specify the request WHERE clause
- default value is 'WHERE='
- note that any custom value should be uppercase and end with a '=' character


1.3.26. TRestServer

TRestServer = class(TRest)

Abstract REpresentational State Transfer (REST) server
- don't use this abstract class, but override and implement the protected EngineList() Retrieve() Add() Update() Delete() methods
- so if you want a REST server with no ORM (e.g. for a pure SOA server), use (or inherit) TRestServerFullMemory; if you want a REST server with tied ORM (with SQLite3 or any external DB), use TRestServerDB
- automatic call of this methods by a generic Uri() RESTful function
- any published method of descendants must match TOnRestServerCallBack prototype, and is expected to be thread-safe


OnAfterUri: TOnAfterUri;

Event trigerred when Uri() finished to process an ORM/SOA command
- the supplied Ctxt parameter will give access to the command which has been executed, e.g. via Ctxt.Call.OutStatus or Ctxt.MicroSecondsElapsed
- since this event will be executed by every TRestServer.Uri call, it should better not make any slow process (like accessing a remote DB)


OnAuthenticationFailed: TOnAuthenticationFailed;

This event handler will be executed when a session failed to initialize (DenyOfService attack?) or the request is not valid (ManIntheMiddle attack?)
- e.g. if the URI signature is invalid, or OnSessionCreate event handler aborted the session creation by returning TRUE (in this later case, the Session parameter is not nil)
- you can access the current execution context from the Ctxt parameter, e.g. to retrieve the caller's IP and ban aggressive users in Ctxt.RemoteIP or the text error message corresponding to Reason in Ctxt.CustomErrorMsg


OnAuthenticationUserRetrieve: TOnAuthenticationUserRetrieve;

A custom method to retrieve the TAuthUser instance for authentication
- will be called by TRestServerAuthentication.GetUser() instead of plain AuthUserClass.Create()


OnBeforeUri: TOnBeforeUri;

Event trigerred when Uri() is about to execute an ORM/SOA command
- the supplied Ctxt parameter will give access to the command about to be executed, e.g. Ctxt.Command=execSoaByInterface will identify a SOA service execution, with the corresponding Service and ServiceMethodIndex parameters as set by TRestServerUriContext.UriDecodeSoaByInterface
- should return TRUE if the method can be executed
- should return FALSE if the method should not be executed, and the callback should set the corresponding error to the supplied context e.g.

 Ctxt.Error('Unauthorized method',HTTP_NOTALLOWED);

- since this event will be executed by every TRestServer.Uri call, it should better not make any slow process (like accessing a remote DB)


OnErrorUri: TOnErrorUri;

Event trigerred when Uri() raise an exception and failed to process a request
- if Ctxt.ExecuteCommand raised an exception, this callback will be run with all neeed information
- should return TRUE to execute Ctxt.Error(E,...), FALSE if returned content has already been set as expected by the client


OnIdle: TNotifyEvent;

Event trigerred when Uri() is called, and at least 128 ms is elapsed
- could be used to execute some additional process after a period of time
- note that if TRestServer.Uri is not called by any client, this callback won't be executed either - consider using TRestServer.Run instead


OnInternalInfo: TOnInternalInfo;

Event to customize the information returned by root/timestamp/info
- called by TRestServer.InternalInfo method
- you can add some application-level information for monitoring


OnServiceCreateInstance: TOnServiceCreateInstance;

This event will be executed by TServiceFactoryServer.CreateInstance
- you may set a callback to customize a server-side service instance, i.e. inject class-level dependencies:

procedure TMyClass.OnCreateInstance(
  Sender: TServiceFactoryServer; Instance: TInterfacedObject);
begin
  if Sender.ImplementationClass=TLegacyStockQuery then
    TLegacyStockQuery(Instance).fDbConnection := fDbConnection;
end;

- consider using a TInjectableObjectClass implementation for pure IoC/DI


OnSessionClosed: TOnOrmSession;

A method can be specified to be notified when a session is closed
- for OnSessionClosed, the returning boolean value is ignored
- Ctxt is nil if the session is closed due to a timeout
- Ctxt is not nil if the session is closed explicitly by the client


OnSessionCreate: TOnOrmSession;

A method can be specified to be notified when a session is created
- for OnSessionCreate, returning TRUE will abort the session creation - and you can set Ctxt.Call^.OutStatus to a corresponding error code
- it could be used e.g. to limit the number of client sessions


OnStartUri: TOnStartUri;

Event trigerred when Uri start to process a request
- should return HTTP_SUCCESS (200) to continue, or an error code to abort
- could also change the Call fields on the fly, if needed


UriPagingParameters: TRestServerUriPagingParameters;

This property can be used to specify the URI parmeters to be used for paged queries
- is set by default to PAGINGPARAMETERS_YAHOO constant by TRestServer.Create() constructor


constructor Create(const aRoot: RawUtf8); reintroduce; overload;

Server initialization with a void Database Model and not authentication
- could be used e.g. for a interface-based services API REST server


constructor Create(aModel: TOrmModel; aHandleUserAuthentication: boolean = false); reintroduce; overload; virtual;

Server initialization with a specified Database Model
- if HandleUserAuthentication is false, will set URI access rights to 'Supervisor' (i.e. all R/W access) by default
- if HandleUserAuthentication is true, will add TAuthUser and TAuthGroup to the TOrmModel (if not already there)


constructor CreateWithOwnModel(const Tables: array of TOrmClass; aHandleUserAuthentication: boolean = false; const aRoot: RawUtf8 = 'root');

Server initialization with a temporary Database Model
- a Model will be created with supplied tables, and owned by the server
- if you instantiate a TRestServerFullMemory or TRestServerDB with this constructor, an in-memory engine will be created, with enough abilities to run regression tests, for instance


constructor RegisteredClassCreateFrom(aModel: TOrmModel; aDefinition: TSynConnectionDefinition; aServerHandleAuthentication: boolean); override;

Initialize REST server instance from a TSynConnectionDefinition


destructor Destroy; override;

Server finalization


function AuthenticationRegister( aMethod: TRestServerAuthenticationClass): TRestServerAuthentication; overload;

Call this method to add an authentication method to the server
- will return the just created TRestServerAuthentication instance, or the existing instance if it has already been registered
- you can use this method to tune the authentication, e.g. if you have troubles with AJAX asynchronous callbacks:

 (aServer.AuthenticationRegister(TRestServerAuthenticationDefault) as
   TRestServerAuthenticationDefault).NoTimestampCoherencyCheck := true;

or if you want to customize the session_signature parameter algorithm:

 (aServer.AuthenticationRegister(TRestServerAuthenticationDefault) as
   TRestServerAuthenticationDefault).Algorithm := suaMD5;

function BanIP(const aIP: RawUtf8; aRemoveBan: boolean = false): boolean;

(un)register a banned IPv4 value
- any connection attempt from this IP Address will be rejected by


function ExportServerGlobalLibraryRequest(Disable: boolean = false): boolean;

Grant access to this database content from a dll using the global LibraryRequest() function
- returns true if the LibraryRequest() function is implemented by this TRestServer, and TRestClientLibraryRequest can access it
- returns false if a TRestServer was already exported
- call with Disable=true to remove the LibraryRequest() function binding


function GetCurrentSessionUserID: TID; override;

Retrieve the current session TAuthUser.ID (if any) from the ServiceRunningContext threadvar


function GetRecordVersionMax(TableIndex: integer): TRecordVersion;

Read access to the TRestOrmServer.RecordVersionMax[TableIndex] property
- used internally by TServiceContainerServer for client/server synchronization


function JwtForUnauthenticatedRequestWhiteIP(const aIP: RawUtf8; aRemoveWhite: boolean = false): boolean;

(un)register a an IPv4 value to the JWT white list
- by default, a JWT validated by JwtForUnauthenticatedRequest will be accepted
- to avoid MiM (Man-In-the-Middle) attacks, if a JWT white list is defined using this method, any connection from a non registered IP will be rejected, even with a valid JWT
- WebSockets connections are secure enough to bypass this list


function OrmInstance: TRestOrm;

Main access to the class implementing IRestOrm methods for this instance
- used internally to avoid ORM: IRestOrm reference counting and enable inlining of most simple methods, if possible
- is a TRestOrmServer instance


function RecordVersionSynchronizeMasterStart( ByPassAuthentication: boolean = false): boolean;

Initiate asynchronous master/slave replication on a master TRest
- allow synchronization of a TOrm table, using its TRecordVersion field, for real-time master/slave replication on the master side
- this method will register the IServiceRecordVersion service on the server side, so that RecordVersionSynchronizeStartSlave() will be able to receive push notifications of any updates
- this method expects the communication channel to be bidirectional, e.g. a mormot.rest.http.server's TRestHttpServer in HTTP_BIDIR mode (either useBidirSocket or useBidirAsync - see WEBSOCKETS_DEFAULT_MODE)


function RecordVersionSynchronizeSlaveStart(Table: TOrmClass; MasterRemoteAccess: TRestClientUri; const OnNotify: TOnBatchWrite = nil): boolean;

Initiate asynchronous master/slave replication on a slave TRest
- start synchronization of a TOrm table, using its TRecordVersion field, for real-time master/slave replication on the slave side
- this method will first retrieve any pending modification by regular REST calls to RecordVersionSynchronizeSlave, then create and register a callback instance using RecordVersionSynchronizeSubscribeMaster()
- this method expects the communication channel to be bidirectional, e.g. a TRestHttpClientWebsockets
- the modifications will be pushed by the master, then applied to the slave storage, until RecordVersionSynchronizeSlaveStop method is called
- an optional OnNotify event may be defined, which will be triggered for all incoming change, supllying the updated TOrm instance


function RecordVersionSynchronizeSlaveStop(Table: TOrmClass): boolean;

Finalize asynchronous master/slave replication on a slave TRest
- stop synchronization of a TOrm table, using its TRecordVersion field, for real-time master/slave replication on the slave side
- expect a previous call to RecordVersionSynchronizeSlaveStart


function RecordVersionSynchronizeSubscribeMaster(Table: TOrmClass; RecordVersion: TRecordVersion; const SlaveCallback: IServiceRecordVersionCallback): boolean; overload;

Low-level callback registration for asynchronous master/slave replication
- you should not have to use this method, but rather RecordVersionSynchronizeMasterStart and RecordVersionSynchronizeSlaveStart RecordVersionSynchronizeSlaveStop methods
- register a callback interface on the master side, which will be called each time a write operation is performed on a given TOrm with a TRecordVersion field
- the callback parameter could be a TServiceRecordVersionCallback instance, which will perform all update operations as expected
- the callback process will be blocking for the ORM write point of view: so it should be as fast as possible, or asynchronous - note that regular callbacks using WebSockets, as implemented by mormot.net.ws.core.server and mormot.rest.http.server's TRestHttpServer in HTTP_BIDIR mode (either useBidirSocket or useBidirAsync - see WEBSOCKETS_DEFAULT_MODE) useBidirSocket/useBidirAsync mode
- if the supplied RecordVersion is not the latest on the server side, this method will return FALSE and the caller should synchronize again via RecordVersionSynchronize() to avoid any missing update
- if the supplied RecordVersion is the latest on the server side, this method will return TRUE and put the Callback notification in place


function ServiceContainer: TServiceContainer; override;

Access or initialize the internal IoC resolver
- overriden to create and initialize the internal TServiceContainerServer if no service interface has been registered yet


function ServiceDefine(aSharedImplementation: TInterfacedObject; const aInterfaces: array of TGuid; const aContractExpected: RawUtf8 = ''): TServiceFactoryServerAbstract; overload;

Register a Service instance on the server side
- this method expects the interface(s) to have been registered previously:

 TInterfaceFactory.RegisterInterfaces([TypeInfo(IMyInterface),...]);

- the supplied aSharedImplementation will be owned by this Server instance
- will return the first of the registered TServiceFactoryServerAbstract on success (i.e. corresponding to aInterfaces[0] - not to the others), or nil if registration failed (e.g. if any of the supplied interfaces is not implemented by the given class)


function ServiceDefine(aClient: TRest; const aInterfaces: array of TGuid; aInstanceCreation: TServiceInstanceImplementation = sicSingle; const aContractExpected: RawUtf8 = ''): boolean; overload;

Register a remote Service via its interface
- this method expects the interface(s) to have been registered previously:

 TInterfaceFactory.RegisterInterfaces([TypeInfo(IMyInterface),...]);

function ServiceDefine(aImplementationClass: TInterfacedClass; const aInterfaces: array of TGuid; aInstanceCreation: TServiceInstanceImplementation = sicSingle; const aContractExpected: RawUtf8 = ''): TServiceFactoryServerAbstract; overload;

Register a Service class on the server side
- this method expects the interface(s) to have been registered previously:

 TInterfaceFactory.RegisterInterfaces([TypeInfo(IMyInterface),...]);

- will return the first of the registered TServiceFactoryServerAbstract on success (i.e. corresponding to aInterfaces[0] - not to the others), or nil if registration failed (e.g. if any of the supplied interfaces is not implemented by the given class)


function ServiceMethodByPassAuthentication( const aMethodName: RawUtf8): integer;

Call this method to disable Authentication method check for a given published method-based service name
- by default, only Auth and Timestamp methods do not require the RESTful authentication of the URI; you may call this method to add another method to the list (e.g. for returning some HTML content from a public URI)
- if the supplied aMethodName='', all method-based services will bypass the authenticaton process
- returns the method index number


function ServiceMethodRegister(aMethodName: RawUtf8; const aEvent: TOnRestServerCallBack; aByPassAuthentication: boolean = false; aMethods: TUriMethods = [mGET, mPOST, mPUT, mDELETE]): PtrInt;

Direct registration of a method for a given low-level event handler
- returns the index in the fPublishedMethod[] internal array
- will use the supplied aMethods or detect '_VERB1_[_VERB2_][..]MethodName' pattern e.g. as '_GET_Info' or '_GET__DELETE_User'


function ServiceRegister(aSharedImplementation: TInterfacedObject; const aInterfaces: array of PRttiInfo; const aContractExpected: RawUtf8 = ''): TServiceFactoryServerAbstract; overload; virtual;

Register a Service instance on the server side
- this methods expects a class instance to be supplied, and the exact list of interfaces to be registered to the server (e.g. [TypeInfo(IMyInterface)]) and implemented by this shared instance
- as a consequence, instance implementation pattern will always be sicShared
- will return the first of the registered TServiceFactoryServer created on success (i.e. the one corresponding to the first item of the aInterfaces array), or nil if registration failed (e.g. if any of the supplied interfaces is not implemented by the given class)
- the same implementation class can be used to handle several interfaces (just as Delphi allows to do natively)
- will return the first of the registered TServiceFactoryServerAbstract on success (i.e. corresponding to aInterfaces[0] - not to the others), or nil if registration failed (e.g. if any of the supplied interfaces is not implemented by the given class)


function ServiceRegister(aImplementationClass: TInterfacedClass; const aInterfaces: array of PRttiInfo; aInstanceCreation: TServiceInstanceImplementation = sicSingle; const aContractExpected: RawUtf8 = ''): TServiceFactoryServerAbstract; overload; virtual;

Register a Service class on the server side
- this methods expects a class to be supplied, and the exact list of interfaces to be registered to the server (e.g. [TypeInfo(IMyInterface)]) and implemented by this class
- class can be any TInterfacedObject, but TInterfacedObjectWithCustomCreate can be used if you need an overridden constructor
- instance implementation pattern will be set by the appropriate parameter
- will return the first of the registered TServiceFactoryServer created on success (i.e. the one corresponding to the first item of the aInterfaces array), or nil if registration failed (e.g. if any of the supplied interfaces is not implemented by the given class)
- the same implementation class can be used to handle several interfaces (just as Delphi allows to do natively)
- will return the first of the registered TServiceFactoryServerAbstract on success (i.e. corresponding to aInterfaces[0] - not to the others), or nil if registration failed (e.g. if any of the supplied interfaces is not implemented by the given class)


function ServiceRegister(aClient: TRest; const aInterfaces: array of PRttiInfo; aInstanceCreation: TServiceInstanceImplementation = sicSingle; const aContractExpected: RawUtf8 = ''): boolean; overload; virtual;

Register a remote Service via its interface
- this overloaded method will register a remote Service, accessed via the supplied TRest/TRestClientUri instance: it can be available in the main TRestServer.Services property, but execution will take place on a remote server - may be used e.g. for dedicated hosting of services (in a DMZ for instance)
- this methods expects a list of interfaces to be registered to the client (e.g. [TypeInfo(IMyInterface)])
- instance implementation pattern will be set by the appropriate parameter
- will return true on success, false if registration failed (e.g. if any of the supplied interfaces is not correct or is not available on the server)
- that is, server side will be called to check for the availability of each interface
- you can specify an optional custom contract for the first interface


function ServicesPublishedInterfaces: RawUtf8;

Compute a JSON description of all available services, and its public URI
- the JSON object matches the TServicesPublishedInterfaces record type
- used by TRestClientUri.ServicePublishOwnInterfaces to register all the services supported by the client itself
- warning: the public URI should have been set via SetPublicUri()


function SessionGetUser(aSessionID: cardinal): TAuthUser;

Returns a copy of the user associated to a session ID
- returns nil if the session does not exist (e.g. if authentication disabled)
- caller MUST release the TAuthUser instance returned (if not nil)
- this method IS thread-safe, calling internally Sessions.Safe.ReadOnlyLock (the returned TAuthUser is a private copy from Sessions[].User instance, in order to be really thread-safe)
- the returned TAuthUser instance will have GroupRights=nil but will have ID, LogonName, DisplayName, PasswordHashHexa and Data fields available


function SessionsAsJson: RawJson;

Retrieve all current session information as a JSON array


function SleepOrShutdown(MS: integer): boolean;

Wait for the specified number of milliseconds
- if Shutdown is called in-between, returns true
- if the thread waited the supplied time, returns false


procedure Auth(Ctxt: TRestServerUriContext);

REST service accessible from ModelRoot/Auth URI
- called by the clients for authentication and session management
- this method won't require an authenticated client, since it is used to initiate authentication
- this global callback method is thread-safe


procedure AuthenticationRegister( const aMethods: array of TRestServerAuthenticationClass); overload;

Call this method to add several authentication methods to the server
- if TRestServer.Create() constructor is called with aHandleUserAuthentication set to TRUE, it will register the two following classes:

 AuthenticationRegister([
   TRestServerAuthenticationDefault, TRestServerAuthenticationSspi]);

procedure AuthenticationUnregister( aMethod: TRestServerAuthenticationClass); overload;

Call this method to remove an authentication method to the server


procedure AuthenticationUnregister( const aMethods: array of TRestServerAuthenticationClass); overload;

Call this method to remove several authentication methods to the server


procedure AuthenticationUnregisterAll;

Call this method to remove all authentication methods to the server


procedure Batch(Ctxt: TRestServerUriContext);

REST service accessible from the ModelRoot/Batch URI
- will execute a set of RESTful commands, in a single step, with optional automatic SQL transaction generation
- this method will require an authenticated client, for safety
- expect input as JSON commands:

 '{"Table":["cmd":values,...]}'

or for multiple tables:

 '["cmd@Table":values,...]'

with cmd in POST/PUT with {object} as value or DELETE with ID
- returns an array of integers: '[200,200,...]' or '["OK"]' if all returned status codes are 200 (HTTP_SUCCESS)
- URI are either 'ModelRoot/TableName/Batch' or 'ModelRoot/Batch'


procedure CacheFlush(Ctxt: TRestServerUriContext);

REST service accessible from the ModelRoot/CacheFlush URI
- it will flush the server result cache
- this method shall be called by the clients when the Server cache may be not consistent any more (e.g. after a direct write to an external database)
- this method will require an authenticated client, for safety
- GET ModelRoot/CacheFlush URI will flush the whole Server cache, for all tables
- GET ModelRoot/CacheFlush/TableName URI will flush the specified table cache
- GET ModelRoot/CacheFlush/TableName/TableID URI will flush the content of the specified record
- POST ModelRoot/CacheFlush/_callback_ URI will be called by the client to notify the server that an interface callback instance has been released
- POST ModelRoot/CacheFlush/_ping_ URI will be called by the client after every half session timeout (or at least every hour) to notify the server that the connection is still alive


procedure ComputeRoutes;

Can be called at startup to validate the URI routes on this server
- is also called from Uri() if needed (e.g. after ResetRoutes)


procedure CreateMissingTables(user_version: cardinal = 0; options: TOrmInitializeTableOptions = []);

Redirect to Server: IRestOrmServer methods


procedure RecordVersionHandle(Occasion: TOrmOccasion; TableIndex: integer; var Decoder: TJsonObjectDecoder; RecordVersionField: TOrmPropInfoRttiRecordVersion); virtual;

Low-level propagation of a record content
- used internally by TServiceContainerServer for client/server synchronization


procedure ResetRoutes;

Called when the routes need to be re-computed
- e.g. is called when a service has been registered, or options changes


procedure ServiceMethodRegisterPublishedMethods(const aPrefix: RawUtf8; aInstance: TObject; aMethods: TUriMethods = [mGET, mPOST, mPUT, mDELETE]);

Add all published methods of a given object instance to the method-based list of services
- all those published method signature should match TOnRestServerCallBack
- will use the supplied aMethods or detect '_VERB1_[_VERB2_][..]MethodName' pattern e.g. as '_GET_Info' or '_GET__DELETE_User'


procedure SessionsLoadFromFile(const aFileName: TFileName; andDeleteExistingFileAfterRead: boolean);

Re-create all in-memory sessions from a compressed binary file
- typical use is after a server restart, with the file supplied to the Shutdown() method: it could be used e.g. for a short maintenance server shutdown, without loosing the current logged user sessions
- WARNING: this method will restore authentication sessions for the ORM, but not any complex state information used by interface-based services, like sicClientDriven class instances - DO NOT use this feature with SOA
- this method IS thread-safe, and calls internally Sessions.Safe.WriteLock


procedure SessionsSaveToFile(const aFileName: TFileName);

Persist all in-memory sessions into a compressed binary file
- you should not call this method it directly, but rather use Shutdown() with a StateFileName parameter - to be used e.g. for a short maintenance server shutdown, without loosing the current logged user sessions
- this method IS thread-safe, and calls internally Sessions.Safe.ReadOnlyLock


procedure SetOrmInstance(aORM: TRestOrmParent); override;

Called by TRestOrm.Create overriden constructor to set fOrm from IRestOrm


procedure SetPublicUri(const Address, Port: RawUtf8);

The HTTP server should call this method so that ServicesPublishedInterfaces registration will be able to work


procedure SetRecordVersionMax(TableIndex: integer; Value: TRecordVersion);

Write access to the TRestOrmServer.RecordVersionMax[TableIndex] property
- used internally by TServiceContainerServer for client/server synchronization


procedure Shutdown(const aStateFileName: TFileName = ''); virtual;

You can call this method to prepare the server for shutting down
- it will reject any incoming request from now on, and will wait until all pending requests are finished, for proper server termination
- you could optionally save the current server state (e.g. user sessions) into a file, ready to be retrieved later on using SessionsLoadFromFile - note that this will work only for ORM sessions, NOT complex SOA state
- this method is called by Destroy itself


procedure Stat(Ctxt: TRestServerUriContext);

REST service accessible from ModelRoot/Stat URI to gather detailed information
- returns the current execution statistics of this server, as a JSON object
- this method will require an authenticated client, for safety
- by default, will return the high-level information of this server
- will return human-readable JSON layout if ModelRoot/Stat/json is used, or the corresponding XML content if ModelRoot/Stat/xml is used
- you can define withtables, withmethods, withinterfaces, withsessions or withsqlite3 additional parameters to return detailed information about method-based services, interface-based services, per session statistics, or prepared SQLite3 SQL statement timing (for a TRestServerDB instance)

 Client.CallBackGet('stat',['withtables',true,'withmethods',true,
   'withinterfaces',true,'withsessions',true,'withsqlite3',true],stats);

- defining a 'withall' parameter will retrieve all available statistics
- note that TRestServer.StatLevels property will enable statistics gathering for tables, methods, interfaces, sqlite3 or sessions
- a specific findservice=ServiceName parameter will not return any statistics, but matching URIs from the server AssociatedServices list


procedure Timestamp(Ctxt: TRestServerUriContext);

REST service accessible from the ModelRoot/Timestamp URI
- returns the server time stamp TTimeLog/Int64 value as UTF-8 text
- this method will not require an authenticated client
- hidden ModelRoot/Timestamp/info command will return basic execution information, less verbose (and sensitive) than Stat(), calling virtual InternalInfo() protected method


procedure Uri(var Call: TRestUriParams); virtual;

Implement a generic local, piped or HTTP/1.1 provider
- this is the main entry point of the server, from the client side
- default implementation calls protected methods EngineList() Retrieve() Add() Update() Delete() UnLock() EngineExecute() above, which must be overridden by the TRestServer child
- for 'GET ModelRoot/TableName', url parameters can be either "select" and "where" (to specify a SQL Query, from the SqlFromSelectWhere function), either "sort", "dir", "startIndex", "results", as expected by the YUI DataSource Request Syntax for data pagination - see http://developer.yahoo.com/yui/datatable/#data
- execution of this method could be monitored via OnBeforeUri and OnAfterUri event handlers


property AssociatedServices: TServicesPublishedInterfacesList read fAssociatedServices;

A list of the services associated by all clients of this server instance
- when a client connects to this server, it will publish its own services (when checking its interface contract), so that they may be identified


property AuthenticationSchemes: TRestServerAuthenticationDynArray read fSessionAuthentication;

Read-only access to the list of registered server-side authentication methods, used for session creation
- note that the exact number or registered services in this list is stored in the AuthenticationSchemesCount property


property AuthenticationSchemesCount: integer read GetAuthenticationSchemesCount;

How many authentication methods are registered in AuthenticationSchemes


property AuthGroupClass: TAuthGroupClass read fAuthGroupClass;

The class inheriting from TAuthGroup, as defined in the model
- during authentication, this class will be used for every TAuthGroup table access


property AuthUserClass: TAuthUserClass read fAuthUserClass;

The class inheriting from TAuthUser, as defined in the model
- during authentication, this class will be used for every TAuthUser table access
- see also the OnAuthenticationUserRetrieve optional event handler


property BypassOrmAuthentication: TUriMethods read fBypassOrmAuthentication write fBypassOrmAuthentication;

Allow to by-pass Authentication for a given set of HTTP verbs
- by default, RESTful access to the ORM will follow HandleAuthentication setting: but you could define some HTTP verb to this property, which will by-pass the authentication - may be used e.g. for public GET of the content by an AJAX client


property HandleAuthentication: boolean read fHandleAuthentication;

Set to true if the server will handle per-user authentication and access right management
- i.e. if the associated TOrmModel contains TAuthUser and TAuthGroup tables (set by constructor)


property JwtForUnauthenticatedRequest: TJwtAbstract read fJwtForUnauthenticatedRequest write fJwtForUnauthenticatedRequest;

Define if unsecure connections (i.e. not in-process or encrypted WebSockets) with no session can be authenticated via JWT
- once set, this instance will be owned by the TRestServer
- by definition, such JWT authentication won't identify any mORMot user nor session (it just has to be valid), so only sicSingle, sicShared or sicPerThread interface-based services execution are possible
- typical usage is for a public API, in conjunction with ServiceDefine(...).ResultAsJsonObjectWithoutResult := true on the server side and TRestClientUri.ServiceDefineSharedApi() method for the client
- see also JwtForUnauthenticatedRequestWhiteIP() for additional security


property NoAjaxJson: boolean read GetNoAjaxJson write SetNoAjaxJson;

Set this property to true to transmit the JSON data in a "not expanded" format
- not directly compatible with Javascript object list decode: not to be used in AJAX environnement (like in TSqlite3HttpServer)
- but transmitted JSON data is much smaller if set it's set to FALSE, and if you use a Delphi Client, parsing will be also faster and memory usage will be lower
- By default, the NoAjaxJson property is set to TRUE in TRestServer.ExportServerNamedPipe: if you use named pipes for communication, you probably won't use javascript because browser communicates via HTTP!
- But otherwise, NoAjaxJson property is set to FALSE. You could force its value to TRUE and you'd save some bandwidth if you don't use javascript: even the parsing of the JSON Content will be faster with Delphi client if JSON content is not expanded
- the "expanded" or standard/AJAX layout allows you to create pure JavaScript objects from the JSON content, because the field name / JavaScript object property name is supplied for every value
- the "not expanded" layout, NoAjaxJson property is set to TRUE, reflects exactly the layout of the SQL request - first line contains the field names, then all next lines are the field content
- is in fact stored in rsoNoAjaxJson item in Options property


property OnNotifyCallback: TOnRestServerClientCallback read fOnNotifyCallback write SetOnNotifyCallback;

This event will be executed to push notifications from the WebSockets server to a remote client, using a (fake) interface parameter
- is nil by default, but may point e.g. to TRestHttpServer.NotifyCallback
- only a single WS server can be assigned to a TRestServer instance


property Options: TRestServerOptions read fOptions write SetOptions;

Allow to customize how TRestServer.Uri process the requests
- e.g. if HTTP_SUCCESS with no body should be translated into HTTP_NOCONTENT


property RootRedirectGet: RawUtf8 read fRootRedirectGet write fRootRedirectGet;

The URI to redirect any plain GET on root URI, without any method
- could be used to ease access from web browsers URI
- consider using faster and more precise THttpServerGeneric.Route.Get()


property Router: TRestRouter read fRouter;

Low-level access to the internal URI multiplexer
- to be used e.g. from overriden TRestServerUriContext.UriComputeRoutes


property Server: IRestOrmServer read fServer;

Main access to the IRestOrmServer methods of this instance


property ServiceMethodStat[const aMethod: RawUtf8]: TSynMonitorInputOutput read GetServiceMethodStat;

Retrieve detailed statistics about a method-based service use
- will return a reference to the actual alive item: caller should not free the returned instance


property ServiceReleaseTimeoutMicrosec: integer read fServiceReleaseTimeoutMicrosec write fServiceReleaseTimeoutMicrosec;

Maximum time allowed to release an interface service instance
- equals 500 microseconds by default - 0 would disable any measurement
- should be enabled for each given interface by setting optFreeTimeout


property ServicesRouting: TRestServerUriContextClass read fServicesRouting write SetRoutingClass;

The routing classs of the service remote request
- by default, will use TRestRoutingRest, i.e. an URI-based layout which is secure (since will use our RESTful authentication scheme), and also very fast
- but TRestRoutingJsonRpc can e.g. be set (on BOTH client and server sides), if the client will rather use JSON/RPC alternative pattern
- NEVER set the abstract TRestServerUriContext class on this property


property SessionClass: TAuthSessionClass read fSessionClass write fSessionClass;

The class inheriting from TAuthSession to handle in-memory sessions
- since all sessions data remain in memory, ensure they are not taking too much resource (memory or process time)


property Sessions: TSynObjectListSorted read fSessions;

Read-only access to the internal list of sessions
- ensure you protect its access using Sessions.Safe TRWLock


property ShutdownRequested: boolean read fShutdownRequested;

Flag set to TRUE when the Shutdown method has been called


property StatLevels: TRestServerMonitorLevels read fStatLevels write fStatLevels;

Which level of detailed information is gathered
- by default, contains SERVERDEFAULTMONITORLEVELS, i.e.

 [mlUri, mlTables, mlMethods, mlInterfaces, mlSQLite3]

- you can add mlSessions to maintain per-session statistics: but it will slow down the process, with higher memory consumption for each session


property Stats: TRestServerMonitor read fStats;

Read-only access to the high-level Server statistics
- see ServiceMethodStat[] for information about method-based services, or TServiceFactoryServer.Stats / Stat[] for interface-based services
- statistics are available remotely as JSON from the Stat() method


property StatUsage: TSynMonitorUsage read fStatUsage write SetStatUsage;

Could be set to track statistic from Stats information
- it may be e.g. a TSynMonitorUsageRest instance for REST storage
- warning: current Uri() implementation is inefficient (single lock)


1.3.27. TRestHttpServerDefinition

TRestHttpServerDefinition = class(TSynPersistentWithPassword)

Parameters supplied to publish a TRestServer via HTTP
- used by the overloaded TRestHttpServer.Create(TRestHttpServerDefinition) constructor in mormot.rest.http.server.pas, and also in dddInfraSettings.pas


constructor Create; override;

Initialize with the default values


property Authentication: TRestHttpServerRestAuthentication read fAuthentication write fAuthentication;

Which authentication is expected to be published


property BindPort: RawByteString read fBindPort write fBindPort;

Defines the port to be used for REST publishing
- may include an optional IP address to bind, e.g. '127.0.0.1:8888'


property DomainHostRedirect: RawUtf8 read fDomainHostRedirect write fDomainHostRedirect;

Register domain names to be redirected to a some Model.Root
- specified as CSV values of Host=Name pairs, e.g.

 'project1.com=root1,project2.com=root2,blog.project2.com=root2/blog'

property EnableCors: RawUtf8 read fEnableCors write fEnableCors;

Allow Cross-origin resource sharing (CORS) access
- set this property to '*' if you want to be able to access the REST methods from an HTML5 application hosted in another location, or define a CSV white list of TMatch-compatible origins
- will set e.g. the following HTTP header:

 Access-Control-Allow-Origin: *

property Https: boolean read fHttps write fHttps;

Defines if https:// protocol should be used
- implemented only by http.sys server under Windows, not by socket servers


property HttpSysQueueName: SynUnicode read fHttpSysQueueName write fHttpSysQueueName;

The displayed name in the http.sys queue
- used only by http.sys server under Windows, not by socket-based servers


property NginxSendFileFrom: TFileName read fNginxSendFileFrom write fNginxSendFileFrom;

Enable NGINX X-Accel internal redirection for STATICFILE_CONTENT_TYPE
- supplied value is passed as argument to THttpServer.NginxSendFileFrom()
- used only by the socket-based servers, not http.sys server on Windows


property Options: TRestHttpServerOptions read fOptions write fOptions;

Customize the TRestHttpServer low-level process


property RemoteIPHeader: RawUtf8 read fRemoteIPHeader write fRemoteIPHeader;

The value of a custom HTTP header containing the real client IP
- by default, the RemoteIP information will be retrieved from the socket layer - but if the server runs behind some proxy service, you should define here the HTTP header name which indicates the true remote client IP value, mostly as 'X-Real-IP' or 'X-Forwarded-For'


property RootRedirectToUri: RawUtf8 read fRootRedirectToUri write fRootRedirectToUri;

Redirect a '/' HTTP or HTTPS request to a given URI via a 307 command
- follow the Https property for the redirection source


property ThreadCount: byte read fThreadCount write fThreadCount;

How many threads the thread pool associated with this HTTP server should create
- if set to 0, will use default value 32
- this parameter may be ignored depending on the actual HTTP server used, which may not have any thread pool


property WebSocketPassword: SpiUtf8 read fPassWord write fPassWord;

If defined, this HTTP server will use WebSockets, and our secure encrypted binary protocol
- when stored in the settings JSON file, the password will be safely encrypted as defined by TSynPersistentWithPassword
- use the inherited PlainPassword property to set or read its value


1.4. Types implemented in the mormot.rest.server unit

1.4.1. PRestServerMethod

PRestServerMethod = ^TRestServerMethod;

Pointer to a description of a method-based service


1.4.2. PServiceRunningContext

PServiceRunningContext = ^TServiceRunningContext;

Points to the currently running service on the server side
- your code may call the ServiceRunningContext global function once in a method, since per-thread access does cost some CPU

var
  context: PServiceRunningContext;
begin
  context := ServiceRunningContext; // threadvar access once
  ...

1.4.3. TAuthSessionClass

TAuthSessionClass = class of TAuthSession;

Class-reference type (metaclass) used to define overridden session instances
- since all sessions data remain in memory, ensure they are not taking too much resource (memory or process time)
- if you plan to use session persistence, ensure you override the TAuthSession.SaveTo/CreateFrom methods in the inherited class


1.4.4. TOnAfterUri

TOnAfterUri = procedure(Ctxt: TRestServerUriContext) of object;

Callback raised after TRestServer.Uri ORM/SOA command execution


1.4.5. TOnAuthenticationFailed

TOnAuthenticationFailed = procedure(Sender: TRestServer; Reason: TOnAuthenticationFailedReason; Session: TAuthSession; Ctxt: TRestServerUriContext) of object;

Callback raised in case of authentication failure
- as used by TRestServerUriContext.AuthenticationFailed event


1.4.6. TOnAuthenticationFailedReason

TOnAuthenticationFailedReason = ( afInvalidSignature, afRemoteServiceExecutionNotAllowed, afUnknownUser, afInvalidPassword, afSessionAlreadyStartedForThisUser, afSessionCreationAborted, afSecureConnectionRequired, afJWTRequired );

Used to identify the authentication failure reason
- as transmitted e.g. by TRestServerUriContext.AuthenticationFailed or TRestServer.OnAuthenticationFailed


1.4.7. TOnAuthenticationUserRetrieve

TOnAuthenticationUserRetrieve = function(Sender: TRestServerAuthentication; Ctxt: TRestServerUriContext; aUserID: TID; const aUserName: RawUtf8): TAuthUser of object;

Callback allowing to customize the retrieval of an authenticated user
- as defined in TRestServer.OnAuthenticationUserRetrieve
- and executed by TRestServerAuthentication.GetUser
- on call, either aUserID will be <> 0, or aUserName is to be used
- if the function returns nil, default Server.AuthUserClass.Create() methods won't be called, and the user will be reported as not found


1.4.8. TOnBeforeUri

TOnBeforeUri = function(Ctxt: TRestServerUriContext): boolean of object;

Callback raised before TRestServer.Uri ORM/SOA command execution
- should return TRUE to execute the command, FALSE to cancel it


1.4.9. TOnErrorUri

TOnErrorUri = function(Ctxt: TRestServerUriContext; E: Exception): boolean of object;

Callback raised if TRestServer.Uri execution failed
- should return TRUE to execute Ctxt.Error(E,...), FALSE if returned content has already been set as expected by the client


1.4.10. TOnInternalInfo

TOnInternalInfo = procedure(Sender: TRestUriContext; var Info: TDocVariantData) of object;

Callback allowing to customize the information returned by root/timestamp/info
- Sender is indeed a TRestServerUriContext instance


1.4.11. TOnOrmEvent

TOnOrmEvent = function(Sender: TRestServer; Event: TOrmEvent; aTable: TOrmClass; const aID: TID; const aSentData: RawUtf8): boolean of object;

Used to define how to trigger Events on record update
- see TRestServer.OnUpdateEvent property and InternalUpdateEvent() method
- returns true on success, false if an error occurred (but action must continue)
- to be used only server-side, not to synchronize some clients: the framework is designed around a stateless RESTful architecture (like HTTP/1.1), in which clients ask the server for refresh (see TRestClientUri.UpdateFromServer)


1.4.12. TOnOrmFieldEvent

TOnOrmFieldEvent = function(Sender: TRestServer; Event: TOrmEvent; aTable: TOrmClass; const aID: TID; const aAffectedFields: TFieldBits): boolean of object;

Used to define how to trigger Events on record field update
- see TRestServer.OnBlobUpdateEvent property and InternalUpdateEvent() method
- returns true on success, false if an error occurred (but action must continue)
- to be used only server-side, not to synchronize some clients: the framework is designed around a stateless RESTful architecture (like HTTP/1.1), in which clients ask the server for refresh (see TRestClientUri.UpdateFromServer)


1.4.13. TOnOrmSession

TOnOrmSession = function(Sender: TRestServer; Session: TAuthSession; Ctxt: TRestServerUriContext): boolean of object;

Session-related callbacks triggered by TRestServer
- for OnSessionCreate, returning TRUE will abort the session creation - and you can set Ctxt.Call^.OutStatus to a corresponding error code


1.4.14. TOnRestServerCallBack

TOnRestServerCallBack = procedure(Ctxt: TRestServerUriContext) of object;

Method prototype to be used on Server-Side for method-based services
- will be routed as ModelRoot/[TableName/TableID/]MethodName RESTful requests
- this mechanism is able to handle some custom Client/Server request, similar to the DataSnap technology, but in a KISS way; it's fully integrated in the Client/Server architecture of our framework
- just add a published method of this type to any TRestServer descendant
- when TRestServer.Uri receive a request for ModelRoot/MethodName or ModelRoot/TableName/TableID/MethodName, it will check for a published method in its self instance named MethodName which MUST be of TOnRestServerCallBack type (not checked neither at compile time neither at runtime: beware!) and call it to handle the request
- important warning: the method implementation MUST be thread-safe
- when TRestServer.Uri receive a request for ModelRoot/MethodName, it calls the corresponding published method with aRecord set to nil
- when TRestServer.Uri receive a request for ModelRoot/TableName/TableID/MethodName, it calls the corresponding published method with aRecord pointing to a just created instance of the corresponding class, with its field ID set; note that the only set field is ID: other fields of aRecord are not set, but must secificaly be retrieved on purpose
- for ModelRoot/TableName/TableID/MethodName, the just created instance will be freed by TRestServer.Uri when the method returns
- Ctxt.Call is set with low-level incoming and outgoing data from client (e.g. Ctxt.Call.InBody contain POST/PUT data message)
- Ctxt.Session* will identify to the authentication session of the remote client (CONST_AUTHENTICATION_NOT_USED=1 if authentication mode is not enabled or CONST_AUTHENTICATION_SESSION_NOT_STARTED=0 if the session not started yet) - code may use SessionGetUser() method to retrieve the user details
- Ctxt.Method will indicate the used HTTP verb (e.g. GET/POST/PUT..)
- if process succeeded, implementation shall call Ctxt.Results([]) method to set a JSON response object with one "result" field name or Ctxt.Returns([]) with a JSON object described in Name/Value pairs; if the returned value is not JSON_CONTENT_TYPE, use Ctxt.Returns() and its optional CustomHeader parameter can specify a custom header like TEXT_CONTENT_TYPE_HEADER
- if process succeeded, and no data is expected to be returned to the caller, implementation shall call overloaded Ctxt.Success() method with the expected status (i.e. just Ctxt.Success will return HTTP_SUCCESS)
- if process failed, implementation shall call Ctxt.Error() method to set the corresponding error message and error code number
- a typical implementation may be:

 procedure TRestServerTest.Sum(Ctxt: TRestServerUriContext);
 begin
   Ctxt.Results([Ctxt.InputDouble['a'] + Ctxt.InputDouble['b']]);
 end;

- Client-Side can be implemented as you wish. By convention, it could be appropriate to define in either TRestServer (if to be called as ModelRoot/MethodName), either TOrm (if to be called as ModelRoot/TableName[/TableID]/MethodName) a custom public or protected method, calling TRestClientUri.URL with the appropriate parameters, and named (by convention) as MethodName; TRestClientUri has dedicated methods like CallBackGetResult, CallBackGet, CallBackPut and CallBack; see also TOrmModel.getURICallBack and JsonDecode function

 function TOrmPeople.Sum(aClient: TRestClientUri; a, b: double): double;
 var err: integer;
 begin
   val(aClient.CallBackGetResult('sum', ['a', a, 'b', b]), result, err);
 end;

1.4.15. TOnRestServerClientCallback

TOnRestServerClientCallback = function(aSender: TRestServer; const aInterfaceDotMethodName, aParams: RawUtf8; aConnectionID: TRestConnectionID; aFakeCallID: integer; aResult, aErrorMsg: PRawUtf8): boolean of object;

Event signature used to notify a client callback
- implemented e.g. by TRestHttpServer.NotifyCallback


1.4.16. TOnServiceCreateInstance

TOnServiceCreateInstance = procedure( Sender: TServiceFactory; Instance: TInterfacedObject) of object;

Event signature used by TRestServer.OnServiceCreateInstance
- as called by TServiceFactoryServer.CreateInstance
- the actual Instance class can be quickly retrieved from TServiceFactoryServer(Sender).ImplementationClass


1.4.17. TOnStartUri

TOnStartUri = function(var Call: TRestUriParams): integer of object;

Callback raised when TRestServer.Uri start to process a request
- should return HTTP_SUCCESS (200) to continue, or an error code to abort
- could also change the Call fields on the fly, if needed


1.4.18. TOrmMonitorUsageClass

TOrmMonitorUsageClass = class of TOrmMonitorUsage;

Class-reference type (metaclass) of a TOrmMonitorUsage table


1.4.19. TRestHttpServerOption

TRestHttpServerOption = ( rsoOnlyJsonRequests, rsoOnlyValidUtf8, rsoRedirectServerRootUriForExactCase, rsoAllowSingleServerNoRoot, rsoHeadersUnFiltered, rsoCompressSynLZ, rsoCompressGZip, rsoLogVerbose, rsoNoXPoweredHeader, rsoIncludeDateHeader, rsoBan40xIP, rsoEnableLogging, rsoTelemetryCsv, rsoTelemetryJson );

Customize TRestHttpServer process
- rsoOnlyJsonRequests will return HTTP 400 "Bad Request" if the input is not of 'application/json' content type
- rsoOnlyValidUtf8 will return HTTP 406 "Non Acceptable" if input JSON or text body is not valid UTF-8 - calling fast IsValidUtf8() function
- rsoRedirectServerRootUriForExactCase to search root URI case-sensitive, mainly to avoid errors with HTTP cookies, which path is case-sensitive - when set, such not exact case will be redirected via a HTTP 307 command
- rsoAllowSingleServerNoRoot will allow URI with no Model.Root prefix, i.e. 'GET url' to be handled as 'GET root/url' - by design, it would work only with a single registered TRestServer (to know which Model.Root to use)
- rsoHeadersUnFiltered maps THttpServer.HeadersUnFiltered property
- rsoCompressSynLZ and rsoCompressGZip enable SynLZ and GZip compression on server side - it should also be enabled for the client
- rsoLogVerbose would include a lot of detailed information, useful only to debug the low-level server process - to be enabled only when required
- rsoNoXPoweredHeader excludes 'X-Powered-By: mORMot 2 synopse.info' header
- rsoIncludeDateHeader will let all answers include a Date: ... HTTP header
- rsoBan40xIP will reject any IP for a few seconds after a 4xx error code is returned (but 401/403) - only implemented by socket servers for now
- rsoEnableLogging enable an associated THttpServerGeneric.Logger instance
- rsoTelemetryCsv and rsoTelemetryJson will enable CSV or JSON consolidated per-minute metrics logging via an associated THttpServerGeneric.Analyzer


1.4.20. TRestHttpServerOptions

TRestHttpServerOptions = set of TRestHttpServerOption;

How to customize TRestHttpServer process


1.4.21. TRestHttpServerRestAuthentication

TRestHttpServerRestAuthentication = ( adDefault, adHttpBasic, adWeak, adSspi );

Supported REST authentication schemes
- used by the overloaded TRestHttpServer.Create(TRestHttpServerDefinition) constructor in mormot.rest.http.server.pas, and also in dddInfraSettings.pas
- map TRestServerAuthenticationDefault, TRestServerAuthenticationHttpBasic, TRestServerAuthenticationNone and TRestServerAuthenticationSspi classes
- asSSPI will use mormot.lib.sspi/gssapi units depending on the OS, and may be not available on some targets (e.g. Android)


1.4.22. TRestNode

TRestNode = ( rnNone, rnTable, rnTableID, rnTableIDBlob, rnTableMethod, rnTableIDMethod, rnState, rnMethod, rnMethodPath, rnInterface, rnInterfaceClientID );

Kind of REST requests defined by TRestServer.ComputeRoutes for TRestTreeNode
- rnTable for ModelRoot/TableName GET POST PUT DELETE BEGIN END ABORT
- rnTableID for ModelRoot/TableName/<id> GET LOCK UNLOCK PUT DELETE
- rnTableIDBlob for ModelRoot/TableName/<id>/Blob GET PUT
- rnTableMethod for ModelRoot/TableName/MethodName GET POST PUT DELETE
- rnTableIDMethod ModelRoot/TableName/<id>/MethodName GET POST PUT DELETE
- rnState for ModelRoot STATE
- rnMethod for ModelRoot/MethodName GET POST PUT DELETE
- rnMethodPath for ModelRoot/MethodName/<path:fulluri> GET POST PUT DELETE
- rnInterface for ModelRoot/InterfaceName[/.InterfaceMethodName]
- rnInterfaceClientID for ModelRoot/InterfaceName/.InterfaceMethodName/<id>


1.4.23. TRestRouterTree

TRestRouterTree = array[mGET .. high(TUriMethod)] of TRadixTreeParams;

Store per-method URI multiplexing Radix Tree in TRestRouter
- each HTTP method would have its dedicated TRestTree parser in TRestRouter


1.4.24. TRestServerAddStat

TRestServerAddStat = ( withTables, withMethods, withInterfaces, withSessions );

The flags used for TRestServer.AddStats


1.4.25. TRestServerAddStats

TRestServerAddStats = set of TRestServerAddStat;

Some flags used for TRestServer.AddStats


1.4.26. TRestServerAuthenticationClass

TRestServerAuthenticationClass = class of TRestServerAuthentication;

Class-reference type (metaclass) used to define an authentication scheme


1.4.27. TRestServerAuthenticationDynArray

TRestServerAuthenticationDynArray = array of TRestServerAuthentication;

Maintain a list of TRestServerAuthentication instances


1.4.28. TRestServerAuthenticationOption

TRestServerAuthenticationOption = ( saoUserByLogonOrID, saoHandleUnknownLogonAsStar );

Optional behavior of TRestServerAuthentication class
- by default, saoUserByLogonOrID is set, allowing TRestServerAuthentication.GetUser() to retrieve the TAuthUser by logon name or by ID, if the supplied logon name is an integer
- if saoHandleUnknownLogonAsStar is defined, any user successfully authenticated could be logged with the same ID (and authorization) than TAuthUser.Logon='*' - of course, this is meaningfull only with an external credential check (e.g. via SSPI or Active Directory)


1.4.29. TRestServerAuthenticationOptions

TRestServerAuthenticationOptions = set of TRestServerAuthenticationOption;

Defines the optional behavior of TRestServerAuthentication class


1.4.30. TRestServerClass

TRestServerClass = class of TRestServer;

Class-reference type (metaclass) of a REST server


1.4.31. TRestServerKind

TRestServerKind = ( sMainEngine, sStaticDataTable, sVirtualTable );

Kind of (static) database server implementation available
- sMainEngine will identify the default main SQlite3 engine
- sStaticDataTable will identify a TRestStorageInMemory - i.e. TRestServer.fStaticData[] which can work without SQLite3
- sVirtualTable will identify virtual TRestStorage classes - i.e. TRestOrmServer.fStaticVirtualTable[] which points to SQLite3 virtual tables (e.g. TObjectList or external databases)


1.4.32. TRestServerMethods

TRestServerMethods = array of TRestServerMethod;

Used to store all method-based services of a TRestServer instance


1.4.33. TRestServerMonitorLevels

TRestServerMonitorLevels = set of ( mlUri, mlTables, mlMethods, mlInterfaces, mlSessions, mlSQLite3);

How TRestServer should maintain its statistical information
- used by TRestServer.StatLevels property


1.4.34. TRestServerOption

TRestServerOption = ( rsoNoAjaxJson, rsoGetAsJsonNotAsString, rsoGetID_str, rsoRedirectForbiddenToAuth, rsoHttp200WithNoBodyReturns204, rsoAddUpdateReturnsContent, rsoComputeFieldsBeforeWriteOnServerSide, rsoSecureConnectionRequired, rsoCookieIncludeRootPath, rsoCookieHttpOnlyFlagDisable, rsoAuthenticationUriDisable, rsoTimestampInfoUriDisable, rsoHttpHeaderCheckDisable, rsoGetUserRetrieveNoBlobData, rsoNoInternalState, rsoNoTableURI, rsoMethodUnderscoreAsSlashUri, rsoValidateUtf8Input, rsoSessionInConnectionOpaque );

Some options for TRestServer process
- read-only rsoNoAjaxJson indicates that JSON data is transmitted in "not expanded" format: you should NEVER change this option by including this property in TRestServer.Options, but always call explicitly TRestServer.NoAjaxJson := true so that the SetNoAjaxJson virtual method should be called as expected (e.g. to flush TRestServerDB cache)
- rsoGetAsJsonNotAsString will let ORM GET return to AJAX (non Delphi) clients JSON objects instead of the JSON text stored in database fields
- rsoGetID_str will add a "ID_str": string field to circumvent JavaScript limitation of 53-bit for integers - only for AJAX (non Delphi) clients
- unauthenticated requests from browsers (i.e. not Delphi clients) may be redirected to the TRestServer.Auth() method via rsoRedirectForbiddenToAuth (e.g. for TRestServerAuthenticationHttpBasic popup)
- some REST/AJAX clients may expect to return status code 204 instead of 200 in case of a successful operation, but with no returned body (e.g. DELETE with SAPUI5 / OpenUI5 framework): include rsoHttp200WithNoBodyReturns204 so that any HTTP_SUCCESS (200) with no returned body will return a HTTP_NOCONTENT (204), as expected by some clients
- by default, Add() or Update() will return HTTP_CREATED (201) or HTTP_SUCCESS (200) with no body, unless rsoAddUpdateReturnsContent is set to return as JSON the last inserted/updated record
- TModTime / TCreateTime fields are expected to be filled on client side, unless you set rsoComputeFieldsBeforeWriteOnServerSide so that AJAX requests will set the fields on the server side by calling the TOrm ComputeFieldsBeforeWrite virtual method, before writing to the database
- rsoSecureConnectionRequired will ensure Call is flagged as llfSecured (i.e. in-process, HTTPS, or encrypted WebSockets) - with the only exception of the Timestamp method-based service (for monitoring purposes) - note that this option doesn't make sense behind a proxy, just with a true HTTPS server
- by default, cookies will contain only 'Path=/Model.Root', but '; Path=/' may be also added setting rsoCookieIncludeRootPath
- you can disable the 'HttpOnly' flag via rsoCookieHttpOnlyFlagDisable
- TRestServerUriContext.AuthenticationBearerToken will return the ?authenticationbearer=... URI parameter value alternatively to the HTTP header unless rsoAuthenticationUriDisable is set (for security reasons)
- you can switch off root/timestamp/info URI via rsoTimestampInfoUriDisable
- Uri() header output will be sanitized for any EOL injection, unless rsoHttpHeaderCheckDisable is defined (to gain a few cycles)
- by default, TAuthUser.Data blob is retrieved from the database, unless rsoGetUserRetrieveNoBlobData is defined
- rsoNoInternalState could be state to avoid transmitting the 'Server-InternalState' header, e.g. if the clients wouldn't need it
- rsoNoTableURI will disable any /root/tablename URI for safety
- rsoMethodUnderscoreAsSlashUri will try to decode /root/method/name as 'method_name' method
- rsoValidateUtf8Input will call IsValidUtf8() on input UTF-8 JSON/text, to sanitize character encodings - with AVX2 this function is very fast so this could be a good option if you don't trust your clients
- rsoSessionInConnectionOpaque uses LowLevelConnectionOpaque^.ValueInternal to store the current TAuthSession - may be used with a lot of sessions


1.4.35. TRestServerOptions

TRestServerOptions = set of TRestServerOption;

Allow to customize the TRestServer process via its Options property


1.4.36. TRestServerUriContextClass

TRestServerUriContextClass = class of TRestServerUriContext;

Class used to define the Server side expected routing
- match TRestClientRoutingClass reciprocal meta-class
- most of the internal methods are declared as virtual, so it allows any kind of custom routing or execution scheme
- TRestServerRoutingJsonRpc and TRestServerRoutingRest classes are provided in this unit, to allow RESTful and JSON/RPC protocols


1.4.37. TSqlRestServer

TSqlRestServer = TRestServer;

Backward compatibility types redirections


1.5. Constants implemented in the mormot.rest.server unit

1.5.1. HTTPSERVER_DEBUG_OPTIONS

HTTPSERVER_DEBUG_OPTIONS = [rsoCompressGZip, rsoCompressSynLZ, rsoLogVerbose];

TRestHttpServer processing options which may be used during raw debugging


1.5.2. HTTPSERVER_DEFAULT_OPTIONS

HTTPSERVER_DEFAULT_OPTIONS = [rsoCompressGZip, rsoCompressSynLZ];

Default TRestHttpServer processing options are to support SynLZ and GZip


1.5.3. PAGINGPARAMETERS_YAHOO

PAGINGPARAMETERS_YAHOO: TRestServerUriPagingParameters = ( Sort: 'SORT='; Dir: 'DIR='; StartIndex: 'STARTINDEX='; Results: 'RESULTS='; Select: 'SELECT='; Where: 'WHERE='; SendTotalRowsCountFmt: '');

The default URI parameters for query paging
- those values are the one expected by YUI components


1.5.4. SERVERDEFAULTMONITORLEVELS

SERVERDEFAULTMONITORLEVELS: TRestServerMonitorLevels = [mlUri, mlTables, mlMethods, mlInterfaces, mlSQLite3];

Default value of TRestServer.StatLevels property
- i.e. gather all statistics, but mlSessions which has a slowdown impact


1.6. Functions or procedures implemented in the mormot.rest.server unit

Functions or proceduresDescription
CurrentNonceReturns a safe 256-bit nonce, changing every 5 minutes
CurrentNonceReturns a safe 256-bit hexadecimal nonce, changing every 5 minutes
CurrentNonce256Returns a safe 256-bit nonce as binary, changing every 5 minutes
IsCurrentNonceValidate a 256-bit binary nonce against current or previous nonce
IsCurrentNonceValidate a 256-bit hexadecimal nonce against current or previous nonce
LibraryRequestThis function can be exported from a DLL to remotely access to a TRestServer
ServiceRunningContextReturns the thread-specific service context execution currently running on the server side
ServiceRunningRequestReturns the thread-specific REST server execution context

1.6.1. CurrentNonce

function CurrentNonce(Ctxt: TRestServerUriContext; Previous: boolean = false): RawUtf8; overload;

Returns a safe 256-bit hexadecimal nonce, changing every 5 minutes
- as used e.g. by TRestServerAuthenticationDefault.Auth
- this function is very fast, even if cryptographically-level SHA-3 secure
- Ctxt may be nil (only used for faster GetTickCount64)


1.6.2. CurrentNonce

procedure CurrentNonce(Ctxt: TRestServerUriContext; Previous: boolean; Nonce: PRawUtf8; Nonce256: PHash256; Tix64: Int64 = 0); overload;

Returns a safe 256-bit nonce, changing every 5 minutes
- can return the (may be cached) value as hexadecimal text or THash256 binary


1.6.3. CurrentNonce256

function CurrentNonce256(Previous: boolean): THash256;

Returns a safe 256-bit nonce as binary, changing every 5 minutes


1.6.4. IsCurrentNonce

function IsCurrentNonce(Ctxt: TRestServerUriContext; const Nonce: RawUtf8): boolean; overload;

Validate a 256-bit hexadecimal nonce against current or previous nonce


1.6.5. IsCurrentNonce

function IsCurrentNonce(Ctxt: TRestServerUriContext; const Nonce256: THash256): boolean; overload;

Validate a 256-bit binary nonce against current or previous nonce


1.6.6. LibraryRequest

function LibraryRequest( Url, Method, SendData: PUtf8Char; UrlLen, MethodLen, SendDataLen: cardinal; out HeadRespFree: TLibraryRequestFree; var Head: PUtf8Char; var HeadLen: cardinal; out Resp: PUtf8Char; out RespLen, State: cardinal): cardinal; cdecl;

This function can be exported from a DLL to remotely access to a TRestServer
- use TRestServer.ExportServerGlobalLibraryRequest to assign a server to this function
- return the HTTP status, e.g. 501 HTTP_NOTIMPLEMENTED if no TRestServer.ExportServerGlobalLibraryRequest has been assigned yet
- once used, memory for Resp and Head should be released with LibraryRequestFree() returned function
- the Server current Internal State counter will be set to State
- simply use TRestClientLibraryRequest to access to an exported LibraryRequest() function
- match TLibraryRequest function signature


1.6.7. ServiceRunningContext

function ServiceRunningContext: PServiceRunningContext;

Returns the thread-specific service context execution currently running on the server side
- just an inlined transtype of the PerThreadRunningContextAddress function
- note that in case of direct server side execution of the service, this information won't be filled, so the safest (and slightly faster) access to the TRestServer instance associated with a service is to inherit your implementation class from TInjectableObjectRest, and not use this threadvar
- is set by TServiceFactoryServer.ExecuteMethod() just before calling the implementation method of a service, allowing to retrieve the current execution context - Request member is set from a client/server execution: Request.Server is the safe access point to the underlying TRestServer, in such context - also consider the CurrentServiceContextServer function to retrieve directly the running TRestServer (if any)
- its content is reset to zero out of the scope of a method execution
- when used, a local copy or a PServiceRunningContext pointer should better be created, since accessing a threadvar has a non negligible performance cost - for instance, if you want to use a "with" statement:

 with ServiceRunningContext do
   ... access TServiceRunningContext members

or as a local variable:

var
  context: PServiceRunningContext;
  inContentType: RawUtf8;
begin
  context := ServiceRunningContext; // threadvar access once
  ...
  inContentType := context.Request.Call^.InBodyType;
end;

1.6.8. ServiceRunningRequest

function ServiceRunningRequest: TRestServerUriContext;

Returns the thread-specific REST server execution context
- just a wrapper around ServiceRunningContext^.Request