1. 개요
AI 및 기술 환경은 그 누구도 따라갈 수 없을 정도로 빠르게 변화하고 있습니다. 매일 새로운 모델, 논문, 제품이 출시됩니다. 오늘의 헤드라인을 가져오고, 간결한 요약을 작성하고, 매일 아침 PDF를 생성하는 요약 에이전트가 있다면 이 문제를 해결할 수 있지만, 이전에는 프레임워크를 선택하고, Python에서 도구를 정의하고, 오케스트레이션 루프를 작성하고, 컨테이너를 패키징하고, Cloud Run에 배포해야 했습니다. 에이전트가 단일 웹 요청을 하기 전의 모든 작업입니다.
Gemini API의 관리형 에이전트는 이 공식을 바꿉니다. 마크다운 구성 파일 2개와 사전 빌드된 렌더러 스크립트를 작성하고 API 호출을 한 번 하면 실제 Ubuntu 샌드박스가 부팅되고, 웹을 탐색하고, 요약을 작성하고, PDF를 생성합니다. 컨테이너가 없습니다. 배포가 없습니다. 조정 코드가 없습니다.
이 Codelab에서는 빈 함수에서 작동하는 일일 요약까지 한 번에 하나의 개념을 사용하여 정확히 그 에이전트를 빌드합니다.
빌드 대상
- 실제 Linux 샌드박스에서 첫 번째 관리형 에이전트 만들기 및 실행
- 자세한 요청 사항으로 에이전트 맞춤설정
- 에이전트의 PDF 출력을 다운로드합니다.
- 웹을 다시 가져오지 않고 대화를 이어가 요약을 다듬습니다.
- 에이전트 구성을 저장하고 향후 실행에서 ID로 호출
필요한 항목
- Python 3.10 이상
- 결제가 사용 설정된 Gemini API 키: aistudio.google.com/api-keys
- API 크레딧 약$1 (각 전체 실행 비용은 $0.30~$1.30)
2. Gemini API의 관리형 에이전트란 무엇인가요?
AI 시스템의 세 가지 수준
코드를 살펴보기 전에 관리 에이전트가 두 가지 대안과 비교해 어떤 위치에 있는지 살펴보세요.
수준 | 어떤 기능인가요? | 인프라를 관리하는 주체 |
표준 LLM | 프롬프트를 입력하면 텍스트로 대답합니다. 손도, 메모리도, 인터넷도 없습니다. | 해당 사항 없음: 스스로 할 수 있는 작업이 없음 |
자체 호스팅 에이전트 | ADK/LangChain/AutoGen + Docker + 도구 + 메모리를 연결합니다. | 모든 것 (또는 Agent Engine과 같은 관리형 플랫폼) |
관리형 에이전트 | 목표를 설정합니다. Google은 보안 샌드박스를 프로비저닝합니다. 에이전트는 코드를 작성하고, 실행하고, 오류를 읽고, 웹을 검색하고, 버그를 자율적으로 수정합니다. | Google: 전체 |
이 Codelab에서는 세 번째 행에 대해 설명합니다. 작업 및 구성 파일을 제공합니다. 나머지는 Google에서 처리합니다.
ADK + Cloud Run으로 빌드할 수 있는 항목
웹을 탐색하고, Python을 실행하고, PDF를 생성하는 뉴스 요약 에이전트를 빌드하려면 ADK + Cloud Run을 사용하여 다음을 모두 수행해야 합니다.
# agent.py: define tools and wire up the agent
from google.adk.agents import LlmAgent
from google.adk.tools import google_search, built_in_code_execution
agent = LlmAgent(
name="digest-agent",
model=MODEL,
instruction=AGENTS_MD, # your editorial voice and rules
tools=[google_search, built_in_code_execution],
)
# app.py: serve the agent over HTTP
from google.adk.runners import FastApiRunner
runner = FastApiRunner(agent=agent)
app = runner.app
# pdf_tool.py: custom tool, install reportlab, render PDF
# scraper.py: custom tool, fetch each news source
# streaming.py: wire agent events to your SSE endpoint
# Dockerfile: package everything
FROM python:3.12
COPY . /app
RUN pip install google-adk reportlab requests
CMD ["uvicorn", "app:app", "--host", "0.0.0.0"]
# Deploy to Cloud Run
gcloud run deploy digest-agent \
--image gcr.io/your-project/digest-agent \
--set-secrets GEMINI_API_KEY=gemini-key:latest \
--memory 2Gi
이는 에이전트가 한 번 실행되기 전입니다. 샌드박스 격리 (따라서 에이전트가 서버를 손상시킬 수 없음), 패키지 설치, 도구 호출 간 상태 관리, 클라이언트에 이벤트를 가져오는 스트리밍 인프라는 여전히 소유하고 있습니다.
관리 에이전트가 대체하는 항목
from google import genai
client = genai.Client()
stream = client.interactions.create(
agent="antigravity-preview-05-2026",
input="",
stream=True,
environment={
"type": "remote",
"sources": [ # your config files, mounted at startup
{
"type": "inline",
"target": ".agents/AGENTS.md",
"content": AGENTS_MD,
},
{
"type": "inline",
"target": ".agents/skills/digest-pdf/SKILL.md",
"content": SKILL_MD,
},
{
"type": "inline",
"target": ".agents/skills/digest-pdf/scripts/generate_pdf.py",
"content": GENERATE_PDF_PY,
},
],
},
)
ADK + Cloud Run에 필요한 사항 | 관리형 에이전트가 처리하는 작업 |
컨테이너 이미지 + Dockerfile + CI/CD | 완전 관리형 Ubuntu 샌드박스 (Python 3.12, Node 22, 4 CPU / 16GB RAM) |
Cloud Run 배포 + 확장 | 상호작용당 프로비저닝, 7일 동안 활동이 없으면 자동 만료 |
샌드박스 격리 | 상호작용별로 격리됨 |
맞춤 PDF 도구 + | 에이전트가 샌드박스 내에 패키지를 설치합니다. |
SSE 스트리밍 인프라 |
|
Python의 도구 정의 | 기본 제공 도구: 웹 탐색, 코드 실행, 파일 시스템 |
도구 호출 간 상태 관리 | 에이전트 추론 루프에 내장됨 |
구성 파일 (AGENTS.md, SKILL.md, 사전 빌드된 스크립트)을 작성하고 API 호출을 한 번 실행합니다. 나머지는 Google에서 처리합니다.
샌드박스 작동 방식
interactions.create() call
│
▼
Google provisions Ubuntu sandbox (Python 3.12, Node 22, 4 CPU / 16 GB RAM)
│
▼
Agent reasoning loop:
plan → fetch URLs → run Python → write files → reason → repeat
│
▼
Events stream back in real time: tool calls, text chunks, completion
│
▼
interaction.completed → environment_id + interaction_id
샌드박스는 7일 동안 비활성 상태로 유지됩니다. environment_id로 다시 시작하여 출력을 개선하거나, 후속 작업을 실행하거나, 저장된 명명된 에이전트로 포크할 수 있습니다.
3. 설정
옵션 A: Cloud Shell (권장)
아래 버튼을 클릭하여 Google Cloud Shell에서 이 Codelab을 엽니다. 모든 종속 항목이 사전 설치되어 있습니다.
옵션 B: 로컬 설정
git clone https://github.com/Saoussen-CH/tech-digest-managed-agent.git
cd tech-digest-managed-agent
필요한 경우 uv을 설치합니다.
curl -LsSf https://astral.sh/uv/install.sh | sh
API 키 구성
cp .env.example .env
cloudshell edit .env
키를 설정합니다.
GEMINI_API_KEY=your-key-here
종속 항목 설치
uv sync
4. 첫 번째 상담사 통화하기
시작 파일 열기
cloudshell edit run_digest.py
run_digest()에는 지금 작성해야 할 TODO가 하나 있고 다음 단계에 필요한 TODO가 세 개 더 있습니다. 위에는 이미 두 개의 도우미가 사전 입력되어 있습니다.
load_source(path): 스크립트와 관련된.agents/에서 파일을 읽습니다. 다음 연습에서 이를 사용하여 언론사 성향, PDF 플레이북, 렌더러를 샌드박스에 마운트합니다.run_stream(stream): 이벤트 스트림을 처리하고(environment_id, interaction_id)를 반환합니다. 이벤트 루프를 직접 작성할 필요가 없습니다.
추가할 항목
TODO 1: pass를 다음으로 바꿉니다 (지금은 TODO 3, 4를 무시하세요. 다음 단계에서 사용됩니다).
from google import genai
client = genai.Client()
stream = client.interactions.create(
agent=BASE_AGENT,
input="Fetch the Hacker News front page and list the top 5 stories.",
stream=True,
environment="remote",
)
environment_id, interaction_id = run_stream(stream)
print(f"\nDone. environment_id={environment_id}")
각 부분이 하는 일
genai.Client()는 환경에서 GEMINI_API_KEY을 읽습니다. 그 외 모든 항목은 이 클라이언트를 통해 전달됩니다.
interactions.create()은 핵심 호출입니다. 다음 네 가지 매개변수가 작동합니다.
agent=BASE_AGENT: Gemini 3.5 Flash로 구동되는 범용 관리형 에이전트인 Antigravity 에이전트 (antigravity-preview-05-2026)를 선택합니다. 기본적으로 사용 설정된 세 가지 내장 도구(code_execution(Bash, Python, Node.js 실행),google_search,url_context(웹페이지 가져오기 및 읽기))가 제공됩니다.environment매개변수를 전달하면 파일 시스템 도구 (read_file,write_file,list_files)가 자동으로 사용 설정됩니다. 한 번의 호출로 Python 3.12, Node.js 22, git, pip, curl이 사전 설치된 완전 관리형 Ubuntu 환경이 프로비저닝됩니다. 빌드할 컨테이너가 없고 실행할 배포가 없습니다.input: 이 실행의 태스크입니다. 에이전트가 Hacker News를 탐색하고 결과에 대해 추론합니다.environment="remote": 이 상호작용을 위해 새로운 클라우드 샌드박스를 프로비저닝합니다.stream=True: 차단하는 대신 이벤트의 반복 가능 객체를 반환합니다. 이 옵션이 없으면 호출이 30~90초 동안 대기하고 모든 출력을interaction.output_text로 한 번에 반환합니다. 스트리밍을 사용하면 에이전트 이유를 확인하고 실시간으로 조치를 취할 수 있습니다. 스트리밍은 여기에서 고급 기능이 아닙니다. 90초 동안의 블랙박스는 에이전트가 작동 중인지 아니면 멈췄는지에 관한 신호를 제공하지 않으므로 스트리밍이 올바른 기본값입니다.
방금 프로비저닝한 항목: 모든 interactions.create() 호출은 전용 샌드박스를 부팅합니다.
구성요소 | 사양 |
운영체제 | 격리된 Ubuntu Linux 환경 |
사전 설치된 런타임 | Python 3.12, Node.js 22, Bash |
컴퓨팅 | CPU 코어 4개, RAM 16GB |
컨텍스트 관리 | 자동 압축은 토큰이 약 135,000개일 때 트리거됩니다. |
네트워킹 | 이그레스 프록시를 통한 아웃바운드 웹 액세스 |
에이전트는 pip 또는 npm로 패키지를 설치하고, 파일을 읽고 쓰고, 아웃바운드 웹 요청을 할 수 있습니다. 머신과 사용자 인증 정보는 절대 건드리지 않습니다.
environment_id은 방금 실행된 샌드박스의 핸들입니다. interaction.completed가 지나도 샌드박스는 종료되지 않고 최대 7일 동안 활성 상태로 유지됩니다. environment_id을 사용하면 다시 돌아갈 수 있습니다. 두 번째 interactions.create() 호출에 전달하면 에이전트가 마치 떠난 적이 없는 것처럼 동일한 파일 시스템에서 동일한 파일과 설치된 패키지를 사용하여 다시 시작됩니다. 다음 단계에서는 이를 사용하여 에이전트를 다시 실행하지 않고 PDF를 다운로드하고, 그 다음 단계에서는 이를 사용하여 대화를 계속합니다.
interaction_id은 방금 완료된 대화 턴의 핸들입니다. 다음 호출에서 previous_interaction_id로 전달하면 에이전트가 이 턴에서 말하고 행동한 내용을 완전히 기억합니다.
확인
uv run python run_digest.py
에이전트가 작동하면 다음과 같은 실시간 출력이 표시됩니다.
[agent started]
[tool] run_code
Here are the top 5 stories currently on the Hacker News front page, retrieved via the official Hacker News API:
1. **Qwen 3.6 27B is the sweet spot for local development** — 471 points
2. **.self: A new top-level domain designed to support self-hosting** — 116 points
...
Done. environment_id=e3de58774073f75a6ef42924c6ce2e88
API는 environment="remote"이 있어도 실제 environment_id를 반환합니다. 샌드박스가 실행되었습니다. 누락된 것은 구성입니다. 음성, 스킬, PDF 생성기가 없습니다. 에이전트가 텍스트로 스토리를 인쇄하고 중지했습니다. 다음 단계에서 이를 추가합니다.
출력의 각 줄은 run_stream()의 이벤트에 매핑됩니다.
| 정의 |
|
| 에이전트가 URL을 가져오는 경우 |
|
| 샌드박스에서 코드를 실행하는 에이전트 |
|
| 에이전트가 웹을 검색함 |
|
| 파일 도구 및 기타 |
|
| 상담사가 텍스트를 작성하고 있음 | stdout으로 직접 스트리밍 |
5. 상담사 맞춤설정
상담사에게는 음성, 스킬, PDF 생성기 등 안내가 없었습니다. 이 단계에서는 .agents/에서 구성 파일을 로드하고 샌드박스에 마운트합니다.
변경할 내용
run_digest.py을 다음과 같이 네 가지로 변경합니다.
TODO 2: load_source() 아래에 세 개의 모듈 수준 상수를 추가합니다 (이러한 상수는 run_digest() 외부에 있으며 파일 상단에 있음).
AGENTS_MD = load_source(".agents/AGENTS.md")
SKILL_MD = load_source(".agents/skills/digest-pdf/SKILL.md")
GENERATE_PDF_PY = load_source(".agents/skills/digest-pdf/scripts/generate_pdf.py")
각 파일을 열어 로드하는 항목을 확인합니다. AGENTS.md는 언론사 성향 및 워크플로 규칙을 설정하고, SKILL.md는 단계별 PDF 플레이북이며, generate_pdf.py는 에이전트가 실행할 사전 빌드된 렌더러입니다.
이제 run_digest() 내에서 두 가지를 더 변경합니다.
TODO 3: environment을 "remote"에서 소스 사전으로 변경하고 input을 ""로 설정합니다.
environment={
"type": "remote",
"sources": [
{
"type": "inline",
"target": ".agents/AGENTS.md",
"content": AGENTS_MD,
},
{
"type": "inline",
"target": ".agents/skills/digest-pdf/SKILL.md",
"content": SKILL_MD,
},
{
"type": "inline",
"target": ".agents/skills/digest-pdf/scripts/generate_pdf.py",
"content": GENERATE_PDF_PY,
},
],
},
TODO 4: print(f"\nDone. environment_id={environment_id}") 바로 뒤에 다음 줄을 추가합니다.
set_key(".env", "ENVIRONMENT_ID", environment_id)
set_key(".env", "INTERACTION_ID", interaction_id)
(set_key은(는) run_digest.py 상단에 이미 가져와져 있습니다.)
이렇게 하면 이번 실행 중에 두 ID가 모두 .env에 기록되므로 다음 단계에서 에이전트를 다시 실행하지 않고도 PDF를 다운로드할 수 있습니다.
각 소스의 기능
각 소스는 에이전트가 실행되기 전에 시작 시 샌드박스 파일 시스템에 마운트된 파일입니다. target 경로는 Antigravity 하네스가 찾을 것으로 예상되는 위치와 일치합니다.
.agents/
├── AGENTS.md ← auto-loaded as global instructions
└── skills/
└── digest-pdf/
├── SKILL.md ← auto-discovered and registered as a skill
└── scripts/
└── generate_pdf.py ← pre-built renderer the agent can run
| 변수 | 하네스가 이를 어떻게 처리하는지 |
|
| 지속적인 안내로 자동 로드됨: 언론사 성향, 워크플로, 실행 규칙 |
|
| 자동으로 검색되어 이름이 지정된 스킬로 등록됩니다. 에이전트가 이름으로 호출합니다. |
|
| 사전 빌드된 PDF 렌더러입니다. 에이전트가 |
확인
uv run python run_digest.py
이제 실행하는 데 1~3분이 걸립니다. 에이전트가 구성 파일을 읽고, 요약을 작성하고, PDF를 저장하는 것을 확인할 수 있습니다.
[agent started]
[tool] read_file (/.agents/skills/digest-pdf/SKILL.md)
[tool] list_files (/.agents/skills/digest-pdf/scripts)
[tool] read_file (/.agents/skills/digest-pdf/scripts/generate_pdf.py)
[tool] run_code
[tool] write_file (/workspace/summaries.json)
[tool] run_code
[tool] delete_file (/tmp/test_scrape.py)
I have successfully generated today's tech news digest and saved the formatted document to /workspace/digest.pdf.
Done. environment_id=4129ffd75574e308748e9425d7ec828f
이제 environment_id이 실제 값입니다. 샌드박스가 구성 파일로 실행되었고 에이전트가 digest.pdf을 만들었습니다. 다음 단계에서 다운로드합니다.
6. PDF 다운로드
에이전트가 샌드박스 내에서 digest.pdf을 /workspace/digest.pdf에 썼습니다. 환경 스냅샷은 Gemini Files API를 통해 tar 보관 파일로 제공됩니다.
필요한 경우 requests을 설치합니다.
uv pip install requests
입력할 내용
download_pdf.py를 엽니다. 할 일(TODO)이 두 개 있습니다.
TODO 1: requests.get() 호출을 작성합니다.
r = requests.get(
f"https://generativelanguage.googleapis.com/v1beta/files/environment-{environment_id}:download",
params={"alt": "media"},
headers={"x-goog-api-key": api_key},
allow_redirects=True,
)
r.raise_for_status()
URL은 샌드박스 스냅샷을 나타냅니다. params={"alt": "media"}는 메타데이터 대신 원시 바이트를 반환합니다. 기존 GEMINI_API_KEY는 Files API도 인증합니다.
TODO 2: tar 보관 파일에서 PDF를 찾아 추출합니다.
member = next(m for m in tar.getmembers() if m.name.endswith("workspace/digest.pdf"))
tar.extract(member, path=tmp, filter="data")
tar 경로 접두사는 실행마다 다르므로 정확한 경로를 하드 코딩하는 대신 접미사로 검색하세요. filter="data"는 안전하지 않은 tar 추출에 관한 Python 3.13 지원 중단 경고를 표시하지 않습니다.
확인
uv run python download_pdf.py
Saved digest.pdf (48,231 bytes)
동일한 디렉터리에서 digest.pdf을 엽니다. 여기에는 에이전트가 실시간 웹페이지에서 생성한 형식화된 요약이 포함됩니다.
7. 대화 이어 나가기
이미 digest.pdf을 보유하고 있습니다. 파일만 필요한 경우 완료된 것입니다. 이 단계는 웹을 다시 가져오지 않고 요약을 변경하도록 에이전트에게 요청하는 것과는 다릅니다.
샌드박스가 계속 활성 상태입니다. 에이전트에는 여전히 /workspace/digest.pdf가 있으며 요약한 모든 스토리를 기억합니다. 두 번째 interactions.create() 호출은 동일한 샌드박스에 후속 메시지를 전송합니다. 여기에서 각 이야기에 '중요한 이유' 메모를 추가해 달라고 요청하면 다시 가져오거나 다시 요약하지 않고 PDF가 업데이트됩니다.
입력할 내용
refine_digest.py를 엽니다. 할 일이 3개 있습니다.
TODO 1과 2: interactions.create() 내에 있는 두 개의 멀티턴 매개변수를 채웁니다.
environment=environment_id,
previous_interaction_id=interaction_id,
environment=environment_id는 파일과 패키지가 포함된 동일한 샌드박스를 재개합니다. previous_interaction_id=interaction_id는 에이전트에게 대화 기록을 제공합니다. 첫 번째 호출에서 다른 변경사항은 없습니다.
TODO 3: 이벤트 루프 후 새 interaction_id을 .env에 다시 유지합니다.
set_key(".env", "INTERACTION_ID", interaction_id)
interactions.create() 호출마다 새 interaction_id가 생성됩니다. 다시 쓰면 다음 실행에서 이 개선사항을 previous_interaction_id로 전달하여 체인이 올바르게 연결됩니다. 샌드박스 ID는 변경되지 않으므로 ENVIRONMENT_ID를 업데이트할 필요가 없습니다.
멀티턴을 작동시키는 두 매개변수
ID | 보존되는 항목 | 비유 |
| 파일, 설치된 패키지, 시스템 상태: Linux 파일 시스템의 모든 항목 | 회의 간에 동일한 사무실 책상 유지 |
| 대화 기록: 이전 턴에서 에이전트가 말하고 수행한 작업 | 지난 회의에서 논의한 내용 기억하기 |
다음과 같이 ID를 개별적으로 전달할 수 있습니다.
environment_id만 해당: 파일과 패키지를 재사용하되 새 대화를 시작합니다. 동일한 워크스페이스의 새 작업에 유용합니다.previous_interaction_id만 해당: 대화 컨텍스트를 계속하지만 새로운 샌드박스에서 진행합니다 (파일이 사라짐).- 둘 다: 전체 연속성(이 단계에서 사용됨)
environment_id가 없는 경우: 빈 샌드박스, PDF 없음 previous_interaction_id이 없는 경우: 컨텍스트가 없으므로 상담사가 특정 섹션을 구체화할 수 없습니다.
확인
uv run python refine_digest.py
스트림은 빨라야 합니다. 에이전트가 아무것도 다시 가져오지 않기 때문입니다. 완료 후:
Refinement done.
Saved digest_v2.pdf (52,418 bytes)
digest_v2.pdf를 열고 digest.pdf와 비교합니다. 이제 각 스토리에 '중요한 이유' 줄이 추가됩니다.
8. 관리 에이전트 구성을 유지합니다.
지금까지 모든 호출은 AGENTS.md, SKILL.md, generate_pdf.py를 인라인으로 전달했습니다. 이렇게 하면 되지만 호출 코드에서 실행할 때마다 전체 파일 콘텐츠를 전달합니다. agents.create()는 Google 측에 저장된 명명된 에이전트에 구성을 베이킹합니다. 다음 호출은 에이전트 ID만 전달합니다.
Inline calls: send sources on every call
Named agent: bake once → invoke by ID, no sources
입력할 내용
save_agent.py를 엽니다. TODO (TODO 1)가 하나 있습니다.
상수는 run_digest.py에서 직접 가져옵니다 (중복 없음).
from run_digest import BASE_AGENT, AGENTS_MD, SKILL_MD, GENERATE_PDF_PY
TODO 1: agents.create() 호출을 작성합니다.
agent = client.agents.create(
id="my-digest",
base_agent=BASE_AGENT,
description="Daily tech digest with editorial voice and PDF generation.",
base_environment={
"type": "remote",
"sources": [
{
"type": "inline",
"target": ".agents/AGENTS.md",
"content": AGENTS_MD,
},
{
"type": "inline",
"target": ".agents/skills/digest-pdf/SKILL.md",
"content": SKILL_MD,
},
{
"type": "inline",
"target": ".agents/skills/digest-pdf/scripts/generate_pdf.py",
"content": GENERATE_PDF_PY,
},
],
},
)
base_environment (environment 아님)은 이전 단계의 인라인 호출과 다른 주요 차이점입니다. 소스가 Google 측에 저장되고 향후 호출마다 자동으로 마운트됩니다. 매번 다이제스트를 실행할 때가 아니라 한 번만 실행합니다.
확인: 에이전트 저장
uv run python save_agent.py
Saved: my-digest
my-digest: Daily tech digest with editorial voice and PDF generation.
저장된 에이전트 호출
invoke_agent.py를 엽니다. 소스 없이 ID로 저장된 에이전트를 호출합니다.
stream = client.interactions.create(
agent="my-digest",
input="",
stream=True,
environment="remote",
)
인라인 호출과 비교해 보세요. agent=BASE_AGENT가 "my-digest"로 대체되고 인라인 소스가 3개인 전체 environment 블록이 environment="remote"로 대체됩니다. 구성 파일은 이미 Google 측에 포함되어 있습니다.
확인: 저장된 에이전트 호출
uv run python invoke_agent.py
인라인 실행과 동일한 라이브 스트림이 표시되지만 호출에는 소스 파일이 포함되지 않습니다. 실행 후 .env의 ENVIRONMENT_ID 및 INTERACTION_ID가 업데이트되므로 이전과 같이 refine_digest.py를 계속 사용할 수 있습니다.
[agent started]
[tool] read_file
[tool] write_file
[tool] run_code
I have successfully created today's tech news digest.
Done. environment_id=9a1c3e02-...
9. 삭제
샌드박스는 7일 동안 활동이 없으면 자동으로 만료됩니다. 중지할 서버가 없습니다. 삭제할 컨테이너가 없습니다.
에이전트 구성을 저장한 경우 삭제합니다.
uv run python delete_agent.py
10. 요약
관리 에이전트를 처음부터 한 번에 하나의 개념으로 빌드했습니다. 각 연습에서 배운 내용은 다음과 같습니다.
연습 | 개념 | 주요 API |
첫 번째 통화하기 | 실제 Linux 샌드박스를 프로비저닝하고 이벤트를 실시간으로 스트리밍합니다. |
|
상담사 맞춤설정 | 구성 파일 마운트, 동일한 실행에서 ID를 |
|
PDF 다운로드 | 에이전트를 다시 실행하지 않고 PDF 다운로드 |
|
대화 계속하기 | 웹을 다시 가져오지 않고 대화 계속하기 |
|
에이전트 구성 유지 | 에이전트 구성을 유지합니다. ID로 호출하며 소스가 필요하지 않습니다. |
|
주요 패턴
- 하나의 호출, 하나의 샌드박스:
interactions.create()에서 모든 인프라를 처리합니다 (배포할 컨테이너 없음, 로컬에 설치할 패키지 없음). - 프로그레시브 스트리밍:
stream=True는 90초의 블랙박스를 도구 호출 및 텍스트 청크의 실시간 피드로 전환합니다. - 인라인 소스: 업로드 또는 배포 단계 없이
AGENTS.md,SKILL.md, 사전 빌드된 스크립트를 샌드박스에 마운트 - 하네스 자동 검색:
.agents/에 배치된 파일이 자동으로 선택됩니다 (SDK 구성 필요 없음). - 2차원 상태:
environment_id는 파일과 패키지를 추적하고previous_interaction_id는 대화 컨텍스트를 추적하며 둘 다 독립적으로 전달할 수 있습니다. - 스냅샷 다운로드: 환경은 Gemini Files API를 통해 액세스할 수 있는 전체 파일 시스템 tar입니다.
- 명명된 에이전트:
agents.create()는 구성을 영구적으로 베이킹합니다. 향후 호출에서는 소스 없이 에이전트 ID와environment="remote"만 전달합니다.
ADK + Cloud Run과 관리형 에이전트: 차이점 한눈에 보기
기능 | ADK + Cloud Run | Gemini API의 관리형 에이전트 |
샌드박스 프로비저닝 |
|
|
도구 정의 | 에이전트에 등록된 Python 함수 | 기본 제공: 웹 탐색, 코드 실행, 파일 시스템 |
패키지 설치 | Dockerfile의 | 에이전트가 샌드박스 내에서 |
스트림 이벤트 | 맞춤 SSE 인프라 |
|
세션 계속하기 | 세션 데이터베이스 + 컨텍스트 삽입 |
|
구성 파일 | 에이전트에 하드 코딩되거나 시작 시 삽입됨 |
|
관리할 인프라 | 컨테이너, Cloud Run, IAM, 보안 비밀 | 없음 |
다음 단계
- Gemini API의 관리형 에이전트 문서를 읽어보세요.