Rivya TypeScript SDK
Rivya TypeScript SDK 베타로 모델, 생성 작업, 파일, 크레딧, Webhook 및 SSE 스트리밍을 포함한 Chat용 Public API v1을 호출하세요.
최근 검토일 2026/08/26
Rivya는 서버 측 Public API 연동을 위한 TypeScript SDK 베타를 제공합니다.
SDK는 Rivya Public API v1을 감싸는 얇은 클라이언트입니다. 하위 수준 계약은 OpenAPI와 스키마 계약에 정의되어 있으며, SDK 메서드는 이 스키마와 계속 일치해야 합니다.
상태
현재 패키지는 이 저장소 안에서 비공개 베타로 유지됩니다. 패키지 이름, 메타데이터, 변경 기록 및 릴리스 절차가 명시적으로 승인되기 전까지 npm에 배포되지 않습니다.
SDK는 다음 기능을 지원합니다.
모델 목록 조회
비동기 생성 작업 생성 및 조회
Files API 업로드 및 조회
크레딧 잔액 조회
Webhook 엔드포인트 관리, 테스트 전송, 이벤트 목록 조회, 전송 목록 조회 및 비밀 키 교체
Webhook 서명 검증
비스트리밍 및 스트리밍 Chat completion, API에서 생성한 채팅 세션
채팅 스트리밍은 이 비공개 베타에서 서버 측 SSE 파싱으로 사용할 수 있습니다. 비밀 API 키는 서버에 보관하세요.
이 저장소에서 설치
SDK가 베타인 동안 로컬 패키지 원본을 사용하세요.
pnpm --dir packages/rivya-sdk typecheck애플리케이션 코드는 비밀 API 키를 서버에 보관해야 합니다.
import { RivyaClient } from "@rivya/sdk";
const rivya = new RivyaClient({
apiKey: process.env.RIVYA_API_KEY
});비밀 API 키를 브라우저 번들, localStorage, 분석 이벤트, 스크린샷 또는 공유 티켓에 넣지 마세요.
모델 목록 조회
models.list는 공개 메서드이며 API 키가 필요하지 않습니다.
const models = await rivya.models.list();
for (const model of models.data) {
console.log(model.id, model.api_status, model.supported_api_inputs);
}생성 작업 만들기
비동기 이미지, 비디오 또는 오디오 생성에는 generations.create를 사용하세요.
const generation = await rivya.generations.create(
{
model: "z-image",
prompt: "A clean editorial product image on a soft studio background",
client_request_id: "order-123-preview"
},
{
idempotencyKey: "order-123-preview"
}
);
console.log(generation.id, generation.status);그런 다음 generations.retrieve로 폴링하세요.
const current = await rivya.generations.retrieve(generation.id);
console.log(current.status, current.result?.primary_url);프로덕션 쓰기 요청에는 Idempotency-Key를 사용하세요. SDK에서는 이를 idempotencyKey로 제공합니다.
파일 업로드
참조 이미지, 비디오 또는 오디오는 files.upload로 업로드하세요.
import { readFile } from "node:fs/promises";
const file = new Blob([await readFile("./reference.png")], {
type: "image/png"
});
const uploaded = await rivya.files.upload({
file,
filename: "reference.png",
kind: "image",
model: "nano-banana-2-lite",
client_request_id: "asset-123"
});
console.log(uploaded.id, uploaded.url);업로드한 메타데이터를 다시 조회하려면 files.retrieve를 사용하세요.
const sameFile = await rivya.files.retrieve(uploaded.id);
console.log(sameFile.mime_type, sameFile.duration_token);생성 작업에서 파일을 사용할 때는 반환된 공개 필드를 params.referenceMediaItems로 전달하세요.
await rivya.generations.create({
model: "nano-banana-2-lite",
prompt: "Restyle this product photo for a clean editorial catalog page",
params: {
referenceMediaItems: [
{
url: uploaded.url,
kind: uploaded.kind,
name: uploaded.file_name,
mimeType: uploaded.mime_type,
durationSeconds: uploaded.duration_seconds ?? undefined,
durationToken: uploaded.duration_token ?? undefined,
width: uploaded.video_width ?? uploaded.width ?? undefined,
height: uploaded.video_height ?? uploaded.height ?? undefined,
sizeBytes: uploaded.video_file_size_bytes ?? uploaded.size_bytes,
imageDimensionsToken: uploaded.image_dimensions_token ?? undefined,
framesPerSecond: uploaded.frames_per_second ?? undefined,
videoBitrateMbps: uploaded.video_bitrate_mbps ?? undefined,
videoMetadataToken: uploaded.video_metadata_token ?? undefined
}
]
}
});모든 Image5 및 Grok Imagine Image 2.0 참조 이미지는 원래의 모델 지정 업로드 응답에 포함된 width, height, size_bytes, image_dimensions_token을 요구합니다. 이후 files.retrieve 호출에서는 토큰이 null일 수 있으므로 MIME 형식, 이미지 크기 또는 바이트 크기를 추측하지 말고 원본 이미지를 다시 업로드하세요. Layer Decomposition에는 이미지 1개 제한과 기하 범위 제한이 추가로 적용되며, Grok Image 2는 표준 이미지 편집에서 서명된 JPEG, PNG 또는 WebP 참조를 1–5개 허용합니다.
Video8 참조 비디오의 경우 원래의 모델 지정 업로드 응답에 포함된 video_width, video_height, frames_per_second, video_bitrate_mbps, video_file_size_bytes, video_metadata_token을 각각 width, height, framesPerSecond, videoBitrateMbps, sizeBytes, videoMetadataToken으로 사용하세요. durationSeconds와 durationToken은 별도의 서명 재생 시간 증명으로 유지해야 합니다. 이후 files.retrieve에서 두 토큰 중 하나라도 누락되어 있다면 원본 비디오를 다시 업로드하세요.
Wan 3.0은 서로 배타적인 text, frames, reference 장면에서 동일한 SDK 필드 매핑을 사용합니다. 각 참조는 model: "wan-3-0-video"로 업로드하세요. 이미지는 서명된 이미지 필드를, 비디오는 서명된 재생 시간과 비디오 메타데이터를 모두 요구하며, 오디오는 원래 응답의 mime_type, size_bytes, duration_seconds, duration_token을 요구합니다. params 안에 seedance_scene, variant, resolution, aspect_ratio, duration, audio와 선택적 seed를 설정하세요. 지능형 재생 시간은 -1이며 30초를 예약하고 참조 비디오와 함께 사용할 수 없습니다. 파일 기반 비디오 생성과 링크 기반 비디오 생성의 단축 경로는 계속 사용할 수 없습니다.
크레딧 확인
const credits = await rivya.credits.retrieve();
console.log(credits.current_credits);Webhook 관리
Webhook 엔드포인트 만들기:
const endpoint = await rivya.webhooks.create({
name: "Production webhook",
url: "https://example.com/rivya/webhook",
event_types: ["generation.succeeded", "generation.failed"]
});
console.log(endpoint.id, endpoint.signing_secret);signing_secret은 생성 또는 교체 호출 직후에만 반환됩니다. 서버에 저장하세요.
그 밖의 Webhook 도우미:
await rivya.webhooks.list();
await rivya.webhooks.retrieve(endpoint.id);
await rivya.webhooks.update(endpoint.id, { status: "disabled" });
await rivya.webhooks.test(endpoint.id);
await rivya.webhooks.rotateSecret(endpoint.id);
await rivya.webhooks.deliveries.list(endpoint.id, { limit: 20 });
await rivya.webhookEvents.list({ limit: 20 });Webhook 페이로드를 신뢰하기 전에 전송 서명을 검증하세요.
import { verifyRivyaWebhookSignature } from "@rivya/sdk";
const ok = await verifyRivyaWebhookSignature({
rawBody,
timestamp: request.headers.get("rivya-webhook-timestamp") || "",
signatureHeader: request.headers.get("rivya-webhook-signature") || "",
signingSecret: process.env.RIVYA_WEBHOOK_SIGNING_SECRET || ""
});
if (!ok) {
throw new Error("Invalid Rivya webhook signature");
}SDK 도우미는 API Webhook에 문서화된 동일한 HMAC-SHA256 계약을 사용합니다.
Chat
비스트리밍 Chat API 대화 한 차례에는 chat.completions.create를 사용하세요.
const completion = await rivya.chat.completions.create(
{
model: "gpt-5-2-chat",
message: "Write a concise launch plan for a new product image campaign",
client_request_id: "chat-001"
},
{
idempotencyKey: "chat-001"
}
);
console.log(completion.session_id, completion.message.content);반환된 session_id로 대화를 이어가세요.
await rivya.chat.completions.create({
model: "gpt-5-2-chat",
session_id: completion.session_id,
message: "Now turn that into a 5-step execution checklist."
});API에서 생성한 세션 조회:
await rivya.chat.sessions.list({ limit: 20 });
await rivya.chat.sessions.retrieve(completion.session_id);Server-Sent Events를 비동기 이터레이터로 처리하려면 chat.completions.stream을 사용하세요.
const stream = await rivya.chat.completions.stream(
{
model: "gpt-5-2-chat",
message: "Write a concise launch plan for a new product image campaign",
client_request_id: "chat-stream-001"
},
{
idempotencyKey: "chat-stream-001"
}
);
for await (const event of stream) {
if (event.event === "message.delta") {
process.stdout.write(event.data.delta);
}
if (event.event === "message.completed") {
console.log(event.data.message.id);
}
}message.delta는 화면 표시 전용입니다. 확정된 결과는 message.completed 이후 사용할 수 있으며, 나중에 chat.sessions.retrieve로 조회할 수 있습니다.
오류
Public API가 2xx 이외의 응답을 반환하면 SDK는 RivyaAPIError를 발생시킵니다.
import { RivyaAPIError } from "@rivya/sdk";
try {
await rivya.generations.retrieve("task_missing");
} catch (error) {
if (error instanceof RivyaAPIError) {
console.log(error.status, error.code, error.requestId);
}
}RivyaAPIError에는 HTTP 상태, 공개 오류 코드, 메시지, 가능한 경우 요청 ID 및 안전한 응답 헤더 일부가 포함됩니다.
검증
변경 작업을 완료로 판단하기 전에 SDK 검사를 실행하세요.
pnpm sdk:check
pnpm --dir packages/rivya-sdk typecheck
pnpm content:api-docspnpm sdk:check에는 정적 계약 검사와 네트워크를 사용하지 않는 런타임 검사가 포함됩니다. 오류 파싱, 안전한 오류 헤더, 멱등성 헤더, Bearer 인증, 공개 모델 목록, 채팅 스트리밍 SSE 파싱, 채팅 스트리밍 오류 이벤트 및 Webhook 서명 검증을 확인합니다.