#1 Re: mORMot 2 » new samples for mormot2, any rules? » 2026-02-17 07:14:19

Thanks a lot @flydev! Really appreciate you sharing this mormot2 MCP implementation and the extensions repo — it looks great!
Just to give you a heads-up: I’m currently buried deep in a production project,so I probably won’t have time to test it properly until after the end of March, unless the project wraps up early unexpectedly.
Once I’m free, I’ll definitely give it a spin and provide feedback! ?

#2 Re: mORMot 2 » EInvalidOp crash on aarch64-linux when C library calls mORMot's export » 2026-01-17 12:57:18

Thank you Chaa, but TSynFPUException.ForLibraryCode cannot solve this issue.

  Our program structure is:

  // Main thread (FPC)
  TS_Init(apiKey, callback);     // Initialize SDK (libvct.so)
  TS_createTask(taskConfig);     // Create transcoding task
  // Main thread now waits for callback...
  while not Terminated do
    Sleep(10);

  The SDK (libvct.so) is a C library that internally uses GStreamer and FFmpeg. When we call TS_createTask(), the function returns immediately. The actual transcoding happens asynchronously inside libvct.so's internal threads.

  The crash occurs like this:

  Main Thread (FPC):              SDK Internal Threads:
    TS_Init()
    TS_createTask() ------>  libvct.so creates worker threads
    waiting...                    |
    waiting...                    v
    waiting...               GStreamer/FFmpeg processing
    waiting...                    |
    waiting...                    v
                             Thread "queue210:src" calls pow()
                             -> resolves to mORMot's p0w()
                             -> FPC ThreadVar not initialized
                             -> CRASH

  We cannot wrap our SDK calls with TSynFPUException.ForLibraryCode:

  with TSynFPUException.ForLibraryCode do begin
    TS_createTask(taskConfig);  // Returns immediately!
  end;
  // ForLibraryCode scope ends here, but crash happens
  // much later in a different thread we don't control

  The ForLibraryCode pattern only works when the C code executes synchronously in the calling thread. It cannot help when the C library spawns its own threads that later call pow().

  This is why we need a fix in mORMot itself - either a define like -dNOLIBCMATH or making the exported functions safe for uninitialized threads.

#3 mORMot 2 » EInvalidOp crash on aarch64-linux when C library calls mORMot's export » 2026-01-17 07:07:54

zen010101
Replies: 3

Environment
- Platform: aarch64-linux (ARM64, Rockchip RK3588)
- FPC: 3.2.2
- mORMot2: latest
- Application: FPC program linked with GStreamer + FFmpeg (libavcodec)

Symptom
Program crashes with EInvalidOp: Invalid floating point operation when FFmpeg's libavcodec calls pow() during audio encoder initialization.

GDB Backtrace

Thread 28 "queue210:src" hit Breakpoint 1, SYSTEM_$_FLOAT_RAISE$TFPUEXCEPTIONMASK ()
(gdb) bt
#0  SYSTEM_$_FLOAT_RAISE$TFPUEXCEPTIONMASK ()
#1  SYSTEM_$_FLOAT_RAISE$TFPUEXCEPTION ()
#2  SYSTEM_$_RAISEPENDINGEXCEPTIONS ()
#3  SYSTEM_$_FPC_THROWFPUEXCEPTION ()
#4  fpc_ln_real ()
#5  MATH_$_POWER$DOUBLE$DOUBLE$DOUBLE ()
#6  p0w (b=-18014398509481984, e=0) at mormot.lib.static.pas:1014
#7  () at /lib/aarch64-linux-gnu/libavcodec.so.58
...
#10 avcodec_open2 () at /lib/aarch64-linux-gnu/libavcodec.so.58

Root Cause Analysis

The issue involves three interacting factors:

1. Symbol Export in mormot.lib.static.pas

mORMot exports C-compatible math functions with standard libc symbol names:

function p0w(b, e: double): double; cdecl; export alias: 'pow';
begin
  result := Power(b, e);  // calls FPC's Math.Power
end;

When the FPC program is linked, these symbols override the libc versions. Any C library (like libavcodec) calling pow() will resolve to mORMot's p0w instead of glibc's implementation.

2. FPC's Soft-Float Exception Handling on aarch64

On aarch64, FPC uses software-based floating-point exception detection. The FPU exception state is stored in a ThreadVar:

// From FPC RTL system unit
threadvar
  softfloat_exception_flags: TFPUExceptionMask;
  softfloat_exception_mask: TFPUExceptionMask;

After each floating-point operation, FPC checks softfloat_exception_flags and raises Pascal exceptions if needed.

3. ThreadVar Initialization in Foreign Threads

The critical issue: ThreadVars are only initialized for threads created by FPC's BeginThread.

When a C library (GStreamer/libavcodec) creates its own threads using pthread_create, FPC's ThreadVar storage is NOT initialized. The softfloat_exception_mask contains garbage/zero instead of the default mask that suppresses common exceptions.

Call Flow

1. GStreamer creates worker thread via pthread_create
   -> FPC ThreadVars NOT initialized (softfloat_exception_mask = 0 or garbage)

2. libavcodec calls pow() for audio encoding setup
   -> Resolves to mORMot's p0w() due to symbol export

3. p0w() calls FPC's Power() -> calls fpc_ln_real()
   -> FPC soft-float code checks softfloat_exception_flags
   -> Uninitialized mask causes false positive exception detection

4. FPC raises EInvalidOp in a non-FPC thread
   -> Crash

Current Workaround

Define NOLIBCSTATIC to disable all C library function exports:

-dNOLIBCSTATIC

This works but disables ALL static C functions, which may be too aggressive.

Suggested Improvement

Rather than disabling all exports, consider a more targeted approach:

Option A: Separate define for math function exports

{$ifndef NOLIBCMATH}
function p0w(b, e: double): double; cdecl; export alias: 'pow';
function fl00r(x: double): double; cdecl; export alias: 'floor';
function ce1l(x: double): double; cdecl; export alias: 'ceil';
// ...
{$endif}

Option B: Make these functions thread-safe for foreign threads

Check if running in a properly initialized FPC thread before using FPC math:

function p0w(b, e: double): double; cdecl; export alias: 'pow';
begin
  // If ThreadVar not initialized, fall back to libc or use safe implementation
  if not IsFPCThreadInitialized then
    result := libc_pow(b, e)  // direct syscall or dlsym
  else
    result := Power(b, e);
end;

Option C: Document the limitation

At minimum, document that programs using C libraries that create threads (GStreamer, FFmpeg, SDL, etc.) should define NOLIBCSTATIC on aarch64.

#4 Re: mORMot 2 » New Wiki Article: JSON Processing Guide (IDocDict/IDocList) » 2026-01-14 16:12:04

docs: update JSON wiki for mORMot 2.4 delimiter syntax support

- Update version info from 2.3 to 2.4 (version 2.4.13376) in all 15 chapters
- Add "Creating Nested Structures" section in Chapter 3 documenting:
  - Delimiter syntax: '{' '}' '[' ']' in DocDict/DocList
  - .AsVariant approach for nested structures
  - Direct IDocDict/IDocList parameters
- Add FAQ Q17 about delimiter syntax support in DocDict/DocList
- Document feature parity between JsonEncode() and DocDict/DocList

Access: https://github.com/zen010101/Claude_Mor … sing-Guide

#5 Re: mORMot 2 » New Wiki Article: JSON Processing Guide (IDocDict/IDocList) » 2026-01-14 11:39:27

Haha, yeah, maybe AI hallucinations offer a new way for humans to innovate. wink

I did see that the recent commits already have these features covered. I've just been swamped with other stuff recently and haven't gotten around to updating this Wiki doc.

#6 Re: mORMot 2 » New Wiki Article: JSON Processing Guide (IDocDict/IDocList) » 2026-01-07 19:38:24

Thank you ab for the valuable feedback! I have updated the JSON wiki documentation accordingly:

  1. Delimiter Syntax Clarification

  Fixed the documentation to clarify that `'{' '}' '[' ']'` delimiter syntax is supported by `JsonEncode()` only, NOT by `DocDict()`/`DocList()`. All examples now correctly use `.AsVariant` for nesting:

  // CORRECT for DocDict/DocList
  dict := DocDict([
    'user', DocDict([
      'name', 'Alice',
      'roles', DocList(['admin', 'user']).AsVariant
    ]).AsVariant
  ]);

  2. SOA Service Best Practices

  Added documentation recommending RawJson + JsonEncode() for SOA interface-based services instead of IDocDict/IDocList:
  - New section in Chapter 3: "SOA Service Considerations"
  - New FAQ Q16: "Should I use IDocDict/IDocList in SOA service methods?"
  - Notes added to API response examples

  3. FPC Stable RTTI Registration

  - Rtti.RegisterType() is NOT enough for FPC stable or older Delphi
  - Must use Rtti.RegisterFromText() with manual field description

  Thanks again for the corrections!

#7 Re: mORMot 2 » New Wiki Article: JSON Processing Guide (IDocDict/IDocList) » 2026-01-07 13:04:42

Thank you very much, Arnaud! Your detailed review is invaluable.

  I've addressed all the issues in the latest update:

  1. Record variable name - Fixed the reserved word issue
  2. O(n) complexity - Corrected to O(log n) for sorted IDocDict lookup
  3. Log format - Changed recommendation from jsonHumanReadable to jsonUnquotedPropNameCompact (grep-friendly, single line per entry)
  4. RTTI clarification - Added note that Rtti.RegisterType is mainly needed for FPC stable versions; Delphi 2010+ has enhanced RTTI for basic serialization
  5. Get() methods - Rewrote section to show all 11 boolean-returning overloads with proper usage patterns
  6. Performance chapter - Deleted due to measurement errors (now 14 chapters total)
  7. Native nested syntax - Added documentation for the '{' '}' '[' ']' delimiter syntax

  The wiki has been updated and chapters renumbered accordingly.

#8 mORMot 2 » New Wiki Article: JSON Processing Guide (IDocDict/IDocList) » 2026-01-07 05:12:09

zen010101
Replies: 8

Hi all,

  Following the RawUtf8 guide, I've created a comprehensive guide for mORMot 2's JSON processing interfaces - IDocList, IDocDict, and IDocDicts.

  Wiki Link: https://github.com/zen010101/Claude_Mor … sing-Guide

  The guide is organized into 15 chapters covering:

  - Core Concepts - What are IDocList/IDocDict, design philosophy, relationship with TDocVariant
  - Type System - Interface hierarchy, IDocDicts array type, TDocVariantModel options
  - Creating Instances - Factory functions (DocList, DocDict, DocListFromResults, DocDictDynArray)
  - IDocList Guide - Element access, iteration, filtering, sorting
  - IDocDict Guide - Key access, path-based navigation (PathDelim), iteration
  - IDocDicts Guide - Working with arrays of IDocDict
  - ORM Integration - jsonfromresults parameter, expanded vs non-expanded formats
  - Serialization - JSON output formats (compact, human-readable)
  - Error Handling - Parse failure behaviors, validation patterns
  - Performance - Typed accessors, Sort for O(log n) lookup, model selection
  - Memory Management - Weak references vs deep copies, Objects iterator pitfalls
  - API Reference - Complete method signatures
  - Practical Examples - Real-world usage patterns
  - FAQ - Common questions and solutions

  All code examples have been validated through unit tests (455 assertions passed).

  Hope this helps those working with JSON in mORMot 2. Feedback and corrections are welcome!

#10 Re: mORMot 2 » New Wiki Article: RawUtf8 Application Guide » 2025-12-25 15:56:55

Good idea, the wiki can also be managed by multiple people collaboratively using git. However, we can wait until I generate more articles later and then move them over uniformly.

#11 Re: mORMot 2 » check this out(sqlite) » 2025-12-25 09:05:28

Another example of Rust's invasion ;-)

#12 Re: mORMot 2 » Help with SQLite3 static encryption » 2025-12-24 07:39:50

Use ChangeSqlEncryptTablePassWord() function from mormot.db.raw.sqlite3.static unit:

     ChangeSqlEncryptTablePassWord('mydata.db3', 'OldPassword', 'NewPassword');

  Notes:
  - Database file must be closed before calling this function
  - To check if a file is encrypted: IsSQLite3FileEncrypted('mydata.db3')

  Don't forget to back up your database before the test!!!

#13 Re: mORMot 2 » More mORMot2 examples: adapted from DMVCframework » 2025-12-24 03:25:53

Wow, there are so many demo programs! It feels like their number has even exceeded the examples that come with mORMot itself! I don't think anyone would dislike more examples, heh heh.

Personally, I still prefer the ThirdParty solution. Just like it is now, it can greatly reduce everyone's cost of obtaining examples.

#14 Re: mORMot 2 » Help with SQLite3 static encryption » 2025-12-22 07:25:46

In mORMot 2, SQLite3 encryption is built into the static library. Here's how to use it:

  1. Download static files from https://synopse.info/files/mormot2static.7z
  2. Add mormot.db.raw.sqlite3.static to your uses clause
  3. Pass password when creating the database:

  uses
    mormot.db.raw.sqlite3.static,
    mormot.orm.sqlite3;

  var
    Model: TOrmModel;
    Rest: TRestServerDB;
  begin
    Model := TOrmModel.Create([...]);
    Rest := TRestServerDB.Create(Model, 'mydata.db3', False, 'MyPassword');

  Or with TSqlDatabase directly:
  DB := TSqlDatabase.Create('mydata.db3', 'MyPassword');

  Important notes:
  - This encryption is NOT compatible with official SQLite SEE or wxsqlite3
  - NOT compatible with old mORMot 1 format (before 1.18.4413) - use OldSqlEncryptTablePassWordToPlain() to migrate
  - Uses AES-128 with PBKDF2 key derivation

#15 Re: mORMot 2 » Need help » 2025-12-22 07:22:26

These questions are more about your application's business logic and architecture design rather than mORMot framework usage itself.

  For general code review and architecture advice, you might consider:
  - Stack Overflow / Code Review Stack Exchange
  - Hiring a consultant
  - Reading DDD/Clean Architecture books

  The mORMot forum is best suited for questions about how to use the framework's APIs and features.

  That said, regarding ComputeFieldsBeforeWrite specifically: the mORMot documentation shows it's intended for lightweight field computation (timestamps, derived values). Querying the database inside it is not recommended.

#16 Re: mORMot 2 » Need help » 2025-12-22 07:19:40

I see your ComputeFieldsBeforeWrite implementation:

  NextID := aRest.TableMaxID(TOrmUser) + 1;
  if (aOccasion = oeAdd) and ((FInviteCode = '') or (NextID <= 3)) then
    FInviteCode := GenerateUniqueInviteCode(NextID);

  Issues:

  1. Race condition — TableMaxID + 1 is unreliable under concurrent inserts. Two users registering simultaneously may get the same NextID, causing duplicate invite codes.
  2. Database query in ComputeFieldsBeforeWrite — This method is called during the write operation. Querying TableMaxID here adds latency and potential deadlocks.

  Recommended fix:

  Generate the invite code after the record is inserted, when you have the actual ID:

  // In your registration service:
  function TDomainUserManager.RegisterUser(...): TID;
  begin
    Result := fOrm.Add(aUser, True);  // Insert first, get real ID
    if Result > 0 then
    begin
      aUser.IDValue := Result;
      aUser.InviteCode := GenerateUniqueInviteCode(Result);
      fOrm.Update(aUser, 'InviteCode');  // Update only this field
    end;
  end;

  Or use a UUID-based invite code that doesn't depend on ID:

  FInviteCode := Int64ToHex(Random64) + Int64ToHex(Random64);  // 32-char hex

  Also, what's the purpose of NextID <= 3? If it's for seeding admin accounts, consider handling that separately in InitializeTable.

#17 mORMot 2 » [PR] Add TQuickJSEngine High-Level Wrapper for QuickJS » 2025-12-22 06:36:10

zen010101
Replies: 1

Hi Arnaud,

  While migrating the mORMot 1 examples (specifically Example 22 "JavaScript HTTPApi web server" and Example 23 "JavaScript Tests") to mORMot 2, I noticed that although mORMot 2 has integrated QuickJS via mormot.lib.quickjs, it lacks a high-level wrapper similar to what SynSM (SpiderMonkey) provided in mORMot 1.

  I've implemented TQuickJSEngine in mormot.script.quickjs.pas to fill this gap. The main features include:

  TQuickJSEngine - Thread-safe JavaScript engine (inherits from TThreadSafeEngine):
  - Evaluate() - Execute JavaScript code and return result as variant
  - Global property - Late-binding variant access to the global object (e.g., Engine.Global.myVar := 123)
  - RegisterMethod() - Register Delphi methods callable from JavaScript
  - TimeoutValue - Script execution timeout control
  - GarbageCollect() / MaybeGarbageCollect() - Manual GC control

  TQuickJSVariant - Custom variant type for late-binding:
  - Allows Pascal code to access JS object properties using variant syntax
  - Example: jsObj.propName or jsObj.method(arg1, arg2)

  TQuickJSObject - Wrapper for JavaScript object operations:
  - HasProperty(), HasOwnProperty()
  - GetPropValue(), SetPropValue(), DefineProperty()
  - RunMethod() - Call a method on the object
  - Root() / UnRoot() - GC protection

  This enables straightforward migration of mORMot 1 JavaScript-based examples and provides a convenient API for embedding JavaScript in Delphi/FPC applications.

  The implementation leverages the existing mormot.script.core framework and follows mORMot 2 coding conventions.

  PR: [https://github.com/synopse/mORMot2/pull/425]

  Looking forward to your feedback!

#18 Re: mORMot 2 » Need help » 2025-12-21 10:12:36

● Hi testgary,

  I reviewed your code using Claude and created a feedback issue on your repository:
  https://github.com/pit500081/mormot2test/issues/1

  Summary of your 4 questions:

  Q1 - TUserRec for inter-layer communication:
  Good approach. Separating TOrmUser from DTO is correct. However, TUserRec has 23 fields serving too many purposes. Consider splitting into smaller DTOs like TUserProfileRec, TUserLoginResultRec, etc.

  Q2 - Captcha in CookieData:
  Security concern. Captcha text should NOT be stored client-side (even encrypted). Move to server-side storage using TSynDictionary (Token → CaptchaText mapping). Delete after verification to prevent replay attacks.

  Q3 - Separate modules for API and Web:
  Architecture is correct - both layers sharing IDomainUserManager is the right design. However:
 

  • REST layer (TRestUserManager.Register) is empty - needs implementation

  • MVC layer is too bloated - Register/Login methods handle captcha, session, validation, response formatting all in one. Extract into separate services (TCaptchaService, etc.) for better testability

  Q4 - Overall strategy:
  Solid foundation. Well done:
 

  • Password hashing with mcfSCrypt

  • Layered architecture (Repo → Domain → Presentation)

  • Dependency injection via interfaces

  • Extends TAuthUser properly

  Issues to fix:
 

  • GetGroupEnum bug in user.repo.impl.pas:55-56 - SizeOf(TUserGroupTypeEnum) returns 1, not enum count

  • LoginAt/LoginIp not updated on successful login

  • No brute-force protection - add login attempt rate limiting

  The architecture is sound - these are refinements rather than fundamental changes.

#19 mORMot 2 » New Wiki Article: RawUtf8 Application Guide » 2025-12-20 15:27:57

zen010101
Replies: 3

Hi everyone,

  I've published a comprehensive guide for RawUtf8-related functions in mORMot 2 on my wiki:

  https://github.com/zen010101/Claude_Mor … tion-Guide

  This guide covers RawUtf8-related functions organized into categories:

  - Type Conversion (To/From RawUtf8)
  - UTF-8 Validation and Detection
  - String Manipulation (Truncation, Append, Case, Trim)
  - Dynamic Array Operations
  - Comparison Functions (Standard, ORM, Prefix Matching/Idem)
  - Search/Locate Functions
  - Formatting, CSV/Array Conversion
  - Date/Time ISO8601, JSON, File Operations
  - And more...

  Each section includes function tables with descriptions and practical code examples.

  Hope this helps newcomers and serves as a quick reference for experienced users.

  Feedback and corrections are welcome!

#21 Re: mORMot 2 » Use of DynArrayLoadCsv » 2025-12-20 02:58:09

on the program dir, run "./bin/CsvDynArrayDemo.exe" command in the terminal window. smile

#22 Re: mORMot 2 » Trying to convert mORMot1 documentation conversion to mORMot2 » 2025-12-19 18:13:16

Javierus wrote:

Will you commit the working examples to the official repository?

I'm not sure if everyone needs it. I can put it in my repo for a while first.

#23 Re: mORMot 2 » mORMot2 vs Indy from claude code perspective » 2025-12-19 05:38:08

Javierus wrote:
zen010101 wrote:

I haven't built an index for the standard library yet. Could you tell me specifically how you did it? I believe this might greatly prevent AI from using hallucinations to make up non-existent functions.

This is the tool I was referring to; it has the whole source and documentation
https://github.com/JavierusTk/delphi-lookup

Wow, that looks good! I'll have a chance to compare it with Serena. Additionally, I'll look into whether your tool can also support FPC/Lazarus builds.

#24 Re: mORMot 2 » Use of DynArrayLoadCsv » 2025-12-19 05:03:00

initialization
    // Register RTTI before any CSV parsing
    Rtti.RegisterFromText([TypeInfo(TCsvItem), _TCsvItem]);

https://github.com/zen010101/Claude_Mor … array-demo

#25 Re: mORMot 2 » Trying to convert mORMot1 documentation conversion to mORMot2 » 2025-12-19 02:59:29

I would like to add one:

### mormot.app.daemon

Daemon (e.g. Windows Service) Stand-Alone Background Executable Support
- Parent Daemon Settings Class
- Parent Daemon Application Class

### mormot.app.agl

Launch, Watch and Kill Services or Executables from a main Service Instance
- `TSynAngelizeService` Sub-Service Settings and Process
- `TSynAngelize` Main Service Launcher and Watcher

#26 Re: mORMot 2 » mORMot2 vs Indy from claude code perspective » 2025-12-18 06:54:03

Javierus wrote:

I started using repomix long time ago, but imo that's for chat AI; now with Claude Code I just have mORMot2 documented, and also have a tool I made that had indexed all the libraries I handle, including the Delphi standard lib and of course mORMot2, and the agent can query for an identifier and gets the best result based on FTS and fuzzy search. Tried RAG, but didn't worked (sure it was my fault)

I started using Serena + pasLS (LSP Server for Pascal) for semantic search yesterday. It is included in the Claude Code Plugin store, and I think the effect is quite good. Of course, the official Serena does not support the Pascal/Delphi language. I have made some modifications, and after a test is completed, I will submit a PR to merge into the official master branch. Below is a list of mORMot 2 functions related to RawUtf8: https://gist.github.com/zen010101/3b27c … f89625fe6e

#27 Re: mORMot 2 » Read SQL Table Properties from a config file » 2025-12-17 14:40:45

I created a working demo for this: https://github.com/zen010101/Claude_Mor … pping-demo

It loads table/column mappings from mapping_config.json and applies them via OrmMapExternal + MapField at runtime - no recompilation needed.

#28 Re: mORMot 2 » How to disable service timeout only during long database processing? » 2025-12-17 14:24:51

===========================================
  Async Task Demo Client
  Demonstrates polling pattern
===========================================

Connected to server

Enter task duration in seconds (1-60): 10

Starting task with 10 second duration...
(Server timeout is 60s, but polling keeps session alive)

Task started with ID: 1

Status: Running... Progress: 4%
Status: Running... Progress: 9%
Status: Running... Progress: 14%
Status: Running... Progress: 20%
Status: Running... Progress: 25%
Status: Running... Progress: 29%
Status: Running... Progress: 35%
Status: Running... Progress: 40%
Status: Running... Progress: 45%
Status: Running... Progress: 50%
Status: Running... Progress: 55%
Status: Running... Progress: 60%
Status: Running... Progress: 65%
Status: Running... Progress: 71%
Status: Running... Progress: 75%
Status: Running... Progress: 80%
Status: Running... Progress: 86%
Status: Running... Progress: 90%
Status: Running... Progress: 95%
Status: COMPLETED!
Result: {"taskId":1,"taskName":"DemoTask","duration":10,"completedAt":"2025-12-17T19:51:42"}

Task finished!

Active tasks on server: 0

Press Enter to exit...

#29 Re: mORMot 2 » How to disable service timeout only during long database processing? » 2025-12-17 14:17:58

I created a demo demonstrating the polling pattern solution for this issue: https://github.com/zen010101/Claude_Mor … -task-demo

Instead of a single blocking call, the client starts the task and polls GetTaskResult() periodically - each poll updates LastAccessTix10, keeping the session alive without disabling TimeoutSec globally.

#30 Re: mORMot 2 » TRestServerAuthenticationDefault bug ?! » 2025-12-16 03:52:01

I'm really glad you like this article. Actually, I'm thinking about expanding this content into a full wiki in the form of FAQ + technical reviews, but it all depends on my spare time. If I get enough free time, I'll definitely keep enriching the wiki with more detailed and practical content. smile

#31 Re: mORMot 2 » TRestServerAuthenticationDefault bug ?! » 2025-12-15 17:26:37

In order to learn this feature, I specifically used Claude to generate a note: https://github.com/zen010101/Claude_Mor … -Explained

#32 Re: mORMot 2 » Read SQL Table Properties from a config file » 2025-12-15 16:45:49

Hah, that's only because your AI-friendly comments are so well-written that even the AI can "get" mORMot quickly -- it's like you left a super clear treasure map, and my AI tools just followed the lines faster than I could read them myself. wink

#33 Re: mORMot 2 » Read SQL Table Properties from a config file » 2025-12-15 14:26:50

Yes, mORMot2 supports reading table/column names from config files using OrmMapExternal + MapField.

  Key Mechanism

  1. Define ORM class with internal property names (compile-time):
  TDbBirthdayRecord = class(TOrmNoCase)
  published
    property DbCountry: RawUtf8 ...;
    property DbBirthdayDate: TDateTime ...;
  end;

  2. Load mapping from config (runtime):
  {
    "tableName": "BirthdayCelebration",
    "columns": {
      "DbCountry": "country_code",
      "DbBirthdayDate": "celebration_date"
    }
  }

  3. Apply mapping:
  // Map table name
  Mapping := OrmMapExternal(Model, TDbBirthdayRecord, ExternalDB, TableName);

  // Map column names
  Mapping^.MapField('DbCountry', 'country_code');
  Mapping^.MapField('DbBirthdayDate', 'celebration_date');

Complete demo: https://gist.github.com/zen010101/713cf … 44f277c1ee

#34 Re: mORMot 2 » Example Echo with TWebSocketAsyncServer » 2025-12-15 05:43:21

Javierus wrote:

IMO, that kind of simple examples is prefect for anyone approaching mORMot2; what for an expert is "just ..." for a newcomer is "ah, that's what I was looking for"

Maybe we can generate many simpler examples using Claude Code and merge them into the master branch smile

#35 Re: mORMot 2 » mormot.core.threads » 2025-12-15 03:48:11

  Key Differences from OmniThreadLibrary

  | Aspect             | OmniThreadLibrary     | mORMot                                    |
  |--------------------|-----------------------|-------------------------------------------|
  | Callback signature | procedure(i: integer) | procedure(IndexStart, IndexStop: integer) |
  | Granularity        | Per-item              | Per-range (more efficient)                |
  | Thread pool        | Implicit              | Explicit TSynParallelProcess              |
  | Anonymous methods  | Supported             | Requires method of object                 |

Full runnable demo is here:  https://gist.github.com/zen010101/a69f7 … 41da1424b7

#36 Re: mORMot 2 » Converting all datetime values in a record to localtime » 2025-12-15 03:15:36

another demo, tested with FPC:

https://gist.github.com/zen010101/4af9a … ebe62f19a9

Usage:

  var
    Rec: TMyRecord;
  begin
    // ... populate Rec ...

    // Convert from UTC to GMT+8
    ConvertRecordDateTimesToTimezone(Rec, TypeInfo(TMyRecord), 8);

    // Convert from UTC to EST (GMT-5)
    ConvertRecordDateTimesToTimezone(Rec, TypeInfo(TMyRecord), -5);
  end;

#37 Re: mORMot 2 » aLog in agl » 2025-12-15 02:46:45

The parent TSynDaemon.Create signature has no aLog parameter:

  constructor TSynDaemon.Create(aSettingsClass: TSynDaemonSettingsClass;
    const aWorkFolder, aSettingsFolder, aLogFolder,
          aSettingsExt, aSettingsName: TFileName;
          aSettingsOptions: TSynJsonFileSettingsOptions;
    const aSectionName: RawUtf8);

  Logging is actually configured via AfterCreate → fSettings.SetLog(TSynLog).

  This appears to be dead code - the parameter exists but does nothing.

#38 Re: mORMot 2 » Trying to convert mORMot1 documentation conversion to mORMot2 » 2025-12-14 15:59:49

Javierus wrote:

The temporal address for it is: http://wp.cyber.es/mORMot2-SAD-Index.html

I really like this version. Even if it doesn't end up being selected as the official version, please keep it.

Thank you again, Javierus, for presenting us with such concise and impactful mORMot 2 materials. I believe this will help many people. smile

#39 Re: mORMot 2 » Trying to convert mORMot1 documentation conversion to mORMot2 » 2025-12-14 15:44:09

Javierus wrote:
zen010101 wrote:

I will share the mormot2-migration skill, which may be helpful to others who wish to use Claude Code

I'm interested, will wait for it

Here is my skill file: ~/.cluade/skill/mormot2-migration/SKILL.md : https://gist.github.com/zen010101/ace68 … 0e1039e312

Here is the progress using it to migrate all the Samples shipped with mORMot 1.18 :

# mORMot 1 Examples Migration Progress

**Updated**: 2025-12-14 | **Target**: Compile with `{$define PUREMORMOT2}`

## Summary

| Compiler | Total | Pass | Fail |
|----------|-------|------|------|
| FPC      | 35    | 34   | 1    |
| Delphi   | 60    | 50   | 10   |
| **All**  | 95    | 84   | 11   |

**Overall: 84/95 (88%) projects compile successfully**

---

## FPC Compilation Results (.lpi)

| #  | Project                           | Status | Notes                          |
|----|-----------------------------------|--------|--------------------------------|
| 1  | 01/Project01.lpi                  | PASS   |                                |
| 2  | 02/Project02.lpi                  | PASS   |                                |
| 3  | 03/Project03Client.lpi            | PASS   |                                |
| 4  | 03/Project03Server.lpi            | PASS   |                                |
| 5  | 04/Project04Client.lpi            | PASS   |                                |
| 6  | 04/Project04Server.lpi            | PASS   |                                |
| 7  | 06/Project06Client.lpi            | PASS   |                                |
| 8  | 06/Project06Server.lpi            | PASS   |                                |
| 9  | 09/HttpApiServer.lpi              | PASS   |                                |
| 10 | 10/httpservice.lpi                | PASS   |                                |
| 11 | 10/httpserviceSetup.lpi           | PASS   |                                |
| 12 | 11/LogView.lpi                    | FAIL   | mormot.ui.controls (VCL only)  |
| 13 | 13/JSONSQLClient.lpi              | PASS   |                                |
| 14 | 13/JSONSQLServer.lpi              | PASS   |                                |
| 15 | 14/Project14Client.lpi            | PASS   |                                |
| 16 | 14/Project14ServerHttp.lpi        | PASS   |                                |
| 17 | 14/Project14ServerHttpWeak.lpi    | PASS   |                                |
| 18 | 14/Project14ServerInMemory.lpi    | PASS   |                                |
| 19 | 15/PerfTest.lpi                   | PASS   | Fixed TRestBatch pattern       |
| 20 | 15/PerfTestConsole.lpi            | PASS   | Fixed TRestBatch pattern       |
| 21 | 24/MongoDBTests.lpi               | PASS   | Fixed TRestBatch pattern       |
| 22 | 25/JSONPerfTests.lpi              | PASS   | Fixed comment syntax           |
| 23 | 27/FPC/JSONconsole.lpi            | PASS   |                                |
| 24 | 27/FPC/LCLClient.lpi              | PASS   |                                |
| 25 | 30/MVCServer.lpi                  | PASS   | Fixed TOrmTable, TRestBatch    |
| 26 | 30/MVCServerMongoDB.lpi           | PASS   | Fixed PBKDF2_SHA3 import       |
| 27 | 30/MVCServerPostgreSQL.lpi        | PASS   | Fixed TSqlDBConnectionProperties |
| 28 | 31/Project31LongWorkClient.lpi    | PASS   |                                |
| 29 | 31/Project31LongWorkServer.lpi    | PASS   |                                |
| 30 | 31/Project31SimpleEchoServer.lpi  | PASS   | Fixed WebSocket API            |
| 31 | 31/Project31WinHTTPEchoServer.lpi | PASS   |                                |
| 32 | 33/ECC.lpi                        | PASS   |                                |
| 33 | 36/RESTBenchmark.lpi              | PASS   |                                |
| 34 | 37/FishShopDaemon.lpi             | PASS   |                                |
| 35 | 37/TestFishShop.lpi               | PASS   |                                |

**FPC: 34/35 (97%) passed**

---

## Delphi Compilation Results (.dpr/.dproj)

### Passed (50)

| #  | Project                              | Notes                   |
|----|--------------------------------------|-------------------------|
| 1  | 04/Project04ServerStatic.dpr         |                         |
| 2  | 05/SynPdfFormCanvas.dpr              |                         |
| 3  | 05/SynPdfLayers.dpr                  |                         |
| 4  | 05/TestSQLite3Pages.dpr              |                         |
| 5  | 07/SynTest.dpr                       |                         |
| 6  | 11/LibraryTest.dpr                   |                         |
| 7  | 11/LoggingTest.dpr                   |                         |
| 8  | 11/RemoteLoggingTest.dpr             |                         |
| 9  | 11/MyLibrary.dpr                     |                         |
| 10 | 11/UnSynLz.dpr                       |                         |
| 11 | 11/Map2Mab.dpr                       |                         |
| 12 | 11/thread512.dpr                     |                         |
| 13 | 12/DBSynLZ.dpr                       |                         |
| 14 | 14/Project14Server.dpr               |                         |
| 15 | 14/Project14ServerExternal.dpr       |                         |
| 16 | 15/mORMotBatchInsert.dpr             |                         |
| 17 | 15/PerfTest.dpr                      | Fixed TRestBatch pattern |
| 18 | 15/PerfTestConsole.dpr               | Fixed TRestBatch pattern |
| 19 | 16/Project16Client.dpr               |                         |
| 20 | 16/Project16ServerHttp.dpr           |                         |
| 21 | 17/mORMotVCLTest.dpr                 | Full PUREMORMOT2        |
| 22 | 18/Project18Server.dpr               |                         |
| 23 | 19/Project19Server.dpr               |                         |
| 24 | 20/Project20Client.dpr               |                         |
| 25 | 20/Project20ServerInMemory.dpr       |                         |
| 26 | 21/Project21HttpClient.dpr           |                         |
| 27 | 21/Project21HttpServer.dpr           |                         |
| 28 | 24/MongoDBTests.dpr                  | Fixed TRestBatch pattern |
| 29 | 25/JSONPerfTests.dpr                 | Fixed comment syntax    |
| 30 | 26/RESTClient.dpr                    |                         |
| 31 | 26/RESTserver.dpr                    |                         |
| 32 | 27/Project14ServerHttpWrapper.dpr    |                         |
| 33 | 27/RegressionTestsServer.dpr         |                         |
| 34 | 28/RESTserver.dpr                    |                         |
| 35 | 28/RESTclient.dpr                    |                         |
| 36 | 30/MVCServer.dpr                     | Fixed TOrmTable, TRestBatch |
| 37 | 30/MVCServerMongoDB.dpr              | Fixed PBKDF2_SHA3 import |
| 38 | 30/MVCServerPostgreSQL.dpr           | Fixed TSqlDBConnectionProperties |
| 39 | 31/Project31ChatServer.dpr           |                         |
| 40 | 31/Project31ChatClient.dpr           |                         |
| 41 | 31/Project31SimpleEchoServer.dpr     | Fixed WebSocket API     |
| 42 | 34/Project34RTSPproxy.dpr            |                         |
| 43 | 35/01/ServBook.dpr                   |                         |
| 44 | 35/01/TestAll.dpr                    |                         |
| 45 | 35/02/ServBook.dpr                   |                         |
| 46 | 35/02/TestAll.dpr                    |                         |
| 47 | 35/03/ServBook.dpr                   |                         |
| 48 | 35/03/TestAll.dpr                    |                         |
| 49 | 35/04/ServBook.dpr                   |                         |
| 50 | 35/04/TestAll.dpr                    |                         |
| 51 | 35/05/ServBook.dpr                   |                         |
| 52 | 35/05/TestAll.dpr                    |                         |

### Failed (10) - Permanently Blocked

| #  | Project                          | Error                                 | Status                       |
|----|----------------------------------|---------------------------------------|------------------------------|
| 1  | 08/TaskDialogTest.dpr            | mormot.ui.login not found             | Blocked: UI unit missing     |
| 2  | 11/LogView.dpr                   | SynMemoEx not found                   | Blocked: SynMemoEx removed   |
| 3  | 12/SynDBExplorer.dpr             | mormot.ui.orm not found               | Blocked: UI framework        |
| 4  | 22/JSHttpApiServer.dpr           | Executable undeclared (SynSM)         | Blocked: SynSM removed       |
| 5  | 23/TestMustache.dpr              | SynSM not found                       | Blocked: SynSM removed       |
| 6  | 23/TestSynSM.dpr                 | SynSM.inc not found                   | Blocked: SynSM removed       |
| 7  | 27/FMClient.dpr                  | SynCrossPlatformJSON not found        | Blocked: CrossPlatform removed |
| 8  | 27/VCLClient.dpr                 | SynCrossPlatformJSON not found        | Blocked: CrossPlatform removed |
| 9  | 27/RegressionTests.dpr           | SynCrossPlatform.inc not found        | Blocked: CrossPlatform removed |
| 10 | 27/MobileClient.dpr              | SynCrossPlatformJSON not found        | Blocked: CrossPlatform removed |
| 11 | 28/RESTserver_wrappers.dpr       | Delphi-only (ODBC), no .lpi           | Blocked: No FPC project file |
| 12 | 30/MVCServerFirebird.dpr         | TSqlDBZeosConnectionProperties        | Blocked: No Zeos/FireDAC driver |
| 13 | MainDemo/SynFile.dpr             | mORMoti18n not found                  | Blocked: UI framework removed |

**Delphi: 52/65 (80%) passed** (excluding permanently blocked projects)

Those who are interested can continue to improve the SKILL.md file, and then use Claude Code to migrate the remaining Samples files to mORMot 2.

#40 Re: mORMot 2 » mORMot2 vs Indy from claude code perspective » 2025-12-13 15:07:14

Javierus wrote:

I started using repomix long time ago, but imo that's for chat AI; now with Claude Code I just have mORMot2 documented, and also have a tool I made that had indexed all the libraries I handle, including the Delphi standard lib and of course mORMot2, and the agent can query for an identifier and gets the best result based on FTS and fuzzy search. Tried RAG, but didn't worked (sure it was my fault)

Great! After using agentic AI like Claude Code, I never touched chat-based AI again because this is the correct way to do AI coding smile

I haven't built an index for the standard library yet. Could you tell me specifically how you did it? I believe this might greatly prevent AI from using hallucinations to make up non-existent functions.

#41 Re: mORMot 2 » mORMot2 vs Indy from claude code perspective » 2025-12-13 14:19:24

ab wrote:

Sharing more input about how to use Claude could be just great.

I will smile

Some AI engines state that we could even use https://github.com/BeRo1985/pasllm for the task, locally in pure CPU, and pure pascal code. wink

To be honest, running models locally is not very realistic, and the results are surprisingly poor. You know, even when running cloud-based models, apart from Anthropic's Opus and Sonnet models, even GPT5.2, which was just released a couple of days ago, doesn't perform well in actual tests. Therefore, from my experience, don't waste time on other models; directly using Claude Code is the best choice.

Second, the two most important pieces of experience with AI Code are TDD and SPEC-first. For the former, I think using skills and following the ex\tdd-service paradigm provided by ab is sufficient. For the latter, one might use spec-kit (produced by GitHub, more suitable for 0->1 scenarios) or open-spec (more suitable for refactoring old projects and adding new features). I am currently researching both. But Claude Code is good enough that even without using these two tools, I can successfully complete projects under the mORMot 2 framework.

Finally, don't treat AI Code as a wishing well; it's better to regard it as an all-round intern. We should act as demand proposers, architecture plan reviewers, and value judgment decision-makers.

#42 Re: mORMot 2 » mORMot2 vs Indy from claude code perspective » 2025-12-13 14:05:52

Javierus wrote:

Thank you very much! It's extraordinarily difficult finding someone sharing AI coding stuff related to Delphi

I also learned a lot of AI knowledge from @flydev, especially his magic prompt: https://github.com/flydev-fr/the-big-prompt smile

#43 Re: mORMot 2 » Trying to convert mORMot1 documentation conversion to mORMot2 » 2025-12-13 14:01:18

I am trying to migrate the examples of Mormot 1.18 to Mormot 2 using Claude Code. Once all are successful, I will share the mormot2-migration skill, which may be helpful to others who wish to use Claude Code. Here is the progress:

| #   | Project Path                                              | Status  |
| --- | --------------------------------------------------------- | ------- |
| 1   | 01 - In Memory ORM/Project01.lpi                          | SUCCESS |
| 2   | 02 - Embedded SQLite3 ORM/Project02.lpi                   | SUCCESS |
| 3   | 03 - NamedPipe Client-Server/Project03Client.lpi          | SUCCESS |
| 4   | 03 - NamedPipe Client-Server/Project03Server.lpi          | SUCCESS |
| 5   | 04 - HTTP Client-Server/Project04Client.lpi               | SUCCESS |
| 6   | 04 - HTTP Client-Server/Project04Server.lpi               | SUCCESS |
| 7   | 06 - Remote JSON REST Service/Project06Client.lpi         | SUCCESS |
| 8   | 06 - Remote JSON REST Service/Project06Server.lpi         | SUCCESS |
| 9   | 09 - HttpApi web server/HttpApiServer.lpi                 | SUCCESS |
| 10  | 10 - Background Http service/httpservice.lpi              | SUCCESS |
| 11  | 10 - Background Http service/httpserviceSetup.lpi         | SUCCESS |
| 12  | 11 - Exception logging/LogView.lpi                        | SUCCESS |
| 13  | 13 - StandAlone JSON SQL server/JSONSQLClient.lpi         | SUCCESS |
| 14  | 13 - StandAlone JSON SQL server/JSONSQLServer.lpi         | SUCCESS |
| 15  | 14 - Interface based services/Project14Client.lpi         | SUCCESS |
| 16  | 14 - Interface based services/Project14ServerHttp.lpi     | SUCCESS |
| 17  | 14 - Interface based services/Project14ServerHttpWeak.lpi | SUCCESS |
| 18  | 14 - Interface based services/Project14ServerInMemory.lpi | SUCCESS |
| 19  | 27 - CrossPlatform Clients/FPC/JSONconsole.lpi            | SUCCESS |
| 20  | 27 - CrossPlatform Clients/FPC/LCLClient.lpi              | SUCCESS |
| 21  | 31 - WebSockets/Project31LongWorkClient.lpi               | SUCCESS |
| 22  | 31 - WebSockets/Project31LongWorkServer.lpi               | SUCCESS |
| 23  | 31 - WebSockets/Project31WinHTTPEchoServer.lpi            | SUCCESS |
| 24  | 33 - ECC/ECC.lpi                                          | SUCCESS |
| 25  | 36 - Simple REST Benchmark/RESTBenchmark.lpi              | SUCCESS |
| 26  | 37 - FishShop Service/FishShopDaemon.lpi                  | SUCCESS |
| 27  | 37 - FishShop Service/TestFishShop.lpi                    | SUCCESS |

#44 Re: mORMot 2 » mORMot2 vs Indy from claude code perspective » 2025-12-13 07:54:13

These skills were also generated with the help of Claude Code. Below is an example of the mormot2-testing skill: https://gist.github.com/zen010101/d1208 … a343d35833

Here is the test code in the project generated by Claude Code after using this skill (I didn't write a single line of code for the entire project; it was all generated by Claude Code): https://gist.github.com/zen010101/16543 … 1e9e0d3022

This is the System Design document generated based on requirements: https://gist.github.com/zen010101/9f623 … 1044874a56

#45 Re: mORMot 2 » mORMot2 vs Indy from claude code perspective » 2025-12-13 07:35:33

Yes, CC can understand mORMot2 code very well. I have generated some skills for it, and CC can smoothly build a project under the mORMot 2 framework from scratch.

  | Skill            | Description                        |
  |------------------|------------------------------------|
  | mormot2-dynarray | TDynArray Usage Guide              |
  | mormot2-json     | JSON Processing (IDocDict/IDocList)|
  | mormot2-keyvalue | TSynDictionary/IKeyValue Usage     |
  | mormot2-testing  | Testing Framework (TSynTestCase/TSynTests) |

#46 Re: mORMot 2 » Log rotation is not working as expect » 2025-09-10 13:32:37

Awesome! Thank you so much for the quick and thorough fix ?

I’ve just reviewed the commits, and they seem to address the key issues I mentioned earlier. I’ll take some time to test these changes carefully when I get the chance, and see if the rotation mechanism now works as expected.

Really appreciate your effort and continuous improvements—mORMot is getting stronger and better!

#47 Re: mORMot 2 » Log rotation is not working as expect » 2025-09-06 17:17:59

Based on code tracing, an excessively small RotateFileSizeKB is not the key cause of the issue. The PerformRotation method is only invoked within the following method:

procedure TSynLog.LogEnterFmt(nfo: PSynLogThreadInfo; inst: TObject;
  fmt: PUtf8Char; args: PVarRec; argscount: PtrInt); 

However, the check and invocation of PerformRotation are missing in the method below:

procedure TSynLog.LogEnter(nfo: PSynLogThreadInfo; inst: TObject; txt: PUtf8Char
  {$ifdef ISDELPHI} ; addr: PtrUInt {$endif});   

This means that calls like `l := TSynLog.Enter;` cannot trigger the rotation check.
This is the first bug.

Even if we use TSynLog.LogEnterFmt (which can trigger the rotation check), the check relies on the following condition:

if pendingRotate in fPendingFlags then // from OnFlushToStream
  PerformRotation;   

And the OnFlushToStream event is only assigned to fWriter.OnFlushToStream if AutoFlushTimeOut is explicitly set to a non-zero value:

if fFamily.AutoFlushTimeOut <> 0 then
begin
  fWriter.OnFlushToStream := OnFlushToStream; // note: overwrites fWriterEcho
  OnFlushToStream(nil, 0);
  fFamily.EnsureAutoFlushThreadRunning;
end; 

In other words, if I do not explicitly set AutoFlushTimeOut, OnFlushToStream will never be triggered—and consequently, PerformRotation will not run either.
This is the second bug.

Thirdly, even if the above two bugs are fixed, the PerformRotation check is only invoked in methods related to TSynLog.Enter. Calls like TSynLog.DoLog or TSynLog.Add.Log will still not trigger rotation checks. This behavior may require further improvement, or at the very least, explicit documentation to clarify it.

#49 Re: mORMot 2 » Check Out This AI-Generated Podcast on mORMot 1.18 SAD » 2025-08-18 14:28:44

Yes, the answers of many large language models are based on the code of mORMot 1. However, even so, it is difficult to directly compile and run. I feel that large language models are confused by the complexity of mORMot and have serious hallucinations. It's hard for me to imagine that with the current training sets of large language models, any AI has really understood mORMot 2 smile

Before you give further hints and demonstrations, I still need to conduct in-depth research on my own for a while. :)

#50 Re: mORMot 2 » Check Out This AI-Generated Podcast on mORMot 1.18 SAD » 2025-08-18 04:01:17

Thanks a lot for sharing your insights! I’d be truly grateful if you could provide a small demo showcasing your entire workflow—it would be incredibly helpful.
I’m also deeply interested in vide coding in the Object Pascal. However, I’ve always felt that current large language models aren’t very friendly toward Object Pascal. This might stem from a lack of high-quality training data. Additionally, the mORMot framework is so BIG and complex that inputting a relatively small number of tokens rarely yields effective outputs.
For these reasons, I’m closely following your practices and progress in AI-assisted coding for Pascal. I sincerely hope your work can bring a fresh wave of AI-driven innovation to the community—something that feels like a breath of fresh air. smile

Board footer

Powered by FluxBB