Repository navigation
Releases: ThorFuchs/Swift-Liquid
Release list
Swift-Liquid 1.3.1
Swift-Liquid 1.3.1
Swift-Liquid 1.3.1 strengthens the dependency-free Shopify Liquid engine at two
resource boundaries: deeply nested JSON no longer exhausts the parser's call
stack, and rendering checks cancellation before admitting output after
synchronous filter work. It also delivers the four public-quality sprints:
clearer documentation, adversarial tests, structured evidence, isolated
contribution checks and measurements you can inspect.
Requires Swift tools/compiler 6.4 or later, in Swift language mode 6. Existing
1.0–1.3 library applications need no API migration.
Safer JSON and reliable cancellation boundaries
The ordered JSON reader now uses an explicit container stack. AddressSanitizer
exposed stack exhaustion at the already admitted 128-level nesting boundary;
the fix preserves that boundary, exact scalar keys, object order, number handling
and existing errors. Fixed-seed truncation, escape, Unicode and depth regressions
exercise successful and rejected inputs through the public API.
Output admission checks cancellation before applying its byte quota, including
final delivery after synchronous standard-filter work. Cancellation takes
precedence for empty, fitting and oversized output and does not consume evaluator
steps. Successful output, quotas and logical counters are unchanged. This adds a
cooperative checkpoint; synchronous helpers and arbitrary host callbacks remain
responsible for their own work. There is no preemption or elapsed-time guarantee.
Explicitly coordinated callback tests cover return and recoverable-error paths,
source and parsed templates, and ordinary, diagnostic, measured and combined
rendering. They assert cancellation identity, no subsequent filter evaluation,
sibling isolation and healthy engine reuse without sleeps or timing deadlines.
See limits and concurrency and
measured maintenance.
A stronger public package
- A rewritten README, six compiled runnable examples, contributor and support
guidance, expanded API comments and a clearer hosted documentation entry point. - Exact Swift Testing event admission: reviewed function/case inventories, raw
JSONL streams, skip/issue/cancellation accounting and negative runner probes.
Expected reference errors remain distinct from successful renders. - GitHub-hosted runner admission and provenance, pinned actions, read-only
contribution qualification and a separate main-only documentation deployment. - A fresh public-URL library/CLI installation gate for immutable 1.3.0, alongside
current-candidate consumers and a clean source-archive rebuild. This published
compatibility anchor remains 1.3.0 until a later explicit change. Publication
additionally verifies exact 1.3.1 resolution from a fresh public-URL consumer. - Swift Package Index registration accepted in
PackageList PR #15709.
Registration acceptance does not establish a live index build matrix.
See testing, contribution isolation
and package discovery for commands and limits.
Compatibility and release qualification
The release retains one Liquid library, one liquid executable and no root
package dependencies. Public inputs, engines and parsed templates keep checked
Sendable conformance; mutable render state belongs to each invocation. All 126
authored public declarations in the published 1.3.0 baseline are retained. CLI
inspection, metrics and dependency-report JSON schemas remain at version 1.
Release qualification requires all nine source-bound gates: native, safety,
reference, platforms, documentation, performance, matched performance, published
installation and archive. The archive gate rebuilds and tests the candidate from
a clean extraction and verifies reproducible tracked-source packaging.
The reviewed inventory contains 75 Swift Testing functions and 2,123 parameter
cases in debug and release. AddressSanitizer covers the full suite;
ThreadSanitizer covers five concurrency functions. The 16-function, 43-case
adversarial/cancellation profile is repeated twice under parallel execution.
Five standalone public consumers and the README consumer check external API use;
CLI qualification retains 60 existing and 24 dependency cases plus six positive
and nineteen negative Swift-JSON schema vectors. These counts describe coverage,
not complete language conformance.
All 1,098 pinned Golden Liquid cases, licenses, checksums and parser modes are
preserved. The Ruby reference retains 2,032 core checks: 1,502 successful renders,
337 parsed grammar cases, 132 expected language errors, 26 recovered errors and
35 explicit supported-year boundaries. The 15 paired host-filter cases remain
separate. No exclusion, missing fixture or reference error counts as success.
Runtime qualification covers macOS 27 with Swift 6.4. Four simulator-SDK gates
establish library compilation; device, Linux, WASI and browser execution are not
qualified. The duplicate-normalized-filename CLI vector remains unavailable on
the qualification macOS filesystem and is not counted as passed.
Measurements and their limits
Matched qualification compares all 26 common records with immutable 1.3.0 commit
9963591f18ef8aa1d1a8d9cd9bcc5508c82b5d4e, using its unchanged harness and
manifest. A separate same-candidate phase measures 24 opt-in metrics pairs.
Both retain three serial ABBA blocks, six runs per side, ten warmup samples and
25 measured samples of 100 repetitions. Builds finish before timing begins.
Absolute median changes of at least 10% and observed run-median ranges of at least
10% produce separate review lists. The qualification archive includes every raw
sample, all four flag lists and their checksum-bound review. The
1.3.1 benchmark review explains the prior flags,
the independent-host study and the release decision. Timing spread is not a
confidence interval and a passing evidence check is not a claim of no regression.
Controlled checkpoint experiments support a latency cost on small rendering
calls. An initial local measured-interpolation case had a +9.34% paired median
change under contention. A separate hosted experiment with the pinned common
harness observed +19.28% for that case, with positive effects in all three blocks;
its identical-source control changed by −4.08%. These observations include
compiler/code-layout effects and are not a universal overhead bound. Retaining
the checkpoint is an explicit correctness tradeoff for the reproduced cancellation
defect. Final flags, distributions and limitations remain
part of the release review.
Four graph records and six larger loop/escaping/partial records remain separate
observations. Sixteen coordinated and eight runnable cancellation scenarios
retain every outcome, including normal completion races. The new output check
improves cancellation observability; it does not impose a hard response bound.
No speedup, zero-overhead, process-memory or cross-engine superiority claim is made.
Final main qualification
All nine release gates passed on main commit
fb81cf4ff01f1bf098ceb5fff65638b1271294e0. Every lane retains the same 194-file
source inventory. The source archive was reproduced byte-for-byte, rebuilt and tested
from a clean extraction, and the matching documentation site deployed after
qualification.
The final comparison retains two common median-change flags, three opt-in metrics
flags, and spread flags in all 26 common and 24 metrics comparisons. The bound review
examines every flagged distribution and three-block effect, alongside all earlier
observations and the independent checkpoint controls.
Ordinary reused interpolation measured +17.03% (21.910 to 25.642 µs); measured reused
interpolation showed +33.43% (22.998 to 30.687 µs). Block effects change sign, and
every common comparison retains a spread flag. The separate control using frozen
sources observed a positive +19.28% effect for the measured checkpoint version; that
finding does not cap the larger main observation. This release accepts the observed
latency costs on small calls for the reproduced cancellation fix and retains every
adverse result.
The metrics phase also flags +12.57% for diagnostic reused interpolation and +13.20%
for loop rendering from source. Its apparent negative custom-filter overhead is
retained without a speedup claim. These observations establish neither zero overhead
nor absence of regressions, and give no universal latency bound.
The qualification archive contains all raw samples, four exact flag lists, tag
provenance and the checksum-bound decision. Runtime qualification covers macOS; Apple
simulator results establish compilation only.
Upgrade and downloads
Select from: "1.3.1" and retain the Liquid product. Existing
1.0–1.3 APIs and package products require no migration. The CLI reports
Swift-Liquid 1.3.1.
The release assets are:
Swift-Liquid-source.tar.gz: tracked source verified by a clean rebuild.Liquid.doccarchive.tar.gz: compiled API reference and guides.Swift-Liquid-qualification.tar.gz: source-bound receipts, raw test streams,
logs, benchmark observations, all review flags and the bound review.SHA256SUMS: SHA-256 checksums for the t...
Swift-Liquid 1.3.0
Swift-Liquid 1.3.0
Swift-Liquid 1.3 adds bounded partial-dependency inspection to the dependency-free
Shopify Liquid engine. Inspect a supplied template bundle before rendering it,
find missing literal references and cycles, and identify unresolved dynamic
includes. The library and CLI share the existing AST inspection authority.
Existing 1.0–1.2 rendering, filters, diagnostics, inspection and metrics APIs keep
their behavior.
Requires Swift tools/compiler 6.4 or later, in Swift language mode 6.
Understand an explicit template bundle
import Liquid
let engine = LiquidEngine()
let source = "{% include 'card' %}{% include selected %}"
let partials = ["card.liquid": "{{ title | escape }}{% include 'badge' %}"]
let graph = try engine.inspectDependencies(
template: source, templates: partials, syntaxMode: .strict2
)
assert(graph.nodes.map(\.id) == [.root, .partial("card.liquid")])
assert(graph.missingReferences.map(\.requestedName) == ["badge"])
assert(graph.dynamicReferences == [.root])The source entry point parses every supplied source under the chosen mode.
The parsed-template overload reuses each template's original parsing:
let root = try LiquidTemplate(source, syntaxMode: .strict2)
let parsed = try partials.mapValues { try LiquidTemplate($0, syntaxMode: .strict2) }
let reused = try engine.inspectDependencies(root, templates: parsed)
assert(reused == graph)Results, node identities, edges and capacity profiles have checked Sendable
conformance. Every operation owns its worklists and sets. Inspection performs no
I/O, context lookup, expression evaluation or filter invocation.
Nodes contain the root and literal-reachable partials, each with its existing
single-template summary. Edges retain the exact requested spelling and actual
supplied key. Lookup follows rendering: the requested key first, then that key
plus .liquid, using Swift String dictionary equality. The result preserves exact
UTF-8 spellings and deterministic order; the root remains distinct from every
partial name. Repeated requests share an edge, and shared dependencies expand once.
Cycles are deterministic strongly connected groups, including self-loops. Both
traversal and cycle detection use iterative worklists. Dynamic include names
remain unresolved; dynamic render names retain their existing syntax rejection.
All retained branches contribute. Findings describe syntax and supplied names;
they do not prove execution paths, required context or render success.
Bound the work
LiquidDependencyLimits defaults to 4,096 supplied templates including the root,
262,144 aggregate supplied-key bytes and 65,536 retained literal edges, including
missing references. The root and every supplied partial share the engine's source
capacity; each AST must pass its syntax-depth limit. Empty and unused sources
still spend admission capacity, and unused malformed sources fail the operation.
Rendering capacities are not consumed. Invalid profiles, syntax and capacity
failures preserve their typed errors; cancellation remains CancellationError.
Failure returns no partial graph. These are logical capacities, not memory or
wall-clock guarantees. See the complete dependency contract
for charging, ordering and failure rules.
Analyze from the command line
liquid analyze page.liquid --dependencies --partials ./partials --format json--dependencies opts into the graph report. The partial directory is optional;
omitting it supplies an empty map. The CLI admits cumulative source, template
count and name bytes before parsing the bundle, skips hidden entries and child
symlinks, checks containment and rejects ambiguous discovered keys.
Dependency reports use separate JSON schema 1 with kind: "liquid.dependencies",
node identities, edges, missing/dynamic references and cycle groups. Successful
findings exit 0, including missing references or cycles. Operational failures
emit no graph, write diagnostics to stderr and exit 1. Consumers choose their own
rejection policy. Ordinary analyze and its inspection schema 1 are unchanged;
rendering and metrics schema 1 are unchanged.
The standalone qualification tool validates actual CLI output and negative
vectors with published Swift-JSON 1.3.0 JSON and JSONSchema. This dependency
belongs only to tooling. Liquid retains its empty root dependency graph and
existing deployment minimums. Schema validity checks report shape; API and CLI
regressions separately check graph relationships and exact-spelling semantics.
Compatibility and qualification
- Preserve all 116 published 1.2 public declarations and all 1.0–1.2 consumers.
DocC exposes 148 public symbols, including the additive dependency API. - Retain fixture bytes, checksums, licenses, parser-mode metadata and reference
pins. The Ruby reference accounts for 2,032 core checks: 1,502 successful renders,
337 parsed grammar cases, 132 expected errors, 26 recovered errors and 35
supported-year boundaries. Host extensions retain 15 separate paired cases.
Dependency inspection adds no Shopify render-conformance cases. - Qualify 65 test functions in debug and release, five public consumers, the
existing 60 CLI cases and 24 dependency CLI cases, plus six positive and nineteen
negative Swift-JSON schema vectors. AddressSanitizer covers the full suite;
ThreadSanitizer covers five mixed concurrency cases. - Canonically equivalent filenames cannot coexist on the qualification macOS
filesystem, so that duplicate-path CLI vector is unavailable there and is not
counted as passed. Public API regressions cover canonical lookup and exact
spelling. The CLI vector runs when the filesystem supports both names. - Compile all four declared simulator SDKs, compile DocC and rebuild a reproducible
source archive from a clean extraction. Runtime qualification covers macOS;
simulator compilation does not certify device, Linux or WASI execution.
Measured against 1.2.0
Matched measurements use immutable 1.2.0 commit
8676da8059e71905632c233cffb438f8edbf51d2, its unchanged benchmark harness and
manifest, and all 26 common ordinary-render, measured-render and inspection
records. A separate same-candidate phase retains 24 enabled/disabled metrics
comparisons across throwing and diagnostic policies. Both phases use three serial
ABBA blocks, six runs per side, ten warmup samples and 25 measured samples of
100 repetitions. All binaries build before timing; outputs, checksums, individual
samples and environment receipts are retained. Every threshold flag is reviewed.
Four additional source/parsed diamond and cycle records measure graph construction
separately, with ten warmups and 25 samples of 20 repetitions. Full result equality
and checksum audits are inside their timing boundary. The previous release has
no graph operation for a direct comparison. The qualification archive carries
measurements and their bound review; this release makes no general speedup,
zero-overhead or process-memory claim. See performance methodology.
Upgrade and downloads
Select from: "1.3.0" and retain the Liquid product. Existing
applications need no migration. Opt into dependency inspection when a host or
tool needs it; parsed template reuse and ordinary rendering keep their APIs.
The release includes:
Swift-Liquid-source.tar.gz: tracked source verified by a clean rebuild.Liquid.doccarchive.tar.gz: compiled API reference and guides.Swift-Liquid-qualification.tar.gz: gate receipts, logs, source inventory,
matched and graph measurements, and reviewed benchmark evidence.SHA256SUMS: SHA-256 checksums for the three archives.
After downloading the published assets together, verify them with
shasum -a 256 -c SHA256SUMS before extraction. See the CLI reference,
dependency report schema,
application reuse and errors and recovery.
Qualification: candidate 9963591f18ef8aa1d1a8d9cd9bcc5508c82b5d4e, source tree bc30f14d27c9d29255c8153386cdf512beadc945, tested as 9963591f18ef8aa1d1a8d9cd9bcc5508c82b5d4e. Exact-source CI evidence.
Final measured qualification
The final CI comparison retains all 26 common records against immutable 1.2.0,
with median changes from −9.05% to +9.00% and no 10% review flags. Qualification
identified and corrected repeated native-string custom-filter bridging slowness;
custom-filter template reuse is +0.03% in the final comparison. Three separate
same-candidate opt-in metrics comparisons show +11.45% to +15.89% higher latency.
The qualification archive retains all eight successful comparisons, every flag
and sample, the failed pre-timing disk attempt, and the full bound review. These
limited workloads establish no general speedup, zero-overhead or portable latency
claim. The public SwiftPM 1.3.0 consumer, annotated tag and hosted DocC contents
are also verified in the qualification evidence.
Swift-Liquid 1.2.0
Swift-Liquid 1.2.0
Swift-Liquid 1.2 adds opt-in render metrics to the dependency-free Shopify Liquid
engine. Measure source or reusable parsed templates, retain explicit recovered
diagnostics when needed, and write CLI metrics separately from rendered output.
Existing 1.0 and 1.1 call sites keep their APIs and default behavior.
Requires Swift tools/compiler 6.4 or later, in Swift language mode 6.
Observe one invocation
import Liquid
let engine = LiquidEngine()
let result = try await engine.renderWithMetrics(
template: "Hello, {{ name }}!", context: ["name": "Swift"]
)
print(result.output) // Hello, Swift!
print(result.metrics.outputBytes) // 13
print(result.metrics.totalDuration)
let parsed = try LiquidTemplate("{{ name }}")
let reused = try await engine.renderWithMetrics(parsed, context: ["name": "Swift"])
assert(reused.metrics.parseDuration == nil)LiquidMeasuredRenderResult and LiquidRenderMetrics are immutable, checked
Sendable values. Total duration uses a monotonic clock and includes suspended
host callbacks. Source calls also report parsing time for the root and all
supplied partials; parsed calls exclude parsing already done by their caller.
The Liquid date reference clock remains independent.
Counts report supplied-source bytes, final output bytes and consumed evaluator,
loop and context/filter admission capacities. Nested partials share one budget.
These are logical observations of this implementation, not heap/RSS usage,
allocation counts, CPU instructions or a portable cost model. Existing render
APIs collect no timing; their cost is checked through matched measurements.
Use renderWithDiagnosticsAndMetrics for the existing explicit recovery policy.
Recovered output retains diagnostics and is not an error-free render. Syntax,
invalid values, quotas, cancellation and unexpected host errors still throw with
their existing identity. Failed invocations return no partial metrics.
Keep CLI output and metrics separate
liquid render page.liquid --data context.json --output page.html --metrics metrics.json--metrics PATH writes a separate UTF-8 JSON document with schema version 1,
integer nanosecond durations and logical counts. The CLI measures its prepared
parsed-template call, excluding CLI file I/O and parsing; parse time is null.
Rendered stdout and --output retain their behavior. The inspection JSON schema
is unchanged.
The CLI rejects input/output aliases, including hard links and symlinked parents.
Metrics are written atomically after successful output delivery. Render failure
preserves any prior metrics file. A late metrics write failure exits nonzero even
if output was delivered; the two destinations are not one transaction.
Compatibility and qualification
- Keep one
Liquidlibrary, oneliquidexecutable and an empty root dependency
graph. Engines and templates retain no mutable measurement state. - Preserve all 99 published 1.1 public symbol declarations, the original 1.0
consumer, typed filters, inspection, parser modes, limits and error policies. - Preserve fixture bytes, checksums, licenses and reference pins. The pinned Ruby
reference evaluates 2,032 core checks: 1,502 successful renders, 337 parsed
grammar cases, 132 expected errors, 26 recovered errors and 35 supported-year
boundaries. Host callbacks have 15 separate paired cases. Metrics tests do not
inflate core conformance accounting. - Qualify 54 test functions in debug and release, four independent public
consumers, 60 CLI cases, AddressSanitizer, four ThreadSanitizer concurrency
cases, compiled DocC and a reproducible clean source-archive rebuild. - Compile the library against all four declared simulator SDKs. Runtime
qualification covers macOS; these checks do not certify device execution,
Linux or WASI. The numeric, UTC and supported-year contracts remain unchanged.
Matched benchmarks compare all 14 common 1.1 workload/mode records with immutable
1.1.0 using its unchanged harness and manifest on one host/toolchain. A separate
candidate comparison measures 24 metrics-enabled/disabled pairs across throwing
and diagnostic policies. Each uses three serial ABBA blocks, six runs per side,
the original sampling policy and verified
output checksums. Measurements and threshold reviews accompany qualification;
this release makes no general speedup or zero-overhead claim.
Upgrade and downloads
Select from: "1.2.0" in SwiftPM and retain the Liquid
product. Existing applications need no migration. Opt into metrics per call;
reuse parsed roots and explicit partial maps as before.
The release includes:
Swift-Liquid-source.tar.gz: tracked source verified by a clean rebuild.Liquid.doccarchive.tar.gz: compiled API reference and guides.Swift-Liquid-qualification.tar.gz: gate receipts, logs, source inventory,
both benchmark comparisons and their reviewed evidence.SHA256SUMS: SHA-256 checksums for the three archives.
Verify downloads together with shasum -a 256 -c SHA256SUMS before extraction.
See metrics and schema 1, CLI,
errors and recovery, application reuse and
performance methodology.
Qualification: candidate 8676da8059e71905632c233cffb438f8edbf51d2, source tree 7a3a07ae6bdc5911dc5d539057a3184c07dcc09b, tested as 8676da8059e71905632c233cffb438f8edbf51d2. Exact-source CI evidence.
Swift-Liquid 1.1.0
Swift-Liquid 1.1 adds typed application filters and read-only template inspection
to the dependency-free Shopify Liquid engine. The 1.0 engine initializer and
render APIs remain available, and default engines retain the existing Shopify
core behavior. Requires Swift tools/compiler 6.4 or later, in Swift language mode 6.
Application filters, scoped to an engine
Register immutable LiquidFilter values when constructing an engine. Callbacks
receive LiquidValue input, positional arguments and an ordered LiquidObject
of named values, and return a value asynchronously. Closures and captures use
checked Sendable conformance; parsed templates retain no callbacks.
import Liquid
let engine = try LiquidEngine(filters: [
LiquidFilter("greet") { value, _, _ in
guard case .string(let name) = value else { throw LiquidFilterFailure("Expected a name") }
return .string("Hello, " + name)
}
])
let output = try await engine.render(template: "{{ name | greet | escape }}", context: ["name": "Ada"])
// Hello, AdaStandard names and aliases cannot be replaced. Filters are available to supplied
partials and compose with standard filters. Value conversion/admission shares
invocation budgets, including returned values. Only explicit LiquidFilterFailure
errors are recoverable through renderWithDiagnostics; cancellation, quotas,
invalid values and unexpected host errors retain their operational meaning.
Callbacks remain trusted application code; rendering limits do not bound host I/O
or uncooperative execution time. The CLI does not discover or load plugins.
Inspect syntax without rendering
LiquidEngine.inspect(template:syntaxMode:) and inspect(_:) return an immutable
LiquidTemplateInspection: variable roots, filter names, literal partial names,
and whether dynamic partial references occur. Lists preserve exact UTF-8 spelling
and use deterministic ordering. Inspection does not invoke callbacks, evaluate
expressions or load partials.
liquid analyze page.liquid
liquid analyze page.liquid --syntax-mode strict2 --format jsonJSON schema 1 gives tools a documented evolution policy. Variable roots are parsed
syntactic reads, including locals and conditional paths; they are not required
context keys. Each template is inspected independently. Source/depth limits and
cancellation apply to source and reused-template inspection.
Compatibility and qualification
- One
Liquidlibrary, oneliquidexecutable, and an empty root dependency graph. - Original 1.0 public consumer and all pinned core fixture bytes, licenses, parser
modes and checksums retained. No custom tags, automatic loaders or new dialect. - The pinned Ruby reference still evaluates 2,032 core checks: 1,502 successful
renders, 337 parsed grammar cases, 132 expected language errors, 26 recovered
errors and 35 supported-year boundaries. Host extensions have 15 separate paired
reference cases; inspection tests do not inflate core conformance accounting. - Debug/release tests, three public consumers, 33 CLI checks, AddressSanitizer,
three ThreadSanitizer concurrency cases, four simulator-SDK library compiles,
compiled DocC and a clean source-archive rebuild. - Matched release benchmarks compare all five original workloads against 1.0.0
using its unchanged harness on the same host/toolchain, with three ABBA blocks
and verified outputs. New filter and inspection workloads have separate records.
Per-run latency summaries and review flags accompany the qualification evidence; this
release makes no general speedup claim.
The numeric/UTC/date-year/resource contracts remain unchanged. Runtime
qualification covers macOS with Swift 6.4; simulator compilation does not certify
device execution, Linux or WASI. Tested cases are evidence, not a proof of complete
Shopify equivalence.
Downloads and upgrade
Select from: "1.1.0" in SwiftPM and keep the Liquid product.
Existing render call sites need no migration. Opt into filters per engine; use
parsed templates and explicit partial maps for application reuse.
Release assets follow the 1.0 layout:
Swift-Liquid-source.tar.gz: tracked source, verified by a clean rebuild.Liquid.doccarchive.tar.gz: compiled API reference and guides.Swift-Liquid-qualification.tar.gz: gate receipts, test/reference logs, matched
benchmark runs, source inventory and archive evidence.SHA256SUMS: SHA-256 checksums for the three archives.
Verify all downloads together with shasum -a 256 -c SHA256SUMS before extraction.
See the filter contract, inspection and JSON schema,
application reuse, CLI, and performance method.
Qualified commit: 1107ec865b9ae7ed35e1245386ba882db3abd93d. All eight main release gates.
Swift-Liquid 1.0.0
The first stable release of Swift-Liquid: Shopify Liquid templates in modern
Swift, with a focused public API, a command-line tool, and no SwiftPM dependencies.
Requires Swift tools/compiler 6.4 or later in Swift language mode 6.
Install
.package(url: "https://github.com/ThorFuchs/Swift-Liquid.git", from: "1.0.0")Add .product(name: "Liquid", package: "swift-liquid") to your target.
Build the CLI with swift build -c release; run .build/release/liquid --help.
Library and CLI
- One
Liquidlibrary and oneliquidexecutable, extracted from RhoeLiquid
with retained source attribution and Apache-2.0 licensing. Ruby Date adaptations
retain their BSD terms; fixture licenses are included. - Checked Sendable values and engines, immutable reusable templates, ordered
objects, and invocation-owned rendering state for concurrent use. - Standard open-source Shopify Liquid tags and filters, lax/strict/strict2 parser
modes, explicit partials, ordered JSON input, and configurable resource limits. - Raising rendering and explicit
renderWithDiagnosticsrecovery, with error
order, line numbers, and partial names. Cancellation and operational failures
remain errors in both APIs. - Ruby Date/Time recognition and missing-component defaults, deterministic
reference clocks, fixed offsets, exact parsed decimal fractions, and Liquid
date formatting. - CLI rendering and validation, stdin and JSON context support, explicit partial
directories, diagnostics on stderr, and atomic output-file replacement. - Compiled DocC API reference and guides, public consumer examples, and documented
language, error, date, concurrency, and performance contracts.
Qualification
- All 1,098 pinned Golden Liquid cases preserved without exclusions, plus 221
authored compatibility probes, 337 Ruby date source-table cases, and 376 public
date-filter cases. - The pinned Ruby reference evaluates 2,032 checks: 1,502 successful renders,
337 parsed grammar cases, 132 expected language errors, 26 recovered errors,
and 35 explicit supported-year boundary checks. No failures, skips, or reference
errors are accepted; recovered errors and boundaries are counted separately. - Debug and release tests, an independent public consumer, CLI behavior checks,
AddressSanitizer, ThreadSanitizer, and simulator-SDK library compilation. - Five native release benchmark workloads with output checksums and environment
receipts. Measurements establish a baseline; no comparative speedup is claimed. - Reproducible tracked-source archives, a clean extraction rebuilt and tested,
compiled documentation archives, and SHA-256 checksums.
Compatibility contract
The target is Shopify's open-source Liquid core, pinned to Liquid 5.14.0, Ruby
4.0.1, Date 3.5.1, and Time 0.4.2. Shopify storefront objects and theme-only tags,
custom tag/filter APIs, Rhoe services, macros, inheritance, and document rendering
are outside this release.
The hosting timezone is UTC; supported calendar years are 1–9999. Values use
bounded Int and finite Double, with configurable resource budgets and native
Unicode case mapping. These are explicit compatibility boundaries, not proof of
equivalence for every possible Liquid program.
Runtime qualification covers macOS with Swift 6.4. Library compilation covers
the iOS, tvOS, watchOS, and visionOS simulator SDKs at the declared deployment
minimums; device execution and Linux are not qualified by those checks.
Downloads and documentation
Swift-Liquid-source.tar.gz: tracked source at the release commit, verified by a clean rebuild and test run.Liquid.doccarchive.tar.gz: compiled DocC API reference and guides; extract it to openLiquid.doccarchivein Xcode.Swift-Liquid-qualification.tar.gz: qualification and benchmark receipts, test logs, fixture/reference results, source inventory, and archive evidence.SHA256SUMS: SHA-256 checksums for all three archives.
Download all four assets into one directory and verify them before extraction:
shasum -a 256 -c SHA256SUMSAPI reference and guides · Language contract · Compatibility evidence · CLI reference
Qualified commit: d36018e6b6822ae408a6c1c439c2307484525b7b. Exact-commit qualification run.