AWS Lambda Durable Functions에서 결정적 코드 작성을 위한 핵심 가이드

by DD
4개월 전
조회수 16

AWS Lambda Durable Functions에서 코드의 결정성(Determinism) 확보의 중요성을 강조하며, 비결정적 코드(Non-deterministic Code)의 문제점을 지적

`Array.prototype.sort()`의 안정성(Stability)과 `Date.now()` 사용의 위험성을 분석하며, 결정성 확보를 위한 구체적인 해결책 제시

`context.step()` 내에서 발생하는 사이드 이펙트(Side Effects)재시도(Retries) 간의 관계를 설명하며, 재시도 안전성(Retry Safety) 확보 방안 제시

`context.map()`을 활용한 병렬 처리(Parallel Processing)와 `StepSemantics`를 이용한 재시도 제어 등, 다양한 결정성 확보 기법 소개

결정성 확보를 통해 재실행(Replay) 시 일관성을 유지하고, 오류 발생 가능성(Error Probability)을 줄이는 방법을 제시

결정적 코드(Deterministic Code)의 중요성

본문은 AWS Lambda Durable Functions에서 결정적 코드(Deterministic Code) 작성을 강조하며, 재실행(Replay) 시 예상치 못한 동작을 방지하는 중요성을 역설한다.

결정적 코드: 동일한 입력(Input)에 대해 항상 동일한 결과를 보장하는 코드

비결정적 코드: `Date.now()`와 같이 실행 시점(Runtime)에 따라 결과가 달라지는 코드

문제점: 재시도(Retries) 및 롤백(Rollback) 시 예측 불가능한 동작(Unpredictable Behavior) 발생

결정성을 확보하기 위해 입력 데이터의 순서, 시간 관련 함수 사용, 사이드 이펙트(Side Effects)를 주의해야 한다.

안정 정렬(Stable Sort)과 입력 순서의 함정

글에서는 `Array.prototype.sort()`의 안정성(Stability)이 보장되더라도, 입력 데이터의 순서가 결정성에 영향을 미칠 수 있음을 지적한다.

안정 정렬: 동일한 우선순위(Priority)의 요소는 입력 순서를 유지

문제 상황: 입력 순서가 의도치 않게 비즈니스 로직(Business Logic)에 영향을 미치는 경우

해결책: 명시적인 정렬 기준(Explicit Sorting Criteria)을 정의하거나, 입력 순서에 의존적인 로직을 제거

입력 데이터의 순서가 의미를 가지는지, 그렇지 않다면 명확한 정렬 기준**을 통해 결정성을 확보해야 한다.

재시도(Retries)와 사이드 이펙트(Side Effects)의 위험성

본문은 `context.step()` 내에서 발생하는 사이드 이펙트(Side Effects)가 재시도(Retries)와 결합될 때 발생하는 문제를 다룬다.

재시도(Retries): 단계(Step) 실패 시 자동으로 재실행

문제점: `chargeCard()`와 같이 여러 사이드 이펙트(Side Effects)를 수행하는 경우, 재시도로 인해 중복 작업 발생 가능성

해결책: 멱등성(Idempotency)을 보장하거나, 각 작업을 별도의 단계(Step)로 분리

재시도 안전성(Retry Safety)을 위해 멱등성을 확보하고, 작업의 격리(Task Isolation)**를 통해 잠재적 문제를 최소화해야 한다.

시간 관련 함수와 결정성 확보

글에서는 `Date.now()`와 같은 시간 관련 함수가 비결정적 코드(Non-deterministic Code)의 주요 원인임을 지적하고, 해결책을 제시한다.

문제점: `Date.now()`는 실행 시점(Runtime)에 따라 다른 값을 반환

영향: 재실행(Replay) 시 시간 기반 로직(Time-based Logic)의 동작 변화

해결책: `context.step()`을 사용하여 시간 값을 캡처하고, 재실행 시 일관성 유지

시간 관련 값은 결정적 코드(Deterministic Code) 내에서 관리하고, 상태 관리(State Management)를 통해 일관성을 유지해야 한다.

context.map()을 활용한 병렬 처리

본문은 `context.map()`을 사용하여 병렬 처리(Parallel Processing)를 구현하고, 결정성을 유지하는 방법을 설명한다.

`context.map()`: 여러 작업을 병렬로 처리하고, 각 작업의 실패를 격리

장점: 개별 작업의 실패 격리(Failure Isolation), 최대 동시 실행 수 제어(Concurrency Control)

단점: 엄격한 순차 처리(Strict Sequencing) 어려움

`context.map()`을 통해 대량의 작업을 효율적으로 처리하고, 결정성(Determinism)을 유지하면서 성능(Performance)**을 향상시킬 수 있다.

Is this code deterministic?