Skip to navigation

통화 전환 결과

View as Markdown

통화 전환 결과

통화를 상담원이나 다른 번호로 넘겼을 때, 그 전환이 어떻게 됐는지가 통화 조회 응답의 transferTo, transferStatus, transferDuration 에 남습니다.

이 필드들은 읽기 전용 관측 필드입니다. 통화 조회 요청에 값을 실어 전환을 지정할 수는 없습니다. 전환은 따로 실행하고, 그 결과가 이 필드들에 사후에 채워집니다. 전환이 없었던 통화는 전부 null 입니다.

전환을 거는 방법은 전환 걸기 를 보세요.

어디서 받나요

경로필드
통화 단건 조회 GET /v1/accounts/{accountId}/calls/{callId}transferTo, transferStatus, transferDuration, transferHangupCauseQ850, transferSipResponseCode, transferReasonText, transfers
통화 목록 조회 GET /v1/accounts/{accountId}/calls위와 동일합니다. 단 transfers 는 제외됩니다
Status Callback webhookTransferStatus, TransferTo, TransferMode, TransferDuration 등을 실시간으로 받습니다

어느 전환이 여기에 기록되나요

전환 방법기록되나
Voice Agent SDK 의 transfer() 와 내장 도구 transfer_call예
콘솔에서 만든 에이전트의 도구 → 통화 전환예
SIP 단말의 REFER 전환 (blind, attended)예
통화 전환 API POST /v1/accounts/{accountId}/calls/{callId}/actions/transfer예
VoiceML <Dial>아니오 — 아래를 보세요

전환 걸기

진행 중인 통화를 다른 번호나 SIP 엔드포인트로 넘깁니다.

curl -X POST "https://api.claw-ops.com/v1/accounts/{accountId}/calls/{callId}/actions/transfer" \
-H "Authorization: Bearer $CLAWOPS_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"to": "0212345678",
"mode": "warm",
"whisper": "예약 변경 문의입니다.",
"callerIdMode": "original",
"requestId": "req_9f3c21"
}'
{ "callId": "CA...", "transferSequence": 1, "status": "initiated", "requestId": "req_9f3c21" }

접수만 하고 즉시 응답합니다. 대상이 받을 때까지 기다리지 않습니다. 진행과 결과는 Status Callback 의 transfer 이벤트로 오고, 응답의 transferSequence 가 그 결과를 아래 transfers 배열에서 찾는 키입니다.

Voice Agent SDK 또는 콘솔 에이전트가 진행 중인 통화에만 사용할 수 있습니다. VoiceML (<Dial> 등)로 진행 중인 통화는 409 TRANSFER_UNSUPPORTED 로 거절됩니다. 그쪽은 <Dial> 로 목적지를 붙이거나, SIP 단말이 보내는 REFER 를 referUrl 로 받아 처리하세요.

주요 파라미터

필드필수설명
to예전환 대상. destinationType 이 pstn(기본)이면 전화번호, sip 이면 SIP URI
mode아니오blind(기본)는 받으면 바로 연결합니다. warm 은 whisper 안내를 대상에게만 들려준 뒤 연결합니다
whisper아니오warm 일 때 대상에게만 들려줄 안내입니다. 발신자에게는 들리지 않습니다
callerIdMode아니오original 을 주면 걸려 온 전화의 발신자 번호가 대상 단말에 표시됩니다. 통신사망 직수신 인입에만 성립하며, 성립하지 않으면 계정 번호로 표시합니다. 받는 쪽에 표시되는 번호만 바뀌는 것이고 통화 자체는 계정 번호에서 넘기는 전환이라, 받는 장비에 따라 계정 번호가 표시될 수도 있습니다
afterTransfer아니오return(기본)은 전환이 끝나도 통화를 유지하고 에이전트가 이어받습니다. terminate 는 통화를 종료합니다
failureMessage아니오전환이 연결되지 않아 통화를 종료할 때 발신자에게 들려줄 문장입니다. 주지 않으면 아무 말 없이 끊깁니다. 200자 이하
failureVoice아니오failureMessage 를 읽을 음성입니다. <Say> 의 voice 와 같은 형식이며, 생략하면 무료 기본 음성으로 읽습니다
requestId아니오같은 값의 재요청은 새 전환을 만들지 않습니다(멱등). 전환 webhook 에 RequestId 로 되돌아옵니다. 255자 이하

전체 파라미터와 오류 코드는 API Reference 의 Calls → 진행 중 통화 전환 에 있습니다.

전환이 실패하면

대상이 받지 않거나 통화 중이면 발신자와의 통화는 그대로 유지됩니다(afterTransfer 기본값 return). 다른 대상으로 다시 걸 수 있습니다.

다만 이어받을 에이전트가 전환 결과를 받을 수 없는 통화 — 콘솔에서 만든 에이전트이거나, 에이전트 연결이 끊긴 경우 — 에서는 return 이 성립하지 않아 통화가 종료됩니다. 전환이 있었다는 사실을 모르는 에이전트가 맥락 없이 대화를 잇게 되기 때문입니다. 그때는 통화 이벤트에 transfer.after_transfer_downgraded 가 남습니다.

끊기 전에 안내하기

통화가 종료되는 경우(afterTransfer: "terminate", 또는 위처럼 return 이 성립하지 않은 경우) 발신자는 아무 말도 듣지 못한 채 끊깁니다. failureMessage 를 주면 끊기 전에 그 문장을 발신자에게 들려줍니다.

{
"to": "0212345678",
"afterTransfer": "terminate",
"failureMessage": "죄송합니다. 담당자와 연결되지 않았습니다. 잠시 후 다시 걸어 주세요."
}

재생이 끝나면 통화가 종료됩니다. 발신자가 재생 도중에 끊으면 거기서 끝납니다 — transferStatus (no-answer·busy 등)는 안내와 무관하게 그대로 남고, Status Callback 의 transfer 이벤트는 안내를 기다리지 않고 먼저 나갑니다. 문장은 200자까지이며, failureVoice 를 주지 않으면 무료 기본 음성으로 읽습니다(whisperVoice 와 같은 형식).

whisper 와 듣는 사람이 반대입니다. whisper 는 전화를 받은 대상에게만 들리고, failureMessage 는 연결되지 못한 발신자에게만 들립니다. 둘은 함께 쓸 수 있습니다.

재시도

응답이 지연돼 503 transfer_timeout 을 받은 경우 전환은 진행 중일 수 있습니다. 같은 requestId 로 재시도하면 중복 전환 없이 먼저 접수된 전환의 transferSequence 를 돌려줍니다.

<Dial> 은 다릅니다

VoiceML 의 <Dial> 은 통화 중에 다른 목적지를 붙이는 것이지, 통화를 넘기고 빠지는 전환이 아닙니다. 그래서 위 transfer* 필드에는 아무것도 남지 않습니다. 결과는 두 가지로 받습니다.

무엇을 알고 싶은가어디서 받나
연결이 어떻게 끝났나<Dial action> 요청의 DialCallStatus 입니다. completed, busy, no-answer, failed, canceled 중 하나입니다
상대가 언제 받았나<Number statusCallback> 또는 <Sip statusCallback> 통지입니다. answered 와 completed 를 받습니다

필드

필드타입설명
transferTostring | null전환 대상 번호 또는 SIP URI 입니다. 전환이 없었으면 null 입니다.
transferStatusstring | null전환 결과입니다. 아래 값 표를 보세요.
transferDurationnumber | null전환 통화 시간(초)입니다. 대상이 받은 시점부터 그 전환이 끝날 때까지이며, 연결되지 못했으면 null 입니다.
transferHangupCauseQ850number | null전환 leg 의 통신망 Q.850 cause 입니다. 사유 미상이면 null 입니다.
transferSipResponseCodenumber | null전환 leg 의 SIP 응답코드입니다. 사유 미상이면 null 입니다.
transferReasonTextstring | null통신망이 준 원본 진단 텍스트입니다. 자유 형식이라 분기 조건으로 쓰지 마세요.
transfersarray전환 leg 전체 이력입니다. 단건 조회에만 실립니다.

transferStatus 값

값뜻
completed대상이 받아 통화가 이뤄졌고 정상 종료됐습니다.
no-answer벨은 울렸으나 받지 않았습니다.
busy대상이 통화 중입니다.
canceled연결되기 전에 취소되거나 중단됐습니다. 걸려 온 통화의 발신자가 먼저 끊는 경우가 여기 들어갑니다.
failed그 외 실패입니다. 사유는 transferHangupCauseQ850 과 transferSipResponseCode 로 봅니다.

진행 중 상태는 이 필드에 나타나지 않습니다. transferStatus 는 끝난 전환의 결과만 담습니다. initiated, ringing, connected, interrupted 는 transfers[].status 와 Status Callback 의 transfer 이벤트에만 존재합니다.

다단계 전환과 재시도

한 통화에서 전환을 여러 번 시도할 수 있습니다. 1번 상담원이 받지 않아 2번으로 넘기는 경우입니다. 이때 transfers 에는 시도마다 한 건씩 쌓이고, 위 transfer* 단일 필드는 그중 대표 leg 하나만 보여줍니다.

대표 leg 는 끝난 leg 중 하나입니다. completed 인 leg 가 있으면 그것을, 없으면 sequence 가 가장 큰 leg 를 보여줍니다.

즉 세 번 시도해 마지막에 성공했다면 transferStatus 는 completed 이고 transferTo 는 그 성공한 번호이며, 앞선 두 번의 실패는 transfers 에만 남습니다. 전환 시도를 빠짐없이 보려면 transfers 를 쓰세요.

필드타입설명
sequencenumber이 통화에서 몇 번째 전환 시도인지입니다. 1부터 시작합니다.
tostring | null전환 대상입니다.
modestring | nullblind(즉시 전환), warm(대상에게 whisper 안내 후 연결), refer와 refer-attended(SIP 단말이 건 REFER 전환)입니다.
destinationTypestring | nullpstn(통신망 번호) 또는 sip(SIP URI 직결)입니다. 2026-07-10 이전 전환은 null 입니다.
statusstring | nullinitiated, ringing, connected, completed, failed, no-answer, busy, canceled, interrupted 중 하나입니다.
durationnumber | null연결부터 종료까지의 초입니다. 관측용이며 연결되지 못했으면 null 입니다.
billableboolean과금 대상 여부입니다. 한 통화에서 최대 한 건만 true 입니다.
billableDurationnumber | null과금 대상 초입니다.
hangupCauseQ850number | null이 leg 의 통신망 Q.850 cause 입니다.
sipResponseCodenumber | null이 leg 의 SIP 응답코드입니다.
reasonTextstring | null통신망 원본 진단 텍스트입니다.
startedAtstring | null전환을 시작한 시각입니다. 2026-07-10 이전 전환은 null 입니다.
connectedAtstring | null대상이 받은 시각입니다. 연결되지 못했으면 null 입니다. 2026-07-10 이전 전환은 연결됐어도 null 이니 아래 주의를 보세요.
endedAtstring | null이 leg 가 끝난 시각입니다. 2026-07-10 이전 전환은 null 입니다.

2026-07-10 이전 전환은 leg 별 시각과 destinationType 이 없습니다. 그때는 전환 결과를 통화 한 건에 한 줄로만 기록했고 지금의 leg 이력은 그 기록에서 되살린 것이라, startedAt · connectedAt · endedAt · destinationType 이 전부 null 입니다. 연결 여부를 connectedAt 으로 판정하면 그 구간을 오분류합니다 — status 와 duration 을 보세요.

transferDuration 과 transfers[].duration 은 관측값이지 과금 초가 아닙니다. 청구 기준 초는 transfers[].billableDuration 이니 duration 을 합산하지 마세요.

예시

전환을 두 번 시도해 두 번째에 연결된 통화입니다.

{
"callId": "CAabcdef1234567890",
"status": "completed",
"from": "01012345678",
"to": "07080588491",
"direction": "inbound",
"duration": 184,
"hangupCause": "normal_clearing",
"transferTo": "0212345679",
"transferStatus": "completed",
"transferDuration": 96,
"transferHangupCauseQ850": 16,
"transferSipResponseCode": null,
"transferReasonText": null,
"transfers": [
{
"sequence": 1,
"to": "0212345678",
"mode": "blind",
"destinationType": "pstn",
"status": "no-answer",
"duration": null,
"billable": false,
"billableDuration": null,
"hangupCauseQ850": 19,
"sipResponseCode": 480,
"reasonText": null,
"startedAt": "2026-08-27T04:11:02.000Z",
"connectedAt": null,
"endedAt": "2026-08-27T04:11:32.000Z"
},
{
"sequence": 2,
"to": "0212345679",
"mode": "blind",
"destinationType": "pstn",
"status": "completed",
"duration": 96,
"billable": true,
"billableDuration": 96,
"hangupCauseQ850": 16,
"sipResponseCode": null,
"reasonText": null,
"startedAt": "2026-08-27T04:11:33.000Z",
"connectedAt": "2026-08-27T04:11:41.000Z",
"endedAt": "2026-08-27T04:13:17.000Z"
}
]
}

조회는 통화 ID 로 합니다.

curl "https://api.claw-ops.com/v1/accounts/AC1a2b3c4d/calls/CAabcdef1234567890" \
-H "Authorization: Bearer sk_..."

통화가 끝나기 전에 알기

위 필드는 통화가 끝난 뒤에 조회해서 봅니다. 전환이 실패했을 때 바로 다른 상담원으로 재시도하거나 안내 문자를 보내려면 Status Callback 의 transfer 이벤트를 쓰세요. 전환 한 건마다 시작, 연결, 종료 순으로 통지됩니다.

transfer 는 기본 이벤트에 포함되지 않습니다. 받으려면 기본 이벤트와 함께 직접 나열해야 합니다.

initiated ringing answered completed transfer

번호의 statusCallbackEvents 또는 발신 요청의 StatusCallbackEvent 에 위 문자열을 그대로 넣으면 됩니다. 통지에 실리는 파라미터는 다음과 같습니다.

파라미터설명
TransferStatusinitiated, connected, completed, failed, no-answer, busy, canceled, interrupted 중 하나입니다.
TransferSequence이 통화의 몇 번째 전환 시도인지입니다.
TransferTo전환 대상입니다.
TransferMode전환 방식입니다.
TransferDuration전환 통화 시간(초)입니다. 종료 이벤트에만 실립니다.
TransferReason에이전트가 파악한 문의 유형입니다. 파악하지 못했으면 파라미터 자체가 오지 않습니다.
TransferContextVoice Agent SDK 의 transfer({ context }) 로 넘긴 구조화 데이터입니다. JSON 문자열로 전달됩니다.
From통화의 발신번호입니다.
To통화의 수신번호입니다.
Directioninbound 또는 outbound 입니다. From 과 To 중 어느 쪽이 고객인지 판단하는 근거입니다.

이 이벤트에는 CallStatus 가 실리지 않습니다. 통화 자체의 상태 통지와 구분하려면 TransferStatus 필드의 존재 여부로 분기하세요. 또한 같은 종료 이벤트가 두 번 이상 도착할 수 있으므로, CallId 와 TransferSequence, TransferStatus 조합을 키로 삼아 멱등하게 처리하세요.