Skip to content

Serialization

Checkpointed data transformation

The SDK serializes durable operation results to checkpoint storage. When your durable function replays the SDK uses those stored results rather than re-running the code wrapped inside the operation. A SerDes (serializer/deserializer) is the object that serializes the operation result, and deserializes it during replay.

Each SDK ships a default SerDes that handles the most common types. You only need a custom SerDes when the default SerDes cannot handle your data types, or when you need special behavior such as encryption, compression or writing to external storage.

The following example uses no SerDes configuration. The SDK serializes and deserializes the step result automatically.

import { DurableContext, withDurableExecution } from "@aws/durable-execution-sdk-js";

interface Order {
  id: string;
  total: string;
}

export const handler = withDurableExecution(
  async (event: unknown, context: DurableContext) => {
    // No SerDes config — the SDK serializes and deserializes the result automatically.
    const order = await context.step("fetch-order", async (): Promise<Order> => {
      return { id: "order-123", total: "99.99" };
    });
    return order;
  },
);
from aws_durable_execution_sdk_python import (
    DurableContext,
    StepContext,
    durable_execution,
    durable_step,
)


@durable_step
def fetch_order(ctx: StepContext) -> dict:
    return {"id": "order-123", "total": "99.99"}


@durable_execution
def handler(event: dict, context: DurableContext) -> dict:
    # No SerDes config — the SDK serializes and deserializes the result automatically.
    order = context.step(fetch_order())
    return order
import java.util.Map;
import software.amazon.lambda.durable.DurableContext;
import software.amazon.lambda.durable.DurableHandler;
import software.amazon.lambda.durable.StepContext;

public class Walkthrough extends DurableHandler<Object, Map<String, String>> {
    @Override
    public Map<String, String> handleRequest(Object input, DurableContext context) {
        // No SerDes config — the SDK serializes and deserializes the result automatically.
        Map<String, String> order = context.step(
            "fetch-order",
            Map.class,
            (StepContext ctx) -> Map.of("id", "order-123", "total", "99.99")
        );
        return order;
    }
}

Lambda handler serialization

The Durable Execution SDK SerDes only applies to durable operation results. It does not affect the final return value of your Lambda handler, which Lambda serializes separately.

Lambda serializes handler return values with JSON.stringify. The same types that work with defaultSerdes work as handler return values.

Lambda serializes handler return values with json.dumps. Types like datetime and Decimal are safe inside steps because ExtendedTypeSerDes handles them, but returning them directly from your handler raises TypeError: Object of type X is not JSON serializable. This is a common error when working with Amazon DynamoDB results. Convert those values to JSON-safe types before returning from the handler.

Lambda serializes handler return values with Jackson. The same JacksonSerDes configuration applies to both step results and handler return values when you use DurableHandler.

Default serialization

Each SDK uses a default SerDes when you do not provide one.

The default is defaultSerdes, which uses JSON.stringify to serialize and JSON.parse to deserialize. It handles any value that JSON.stringify accepts.

The default is ExtendedTypeSerDes. It uses plain JSON for primitives (None, str, int, float, bool, and lists of primitives) and an envelope format for everything else. The envelope format preserves the exact Python type through the round-trip.

Supported types beyond primitives: datetime, date, Decimal, UUID, bytes, bytearray, memoryview, tuple, list, dict, and BatchResult.

The default is JacksonSerDes, which uses Jackson's ObjectMapper. It supports Java 8 time types, serializes dates as ISO-8601 strings, and ignores unknown properties during deserialization.

Pass a custom ObjectMapper to the JacksonSerDes constructor to override the default configuration.

SerDes interface definition

import { Serdes, SerdesContext } from "@aws/durable-execution-sdk-js";

// Serdes<T> interface
interface SerdesInterface<T> {
  serialize: (value: T | undefined, context: SerdesContext) => Promise<string | undefined>;
  deserialize: (data: string | undefined, context: SerdesContext) => Promise<T | undefined>;
}

// SerdesContext
interface SerdesContextShape {
  entityId: string;
  durableExecutionArn: string;
}

Parameters:

  • serialize An async function that receives the value and a SerdesContext, and returns Promise<string | undefined>.
  • deserialize An async function that receives the serialized string and a SerdesContext, and returns Promise<T | undefined>.

Both methods are async so that implementations can interact with external services such as S3 or KMS.

SerdesContext fields:

  • entityId The operation ID for the current step or operation.
  • durableExecutionArn The ARN of the current durable execution.
from abc import ABC, abstractmethod
from dataclasses import dataclass
from typing import Generic, TypeVar

T = TypeVar("T")


@dataclass(frozen=True)
class SerDesContext:
    operation_id: str = ""
    durable_execution_arn: str = ""


class SerDes(ABC, Generic[T]):
    @abstractmethod
    def serialize(self, value: T, serdes_context: SerDesContext) -> str: ...

    @abstractmethod
    def deserialize(self, data: str, serdes_context: SerDesContext) -> T: ...

Parameters:

  • serialize(value, serdes_context) Converts the value to a string.
  • deserialize(data, serdes_context) Converts the string back to the original type.

SerDesContext fields:

  • operation_id The operation ID for the current step or operation.
  • durable_execution_arn The ARN of the current durable execution.
import software.amazon.lambda.durable.TypeToken;
import software.amazon.lambda.durable.serde.SerDes;

// SerDes interface
interface SerDesInterface {
    String serialize(Object value);

    <T> T deserialize(String data, TypeToken<T> typeToken);
}

Parameters:

  • serialize(Object value) Converts the value to a JSON string. Returns null if value is null.
  • deserialize(String data, TypeToken<T> typeToken) Converts the JSON string back to type T. Returns null if data is null.

Use TypeToken<T> to capture generic type information that Java erases at runtime. For example: new TypeToken<List<String>>() {}.

Custom SerDes example

Implement the SerDes interface when the default cannot handle your types, or when you need special behavior such as encryption or compression.

import { Serdes, SerdesContext } from "@aws/durable-execution-sdk-js";

interface Order {
  id: string;
  total: string;
}

const orderSerdes: Serdes<Order> = {
  serialize: async (value: Order | undefined, _ctx: SerdesContext) => {
    if (value === undefined) return undefined;
    return JSON.stringify(value);
  },
  deserialize: async (data: string | undefined, _ctx: SerdesContext) => {
    if (data === undefined) return undefined;
    return JSON.parse(data) as Order;
  },
};
import json

from aws_durable_execution_sdk_python.serdes import SerDes, SerDesContext


class OrderSerDes(SerDes[dict]):
    def serialize(self, value: dict, ctx: SerDesContext) -> str:
        return json.dumps(value)

    def deserialize(self, data: str, ctx: SerDesContext) -> dict:
        return json.loads(data)
import com.fasterxml.jackson.databind.ObjectMapper;
import software.amazon.lambda.durable.TypeToken;
import software.amazon.lambda.durable.exception.SerDesException;
import software.amazon.lambda.durable.serde.SerDes;

public class OrderSerDes implements SerDes {
    private final ObjectMapper mapper = new ObjectMapper();

    @Override
    public String serialize(Object value) {
        try {
            return mapper.writeValueAsString(value);
        } catch (Exception e) {
            throw new SerDesException("Serialization failed", e);
        }
    }

    @Override
    public <T> T deserialize(String data, TypeToken<T> typeToken) {
        try {
            return mapper.readValue(data, mapper.getTypeFactory().constructType(typeToken.getType()));
        } catch (Exception e) {
            throw new SerDesException("Deserialization failed", e);
        }
    }
}

Custom SerDes on durable operations

Pass a SerDes instance in the configuration object for the operation you want to customize. The SDK uses that SerDes for that operation only. Other operations in the same handler continue to use the default.

StepConfig

import {
  DurableContext,
  Serdes,
  SerdesContext,
  StepConfig,
  withDurableExecution,
} from "@aws/durable-execution-sdk-js";

interface Order {
  id: string;
  total: string;
}

const orderSerdes: Serdes<Order> = {
  serialize: async (value: Order | undefined, _ctx: SerdesContext) =>
    value !== undefined ? JSON.stringify(value) : undefined,
  deserialize: async (data: string | undefined, _ctx: SerdesContext) =>
    data !== undefined ? (JSON.parse(data) as Order) : undefined,
};

const stepConfig: StepConfig<Order> = { serdes: orderSerdes };

export const handler = withDurableExecution(
  async (event: unknown, context: DurableContext) => {
    const order = await context.step(
      "fetch-order",
      async (): Promise<Order> => ({ id: "order-123", total: "99.99" }),
      stepConfig,
    );
    return order;
  },
);
import json

from aws_durable_execution_sdk_python import (
    DurableContext,
    StepContext,
    durable_execution,
    durable_step,
)
from aws_durable_execution_sdk_python.config import StepConfig
from aws_durable_execution_sdk_python.serdes import SerDes, SerDesContext


class OrderSerDes(SerDes[dict]):
    def serialize(self, value: dict, ctx: SerDesContext) -> str:
        return json.dumps(value)

    def deserialize(self, data: str, ctx: SerDesContext) -> dict:
        return json.loads(data)


@durable_step
def fetch_order(ctx: StepContext) -> dict:
    return {"id": "order-123", "total": "99.99"}


@durable_execution
def handler(event: dict, context: DurableContext) -> dict:
    order = context.step(
        fetch_order(),
        config=StepConfig(serdes=OrderSerDes()),
    )
    return order
import java.util.Map;
import software.amazon.lambda.durable.DurableContext;
import software.amazon.lambda.durable.DurableHandler;
import software.amazon.lambda.durable.StepContext;
import software.amazon.lambda.durable.config.StepConfig;
import software.amazon.lambda.durable.serde.JacksonSerDes;

public class StepConfigExample extends DurableHandler<Object, Map<String, String>> {
    @Override
    public Map<String, String> handleRequest(Object input, DurableContext context) {
        StepConfig config = StepConfig.builder()
            .serDes(new JacksonSerDes())
            .build();

        Map<String, String> order = context.step(
            "fetch-order",
            Map.class,
            (StepContext ctx) -> Map.of("id", "order-123", "total", "99.99"),
            config
        );
        return order;
    }
}

CallbackConfig

The callback SerDes controls how the SDK deserializes the payload that an external system sends when it completes the callback.

In TypeScript, the callback SerDes only needs deserialize. The serialize method is not used because the external system provides the payload directly.

import {
  DurableContext,
  Serdes,
  SerdesContext,
  withDurableExecution,
} from "@aws/durable-execution-sdk-js";

interface ApprovalResult {
  approved: boolean;
  reason: string;
}

// Callbacks only need deserialization — the external system sends the payload.
const approvalSerdes: Omit<Serdes<ApprovalResult>, "serialize"> = {
  deserialize: async (data: string | undefined, _ctx: SerdesContext) =>
    data !== undefined ? (JSON.parse(data) as ApprovalResult) : undefined,
};

export const handler = withDurableExecution(
  async (event: unknown, context: DurableContext) => {
    const [approval, callbackId] = await context.createCallback("await-approval", {
      serdes: approvalSerdes,
    });

    // Send callbackId to the external system here.
    console.log("Callback ID:", callbackId);

    const result = await approval;
    return result;
  },
);
import json

from aws_durable_execution_sdk_python import (
    DurableContext,
    durable_execution,
)
from aws_durable_execution_sdk_python.config import CallbackConfig
from aws_durable_execution_sdk_python.serdes import SerDes, SerDesContext


class ApprovalSerDes(SerDes[dict]):
    def serialize(self, value: dict, ctx: SerDesContext) -> str:
        return json.dumps(value)

    def deserialize(self, data: str, ctx: SerDesContext) -> dict:
        return json.loads(data)


@durable_execution
def handler(event: dict, context: DurableContext) -> dict:
    callback = context.create_callback(
        "await-approval",
        config=CallbackConfig(serdes=ApprovalSerDes()),
    )

    # Send callback.callback_id to the external system here.
    result = callback.result()
    return result
import java.util.Map;
import software.amazon.lambda.durable.DurableCallbackFuture;
import software.amazon.lambda.durable.DurableContext;
import software.amazon.lambda.durable.DurableHandler;
import software.amazon.lambda.durable.config.CallbackConfig;
import software.amazon.lambda.durable.serde.JacksonSerDes;

public class CallbackConfigExample extends DurableHandler<Object, Map<String, Object>> {
    @Override
    public Map<String, Object> handleRequest(Object input, DurableContext context) {
        CallbackConfig config = CallbackConfig.builder()
            .serDes(new JacksonSerDes())
            .build();

        DurableCallbackFuture<Map<String, Object>> callback =
            context.createCallback("await-approval", Map.class, config);

        // Send callback.getCallbackId() to the external system here.
        return callback.get();
    }
}

MapConfig & ParallelConfig

Map and parallel perations support two SerDes fields that apply at different levels.

import {
  BatchResult,
  DurableContext,
  MapConfig,
  Serdes,
  SerdesContext,
  withDurableExecution,
} from "@aws/durable-execution-sdk-js";

interface ProcessedItem {
  id: string;
  status: string;
}

const itemSerdes: Serdes<ProcessedItem> = {
  serialize: async (value: ProcessedItem | undefined, _ctx: SerdesContext) =>
    value !== undefined ? JSON.stringify(value) : undefined,
  deserialize: async (data: string | undefined, _ctx: SerdesContext) =>
    data !== undefined ? (JSON.parse(data) as ProcessedItem) : undefined,
};

const mapConfig: MapConfig<string, ProcessedItem> = {
  itemSerdes,
};

export const handler = withDurableExecution(
  async (event: unknown, context: DurableContext) => {
    const items = ["a", "b", "c"];
    const result: BatchResult<ProcessedItem> = await context.map(
      "process-items",
      items,
      async (_ctx, item) => ({ id: item, status: "done" }),
      mapConfig,
    );
    return result.getResults();
  },
);
  • itemSerdes serializes each item result.
  • serdes serializes the aggregated BatchResult.
  • ParallelConfig has the same two fields.
import json

from aws_durable_execution_sdk_python import (
    DurableContext,
    durable_execution,
)
from aws_durable_execution_sdk_python.config import MapConfig
from aws_durable_execution_sdk_python.serdes import SerDes, SerDesContext


class ItemSerDes(SerDes[dict]):
    def serialize(self, value: dict, ctx: SerDesContext) -> str:
        return json.dumps(value)

    def deserialize(self, data: str, ctx: SerDesContext) -> dict:
        return json.loads(data)


@durable_execution
def handler(event: dict, context: DurableContext) -> list:
    items = ["a", "b", "c"]
    result = context.map(
        items,
        lambda ctx, item, idx, arr: {"id": item, "status": "done"},
        config=MapConfig(item_serdes=ItemSerDes()),
    )
    return result.get_results()
  • item_serdes serializes each item result.
  • serdes serializes the aggregated BatchResult.
  • When you provide only serdes, the SDK uses it for both for backward compatibility. ParallelConfig has the same two fields.
import java.util.List;
import java.util.Map;
import software.amazon.lambda.durable.DurableContext;
import software.amazon.lambda.durable.DurableHandler;
import software.amazon.lambda.durable.config.MapConfig;
import software.amazon.lambda.durable.model.MapResult;
import software.amazon.lambda.durable.serde.JacksonSerDes;

public class MapConfigExample extends DurableHandler<Object, List<Map<String, String>>> {
    @Override
    public List<Map<String, String>> handleRequest(Object input, DurableContext context) {
        MapConfig config = MapConfig.builder()
            .serDes(new JacksonSerDes())
            .build();

        List<String> items = List.of("a", "b", "c");
        MapResult<Map<String, String>> result = context.map(
            "process-items",
            items,
            Map.class,
            (item, index, ctx) -> Map.of("id", item, "status", "done"),
            config
        );
        return result.succeeded();
    }
}
  • serDes applies to each item result.
  • Java ParallelConfig does not have a serDes field.

Built-in SerDes helpers

createClassSerdes(cls) creates a Serdes<T> that preserves class instances through the round-trip. It deserializes by calling Object.assign(new cls(), JSON.parse(data)), so class methods are available on the deserialized value. The constructor must take no required parameters. Private fields and getters are not preserved.

import {
  DurableContext,
  createClassSerdes,
  withDurableExecution,
} from "@aws/durable-execution-sdk-js";

class Order {
  id: string = "";
  total: string = "";

  label() {
    return `Order ${this.id}${this.total}`;
  }
}

const orderSerdes = createClassSerdes(Order);

export const handler = withDurableExecution(
  async (event: unknown, context: DurableContext) => {
    const order = await context.step(
      "fetch-order",
      async () => Object.assign(new Order(), { id: "order-123", total: "99.99" }),
      { serdes: orderSerdes },
    );
    // order.label() works — class methods are preserved after deserialization
    return order.label();
  },
);

PassThroughSerDes stores the value as-is (the value must already be a string). JsonSerDes uses json.dumps and json.loads without the envelope format that ExtendedTypeSerDes adds for complex types.

from aws_durable_execution_sdk_python import (
    DurableContext,
    StepContext,
    durable_execution,
    durable_step,
)
from aws_durable_execution_sdk_python.config import StepConfig
from aws_durable_execution_sdk_python.serdes import JsonSerDes, PassThroughSerDes

# PassThroughSerDes — stores the value as-is (must already be a string)
# JsonSerDes — standard json.dumps / json.loads, no envelope format


@durable_step
def fetch_raw(ctx: StepContext) -> str:
    return '{"id":"order-123"}'


@durable_execution
def handler(event: dict, context: DurableContext) -> str:
    raw = context.step(
        fetch_raw(),
        config=StepConfig(serdes=PassThroughSerDes()),
    )
    return raw

The built-in JacksonSerDes handles class instances via Jackson's ObjectMapper. You can create your own passthrough SerDes like this:

import software.amazon.lambda.durable.DurableContext;
import software.amazon.lambda.durable.DurableHandler;
import software.amazon.lambda.durable.StepContext;
import software.amazon.lambda.durable.TypeToken;
import software.amazon.lambda.durable.config.StepConfig;
import software.amazon.lambda.durable.exception.SerDesException;
import software.amazon.lambda.durable.serde.SerDes;

// A pass-through SerDes stores the value as-is (already a JSON string).
class PassThroughSerDes implements SerDes {
    @Override
    public String serialize(Object value) {
        return (String) value;
    }

    @Override
    public <T> T deserialize(String data, TypeToken<T> typeToken) {
        @SuppressWarnings("unchecked")
        T result = (T) data;
        return result;
    }
}

public class PassThroughSerdesExample extends DurableHandler<Object, String> {
    @Override
    public String handleRequest(Object input, DurableContext context) {
        StepConfig config = StepConfig.builder()
            .serDes(new PassThroughSerDes())
            .build();

        return context.step(
            "fetch-raw",
            String.class,
            (StepContext ctx) -> "{\"id\":\"order-123\"}",
            config
        );
    }
}

FileSystem serdes

The FileSystem serdes stores data on the filesystem and keeps a file pointer in the checkpoint. This can be useful when you do not want to store your data in the checkpoint itself, for example when your payload exceeds the durable execution checkpoint size limit. The persisted value lives on the filesystem and the SDK reads it on replay.

The FileSystem serdes requires a filesystem that persists across invocations and that every Lambda execution environment can read. In AWS Lambda, this means:

  • Amazon Elastic File System (Amazon EFS). Serverless file system that scales automatically with your workloads.
  • Amazon S3 Files. Serverless file system for mounting an Amazon S3 bucket. Amazon S3 Files provides access to Amazon S3 objects as files using standard file system operations such as read and write on the local mount path.

Do not use Lambda's /tmp directory

Lambda's /tmp filesystem is local to a single execution environment. A different execution environment may run the next invocation, so the SDK cannot find files written to /tmp on replay and deserialization fails. Always mount a persistent, shared filesystem.

Pass the FileSystem serdes to a single operation through StepConfig, CallbackConfig, MapConfig, or ParallelConfig. Other operations in the same handler continue to use the default serdes.

import {
  DurableContext,
  withDurableExecution,
  createFileSystemSerdes,
} from "@aws/durable-execution-sdk-js";

export const handler = withDurableExecution(
  async (event: { customerId: string }, context: DurableContext) => {
    const fsSerdes = createFileSystemSerdes("/mnt/s3");

    // Pass the FileSystem serdes to one step. Other operations in this handler
    // keep using the default JSON serdes.
    const profile = await context.step(
      "load-profile",
      async () => loadLargeProfile(event.customerId),
      { serdes: fsSerdes },
    );

    return { name: profile.name };
  },
);

declare function loadLargeProfile(
  customerId: string,
): Promise<{ name: string }>;

createFileSystemSerdes signature

import {
  Serdes,
  FileSystemSerdesConfig,
} from "@aws/durable-execution-sdk-js";

export type CreateFileSystemSerdes = (
  basePath: string,
  config?: FileSystemSerdesConfig,
) => Serdes<unknown>;

Parameters:

  • basePath Directory path where data files are written. Set this to your filesystem mount point.
  • config (optional) FileSystemSerdesConfig controlling storage mode, path encoding, and preview generation.

Returns: A Serdes that reads and writes JSON files under basePath.

Coming soon.

Coming soon.

FileSystemSerdesConfig

import {
  FileSystemSerdesMode,
  FileSystemPathEncoding,
} from "@aws/durable-execution-sdk-js";

export interface FileSystemSerdesConfig {
  storageMode?: FileSystemSerdesMode;
  pathEncoding?: FileSystemPathEncoding;
  generatePreview?: (value: unknown) => Record<string, unknown> | undefined;
}

Fields:

  • storageMode (optional) A FileSystemSerdesMode value. Default: FileSystemSerdesMode.ALWAYS.
  • pathEncoding (optional) A FileSystemPathEncoding value. Default: FileSystemPathEncoding.URI.
  • generatePreview (optional) Function that returns a preview object. The SDK stores the preview inline in the checkpoint envelope alongside the file pointer. Use the buildPreview helper or write your own.

Coming soon.

Coming soon.

Storage modes

The storageMode enumerated field controls when the SDK writes to the filesystem.

FileSystemSerdesMode.ALWAYS writes every value to a file. The checkpoint stores only the file pointer.

FileSystemSerdesMode.OVERFLOW uses the standard durable execution checkpoint store and only writes to the filesystem when the value would exceed the durable execution checkpoint size limit. See AWS Lambda service quotas.

import {
  createFileSystemSerdes,
  FileSystemSerdesMode,
} from "@aws/durable-execution-sdk-js";

// Small payloads stay inline in the checkpoint. The SDK only writes to the
// filesystem when the checkpoint envelope would exceed the size limit.
export const overflowFileSystemSerdes = createFileSystemSerdes("/mnt/s3", {
  storageMode: FileSystemSerdesMode.OVERFLOW,
});

Coming soon.

Coming soon.

Path encoding

The pathEncoding field controls how the durable execution ARN and the entity ID become the on-disk directory and file names.

FileSystemPathEncoding.URI builds a per-execution directory from the function name, execution name, and invocation ID parsed from the ARN, and encodes the entity ID with encodeURIComponent for the file name. Names stay readable when you read files directly from the mount. A very long entity ID may exceed the filesystem's per-name length limit, commonly 255 bytes.

FileSystemPathEncoding.HASH replaces the ARN and the entity ID with their SHA-256 hex digests. Names are a fixed 64 characters and are always filesystem-safe regardless of the input characters or length. Choose HASH when entity IDs may contain characters that are unsafe in a file name, such as /, or may be long enough to exceed the name-length limit.

import {
  createFileSystemSerdes,
  FileSystemPathEncoding,
} from "@aws/durable-execution-sdk-js";

// Hash the ARN and the entity ID into fixed-length, filesystem-safe segments.
// Use HASH when entity IDs may contain unsafe characters or be very long.
export const hashedFileSystemSerdes = createFileSystemSerdes("/mnt/s3", {
  pathEncoding: FileSystemPathEncoding.HASH,
});

Coming soon.

Coming soon.

Preview and PII masking

When the FileSystem serdes writes to a file, the checkpoint envelope only contains the file pointer, so the GetDurableExecution API and the AWS Console cannot show the actual data for that operation. Configure generatePreview to embed a small object inline so you can see the data without reading the file.

Use buildPreview to compute the preview from a PreviewConfig. The config selects which fields to include, exclude, or mask. Masking replaces a field's value with *** or a custom string. The preview object is capped at 4096 bytes by default.

import {
  createFileSystemSerdes,
  buildPreview,
  PreviewMode,
} from "@aws/durable-execution-sdk-js";

// The checkpoint envelope stores the file pointer plus a small preview object,
// so the console can show id and status without reading the full file. The
// email field is visible but masked, so PII does not land in the checkpoint.
export const previewFileSystemSerdes = createFileSystemSerdes("/mnt/s3", {
  generatePreview: (value) =>
    buildPreview(value, {
      mode: PreviewMode.EXCLUDE_ALL,
      include: [{ name: "id" }, { name: "status" }],
      mask: [{ name: "email" }],
    }),
});

PreviewConfig fields:

  • mode Either PreviewMode.INCLUDE_ALL or PreviewMode.EXCLUDE_ALL. Sets the starting point before applying include, exclude, and mask.
  • include (optional) Fields to add when starting from EXCLUDE_ALL, or to force-include when starting from INCLUDE_ALL.
  • exclude (optional) Fields to remove. Always wins over mask.
  • mask (optional) Fields whose values become maskString. A masked field is visible in the preview unless it is also excluded.
  • maskString (optional) Replacement value for masked fields. Default: ***.
  • maxPreviewBytes (optional) Maximum size in bytes for the preview object when JSON-serialized. Default: 4096.

Each PreviewField selector has a name and an optional match. Use FieldMatchMode.ANYWHERE (default) to match the field name at any depth in the object tree, or FieldMatchMode.PATH to match an exact dot-notation path from the root.

Field names that contain a dot are not supported in selectors because a dot is indistinguishable from a path separator. Array structure is not preserved in the output: fields from array elements merge into a plain object at the array's path.

Coming soon.

Coming soon.

Set as the default for the handler

When you want every step result, child-context result, invoke result, and waitForCondition result in the handler to use the FileSystem serdes, configure it once with configureSerdes.

import {
  DurableContext,
  withDurableExecution,
  createFileSystemSerdes,
} from "@aws/durable-execution-sdk-js";

export const handler = withDurableExecution(
  async (event: { customerId: string }, context: DurableContext) => {
    // Configure once. Every step result, child-context result, invoke result,
    // and waitForCondition result in this handler is now stored on /mnt/s3.
    context.configureSerdes({
      defaultSerdes: createFileSystemSerdes("/mnt/s3"),
    });

    const profile = await context.step("load-profile", async () => {
      return loadLargeProfile(event.customerId);
    });

    return { name: profile.name };
  },
);

declare function loadLargeProfile(
  customerId: string,
): Promise<{ name: string }>;

Serialization errors

When serialization or deserialization fails, each SDK raises or throws a specific exception type. See Serialization errors for the exception hierarchy and how to handle serialization failures.

See also