feat: add context-aware filesystem SerDes - #672
Conversation
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
|
|
||
| var inputPayload = executionOp.executionDetails().inputPayload(); | ||
| return serDes.deserialize(inputPayload, inputType); | ||
| return serDesRunner.deserialize(serDes, inputPayload, inputType, serDesContext); |
There was a problem hiding this comment.
Codex AI review · Finding arf_v1_ijtikdiu4z2pfc5y5degiqq7ru
[P1] Preserve context-free decoding for initial input. Invocation input is serialized before a durable ARN exists through SerDes.serialize(Object), but this invokes the context-aware deserializer. A valid SerDes using distinct raw and contextual encodings will therefore fail every initial invocation. Add a context-free dispatch method to SerDesRunner and use it here—and for other externally produced raw boundaries—with a regression test covering distinct encodings.
| private static final Object NULL_VALUE = new Object(); | ||
|
|
||
| private final ExecutorService executorService; | ||
| private final ConcurrentHashMap<ContextKey, AtomicLong> contextGenerations = new ConcurrentHashMap<>(); |
There was a problem hiding this comment.
Codex AI review · Finding arf_v1_zrfjhwzrlpr5feemsk7pt3ypuu
[P2] Bound generation bookkeeping with the cache. The 256-entry limit applies only to completed values; every unique SerDes/entity context is retained here for the entire invocation. Large maps or long workflows can consequently exhaust Lambda memory. Evict inactive generation state alongside completed/in-flight entries, and test that all runner bookkeeping remains bounded across many entities.
| || failure instanceof FileSystemLoopException) { | ||
| return new SerDesException(message, failure); | ||
| } | ||
| return new RetryableSerDesException(message, failure); |
There was a problem hiding this comment.
Codex AI review · Finding arf_v1_fphsma5t5ymczje74zssfgxx6q
[P2] Treat a missing configured base directory as permanent. NoSuchFileException while traversing a missing base-path component reaches this retryable fallback, so RetrySerDes repeatedly delays for a pre-provisioning/configuration error. Distinguish base-directory traversal failures from a missing payload file, wrap the former in SerDesException, and update the missing-base test accordingly.
Codex AI reviewThree actionable issues remain. The main risk is incompatibility at the initial-input boundary for context-aware SerDes implementations; cache bookkeeping and filesystem retry classification also need correction. Static review only; tests were not run per constraints. Reviewed commit |
By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license.
Issue Link, if available
Closes #463.
Related to #509.
This is a smaller explicit-context alternative to #648 and #649.
Description
SerDesmethods unchanged and add backward-compatible default overloads that receiveSerDesContextexplicitly.SerDesRunnerthat runs inline by default, optionallyuses a dedicated executor, passes context directly, shares in-flight deserializations, and keeps a bounded
weak-reference cache keyed by SerDes identity, execution/entity, serialization generation, type, and payload hash.
FileSystemSerDesto the core SDK withALWAYSandOVERFLOWmodes, URI/hash path encodings, a configurable checkpoint-envelope limit, structured and custom previews, content-addressed immutable files,SecureDirectoryStreamtraversal,NOFOLLOW_LINKSfile I/O, digest verification, and strict marker-only envelope recognition.FileSystemSerDes.delegate(...), while existing operation configs select the SerDes used for step, invoke payload/result, callback, child-context, map, parallel, and wait-for-condition boundaries.RetryableSerDesExceptionand addRetrySerDes, a non-pipeline decorator that applies existing boundedRetryStrategyimplementations only to transient failures.serialization/filesystem/retry guide, exact filesystem wire-format reference, invoke-boundary guidance, and runnable
example.
children of a pre-provisioned base directory so all directory traversal remains relative to held secure handles.
Applicable parity with #648
This PR now carries over the #648 coverage that applies to an explicit-context
SerDes:Pipeline composition, binary stages, chained-invoke source framing/JavaScript compatibility, and pipeline-specific
producer/attempt metadata remain intentionally out of scope for this explicit-context design.
Demo/Screenshots
Not applicable. Configuration examples are included in the documentation.
Checklist
Testing
mvn -Dmaven.repo.local=/home/frankchn/.codex-tmp/m2 clean installmvn -Dmaven.repo.local=/home/frankchn/.codex-tmp/m2 -pl sdk -Dtest=SerDesRunnerTest,RetrySerDesTest,FileSystemSerDesTest testmvn -Dmaven.repo.local=/home/frankchn/.codex-tmp/m2 -pl sdk-integration-tests -am -Dtest=FileSystemSerDesIntegrationTest -Dsurefire.failIfNoSpecifiedTests=false testmvn -Dmaven.repo.local=/home/frankchn/.codex-tmp/m2 -pl sdk-testing -am -Dtest=LocalDurableTestRunnerTest -Dsurefire.failIfNoSpecifiedTests=false testmvn -Dmaven.repo.local=/home/frankchn/.codex-tmp/m2 -pl examples -am -Dtest=FileSystemSerDesExampleTest -Dsurefire.failIfNoSpecifiedTests=false testpython3 -m unittest examples/test_generate_template.pymvn -Dmaven.repo.local=/home/frankchn/.codex-tmp/m2 spotless:checkgit diff --checkThe full eight-module reactor passed, including 1,229 SDK tests. The EFS-backed cloud test is opt-in locally and is
enabled by the updated E2E workflow.
Unit Tests
Yes. The focused SDK parity set contains 53 tests across
SerDesRunnerTest,RetrySerDesTest, andFileSystemSerDesTest. Coverage includes default-method compatibility, explicit context propagation, inline andconfigured-executor dispatch, cache
identity/eviction/concurrency/generation invalidation, retry selection/exhaustion/delay/interruption, retryable
filesystem I/O, filesystem modes, immutable unique files, configurable envelope limits, delegate encoding, structured
previews, strict marker-only envelope validation, digest verification, secure-directory provider enforcement, and
non-retryable structural, permission, invalid-path, and symlink rejection for base paths, directories, and files. The
envelope limit cannot exceed the safe 255 KiB checkpoint ceiling, and raw boundaries remain context-free even when the
delegate implements contextual encoding.
Integration Tests
Yes. Eleven
FileSystemSerDesIntegrationTestscenarios cover raw root input and offloaded output, operation-levelselection, step/wait/child/map replay, raw callback/invoke results, standard JSON invoke overrides, caller/callee
offloaded payload/result exchange, repeated-get caching, custom exception payloads, and deterministic external-storage
keys across state/exception replay. The operation override is also inspected through its effective filesystem SerDes,
with equivalent resolver coverage for cloud history. Checkpoint-failure replay verifies old and new immutable
filesystem references remain independently readable. Local-runner coverage verifies large-output replay without
duplicate operation execution.
Examples
Yes.
FileSystemSerDesExampledemonstrates EFS-style configuration, structured previews and masking, boundedfilesystem retries, forced replay, and checksum verification. It has a local test and an opt-in cloud test backed by
the same persistent EFS/VPC SAM infrastructure pattern used by #648.