AceDataCloud AI Chat v2로 에이전틱 앱 구축하기

채팅 엔드포인트는 텍스트를 반환할 수 있습니다. 에이전트 엔드포인트는 파일을 검사하고, 웹을 검색하며, 승인된 도구를 호출하고, 누락된 정보를 요청하며, 모든 단계를 인터페이스로 다시 스트리밍할 수 있습니다.

이것이 AceDataCloud AI Chat v2 뒤에 있는 실질적인 차이입니다. POST https://api.acedata.cloud/aichat2/conversations의 엔드포인트는 원래 대화 API의 간단한 요청 스타일을 유지하면서 멀티모달 콘텐츠 블록, 자율적인 다중 라운드 도구 사용, MCP 연결, 구조화된 스트리밍 이벤트, 재개 가능한 대화, 대화 CRUD 작업을 추가합니다.

AI Chat v2 아키텍처: 멀티모달 입력, 에이전트 도구, 구조화된 이벤트

이 가이드는 기본 챗봇에서 프로덕션 에이전트 경험으로 이동할 때 중요한 통합 결정을 중점적으로 다룹니다.

AI Chat v2에서 무엇이 바뀌나요?

AI Chat v2는 원래 /aichat/conversations 인터페이스의 종합적인 업그레이드입니다. 주요 기능은 다음과 같습니다:

  • 멀티모달 입력: 하나의 message 배열에서 순서가 지정된 text, image_url, file_url 블록을 전송합니다.
  • 자율적인 도구 사용: 모델은 여러 라운드에 걸쳐 내장 도구와 사용자가 승인한 MCP 서버를 호출할 수 있습니다.
  • 유형화된 스트리밍: 텍스트, 도구 활동, 인용, 카드, 아티팩트, 오류, 완료 데이터를 별도의 이벤트로 렌더링합니다.
  • 일시 중지 및 재개: ask_user_question 이벤트를 처리하고 도구 결과로 동일한 대화를 계속합니다.
  • 대화 관리: 동일한 엔드포인트의 작업을 통해 검색, 일괄 검색, 업데이트, 삭제를 수행합니다.
  • 하위 호환 요청: 기존 model + question 클라이언트는 엔드포인트 경로를 변경하여 마이그레이션할 수 있습니다.

중요한 아키텍처 변화는 프런트엔드가 더 이상 응답을 하나의 불투명한 문자열로 취급할 필요가 없다는 점입니다. 이벤트 기반 작업 공간이 될 수 있습니다.

하위 호환 경로로 시작하기

가장 낮은 위험의 마이그레이션은 의도적으로 작습니다. 기존 요청 본문을 유지하고 엔드포인트만 변경합니다:

curl -X POST 'https://api.acedata.cloud/aichat2/conversations' \
  -H 'accept: application/json' \
  -H 'authorization: Bearer YOUR_API_TOKEN' \
  -H 'content-type: application/json' \
  -d '{
    "model": "YOUR_SUPPORTED_MODEL",
    "question": "Summarize the three most important points in this request.",
    "stateful": true
  }'

JSON 모드에서 응답은 익숙한 형태를 유지합니다:

{
  "answer": "...",
  "id": "conversation-uuid"
}

반환된 id를 유지하세요. 다음 요청에서 이를 전송하면 클라이언트가 전체 메시지 기록을 다시 전송할 필요 없이 관리되는 대화를 계속할 수 있습니다.

stateful의 기본값은 true입니다. 라운드를 저장하지 않아야 할 때는 명시적으로 false로 설정하세요.

이 첫 번째 마이그레이션 단계는 도구 또는 새로운 스트리밍 UI를 도입하기 전에 인증, 모델 가용성, 지연 시간, 애플리케이션 동작을 검증할 수 있게 합니다.

순서와 모달리티가 중요할 때 message 사용하기

이전의 question 필드는 텍스트 전용 프롬프트에 편리합니다. 이미지나 파일과 혼합된 텍스트에는 순서가 지정된 message 배열을 사용하세요:

{
  "model": "YOUR_SUPPORTED_MODEL",
  "stateful": true,
  "message": [
    {
      "type": "text",
      "text": "Read the attached report and compare its chart with this screenshot. Return five findings."
    },
    {
      "type": "file_url",
      "file_url": {
        "url": "https://example.com/report.pdf"
      }
    },
    {
      "type": "image_url",
      "image_url": {
        "url": "https://example.com/dashboard.png"
      }
    }
  ]
}

지원되는 콘텐츠 블록은 다음과 같습니다:

블록 필수 값 최적의 사용 사례
text text 지침, 컨텍스트, 질문
image_url image_url.url 스크린샷, 차트, 제품 이미지
file_url file_url.url PDF, CSV, TXT 및 기타 파일

AI Chat v2는 여전히 이전 references 배열을 인식합니다. 이미지 확장자는 이미지 블록으로 변환되고, 다른 URL은 파일 블록이 됩니다. 이 호환성은 마이그레이션 중에 유용하지만, 콘텐츠 순서가 중요할 때는 message가 더 나은 장기 계약입니다.

토큰뿐 아니라 이벤트를 중심으로 클라이언트 설계하기

accept 헤더로 응답 형식을 선택하세요:

클라이언트 헤더 형식
브라우저 UI text/event-stream Server-Sent Events
Node, Python, CLI, 워커 application/x-ndjson 줄당 하나의 JSON 이벤트
단순 백엔드 요청 application/json 최종 {answer, id} 객체

최소한의 Python NDJSON 소비자는 다른 이벤트 유형을 보존하면서 텍스트를 조합할 수 있습니다:

import json
import os
import requests

url = "https://api.acedata.cloud/aichat2/conversations"
headers = {
    "accept": "application/x-ndjson",
    "authorization": f"Bearer {os.environ['ACEDATA_API_TOKEN']}",
    "content-type": "application/json",
}
payload = {
    "model": os.environ["ACEDATA_CHAT_MODEL"],
    "question": "Research the topic, cite sources, and return a concise brief.",
    "stateful": True,
}

with requests.post(url, json=payload, headers=headers, stream=True, timeout=120) as response:
    response.raise_for_status()
    answer = []

    for raw_line in response.iter_lines():
        if not raw_line:
            continue

        event = json.loads(raw_line)
        event_type = event.get("type")

        if event_type == "text_delta":
            answer.append(event.get("content", ""))
        elif event_type == "tool_use":
            print("tool started:", event.get("tool_name"))
        elif event_type == "tool_result":
            print("tool finished; error =", event.get("is_error"))
        elif event_type == "citation":
            print("source:", event)
        elif event_type == "artifact":
            print("artifact:", event)
        elif event_type == "error":
            raise RuntimeError(event.get("message", "unknown agent error"))
        elif event_type == "done":
            print("usage:", event.get("usage"))
            print("terminal reason:", event.get("terminal_reason"))

print("".join(answer))

프로덕션 인터페이스는 각 이벤트 계열에 대해 렌더러 또는 핸들러를 정의해야 합니다:

  • text_delta는 답변 영역을 업데이트합니다.
  • tool_use 및 tool_result는 활동 상태와 감사 뷰를 구동합니다.
  • citation은 관련 출력에 소스를 연결합니다.
  • card는 구조화된 미리보기를 렌더링합니다.
  • artifact는 별도의 생성된 결과물을 노출합니다.
  • thinking은 선택한 모델이 이를 노출할 때만 처리해야 합니다.
  • error는 현재 라운드를 종료하거나 복구합니다.
  • done은 스트림을 닫고 토큰 사용량과 종료 이유를 기록합니다.

인터페이스에 최종 답변만 필요하다면 모든 text_delta의 content를 연결하세요. 이는 JSON 모드에서 반환되는 answer와 동일합니다.

에이전트가 도구를 사용하게 하되—활동을 보이게 하세요

도구 호출은 기본적으로 활성화되어 있습니다. AI Chat v2는 웹 검색, 페이지 추출, 파일 읽기와 같은 내장 기능을 사용할 수 있습니다. 또한 Google Drive, Notion, Slack, GitHub와 같이 사용자가 승인한 MCP 연결을 마운트할 수도 있습니다.

스트림은 경계를 명확하게 노출합니다:

{"type":"tool_use","tool_id":"toolu_01","tool_name":"web_search","input":{"query":"topic"}}
{"type":"tool_result","tool_id":"toolu_01","output":"...","is_error":false}

tool_id로 tool_use와 tool_result를 쌍으로 연결하세요. 이는 진행률 표시기, 지연 시간 측정, 오류 처리, 운영자가 읽을 수 있는 감사 추적을 지원합니다.

하나의 요청에서 발생할 수 있는 자율 도구 라운드 수를 제한하려면 max_turns를 사용하세요. 허용 범위는 1–500이며, 문서화된 기본값은 500입니다. 더 낮은 값은 제한 없는 실행을 줄입니다. max_turns: 1을 설정하면 단일 응답을 강제하고 도구 호출을 방지합니다.

실용적인 배포 패턴은 다음과 같습니다:

  1. 제품 UI에서 도구 없이 JSON 모드로 시작합니다.
  2. NDJSON 또는 SSE를 추가하고 text_delta와 done을 렌더링합니다.
  3. 접을 수 있는 타임라인으로 도구 활동을 노출합니다.
  4. 인용 및 아티팩트 렌더링을 추가합니다.
  5. 작업 복잡성과 비용 허용 범위에 따라 의도적인 max_turns를 설정합니다.
  6. 쓰기 가능한 연결은 확인 모델을 검토한 후에만 활성화합니다.

질문을 재개 가능한 상태 머신으로 처리하기

에이전트는 때때로 명확한 설명이 필요합니다. 이 경우 스트림은 ask_user_question을 내보낼 수 있으며, 대화는 awaiting_user_input 상태로 전환됩니다.

클라이언트는 다음을 수행해야 합니다:

  1. 대화 id와 tool_id를 저장합니다.
  2. 질문과 옵션을 렌더링합니다.
  3. 사용자의 응답을 수집합니다.
  4. 동일한 대화 id로 다른 요청을 전송합니다.
  5. 보류 중인 도구 호출에 대한 답변을 tool_results를 통해 반환합니다. 이는 에이전트가 누락된 정보로 완료할 수 있는 척하는 것보다 더 견고합니다. 또한 민감한 작업에 대한 승인 게이트를 가능하게 합니다.

대화형 실행과 무인 실행 분리

웹훅, CI/CD 작업 및 모니터링 시스템의 경우, async: true는 작업이 계속되는 동안 작업 식별자를 반환합니다. 결과는 나중에 검색하거나 HTTP(S) 콜백 URL로 전달할 수 있습니다.

무인 쓰기 액세스는 명시적이어야 합니다. AI Chat v2는 allowed_skills, allowed_mcp_servers 또는 동등한 unattended_policy 객체를 지원합니다. 빈 목록은 어떤 기능도 승인하지 않습니다. 사전 승인은 커넥터 자체의 보안 메커니즘을 우회하지 않습니다. 무인 확인을 지원하지 않는 스킬은 여전히 드라이런을 수행하거나 쓰기를 거부해야 합니다.

그 구분은 중요합니다: 연결 가용성은 사람이 없는 상태에서 행동할 권한과 동일하지 않습니다.

프로덕션 체크리스트

에이전트 인터페이스를 출시하기 전에 다음을 확인하세요:

  • API 자격 증명은 브라우저 코드가 아닌 서버 측에 저장됩니다.
  • 모델 이름은 하드코딩된 가정이 아니라 현재 지원되는 모델 목록에서 가져옵니다.
  • 스트림 파서는 부분적인 네트워크 청크와 알 수 없는 이벤트 유형을 허용합니다.
  • 도구 이벤트는 tool_id로 쌍을 이루며 오류가 기록됩니다.
  • max_turns가 의도적으로 설정됩니다.
  • 인용 및 아티팩트 URL이 안전하게 렌더링됩니다.
  • ask_user_question은 나중에 재개할 수 있을 만큼 충분한 상태를 유지합니다.
  • 쓰기 가능한 연결은 확인 또는 범위가 좁은 무인 승인을 유지합니다.
  • done.usage 및 terminal_reason이 관측 가능성에 반영됩니다.
  • 대화 삭제 및 보존 정책이 제품 요구 사항과 일치합니다.

챗봇에서 에이전트로 가는 가장 짧은 경로

AI Chat v2는 전체 재작성을 강제하지 않습니다. 엔드포인트를 변경하고 현재 요청 본문을 유지하는 것부터 시작하세요. 그런 다음 멀티모달 message 블록으로 이동하고, 구조화된 스트리밍을 채택하고, 도구 진행 상황을 노출하며, 일시 중지 및 재개 처리를 추가하세요.

그 결과 파일, 도구, 인용, 아티팩트 또는 사용자 확인을 위한 별도의 프로토콜을 만들지 않고도 단순한 답변에서 감사 가능한 에이전트 워크플로로 성장할 수 있는 클라이언트가 됩니다.

공식 리소스