Standardbibliothek
Antra::Time
import Antra::TimeSmall UTC time helpers for logger timestamps, deadlines and comparisons.
Antra::Time is a deliberately small time surface for absolute timestamps,
lightweight formatting and simple parsing.
Practical defaults:
%Time{...}is a plain copyable data value- stored values stay in UTC with
unix_msprecision - local time is a display or parse option, not a second stored representation
to_iso8601(...)andformat(...)cover the most common output pathsstrftime(...)/strptime(...)expose the thinner host-backed Perl pathformat_locale(...)andparse(..., [locale: ...])cover small:deand:usenduser formsmonotonic_us(),monotonic_resolution_us(),measure_ms(...)andmeasure_avg_ms(...)cover runtime measurement without wall-clock jumps
Core %Time{...} shape:
unix_ms:absolute Unix timestamp in millisecondszone:currently always:utcinside the stored value
Common output choices:
- machine/API timestamp:
Time.to_iso8601(time) - small readable date:
Time.format(time, :date) - custom display:
Time.format(time, "MMM dd, yyyy hh:mm:ss a") - existing Perl/Unix format:
Time.strftime(time, "%Y-%m-%d %H:%M:%S") - German default:
Time.format_locale(time, :de) - US default:
Time.format_locale(time, :us) - direct calendar/time parts:
Time.year(time),Time.month(time),Time.day(time),Time.hour(time)
Locale preset defaults:
:de, :datetime->31.12.2026 23:59:59:de, :date->31.12.2026:de, :time->23:59:59:us, :datetime->12/31/2026 11:59:59 PM:us, :date->12/31/2026:us, :time->11:59:59 PM
Parse paths stay intentionally small:
Time.parse("2026-12-31T23:59:59.123Z")for ISO-8601Time.parse("31.12.2026 23:59:59", [locale: :de])for German presetsTime.parse("12/31/2026 11:59:59 PM", [locale: :us])for US presetsTime.strptime("2026-12-31 23:59:59", "%Y-%m-%d %H:%M:%S")for explicit host formats
Time.format(...) template symbols:
yyyyyear with century,yyshort yearMMMMfull month name,MMMshort month name,MMmonth numberddddfull weekday name,dddshort weekday nameddday of monthHH24-hour,hh12-hourmmminute,sssecond,SSSmillisecondalowercase am/pmZUTCZor local numeric offset like+02:00
Literal text stays literal. For text that would otherwise look like a token, quote it with single quotes, for example:
"yyyy-MM-dd 'at' HH:mm:ss"
For host-native %Y, %m, %d, ... directives use Time.strftime(...)
or Time.strptime(...) instead of the template parser.
If an input text has no explicit offset, [zone: :utc | :local] decides how
that wall-clock time is interpreted.
Field helpers stay numeric and follow the same projection rules:
Time.year/month/day(...)Time.hour/minute/second/millisecond(...)Time.day_of_year(...)
They default to UTC and accept the same [zone: :utc | :local] option when
you want local calendar fields instead of UTC ones.
Example:
import Antra::Duration as Duration
import Antra::Time as Time
my start = Time.from_unix_ms(0)
my deadline = Time.add(start, 90sec)
my [result, elapsed_ms] = Time.measure_ms(|| -> 42)
my [_last, average_ms] = Time.measure_avg_ms(5, || -> 42)
Time.sleep(Duration.parse(dur"PT0.01S"))
println(Time.to_iso8601(deadline))
println(Time.format(deadline, "yyyy-MM-dd HH:mm:ss.SSS Z"))
println(Time.format_locale(deadline, :de))
println(Time.year(deadline))
println(Time.hour(deadline, [zone: :local]))
println(Time.diff_as(deadline, start, :min))
println(elapsed_ms)
println(average_ms)Example:
import Antra::Time as Time
my de = Time.parse("31.12.2026 23:59:59", [locale: :de])
my us = Time.parse("12/31/2026 11:59:59 PM", [locale: :us])
my raw = Time.strptime("2026-12-31 23:59:59", "%Y-%m-%d %H:%M:%S")
println(Time.to_iso8601(de))
println(Time.to_iso8601(us))
println(Time.to_iso8601(raw))Überblick#
Fuer echte Zeitpunkte gibt es jetzt ein kleines UTC-orientiertes Paket
Antra::Time.
Der erste Wertkern ist bewusst schlicht:
%Time{
unix_ms: 1719150000123,
zone: :utc
}Damit laesst sich ein Zeitpunkt als normaler Datenwert herumreichen, matchen,
loggen und mit Duration kombinieren, ohne sofort eine groessere
DateTime-/Zeitzonen-Surface einzufuehren.
Ein typischer Einstieg ist:
import Antra::Duration as Duration
import Antra::Time as Time
my epoch = Time.from_unix_ms(0)
my deadline = Time.add(epoch, 90sec)
println(Time.to_iso8601(epoch))
println(Time.to_iso8601(deadline))
println(Time.compare(epoch, deadline))
println(Duration.to_sec(Time.diff(deadline, epoch)))
println(Time.to_iso8601(deadline, [zone: :local]))
println(Time.diff_as(deadline, epoch, :min))Die erste kleine API ist bewusst knapp:
Time.now_utc()Time.monotonic_us()fuer monotone LaufzeitmessungTime.monotonic_resolution_us()fuer die gemeldete Host-Clock-AufloesungTime.from_unix_ms(...),Time.to_unix_ms(...)Time.from_unix(...),Time.to_unix(...)Time.to_iso8601(...), optional mit[zone: :utc | :local]Time.format(..., :iso8601 | :date | :time), optional mit[zone: :utc | :local]Time.format(..., "MM dd"),Time.format(..., "MMM dd, yyyy hh:mm:ss a")oderTime.format(..., "yyyy-MM-dd HH:mm:ss.SSS Z")fuer kleine eigene LayoutsTime.strftime(..., "%Y-%m-%d %H:%M:%S"), optional mit[zone: :utc | :local]Time.format_locale(..., :de | :us), optional mit[kind: :date | :time | :datetime, zone: :utc | :local]Time.year/month/day/hour/minute/second/millisecond/day_of_year(...), optional mit[zone: :utc | :local]Time.parse(...)fuer ISO-8601,Time.parse(..., [locale: :de | :us, ...])fuer Locale-PresetsTime.strptime(..., "%Y-%m-%d %H:%M:%S"), optional mit[zone: :utc | :local]Time.add(time, duration)Time.measure_ms(fn)fuer[result, elapsed_ms]ohne Wall-Clock-SpruengeTime.diff(later, earlier)Time.diff_as(later, earlier, :sec | :min | :hour | :day | :week)Time.before?(a, b),Time.after?(a, b)Time.compare(a, b)mit:lt,:eq,:gtwie bei<=>Time.time?(...)
Der MVP bleibt absichtlich eng:
- der gespeicherte
%Time{...}-Wert bleibt aktuell immer beizone: :utc - lokale Zeit gibt es bisher nur als Ausgabe-Projektion ueber
[zone: :local] - Parse ist bewusst klein und deckt nur ISO-8601, die eingebauten
:de/:us-Presets und explizitestrptime-Formate ab Timeist im Moment eher ein kleiner UTC-Zeitpunkt als ein grossesDateTime-Framework
Bei Time.format(...) gibt es neben den benannten Styles auch einen kleinen
Template-Modus. Aktuell unterstuetzt er bewusst nur einen sicheren Kern an
gut lesbaren Tokens:
yyyy,yyMMMM,MMM,MMdddd,ddd,ddHH,hh,mm,ss,aSSSZ
Damit sind Formen wie "MM dd", "MMM dd, yyyy hh:mm:ss a",
"dddd, MMMM dd 'at' hh:mm:ss a", "yyyy-MM-dd" oder
"yyyy-MM-dd HH:mm:ss.SSS Z" moeglich, ohne gleich ein grosses Kalender-
Framework einzufuehren. Literaler Text innerhalb des Templates kann mit
einfachen Quotes markiert werden.
Wenn du stattdessen direkt das aus Perl und vielen Unix-Tools bekannte
strftime-Format nutzen willst, gibt es zusaetzlich Time.strftime(...).
Das ist der duennere Pfad fuer bestehende %Y-%m-%d-Formate, waehrend
Time.format(...) eher die lesbarere Antra-Oberflaeche fuer neue Skripte ist.
Fuer haeufige Enduser-Formen gibt es zusaetzlich kleine Locale-Presets:
Time.format_locale(time, :de)->31.12.2026 23:59:59Time.format_locale(time, :de, [kind: :date])->31.12.2026Time.format_locale(time, :us)->12/31/2026 11:59:59 PMTime.format_locale(time, :us, [kind: :time])->11:59:59 PM
Das ist bewusst kein allgemeines i18n-System, sondern nur ein kleiner fester Preset-Satz fuer Deutschland und US-Formen.
Wenn du statt formatierter Strings lieber direkt Zahlen brauchst, gibt es zusätzlich kleine Feld-Getter:
Time.year(time)Time.month(time)Time.day(time)Time.hour(time)Time.minute(time)Time.second(time)Time.millisecond(time)Time.day_of_year(time)
Diese Helper sind bewusst nur Projektionen auf denselben absoluten Zeitpunkt.
Sie aendern also keinen %Time{...}-Wert, sondern lesen ihn nur als UTC oder
mit [zone: :local] als lokale Kalender-/Uhrzeit-Sicht aus.
Zum Einlesen gibt es den passenden Gegenpfad:
Time.parse("2026-12-31T23:59:59.123Z")fuer ISO-8601Time.parse("31.12.2026 23:59:59", [locale: :de])fuer deutsche PresetsTime.parse("12/31/2026 11:59:59 PM", [locale: :us])fuer US-PresetsTime.strptime("2026-12-31 23:59:59", "%Y-%m-%d %H:%M:%S")fuer freie Host-Formate
Wenn die Eingabe selbst keinen Offset traegt, bestimmt [zone: :utc | :local],
wie die gelesene Uhrzeit interpretiert wird.
Typen#
typedef Zone = :utc | :localDisplay zone of a %Time{...} value.
typedef Locale = :de | :usLocale presets of format_locale and parse.
typedef LocaleKind = :date | :time | :datetimeWhat a locale preset shows.
typedef FormatStyle = :iso8601 | :date | :timePreset styles of format.
typedef DiffUnit = :sec | :min | :hour | :day | :weekUnits of diff_as.
Funktionen#
addafter?before?comparedayday_of_yeardiffdiff_asformatformat_localefrom_unixfrom_unix_mshourmeasure_avg_msmeasure_msmillisecondminutemonotonic_resolution_usmonotonic_usmonthnow_utcparsesecondsleepstrftimestrptimetime?to_iso8601to_unixto_unix_msyear
fn add(time, duration)
fn add(_time, duration)Returns a new %Time{...} shifted by the given Duration.
fn after?(a, b)Returns true if a is later than b.
fn before?(a, b)Returns true if a is earlier than b.
fn compare(a, b)Compares two %Time{...} values and returns :lt, :eq or :gt.
fn day(time)
fn day(time, [zone :- Zone = :utc, ..])
fn day(_time, [zone: = :utc, ..])Returns the projected day of month in the range 1..31.
fn day_of_year(time)
fn day_of_year(time, [zone :- Zone = :utc, ..])
fn day_of_year(_time, [zone: = :utc, ..])Returns the projected day of year in the range 1..366.
fn diff(later, earlier)Returns the signed Duration difference later - earlier as %sec[...].
fn diff_as(later, earlier)
fn diff_as(later, earlier, unit :- DiffUnit)Returns the signed time difference projected into a fixed unit.
fn format(time)
fn format(time, [zone: = :utc, ..])
fn format(time, template :- String | FormatStyle | [zone :- Zone?, ..])
fn format(time, template :- String | FormatStyle, [zone :- Zone = :utc, ..])
fn format(time, style)
# … 3 weitere KlauselnFormats a %Time{...} value using the default :iso8601 style.
Named styles stay available via :iso8601, :date and :time.
For custom layouts you can also pass a template string such as
"MM dd", "MMM dd, yyyy hh:mm:ss a" or
"yyyy-MM-dd HH:mm:ss.SSS Z".
fn format_locale(time, locale :- Locale)
fn format_locale(time, locale :- Locale, [kind :- LocaleKind = :datetime, zone :- Zone = :utc, ..])Formats a %Time{...} value using locale presets for Germany or the US.
fn from_unix(sec)Builds a %Time{...} value from Unix seconds.
fn from_unix_ms(ms)Builds a %Time{...} value from Unix milliseconds.
fn hour(time)
fn hour(time, [zone :- Zone = :utc, ..])
fn hour(_time, [zone: = :utc, ..])Returns the projected hour in the range 0..23.
fn measure_avg_ms(n, fn)
fn measure_avg_ms(n, _fn)Runs fn n times and returns [last_result, average_elapsed_ms].
This is intentionally a tiny helper for focused microbenchmarks where the caller still wants control over output formatting and setup.
fn measure_ms(fn)Runs fn and returns [result, elapsed_ms] based on the monotonic clock.
The elapsed value is a plain millisecond number and may be fractional for very short calls.
fn millisecond(time)
fn millisecond(time, [zone :- Zone = :utc, ..])
fn millisecond(_time, [zone: = :utc, ..])Returns the millisecond fraction in the range 0..999.
fn minute(time)
fn minute(time, [zone :- Zone = :utc, ..])
fn minute(_time, [zone: = :utc, ..])Returns the projected minute in the range 0..59.
fn monotonic_resolution_us()Returns the reported monotonic clock resolution in microseconds.
This is the host clock granularity that monotonic_us() and
measure_ms(...) build on, not a promise about end-to-end benchmark
noise or scheduler jitter.
fn monotonic_us()Reads a monotonic host clock in microseconds.
This is intended for runtime measurement and timeout bookkeeping, not for wall-clock timestamps or user-visible calendar output.
fn month(time)
fn month(time, [zone :- Zone = :utc, ..])
fn month(_time, [zone: = :utc, ..])Returns the projected month number in the range 1..12.
fn now_utc()Reads the current host time as a %Time{...} value in UTC.
fn parse(text)
fn parse(text, [locale :- Locale, kind :- LocaleKind = :datetime, zone :- Zone = :utc, ..])
fn parse(text, [zone :- Zone = :utc, ..])
fn parse(text, format)
fn parse(text, format, [zone :- Zone = :utc, ..])
fn parse(_text, format)Parses ISO-8601 text, locale preset text, or explicit strptime text
into a %Time{...} value.
fn second(time)
fn second(time, [zone :- Zone = :utc, ..])
fn second(_time, [zone: = :utc, ..])Returns the projected second in the range 0..59.
fn sleep(duration)Blocks for approximately the given Duration and returns undef.
fn strftime(time, format)
fn strftime(time, format, [zone :- Zone = :utc, ..])
fn strftime(_time, format)Formats a %Time{...} value using Perl-style strftime directives such
as "%Y-%m-%d %H:%M:%S".
fn strptime(text, format)
fn strptime(text, format, [zone :- Zone = :utc, ..])
fn strptime(_text, format)Parses text using Perl-style strptime directives such as
"%Y-%m-%d %H:%M:%S".
fn time?(value)Returns true if value is a valid %Time{unix_ms: ..., zone: :utc} value.
fn to_iso8601(time)
fn to_iso8601(time, [zone :- Zone = :utc, ..])
fn to_iso8601(_time, [zone: = :utc, ..])Formats a %Time{...} value as RFC-3339 / ISO-8601.
fn to_unix(time)Returns the Unix second timestamp from a %Time{...} value.
fn to_unix_ms(time)Returns the Unix millisecond timestamp from a %Time{...} value.
fn year(time)
fn year(time, [zone :- Zone = :utc, ..])
fn year(_time, [zone: = :utc, ..])Returns the projected calendar year.
