REST API
기본 주소 https://rerent.ai · 인증 Authorization: Bearer <토큰> (설정 → API 토큰) · 요청·응답 JSON · 시각은 epoch 초(분 단위 정렬, 60의 배수) · 금액·가격은 KRW 정수.
응답 규약: 단건은 { "object": "order", "id": "ordr_…", … }, 목록은 { "object": "list", "data": [...], "has_more": false, "cursor": null }. 오류는 { "error": { "code": "insufficient_balance", "message": "…" } }.
스케줄(*_allocation_schedule_delta)은 [{start_at, end_at, node_count}] 배열이고 응답에서는 마지막에 end_at: null, node_count: 0 종결자가 붙어요. 반열림 구간 [start_at, end_at).
계정
| 메서드 | 경로 | 설명 |
|---|---|---|
| GET | /v1/account | 조직·사용자·잔액·홀드·가용 |
| GET | /v1/stats/realized | 실현 할인 통계 + 공급자 매출 |
SKU
| 메서드 | 경로 | 설명 | |
|---|---|---|---|
| GET | /v1/skus | 거래 중인 SKU. ?all=1 이면 중단 포함 | |
| GET | `/v1/skus/{id\ | alias}` | 상세 |
| GET | `/v1/skus/{id\ | alias}/availability?range_start_at&range_end_at` | 살 수 있는 노드 수 스케줄(가격 무관) + 최저·최고 매도가 |
풀
| 메서드 | 경로 | 설명 | |
|---|---|---|---|
| GET | /v1/pools?full=1 | 내 풀 목록(full 이면 스케줄 포함) | |
| POST | /v1/pools | {name} | |
| GET | `/v1/pools/{id\ | name}` | 스케줄 · 매도 중 · 팔 수 있는 시간(SKU 별) |
| PATCH | /v1/pools/{id} | {name} | |
| DELETE | /v1/pools/{id} | 열린 주문·남은 할당이 없을 때만 | |
| GET | /v1/pools/{id}/sellable?sku= | 팔 수 있는 스케줄 | |
| POST | /v1/pools/{id}/extend | `{sku, duration_hours\ | end_at, max_price, allow_standing?, estimate?}` |
| GET / POST | /v1/pools/transfers | {from_pool, to_pool, sku, start_at, end_at, node_count} | |
| GET | /v1/pools/transfers/{id} |
주문
| 메서드 | 경로 | 설명 |
|---|---|---|
| GET | /v1/orders?side=&state=&pool=&limit=&starting_after=&fills=1 | 내 주문. state 반복 가능 |
| POST | /v1/orders | 주문 생성(아래) · Idempotency-Key 헤더 지원 |
| POST | /v1/orders/estimate | 같은 본문으로 견적(체결 없음) |
| GET | /v1/orders/{id} | 상세 + fills |
| POST | /v1/orders/{id}/cancel | 204 · 남은 부분만 취소 |
주문 본문:
{
"side": "buy", // buy | sell
"pool": "default", // 풀 ID 또는 이름
"sku": "icn-1-h100", // SKU ID 또는 alias
"start_at": "now", // epoch 초 또는 "now"
"end_at": 1789380000, // 또는 duration_hours
"node_count": 2,
"max_price": 30000, // buy: max_price · sell: min_price (또는 limit_price)
"allow_standing": false,
"allow_partial": false,
"memo": "nightly-train"
}
allocation_schedule_delta: [{start_at, end_at, node_count}] 한 구간으로 줘도 돼요(SF Compute 호환 꼴).
주문 응답의 주요 필드: state, allocation_schedule_delta(요청), remaining_allocation_schedule_delta(호가에 남은 것), filled_allocation_schedule_delta(체결된 것), fills[](각 체결의 price_krw_per_node_hour, gross_krw, fee_krw, net_krw, maker_side), filled_average_price_krw_per_node_hour.
오류 코드: insufficient_balance(402) · insufficient_allocation(409) · invalid_window · start_in_past · end_too_far · invalid_price · sku_not_found · pool_not_found · idempotency_mismatch(409).
공개 오더북(익명)
| 메서드 | 경로 | 설명 |
|---|---|---|
| GET | /v1/orderbook/summary | SKU 별 최저 매도·가능 노드·24h 체결 |
| GET | /v1/orderbook/windows?sku=&range_start_at=&range_end_at= | 열린 주문이 있는 SKU×윈도우와 best bid/ask |
| GET | /v1/orderbook/quote?sku=&start_at=&end_at= | 한 윈도우의 톱오브북 |
| GET | /v1/orderbook/depth?sku=&start_at=&end_at=&depth=20 | 가격 레벨별 노드 수 |
| GET | /v1/orderbook/fills?sku=&start_at=&end_at=&since_at=&limit= | 체결 내역 |
하드웨어 필터는 sku= 대신 requirements=accelerator:h100;region:kr 꼴도 받아요.
인스턴스(실행층)
| 메서드 | 경로 | 설명 |
|---|---|---|
| GET / POST | /v1/instances | 목록(?pool=&state=&all=1) / 생성 {pool, sku?, count?, name?, image?, mode?, command?, startup_script?, env?, ports?, priority?} |
| GET / DELETE | /v1/instances/{id} | 단건 / 종료 |
| POST | /v1/instances/{id}/replace | 종료 + 같은 설정으로 새 인스턴스 대기열 |
| GET | /v1/instances/{id}/logs?tail= | 컨테이너 로그 |
| POST | /v1/instances/{id}/exec | {cmd, timeout_secs?} 명령 한 번(≤50초) |
| GET | /v1/instances/presets | (공개) 이미지 프리셋·기본값 |
| PATCH | /v1/pools/{id} | {launch_template:{enabled, image, mode, command?, startup_script?, env?, ports?, priority}} 자동 시작 |
| GET | /v1/nodes | 내 배정 노드(현재·예정) — 노드 상태·감지 GPU·그 위의 인스턴스와 ssh_command |
| GET / POST | /v1/ssh-keys · DELETE /v1/ssh-keys/{id} | 조직 SSH 공개키(돌고 있는 인스턴스에 즉시 반영) |
자동 매수(배포)
풀에 「이 SKU 노드 N대를 앞으로 H시간 동안 항상」 걸어 두면 매 분 보유 스케줄의 빈 구간을 상한가 이하 매물에서 즉시 사요(부분 체결 허용 · 호가에 남기지 않음). 공급자 자동 매도의 반대편이고, 풀의 자동 시작 템플릿과 함께 쓰면 사자마자 인스턴스가 떠요.
| 메서드 | 경로 | 설명 | |
|---|---|---|---|
| GET / POST | /v1/deployments | 목록(?pool=) / 생성 {pool, sku, name?, target_node_count, max_price, horizon_hours?=6, block_hours?=1, enabled?} | |
| GET / PATCH / DELETE | `/v1/deployments/{id\ | name}` | 단건 / {enabled?, target_node_count?, max_price?, horizon_hours?, block_hours?, name?} / 중단(산 시간·주문은 남음) |
| POST | /v1/deployments/{id}/run | 지금 한 번 확보 시도(꺼져 있어도) → {bought_node_hours, buy_orders, error, deployment} |
horizon_hours1~168: 지금부터 몇 시간 앞까지 확보해 둘지.block_hours1~24: 한 번에 사는 최소 길이 — 지평 끝의 1분 조각이 매 분 1분짜리 매수가 되지 않게 블록마다 한 번 사요.- 응답
coverage: {now_nodes, horizon_covered_pct, next_gap_at}·spent_krw·bought_node_hours·buy_orders·last_error(크레딧 부족 · 상한가 이하 매물 없음 등 — 다음 분에 다시 시도). - 자동 매수 주문은
managed_by가 배포 id 예요(주문 목록에 「자동」 표시).
공급자
| 메서드 | 경로 | 설명 |
|---|---|---|
| GET / POST | /v1/clusters | 목록 / 등록(응답 installs[] 에 노드별 에이전트 설치 명령 · bootstrap 토큰 1회) |
| GET / PATCH / DELETE | /v1/clusters/{id} | PATCH {name?, auto_sell?, available_to_at?} |
| POST | /v1/clusters/{id}/nodes | {nodes:[…]} 또는 줄바꿈 문자열 → 응답 installs[] |
| POST | /v1/clusters/{id}/nodes/{nodeId}/install | 설치 명령 다시 받기(bootstrap 재발급 · 등록된 노드는 재설치용 새 호스트) |
| DELETE | /v1/clusters/{id}/nodes/{nodeId} | 노드 제거(구매자 인스턴스가 돌고 있으면 409) |
| GET | /v1/clusters/{id}/assignments | 노드별 배정(익명 꼬리표) |
크레딧·조직
| 메서드 | 경로 | 설명 |
|---|---|---|
| GET | /v1/credits/ledger | 원장 |
| GET / POST | /v1/credits/topups | 충전 요청 {amount_krw} |
| GET / POST | /v1/credits/payouts | 출금 요청 {amount_krw, bank_info} (소유자) |
| GET / POST | /v1/tokens · DELETE /v1/tokens/{id} | API 토큰 |
| GET | /v1/members · PATCH/DELETE /v1/members/{userId} | 멤버·역할 |
| POST | /v1/invites | {email, role} → 초대 링크 |
역할
| 역할 | 할 수 있는 것 |
|---|---|
| owner | 전부 + 출금 + 역할 변경 |
| admin | 매도·클러스터·토큰·초대·충전 요청 |
| member | 매수·조회 |
API 토큰은 admin 권한으로 동작해요.