תיעוד 189
תצפיתיות עם OpenTelemetry
ייצוא עקבות, מדדים ואירועים מ-Agent SDK אל שרת הניטור שלכם באמצעות OpenTelemetry.
כשמריצים סוכנים בייצור, צריך לראות מה הם עשו:
- אילו כלים הם קראו
- כמה זמן לקחה כל בקשת מודל
- כמה אסימונים הוצאו
- איפה התרחשו כשלים
Agent SDK יכול לייצא את הנתונים האלה כעקבות, מדדים ואירועי יומן של OpenTelemetry לכל שרת שמקבל את OpenTelemetry Protocol (OTLP), בין אם פלטפורמת ניטור מתארחת או אספן שמופעל אצלכם.
המדריך הזה מסביר איך ה-SDK פולט טלמטריה, איך להגדיר את הייצוא, ואיך לתייג ולסנן את הנתונים אחרי שהם מגיעים לשרת שלכם. כדי לקרוא שימוש באסימונים ועלות ישירות מזרם התשובות של ה-SDK במקום לייצא לשרת, ראו מעקב אחר עלות ושימוש.
[!NOTE]
עבור Claude API או Managed Agents, ראו OpenTelemetry עבור Claude API.
#איך הטלמטריה זורמת מה-SDK
Agent SDK מריץ את Claude Code CLI כתהליך בן ומתקשר איתו דרך צינור מקומי. ל-CLI יש מכשור OpenTelemetry מובנה: הוא רושם spans סביב כל בקשת מודל וכל הרצת כלי, פולט מדדים למוני אסימונים ועלות, ופולט אירועי יומן מובנים להנחיות ולתוצאות כלים. ה-SDK לא מייצר טלמטריה משלו. במקום זאת, הוא מעביר הגדרות לתהליך ה-CLI, וה-CLI מייצא ישירות לאספן שלכם.
ההגדרות מועברות כמשתני סביבה. כברירת מחדל, תהליך הבן יורש את סביבת היישום שלכם, כך שאפשר להגדיר טלמטריה באחד משני מקומות:
- סביבת התהליך: הגדירו את המשתנים במעטפת, בקונטיינר או באורקסטרטור לפני שהיישום מתחיל. כל קריאה ל-
query()קולטת אותם אוטומטית בלי שינוי בקוד. זו הגישה המומלצת לפריסות ייצור. - אפשרויות לכל קריאה: הגדירו את המשתנים ב-
ClaudeAgentOptions.env(Python) או ב-options.env(TypeScript). השתמשו בזה כשסוכנים שונים באותו תהליך צריכים הגדרות טלמטריה שונות. ב-Python,envממוזג מעל הסביבה שעברה בירושה. ב-TypeScript,envמחליף את הסביבה שעברה בירושה לגמרי, אז כללו...process.envבאובייקט שאתם מעבירים.
ה-CLI מייצא שלושה אותות OpenTelemetry עצמאיים. לכל אחד מתג הפעלה משלו ומייצא משלו, כך שאפשר להפעיל רק את אלה שצריך.
| אות | מה הוא מכיל | הפעלה באמצעות |
|---|---|---|
| מדדים | מונים לאסימונים, עלות, סשנים, שורות קוד והחלטות כלים | OTEL_METRICS_EXPORTER |
| אירועי יומן | רשומות מובנות לכל הנחיה, בקשת API, שגיאת API ותוצאת כלי | OTEL_LOGS_EXPORTER |
| עקבות | spans לכל אינטראקציה, בקשת מודל, קריאת כלי ו-hook (בטא) | OTEL_TRACES_EXPORTER וגם CLAUDE_CODE_ENHANCED_TELEMETRY_BETA=1 |
לרשימה המלאה של שמות מדדים, שמות אירועים ומאפיינים, ראו את מדריך Monitoring של Claude Code. Agent SDK פולט את אותם נתונים כי הוא מריץ את אותו CLI. שמות ה-spans מופיעים ב-קריאת עקבות סוכן למטה.
#הפעלת ייצוא טלמטריה
הטלמטריה כבויה עד שמגדירים CLAUDE_CODE_ENABLE_TELEMETRY=1 ובוחרים לפחות מייצא אחד. ההגדרה הנפוצה ביותר שולחת את שלושת האותות ב-OTLP HTTP לאספן.
הדוגמה הבאה מגדירה את המשתנים במילון ומעבירה אותם דרך options.env. הסוכן מריץ משימה אחת, וה-CLI מייצא spans, מדדים ואירועים לאספן ב-collector.example.com בזמן שהלולאה צורכת את זרם התשובות:
Python
import asyncio
from claude_agent_sdk import query, ClaudeAgentOptions
OTEL_ENV = {
"CLAUDE_CODE_ENABLE_TELEMETRY": "1",
# נדרש לעקבות, שנמצאות בבטא. מדדים ואירועי יומן לא צריכים את זה.
"CLAUDE_CODE_ENHANCED_TELEMETRY_BETA": "1",
# בחרו מייצא לכל אות. השתמשו ב-otlp עבור ה-SDK. ראו את ההערה למטה.
"OTEL_TRACES_EXPORTER": "otlp",
"OTEL_METRICS_EXPORTER": "otlp",
"OTEL_LOGS_EXPORTER": "otlp",
# הגדרת תעבורה סטנדרטית של OTLP.
"OTEL_EXPORTER_OTLP_PROTOCOL": "http/protobuf",
"OTEL_EXPORTER_OTLP_ENDPOINT": "http://collector.example.com:4318",
"OTEL_EXPORTER_OTLP_HEADERS": "Authorization=Bearer your-token",
}
async def main():
options = ClaudeAgentOptions(env=OTEL_ENV)
async for message in query(
prompt="List the files in this directory", options=options
):
print(message)
asyncio.run(main())TypeScript
import { query } from "@anthropic-ai/claude-agent-sdk";
const otelEnv = {
CLAUDE_CODE_ENABLE_TELEMETRY: "1",
// נדרש לעקבות, שנמצאות בבטא. מדדים ואירועי יומן לא צריכים את זה.
CLAUDE_CODE_ENHANCED_TELEMETRY_BETA: "1",
// בחרו מייצא לכל אות. השתמשו ב-otlp עבור ה-SDK. ראו את ההערה למטה.
OTEL_TRACES_EXPORTER: "otlp",
OTEL_METRICS_EXPORTER: "otlp",
OTEL_LOGS_EXPORTER: "otlp",
// הגדרת תעבורה סטנדרטית של OTLP.
OTEL_EXPORTER_OTLP_PROTOCOL: "http/protobuf",
OTEL_EXPORTER_OTLP_ENDPOINT: "http://collector.example.com:4318",
OTEL_EXPORTER_OTLP_HEADERS: "Authorization=Bearer your-token",
};
for await (const message of query({
prompt: "List the files in this directory",
// ב-TypeScript, env מחליף את הסביבה שעברה בירושה, אז פרסו
// את process.env קודם כדי לשמור את PATH, ANTHROPIC_API_KEY ומשתנים אחרים.
options: { env: { ...process.env, ...otelEnv } },
})) {
console.log(message);
}מכיוון שתהליך הבן יורש כברירת מחדל את סביבת היישום שלכם, אפשר להגיע לאותה תוצאה על ידי ייצוא המשתנים האלה ב-Dockerfile, במניפסט Kubernetes או בפרופיל מעטפת, והשמטת options.env לגמרי.
כדי לוודא שהייצוא עובד, בדקו ביומני האספן spans, מדדים ואירועי יומן נכנסים אחרי שהמשימה מסתיימת. ה-CLI נכשל בשקט בשגיאות ייצוא כברירת מחדל: אם נקודת הקצה לא נגישה או דוחה את הנתונים, הסוכן עדיין רץ כרגיל וה-CLI משליך את הטלמטריה בלי להציג שגיאה ביישום שלכם. כדי להציג שגיאות מייצא, הגדירו CLAUDE_CODE_OTEL_DIAG_STDERR=1 לצד משתני המייצא וקראו את האבחון דרך ה-callback של stderr ב-SDK (Python) או אפשרות stderr (TypeScript). נדרש Claude Code מגרסה v2.1.179 ואילך.
[!NOTE]
מייצא
consoleכותב טלמטריה לפלט הסטנדרטי, שה-SDK משתמש בו כערוץ ההודעות שלו. אל תגדירוconsoleכערך מייצא כשמריצים דרך ה-SDK. כדי לבדוק טלמטריה מקומית, כוונו אתOTEL_EXPORTER_OTLP_ENDPOINTאל OpenTelemetry Collector מקומי.
#ריקון טלמטריה מקריאות קצרות
ה-CLI אוסף טלמטריה באצוות ומייצא במרווח זמן. ביציאה נקייה של התהליך הוא מנסה לרוקן נתונים ממתינים, אבל הריקון מוגבל בזמן קצוב קצר, כך ש-spans עדיין יכולים להיזרק אם האספן מגיב לאט. אם התהליך שלכם נהרג לפני שה-CLI נכבה, כל מה שנשאר במאגר האצווה אובד. הורדת מרווחי הייצוא מקטינה את שני החלונות.
כברירת מחדל, מדדים מיוצאים כל 60 שניות, ועקבות ויומנים מיוצאים כל 5 שניות. הדוגמה הבאה מקצרת את שלושת המרווחים כדי שהנתונים יגיעו לאספן בזמן שמשימה קצרה עדיין רצה:
Python
OTEL_ENV = {
# ... הגדרת המייצא מהדוגמה הקודמת ...
"OTEL_METRIC_EXPORT_INTERVAL": "1000",
"OTEL_LOGS_EXPORT_INTERVAL": "1000",
"OTEL_TRACES_EXPORT_INTERVAL": "1000",
}TypeScript
const otelEnv = {
// ... הגדרת המייצא מהדוגמה הקודמת ...
OTEL_METRIC_EXPORT_INTERVAL: "1000",
OTEL_LOGS_EXPORT_INTERVAL: "1000",
OTEL_TRACES_EXPORT_INTERVAL: "1000",
};#קריאת עקבות סוכן {#read-agent-traces}
עקבות נותנות את המבט המפורט ביותר על הרצת סוכן. כש-CLAUDE_CODE_ENHANCED_TELEMETRY_BETA=1 מוגדר, כל שלב בלולאת הסוכן הופך ל-span שאפשר לבדוק בשרת המעקב שלכם:
claude_code.interaction: עוטף תור אחד של לולאת הסוכן, מקבלת הנחיה ועד הפקת תשובה.claude_code.llm_request: עוטף כל קריאה ל-Claude API, עם שם מודל, השהיה ומספרי אסימונים כמאפיינים.claude_code.tool: עוטף כל הפעלת כלי, עם spans ילדים להמתנה להרשאה (claude_code.tool.blocked_on_user) ולהרצה עצמה (claude_code.tool.execution).claude_code.hook: עוטף כל הרצת hook. נדרש מעקב בטא מפורט (ENABLE_BETA_TRACING_DETAILED=1ו-BETA_TRACING_ENDPOINT), זוג שגם משנה לאן היומנים והעקבות שלכם הולכים.
ה-spans של llm_request, tool ו-hook הם ילדים של ה-span העוטף claude_code.interaction. כשהסוכן מפעיל תת סוכן דרך כלי Agent, ה-spans של llm_request ו-tool של תת הסוכן מקוננים תחת ה-span claude_code.tool של סוכן האב, כך ששרשרת ההאצלה המלאה מופיעה כעקבה אחת.
ל-spans יש מאפיין session.id כברירת מחדל. כשעושים כמה קריאות query() מול אותו סשן, סננו לפי session.id בשרת שלכם כדי לראות אותם כציר זמן אחד. Claude Code משמיט את המאפיין אם מגדירים את OTEL_METRICS_INCLUDE_SESSION_ID לערך שקרי.
[!NOTE]
המעקב בבטא. שמות spans ומאפיינים עשויים להשתנות בין גרסאות. ראו Traces (beta) במדריך Monitoring למשתני ההגדרה של מייצא העקבות.
#קישור עקבות ליישום שלכם
ה-SDK מפיץ אוטומטית הקשר עקבה של W3C אל תת תהליך ה-CLI. כשקוראים ל-query() בזמן ש-span של OpenTelemetry פעיל ביישום שלכם, ה-SDK מזריק את TRACEPARENT ו-TRACESTATE לסביבת תהליך הבן, וה-CLI קורא אותם כך שה-span claude_code.interaction שלו הופך לילד של ה-span שלכם. הרצת הסוכן מופיעה אז בתוך העקבה של היישום שלכם במקום כשורש מנותק.
רשומות יומן אירועים של OTLP שנפלטות במהלך ההרצה נושאות את אותו הקשר עקבה: כש-TRACEPARENT מוגדר, trace_id ו-span_id של כל רשומה תואמים לעקבה של היישום שלכם, כך שאפשר לחבר אירועים ל-spans בשרת שלכם. לפני v2.1.212, רשומות אירועים שנפלטו מחוץ ל-span פעיל לא נשאו trace_id או span_id.
כשהפצת הקשר העקבה מופעלת, ה-CLI גם מעביר את TRACEPARENT לכל פקודת Bash ו-PowerShell שהוא מריץ. אם פקודה שהופעלה דרך כלי Bash פולטת spans משלה של OpenTelemetry, ה-spans האלה מקוננים תחת ה-span claude_code.tool.execution שעוטף את הפקודה.
ההזרקה האוטומטית מדולגת כשמגדירים TRACEPARENT במפורש ב-options.env, כך שאפשר לקבע הקשר אב מסוים אם צריך. סשנים אינטראקטיביים של CLI מתעלמים מ-TRACEPARENT נכנס לגמרי. רק הרצות של Agent SDK ושל claude -p מכבדות אותו. ראו Traces (beta) במדריך Monitoring לרשימת הייחוס המלאה של spans ומאפיינים.
#תיוג טלמטריה מהסוכן שלכם
כברירת מחדל, ה-CLI מדווח את service.name כ-claude-code. אם מריצים כמה סוכנים, או מריצים את ה-SDK לצד שירותים אחרים שמייצאים לאותו אספן, דרסו את שם השירות והוסיפו מאפייני משאב כדי לסנן לפי סוכן בשרת שלכם.
הדוגמה הבאה משנה את שם השירות ומצרפת מטא נתוני פריסה. הערכים האלה מוחלים כמאפייני משאב של OpenTelemetry על כל span, מדד ואירוע שהסוכן פולט:
Python
options = ClaudeAgentOptions(
env={
# ... הגדרת המייצא מהדוגמה הפעלת ייצוא טלמטריה ...
"OTEL_SERVICE_NAME": "support-triage-agent",
"OTEL_RESOURCE_ATTRIBUTES": "service.version=1.4.0,deployment.environment=production",
},
)TypeScript
const options = {
env: {
...process.env,
// ... הגדרת המייצא מהדוגמה הפעלת ייצוא טלמטריה ...
OTEL_SERVICE_NAME: "support-triage-agent",
OTEL_RESOURCE_ATTRIBUTES:
"service.version=1.4.0,deployment.environment=production",
},
};#שיוך פעולות למשתמשי הקצה שלכם
ה-CLI מצרף מאפייני זהות לכל אירוע לפי האישור שהוא משתמש בו כדי לקרוא ל-Anthropic. כשבונים יישום שמשרת משתמשי קצה רבים מפריסה אחת, המאפיינים האלה מזהים את האישור של השירות שלכם, ולא את משתמש הקצה שבשמו הסוכן פעל.
כדי לייחס קריאות כלים ופעילות MCP למשתמשי הקצה של היישום שלכם, הזריקו זהות של משתמש קצה כמאפייני משאב בכל קריאת query(). קודדו את הערכים בקידוד אחוזים לפני שמשלבים אותם, כי OTEL_RESOURCE_ATTRIBUTES שומר פסיקים, רווחים וסימני שוויון. הדוגמה הבאה מצרפת את המשתמש המבקש ואת הדייר לכל span ואירוע מבקשה אחת. היא מניחה אובייקט request ממסגרת הווב שלכם שנושא את מזהי המשתמש והדייר:
Python
from urllib.parse import quote
options = ClaudeAgentOptions(
env={
# ... הגדרת המייצא מהדוגמה הפעלת ייצוא טלמטריה ...
# request הוא אובייקט הבקשה הנכנסת ממסגרת הווב שלכם.
"OTEL_RESOURCE_ATTRIBUTES": f"enduser.id={quote(request.user_id)},tenant.id={quote(request.tenant_id)}",
},
)TypeScript
const options = {
env: {
...process.env,
// ... הגדרת המייצא מהדוגמה הפעלת ייצוא טלמטריה ...
// request הוא אובייקט הבקשה הנכנסת ממסגרת הווב שלכם.
OTEL_RESOURCE_ATTRIBUTES: `enduser.id=${encodeURIComponent(request.userId)},tenant.id=${encodeURIComponent(request.tenantId)}`,
},
};אחרי שמצרפים זהות של משתמש קצה, האירועים האלה הופכים למסלול ביקורת לכל משתמש שאפשר להעביר לפלטפורמת Security Information and Event Management (SIEM):
tool_decisionו-tool_result: כל קריאת כלי, אם היא הותרה או נדחתה, והתוצאה שלהsafety_event: איזו בדיקה סירבה לקריאת כלי או דרשה עבורה הנחיית הרשאה, כמו כלל הרשאה או המסווג של המצב האוטומטי. לחלק מהקריאות אין אירוע בטיחות. נדרש Claude Code מגרסה v2.1.307 ואילךmcp_server_connection: חיבורי שרת MCP וכשלי חיבורpermission_mode_changed: שינויים במצב הרשאה
האירועים האלה מיוצאים כרשומות יומן עם קידומת claude_code., למשל claude_code.safety_event. ראו Audit security events במדריך Monitoring לרשימה המלאה של אירועים שרלוונטיים לאבטחה ולמאפיינים שכל אחד נושא.
#שליטה בנתונים רגישים בייצוא
הטלמטריה מבנית כברירת מחדל. משכי זמן, שמות מודלים ושמות כלים נרשמים על כל span. מספרי אסימונים נרשמים כשבקשת ה-API הבסיסית מחזירה נתוני שימוש, כך ש-spans של בקשות שנכשלו או בוטלו עשויים להשמיט אותם. התוכן שהסוכן קורא וכותב לא נרשם כברירת מחדל. המשתנים האלה, שמופעלים רק אם בוחרים בהם, מוסיפים תוכן לנתונים המיוצאים:
| משתנה | מוסיף |
|---|---|
OTEL_LOG_USER_PROMPTS=1 | טקסט ההנחיה באירועי claude_code.user_prompt וב-span claude_code.interaction |
OTEL_LOG_TOOL_DETAILS=1 | ארגומנטי קלט של כלים כמו נתיבי קבצים, פקודות מעטפת ותבניות חיפוש באירועי claude_code.tool_result, ושמות אמיתיים של סוכן, מיומנות, תוסף ושרת MCP במדדי עלות ואסימונים. הכלל המובנה שהמסווג של המצב האוטומטי ציין כשחסם קריאה, כ-classifier_category באירועי claude_code.tool_decision ו-claude_code.safety_event |
OTEL_LOG_TOOL_CONTENT=1 | אירוע span בשם tool.output על claude_code.tool עם תוכן קבצים, פלט Bash, ומה שכלי MCP, WebFetch ו-WebSearch מחזירים, חתוך ב-60 KB כברירת מחדל, ניתן להגדרה דרך CLAUDE_CODE_OTEL_CONTENT_MAX_LENGTH, שדורש Claude Code מגרסה v2.1.214 ואילך. תוצאות מכלי MCP, WebFetch ו-WebSearch דורשות Claude Code מגרסה v2.1.283 ואילך. נדרש שמעקב יהיה מופעל. מאפייני span נושאים תוכן כלים תחת שערים משלהם |
OTEL_LOG_RAW_API_BODIES | JSON מלא של בקשה ותשובה של Anthropic Messages API כאירועי יומן claude_code.api_request_body ו-claude_code.api_response_body. הגדירו ל-1 לגופים מוטמעים חתוכים ב-60 KB כברירת מחדל, או ל-file:<dir> לגופים לא חתוכים על הדיסק עם נתיב body_ref באירוע. CLAUDE_CODE_OTEL_CONTENT_MAX_LENGTH מגדיר את מגבלת החיתוך המוטמע, ודורש Claude Code מגרסה v2.1.214 ואילך. הגופים כוללים את כל היסטוריית השיחה ותוכן חשיבה מורחבת מושחר בהם. הפעלה של זה משמעה הסכמה לכל מה ששלושת המשתנים שלמעלה היו חושפים |
השאירו אותם לא מוגדרים אלא אם צינור הניטור שלכם מאושר לאחסן את הנתונים שהסוכן מטפל בהם. ראו אבטחה ופרטיות במדריך Monitoring לרשימה המלאה של מאפיינים ולהתנהגות ההשחרה.
#תיעוד קשור
המדריכים האלה מכסים נושאים סמוכים לניטור ולפריסת סוכנים:
- מעקב אחר עלות ושימוש: קריאת נתוני אסימונים ועלות מזרם ההודעות בלי backend חיצוני.
- אירוח ה-Agent SDK: פריסת סוכנים בקונטיינרים שבהם אפשר להגדיר משתני OpenTelemetry ברמת הסביבה.
- ניטור: המדריך המלא לכל משתנה סביבה, מדד ואירוע שה-CLI פולט.