And 3 parameters for the spec class that help: HandleCorsRequest - it is most likely CORS will be needed, applicaton/json to support JSON content and ExposeServerExceptions for debug reasons:

Class shvarov.travel.spec Extends %REST.Spec [ ProcedureBlock ]

{

Parameter HandleCorsRequest = 1;

Parameter CONTENTTYPE = "application/json";

Parameter ExposeServerExceptions = 1;
...

also I always add the same _spec GET endpoint to let swagger have a working specification in docker - the default one doesn't work in docker as IRIS default spec one overrides the host variable to one, that doesn't work.

ClassMethod GetSpec() As %DynamicObject
{

set specname=$p(..%ClassName(1),".impl")

Set spec = {}.%FromJSON(##class(%Dictionary.CompiledXData).%OpenId(specname_".spec||OpenAPI").Data)

Set url = $Select(%request.Secure:"https",1:"http") _ "://"_$Get(%request.CgiEnvs("SERVER_NAME")) _ ":" _ $Get(%request.CgiEnvs("SERVER_PORT")) _ %request.Application
Set spec.servers = [{"url" : (url)}]

Quit spec

}

Just've published the shvarov-persistent package once installed by
USER>zpm "install shvarov-persistent"

will add shvarov.persistent.base class which can be used as an ancestor after %Persistent, like:

Class yourclass Extends (%Persistent, shvarov.persistent.base)

, which will add two properties:

Property CreatedAt As %TimeStamp [ InitialExpression = {$ZDT($H, 3)} ];

Property LastUpdate As %TimeStamp [ SqlComputeCode = {set {*}=$ZDATETIME($HOROLOG,3)}, SqlComputed, SqlComputeOnChange = (%%INSERT, %%UPDATE) ];

Also this could be a typical copy-paste for a REST API app created in a module.xml in a <module> section:

<CSPApplication 
        Url="/travel/api"
        PasswordAuthEnabled="0"
        UnauthenticatedEnabled="1"
        DispatchClass="shvarov.travel.disp"
        MatchRoles=":{$dbrole}"
        Recurse="1"
        UseCookies="2"
        CookiePath="/travel/api"
       />

where /travel/api is the app name, and shvarov.travel.disp - a generated class vs the swagger spec file and shvarov.travel.spec class.

I think it is a good use-case for embedded python. I asked gpt and it suggested the following python code:

from datetime import datetime
from zoneinfo import ZoneInfo

# Original string
input_str = "Thu Jul 03 08:20:00 CEST 2025"

# Strip the abbreviation since it's not useful for parsing
# Replace it with an IANA timezone
# Let's assume "CEST" corresponds to Europe/Paris
input_str_cleaned = input_str.replace("CEST", "").strip()

# Parse the datetime
dt_naive = datetime.strptime(input_str_cleaned, "%a %b %d %H:%M:%S %Y")

# Localize to the correct zone
dt_aware = dt_naive.replace(tzinfo=ZoneInfo("Europe/Paris"))

# Format in ISO format with UTC offset
print(dt_aware.isoformat())  # e.g., '2025-07-03T08:20:00+02:00'

Also it suggested to make a mapping for CEST/CET:

tz_abbreviation_map = {
    "CEST": "Europe/Paris",
    "CET": "Europe/Paris",
    "EDT": "America/New_York",
    "EST": "America/New_York",
    "PST": "America/Los_Angeles",
    # Add more mappings as needed
}

Hi @Phillip Wu !

Namespaces give flexibility and were introduced to make a lot of powerful things possible.

If you are confused with all this uncertainty and don't need flexibility for now you can create Namespace DEV that has only one database DEV for everything and you can think that you are working with database DEV only with no any confusion.

But you will sign in into Namespace DEV in your IRIS system as users log in into Namespaces in InterSystems IRIS.
 

Or, e.g., if you take any vanilla IRIS docker image and run it, it will have a USER namespace that provides access to the USER database, which is convenient to use for any dev experiments.