본문으로 건너뛰기

바닐라 배칭 가이드

배칭은 항목을 수집하여 하나의 함수에 배열로 전달합니다. 설정된 크기에 도달하거나 설정된 대기 시간 동안 새 항목이 들어오지 않거나 사용자 지정 로직에서 준비되었다고 판단하면 배치를 실행할 수 있습니다.

배칭은 여러 항목을 함께 처리하여 작업 수를 줄입니다. 큐와 달리 각 항목마다 래핑된 함수를 한 번씩 호출하지 않습니다.

배칭의 작동 방식​

Batching (process every 3 items or after 2 quiet ticks)
Timeline: [1 second per tick]
Calls: ⬇️ ⬇️ ⬇️ ⬇️ ⬇️ ⬇️ ⬇️ ⬇️
Batch: [ABC] [] [DE] [] [FGH] []
Executed: ✅ ✅ ✅
[======================================================]
^ Items are grouped and processed together

[Size reached] [Wait elapsed] [Size reached]

각 실행은 현재 수집된 항목의 복사본을 받습니다. 배처는 래핑된 함수를 호출하기 전에 해당 항목을 지웁니다.

배칭을 사용하는 경우​

다음과 같은 경우 배칭을 선택합니다.

  • 개별 작업보다 대량 작업이 더 효율적입니다.
  • 네트워크 요청, 데이터베이스 쓰기 또는 분석 이벤트를 그룹화할 수 있습니다.
  • 최대 배치 크기 또는 유휴 기간 트리거가 워크로드에 적합합니다.
  • 개별 항목의 결과가 필요하지 않습니다.

다음과 같은 경우 다른 유틸리티를 선택합니다.

  • 모든 항목을 개별적으로 순서대로 실행해야 합니다. 큐를 사용합니다.
  • 가장 최근 값만 중요합니다. 디바운스를 사용합니다.
  • 호출 사이에 시간 간격을 두어야 합니다. 스로틀을 사용합니다.
  • 배치 처리가 Promise를 반환하거나 재시도 및 중단 지원이 필요합니다. 비동기 배칭을 사용합니다.

TanStack Pacer에서 배칭 사용하기​

TanStack Pacer는 두 가지 코어 API를 제공합니다.

  • batch는 배치에 항목 하나를 추가하는 함수를 반환합니다.
  • Batcher는 생명주기 메서드, 사용자 지정 트리거, 콜백, 상태를 노출합니다.

편의 함수​

import { batch } from '@tanstack/pacer'

const sendEvents = batch<string>(
(events) => {
analytics.send(events)
},
{
maxSize: 3,
wait: 2000,
},
)

sendEvents('opened-page')
sendEvents('clicked-button')
sendEvents('submitted-form') // Executes a batch of three items.

반환된 함수는 생명주기 메서드를 노출하지 않으며 void를 반환합니다.

클래스 API​

import { Batcher } from '@tanstack/pacer'

const eventBatcher = new Batcher<string>(
(events) => {
analytics.send(events)
},
{
maxSize: 5,
wait: 2000,
},
)

eventBatcher.addItem('opened-page')
eventBatcher.addItem('clicked-button')

console.log(eventBatcher.peekAllItems())

결과 및 오류​

동기 배처는 래핑된 함수의 반환 값을 유지하거나 오류를 포착하지 않습니다. 함수를 호출하기 전에 현재 배치를 지웁니다. 함수에서 오류가 발생하면 해당 항목은 더 이상 큐에 있지 않습니다.

Promise 결과, 실패 항목 추적, 설정 가능한 오류 처리, 재시도, 중단 지원에는 비동기 배칭을 사용합니다.

배치 트리거 선택하기​

배치 크기​

maxSize는 수집된 항목 수가 제한에 도달하는 즉시 배치를 실행합니다.

const batcher = new Batcher(processBatch, {
maxSize: 100,
})

기본값은 Infinity이므로 크기 트리거를 제공하지 않으면 비활성화됩니다.

대기 시간​

wait는 설정된 시간 동안 새 항목이 들어오지 않으면 배치를 실행합니다. 항목을 추가할 때마다 타이머가 다시 시작됩니다.

const batcher = new Batcher(processBatch, {
wait: 1000,
})

기본값은 Infinity이므로 시간 트리거를 제공하지 않으면 비활성화됩니다. 항목이 계속 들어오면 타이머가 계속 다시 시작될 수 있습니다. 트래픽이 계속되는 중에도 배치를 최종적으로 실행해야 한다면 wait와 maxSize를 함께 사용합니다.

사용자 지정 트리거​

getShouldExecute는 항목이 추가될 때마다 실행됩니다. 현재 배치를 즉시 실행하려면 true를 반환합니다.

const batcher = new Batcher<number>(processBatch, {
getShouldExecute: (items) => items.includes(0),
})

batcher.addItem(4)
batcher.addItem(0) // Executes [4, 0].

여러 트리거를 설정하면 가장 먼저 도달한 트리거가 배치를 실행합니다.

수집된 항목 제어하기​

플러시​

flush()는 대기 중인 타이머를 지우고 현재 수집된 모든 항목을 실행합니다. 배치가 비어 있으면 아무 작업도 하지 않습니다.

batcher.addItem('event-1')
batcher.addItem('event-2')
batcher.flush()

취소​

cancel()은 대기 중인 타이머를 지우지만 수집된 항목은 유지합니다. 이후 항목이 새 타이머를 예약하거나 flush()를 호출할 수 있습니다.

batcher.cancel()
console.log(batcher.peekAllItems()) // Items are still present.

지우기​

clear()는 수집된 모든 항목을 제거합니다. 타이머 자체는 지우지 않지만 항목을 더 추가하지 않는 한 해당 타이머에서 실행할 항목은 없습니다.

batcher.clear()

재설정​

reset()은 배치 상태와 카운터를 기본값으로 복원합니다. 이미 예약된 타이머는 취소하지 않습니다. 대기 중인 작업을 버려야 한다면 reset() 전에 cancel()을 호출합니다.

batcher.cancel()
batcher.reset()

배치 설정 및 관찰하기​

이후 트리거 동작을 업데이트하려면 setOptions()를 사용합니다.

batcher.setOptions({
maxSize: 20,
wait: 500,
})

wait를 변경해도 기존 타이머의 일정은 다시 잡히지 않습니다. 다음 addItem() 호출이 현재 값을 사용하여 해당 타이머를 교체합니다.

wait 옵션에는 배처 인스턴스를 받는 함수를 지정할 수 있습니다.

const batcher = new Batcher(processBatch, {
wait: (batcher) => (batcher.store.state.size > 10 ? 100 : 500),
})

컬렉션 변경을 관찰하려면 onItemsChange를, 완료된 배치 호출을 관찰하려면 onExecute를 사용합니다.

const batcher = new Batcher(processBatch, {
maxSize: 10,
onItemsChange: (batcher) => {
console.log('Collected:', batcher.store.state.size)
},
onExecute: (items, batcher) => {
console.log('Processed:', items)
console.log('Batches:', batcher.store.state.executionCount)
},
})

배처를 일시 중지하는 데 started를 사용하지 않습니다. 현재 아무 작업도 하지 않으므로 모든 addItem() 호출이 설정된 트리거를 평가합니다.

상태​

애플리케이션이 유지한 일부 상태를 복원하려면 부분 스냅샷을 initialState로 전달합니다. 이 스냅샷은 기본값과 병합됩니다. 지속 가능한 필드만 복원합니다. 대기 중인 타이머는 복원되지 않습니다.

일반적으로 유용한 상태는 다음과 같습니다.

  • items: 현재 수집된 항목입니다.
  • size: 수집된 항목 수입니다.
  • isEmpty: 배치가 비어 있는지 나타냅니다.
  • isPending: 대기 타이머가 활성 상태인지 나타냅니다.
  • executionCount: 완료된 배치 실행 횟수입니다.
  • totalItemsProcessed: 완료된 배치 실행에 전달된 항목 수입니다.
  • status: 'idle' 또는 'pending'입니다.

전체 옵션과 상태 타입은 Batcher API 레퍼런스를 참고합니다.