OpenAI Decisions API 사용 전, Python으로 확률 및 보류 조건 검증하기
요약
OpenAI의 Decisions API는 문의 분류 외에 판단이 모호하거나 보류가 필요한 경우를 처리하는 데 적합합니다. 본 기사는 GPT-6 Luna 모델을 사용하여 후보와 확률 정보를 읽고, Python으로 분배 처리를 구현하는 방법을 다룹니다. 특히 choice 유형에 초점을 맞춰 안정적인 운영 로직을 구축하는 것이 중요함을 강조합니다.
핵심 포인트
- Decisions API는 분류 외의 모호한 입력이나 보류 케이스를 처리할 때 유용하다.
- choice 유형은 후보와 확률 정보를 받아 애플리케이션에서 처리가 가능하다.
- API 사용 시, 데이터 누락 및 확률 합계 오차 등을 검증하는 로직이 필요하다.
- 단일 카테고리가 필요하면 choice를 선택하거나 별도의 변환 로직을 설계해야 한다.
문의를 AI로 분배할 때, '분류명이 반환되었다'는 것만으로는 자동 처리를 진행할 수 없습니다. 분류 외의 문의, 판단이 갈리는 입력, 거부된 응답을 어떤 큐(queue)로 되돌릴지 여부도 필요합니다.
OpenAI는 2026년 10월 6일 Decisions API를 베타 공개했습니다. 본 기사에서는 GPT-6 Luna가 반환하는 타입형 답변을 읽고, 보류할 수 있는 분배 처리를 Python으로 구현합니다. 공식에서 'Responses API보다 약 10배 빠르다'는 것은 제공처의 설명입니다. 본 글에서는 속도나 정확도를 측정하지 않았습니다. 공식 변경 이력
기존 JSON 생성과 무엇이 달라지는가
Responses API의 Structured Outputs는 지정한 JSON Schema에 따라 출력을 생성하는 메커니즘입니다. 예를 들어 분류명 외에도 주문 번호나 설명문 등을 반환하도록 설계할 수 있습니다. Structured Outputs
Decisions에서는 질문마다 답변 형식을 선택합니다. 조건이 성립할 확률을 다루는 predicate, 후보 중 하나를 선택하는 choice, 순서가 있는 기준으로 평가하는 score입니다. 본 기사는 choice에 초점을 맞춥니다. 입력, 후보, 그리고 그 설명을 전달받아 반환된 후보와 확률 정보를 애플리케이션에서 받습니다.
이 설계가 적합한 경우는 출력지가 소수의 알려진 큐로 결정되는 처리입니다. 자유문 답변 생성까지 한 번에 할 것이라면, 필요한 출력 계약을 미리 정리해야 합니다. 기존 시스템에서 '분류 및 회신문 생성'을 하나로 통합하고 있는 경우에도, 분류만 분리하더라도 회신문에 사용되는 시간과 비용은 여전히 발생합니다.
API 진입점과 실행 범위를 확인하기
전용 엔드포인트는 POST /v1/decisions이며, 현재 지원하는 모델은 gpt-6-luna입니다. 기본 입력은 model, input, questions입니다. 질문에는 name을 지정하고, 반환된 답변을 이름으로 대조합니다. Decisions 가이드
공식 Python SDK에서는 3.26.0 버전에서 대응이 추가되었습니다. 만약 SDK를 사용하는 별도의 환경을 준비한다면, 예시로 다음과 같이 버전을 고정할 수 있습니다. 다만, 본 기사의 오프라인 검증은 SDK를 설치하지 않고 Python 3.12.14의 표준 라이브러리만으로 실행했습니다. 공개 준비 시에는 Python 3.14.8에서도 동일한 25 테스트 통과를 확인했습니다. SDK 릴리스
# 실제 API 연결을 별도로 검증할 환경용. 본 기사에서는 실행하지 않음
python3 -m pip install
앞부분을 생략하면, 딕셔너리 키 누락, 미지의 후보, NaN, 극단적으로 큰 정수, 중복된 확률 항목 등이 섞입니다. 부록의 decision_gate.py는 모델명, 답변 건수, 질문명, 답변 유형, 후보 집합을 확인합니다. 확률은 유한한 0~1 사이의 수치로 제한하고, 후보의 중복을 거부하며, 합계가 1에서 크게 벗어나면 보류합니다. 합계의 절대 허용 오차는 본 샘플의 규약으로 0.000001로 설정했습니다.
이는 전체 API를 재구현하는 검증기가 아닙니다. 이번 것은 세 후보・한 질문만 받는 좁은 계약입니다. 질문을 늘리거나 다른 모델로 전환하는 버전에서는 이 계약과 테스트도 업데이트됩니다. 알 수 없는 형식을 추측하여 처리 계속하기보다는, review로 되돌린 이유를 기록할 수 있도록 하는 것이 운영상 더 용이합니다.
참고로, score를 사용할 때는 추가적인 주의가 필요합니다. 값은 기준 인덱스의 확률 가중 평균이기 때문에 소수가 될 수 있습니다. '1.6이 반환되었으므로 중요도 2로 반올림한다'는 규칙은 API가 선택한 카테고리와 같은 의미가 아닙니다. 단일 카테고리가 필요하다면 choice를 선택하거나, 분포를 어떻게 업무 판정으로 변환할지 별도로 결정해야 합니다.

## 가상의 응답으로 25건을 검증하기
기사 말미 부록에 있는 3개의 파일(decision_gate.py, fixtures.json, test_decision_gate.py)을 같은 sample 폴더에 저장하고 해당 폴더에서 실행합니다. 외부 배포처에 접근하지 않아도 재현할 수 있습니다. 추가 의존성, API 키, 네트워크 연결은 필요 없습니다. 샘플 버전은 1.0.0입니다.
python3 decision_gate.py
python3 -m unittest -v
네 가지 가상 케이스는 충분한 확률과 confidence를 가진 billing만 통과시키고, 확률이 높더라도 confidence가 낮은 경우, other, refusal를 review로 되돌립니다. 게다가 임계치 경계, 미지 후보, 답변 누락・중복, 확률 누락・중복, 합계 불일치, 비수치 등을 테스트하여 25건이 통과했습니다.
테스트에서 확인한 것은 직접 만든 분류 규칙입니다. GPT-6 Luna의 한국어 분류 정확도, 응답 시간, SDK의 통신 처리, 실제 API와의 호환성은 미검증입니다. api_example.py는 단독 실행하면 멈추고 실 API에 연결하지 않습니다. 위의 오프라인 실행 명령어로는 API에 연결하지 않으며, 청구도 발생하지 않습니다.
## 입력 과금과 데이터 조건을 함께 보기
Decisions 가이드의 기본 요금은 입력 100만 토큰당 0.10달러이며, 출력 및 캐시 읽기/쓰기 추가 요금은 없습니다. 다만 지역 처리의 가산이나 장문 입력의 배율이 있어 이 단가를 같은 모델의 다른 엔드포인트에 유용하게 사용할 수 없습니다.
가령 과금 대상 입력이 1건당 1,000 토큰이고 1만 건이라면, 1,000만 토큰이므로 기본 요금 계산은 1달러입니다. 이는 개략식 예시일 뿐 실제 청구액은 아닙니다. 입력 본문뿐 아니라 질문이나 후보 설명을 포함하는 usage를 연결 검증에서 확인하고, 재시도 건수와 사람의 확인에 필요한 공수도 별도로 계산합니다. 단가가 작더라도 긴 후보 설명을 전 건에 붙이거나, 보류가 늘어나면 전체 설계 판단이 바뀝니다.
실 API에서는 서버 측 인증이 필요합니다. API 키를 브라우저에 포함시키지 않고, 소스 관리나 로그에 남기지 않는 구성을 합니다. 이번에는 인증 정보를 얻거나 생성하지 않았고, 기존 키도 사용하지 않습니다.
데이터 조건에서는 일반적인 부정 이용 감시 로그는 최대 30일 보관되며, 대상 고객은 조건부로 Zero Data Retention을 이용할 수 있습니다. 프롬프트 캐시는 암호화된 KV 텐서를 최장 24시간 동안 보관할 수 있습니다. 이미지 입력의 예외도 있기 때문에, '학습에 사용되지 않는다'와 '아무것도 저장되지 않는다'는 구분하여 확인해야 합니다. 이용 가능한 지역과 실제 추론 지역도 같지 않습니다. 데이터 제어
문의 본문에는 성명, 연락처, 계약 내용이 포함될 수 있습니다. 채용 검토에서는 분류에 불필요한 항목을 제외하고, 전송 대상・보관 기간・접근 권한을 먼저 결정합니다. 검증용으로 가상의 입력을 사용했더라도, 실제 데이터 전송 가능 여부까지 확인한 것은 아닙니다.
## 실패하기 쉬운 사용법과 채택 조건
분류명을 업무 조작에 직결시키는 설계에는 주의가 필요합니다. billing은 청구 담당자의 후보일 뿐, 환불 허가는 아닙니다. 분류 결과를 계기로 전송・삭제・환불을 수행한다면, 그 조작의 승인과 업무 조건을 별도로 확인해야 합니다. 입력 내의 명령문을 무시하는 프롬프트도, 그것만으로는 부정한 유도를 막는 보증이 되지 않습니다.
또한, 실제 운영 환경에서는 429(Rate Limit), 타임아웃, 통신 후 결과를 받을 수 없는 경우가 있습니다. 이 샘플은 통신 계층을 포함하지 않으므로 재시도 로직의 정확성은 다루지 않습니다. 연결 시에는 재시도 상한선, 비용 상한선, 보류처를 마련하고, 결과가 불분명한 처리를 무제한으로 반복하지 않도록 합니다.
본격적인 평가에서는 처음부터 모든 건을 자동 분류하는 것이 아니라, 사람의 정답 라벨과 대조하는 기간을 둡니다. 전체 정확도뿐만 아니라 '통과된 건의 오분류율', '보류율', '카테고리별 누락' 등을 측정합니다. 보류만 늘려서 보여지는 정확도를 높여도 담당자의 부하가 증가한다면 채택 목적을 충족하지 못합니다.
임계값을 선택하는 데이터와 최종적으로 평가할 데이터를 분리하고, 단문, 복합 문의, 분류 외, 표기 오류 등을 포함해야 합니다. 설명 문구나 후보를 변경했다면 재평가를 하고, 모델 이름, 질문 버전, 임계값 버전, 판정 시각을 로그로 남깁니다. 답변 본문을 장기간 보관하지 않아도, 어떤 규칙으로 보류했는지 추적할 수 있는 설계가 가능합니다.
채택 후보가 되는 것은 분류 범위가 명확하고, 보류를 받아줄 담당자가 있으며, 실제 데이터의 평가 결과를 보고 수정할 수 있는 처리입니다. 근거를 갖춘 장문 설명, 자유로운 정보 추출, 다단계 도구 조작이 중심이라면 Responses API 등을 포함하여 구성을 선택합니다. 베타 신기능으로 시도해 볼 가치는 있지만, 채택의 결정적인 요인은 '고속'이라는 설명뿐만 아니라 자사의 예외 상황을 처리할 수 있는지 여부입니다.
정보 확인일: 2026년 10월 13일(일본 시간).
## 부록: 재현용 파일 전체 내용
처음 세 개의 파일이 오프라인 실행에 필요합니다. request.json과 api_example.py는 미실행 연결 예시로, 오프라인 테스트에는 불필요합니다. 코드는 검증용 ZIP 내부의 원본과 동일합니다.
## decision_gate.py (전체 내용)
"""
Local-only routing gate for a synthetic Decisions API response.
No networking, SDK, API key lookup, or external actions are implemented.
"""
...
## fixtures.json (전체 내용)
[
{
"id": "confident_billing",
...
## test_decision_gate.py (전체 내용)
import copy
import json
import math
...
## request.json (전체 내용)
{
"model": "gpt-6-luna",
"input": "같은 주문의 대금이 두 번 인출되었습니다.",
...
## api_example.py (전체 내용)
"""
Illustrative SDK integration, not run in the article's validation.
This file intentionally refuses standalone execution. It does not read a key
or instantiate a client. A separately authorized caller may inject a configured
...
### 논의 (Discussion)

AI 자동 생성 콘텐츠
본 콘텐츠는 Zenn ML의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기