주요 내용
브라우저 사용: 에이전트는 API가 없는 사이트에서도 여행 예약이나 청구서 제출을 할 수 있습니다. 사이트에서 로그인하라고 요청할 경우, 에이전트는 브라우저 창을 사용자에게 전달하여 비밀번호가 모델의 메시지나 추적 기록에 노출되는 것을 방지합니다.
비동기 서브 에이전트 (Async subagents): 장시간 작업은 서브 에이전트로 보내 백그라운드에서 실행되도록 할 수 있으며, 이 시간 동안 메인 에이전트는 사용자에게 계속 대화할 수 있습니다. 사용자는 에이전트에게 해당 작업의 진행 상황을 확인하거나 경로를 변경하도록 요청할 수 있으며, 결과는 서브 에이전트가 완료되면 대화로 돌아옵니다.
스레드 출처 및 실행 중지: 응답은 요청이 시작된 Slack 스레드로 되돌아가며, 여기에는 예약된 실행이나 나중에 완료된 서브 에이전트의 응답도 포함됩니다. 스레드의 '중지(Stop)' 버튼을 누르면 해당 실행이 취소됩니다.
Managed Deep Agents v0.10이 오늘 출시되었습니다. 이 버전은 브라우저 사용 기능을 추가하여 API가 없는 웹사이트에서도 에이전트가 작업할 수 있게 했으며, 비동기 서브 에이전트를 통해 장시간 작업을 백그라운드에서 실행하는 기능도 제공합니다.
본 게시물에서는 각 기능이 왜 필요한지, 그리고 어떻게 활성화하는지 설명한 후 나머지 릴리스 내용을 다룹니다.
에이전트에게 브라우저 제공하기
여행 예약, 구독 취소 또는 청구서 제출은 모두 사람이 페이지를 클릭하며 사용하는 사이트에서 이루어지며, 종종 에이전트가 호출할 수 있는 API가 없습니다. 에이전트는 작업을 완료하는 방법을 추론할 수는 있지만, API가 없는 웹사이트에서는 실제 행동을 취할 수 없습니다. curl로 페이지를 가져오는 것만으로는 충분하지 않습니다. 이는 JavaScript가 페이지를 렌더링하기 전에 HTML만 생성하며, 에이전트가 아무것도 클릭할 수 없게 만듭니다.
Instinct나 Meta의 Muse 같은 개인화된 에이전트는 웹사이트를 탐색하여 더 광범위한 사용 사례를 열어줄 수 있으며, DataDome은 9월 한 달 동안만 에이전트 브라우저 요청이 무려 4.7배 증가했습니다. 코딩 에이전트 역시 앱의 변경 사항이 실제로 렌더링되고 작동하는지 확인하기 위해 브라우저가 필요합니다.
'Managed Deep Agents에서 브라우저 사용(Browser use in Managed Deep Agents)' 섹션에서 브라우저가 어디에 도움이 되는지, 그리고 내부적으로 어떻게 작동하는지를 다룹니다. 이를 활성화하려면 프로젝트 루트에 브라우저를 선언해야 합니다:
browser.py
from managed_deepagents import define_browser
browser = define_browser(scope="thread", idle_ttl_seconds=600)
Managed Deep Agents는 브라우저를 자체 LangSmith 샌드박스에서 실행하며, 다음 브라우저 도구들을 에이전트에 자동으로 추가합니다:
| Tool | What it does |
|---|
browser_snapshot | 페이지의 접근성 트리(accessibility tree)를 읽고 요소 ID를 할당합니다. |
browser_run | JavaScript 또는 스냅샷 ID 배치 액션들을 통해 탐색하고 상호작용합니다. |
browser_screenshot | 페이지를 캡처하며, 선택적으로 이미지를 샌드박스에 저장합니다. |
browser_handoff | 사람에게 창 제어권을 넘겨줍니다. |
기본적으로 각 대화는 자체 브라우저를 사용하며, 이 브라우저는 턴(turns) 전반에 걸쳐 재사용되며 다른 스레드의 쿠키나 로그인 정보가 없습니다. 하지만 scope="user"를 사용하면, 로그인한 사용자 한 명당 하나의 브라우저가 할당되어 해당 로그인이 그들의 모든 대화에 걸쳐 유지되므로 에이전트가 사이트에 로그인하도록 요청하는 횟수가 줄어듭니다.
사람에게 브라우저 넘기기 (Hand the browser to a person)
대부분의 브라우저 에이전트는 로그인 장벽(login wall)이나 2단계 인증 프롬프트에서 멈춥니다. browser_handoff를 사용하면, 대신 에이전트가 창을 사용자에게 넘겨주므로 비밀번호가 모델의 메시지나 추적 기록에 남지 않습니다.
에이전트는 browser_handoff(reason)을 호출하며 왜 도움이 필요한지 설명합니다. Slack이나 Studio와 같은 사용자 지정 에이전트 채널은 사용자가 에이전트 제어권을 네이티브하게 넘겨받을 수 있는 링크를 보여주며, 이 링크는 원격 브라우저와 상호작용할 수 있는 링크와 제어권 반환(Hand back) 버튼을 포함합니다. 맞춤형 클라이언트는 핸드오프 아티팩트를 자체적으로 렌더링할 수 있습니다. 사용자가 로그인하고 제어권을 반환하면, 에이전트는 페이지를 확인하여 로그인이 성공했는지 검사한 후 작업을 계속합니다. 핸드오프는 즉시 반환되므로, 에이전트는 기다리는 동안 다른 작업을 수행할 수 있습니다. 핸드오프 링크는 15분 후에 만료됩니다.
핸드오프 기능을 사용하면 사용자 자격 증명(credentials)을 보지 않고도 웹페이지를 사용할 수 있게 됩니다.
브라우저 사용 관련 문서는 스코프, 실행별 구성 및 전체 핸드오프 흐름에 대해 다루고 있습니다.
백그라운드에서 서브 에이전트 실행 (Run subagents in the background)
서브 에이전트(Subagents)는 에이전트가 자체 컨텍스트 창을 가진 도우미에게 집중된 작업을 위임할 수 있게 합니다. 이전 Managed Deep Agents에서는 서브 에이전트가 인라인으로 실행되었기 때문에, 에이전트는 서브 에이전트를 호출하고 그 답변을 기다려야 했습니다. 이는 간단한 조회(quick lookup)의 경우 작동하며 여전히 지원되는 패턴입니다. 하지만 동기적(synchronous) 에이전트에 의해 뒷받침되는 장기 작업이거나 여러 에이전트가 병렬로 실행되어야 하는 경우에는, 에이전트와 대화하는 사람이 기다려야 하며 오케스트레이터 에이전트(orchestrator agent)와의 추가적인 상호작용이 차단됩니다.
Managed Deep Agents v0.10을 사용하면 async를 서브 에이전트 정의에 추가하여, 오케스트레이터 에이전트를 차단하지 않고 비동기적으로 서브 에이전트를 실행할 수 있습니다:
from managed_deepagents import define_deep_agent
agent = define_deep_agent(
name="research-assistant",
...
에이전트는 자체 스레드에서 비동기 서브 에이전트를 시작하고, 해당 서브 에이전트들이 실행되는 동안 사용자에게 계속 대화할 수 있습니다. 오케스트레이터 에이전트는 일련의 비동기 작업 도구(async task tools)를 사용하여 이러한 작업을 시작하고, 상태를 확인하며, 업데이트하고, 취소할 수 있습니다. 또한 모든 서비스된 에이전트에는 일반 목적의 서브 에이전트 백그라운드 사본이 제공되어, 런타임에 위임된 작업(delegated work)을 포그라운드에서 실행할지 백그라운드에서 실행할지 선택할 수 있습니다.
비동기 서브 에이전트는 자체적으로 에이전트에게 알림을 보내므로, 에이전트가 폴링 루프(polling loop)에 머무르는 일이 없습니다. 다음에 무슨 일이 일어날지는 서브 에이전트가 완료될 때 에이전트가 어떤 작업을 하고 있었는지에 따라 달라집니다:
| 상황 | 설명 |
|---|
| 완료 시 | 에이전트는 작업 미완료 여부를 모델 호출 전에 확인하며, 결과는 실행 도중에 도착합니다. |
| 바쁨(Busy) | - |
| 유휴(Idle) | 서브 에이전트가 새로운 실행으로 깨웁니다. |
| 승인 대기 중 | 승인은 그대로 유지되며, 사용자가 답변할 때 결과가 도착합니다. |
비동기 서브 에이전트는 에이전트의 샌드박스(sandbox)를 공유하므로, 에이전트가 이미 작성한 파일을 가져옵니다. 그 실행은 LangSmith에서 에이전트의 실행 아래에 나타납니다. Slack에서는 승인 요청이 원래 스레드로 게시되며, 거기서 답변하면 서브 에이전트가 재개됩니다.
v0.10 추가 기능
: 이제 모든 스레드는 Slack 스레드와 같이 시작 지점 및 참여자를 기록합니다. 도구는 runtime.thread를 읽을 수 있습니다.
runtime.thread
모든 실행(run)에서, 즉 Studio 재개, 예약된 실행, 비동기 서브 에이전트의 웨이크업 실행 모두가 원래 Slack 스레드에 응답하는 방식입니다.
런타임 문서는 도구가 읽을 수 있는 관리되는 필드를 다룹니다.
실행 중지(Stopping runs): Slack 스레드에는 해당 스레드의 실행을 취소하는 네이티브 '중지(Stop)' 버튼이 제공되며, Studio에서도 Slack 스레드에서 실행을 취소할 수 있습니다.
Slack 채널 핸들러 (실험적) (Slack channel handlers (experimental)):
onEvent는 언급(mentions), 다이렉트 메시지(direct messages), 기타 메시지, 버튼 클릭을 포함하여 각 Slack 이벤트가 무엇을 시작할지 결정합니다. status는 실행이 진행되는 동안 Slack에 표시될 내용을 설정하며, reply: "none"은 에이전트에 대한 응답을 남기지 않습니다. Slack 채널 문서를 참조하세요.
사용자 지정 Slack 앱 가져오기 (Bring your own Slack app):
mda deploy는 새로운 Slack 채널이 어떤 앱을 사용해야 하는지 묻습니다. LangSmith가 생성하고 관리하는 앱 중 하나를 선택하거나, 매니페스트(manifest)에서 새 앱을 만들거나, 이미 가지고 있는 앱을 사용할 수 있습니다. Slack과 같은 채널에서 누군가가 에이전트에게 메시지를 보내면, Managed Deep Agents는 누가 보냈는지 확인합니다.
resolveUser
resolveUser는 해당 발신자를 자체 시스템의 일치하는 사용자에게 매핑하여, 도구가 그 사람의 계정 및 권한을 조회할 수 있도록 합니다. 이를 함수로 작성하거나 우리가 부르는 엔드포인트(endpoint)를 가리키도록 지정하고, 모든 채널에 적용하려면 identitydeclaration에 설정하거나 단일 채널에만 설정할 수 있습니다.
주요 변경 사항 (Breaking changes):
connectors.mcp()와 connectors/ 레이아웃이 제거되었습니다. MCP 서버는 tools/mcp.ts 또는 tools/mcp.py에서 선언해야 합니다. 샌드박스(sandbox)의 scope 옵션도 제거되었습니다. LANGSMITH_* 변수의 경우, 이제 셸 환경 변수가 프로젝트 .env보다 우선합니다.
시작하기 (Getting started)
Managed Deep Agents v0.10이 오늘 공개 베타로 이용 가능합니다. 문서를 참조하거나 새 프로젝트를 생성하세요:
uvx --from managed-deepagents mda init my-agent
cd my-agent
uv run mda deploy
언제나처럼, 여러분이 무엇을 만들지 알려주시는 것이 기대됩니다.
놓치셨다면 (ICYMI): v0.9에서는 에이전트가 생성한 스케줄, 실행별 구성(per-run configuration), Slack 반응 기능이 추가되었습니다. v0.9 게시물 읽기.