Ενσωματώστε την παρατηρησιμότητα των παραγόντων με άμεση χρήση του OTel

Αυτός ο οδηγός σάς καθοδηγεί βήμα προς βήμα στην αποστολή τηλεμετρίας παραγόντων απευθείας στο Agent 365 μέσω OpenTelemetry (OTLP/HTTP+JSON). Πριν ξεκινήσετε, διαβάστε έννοιες παρατηρησιμότητας του Agent 365 για να κατανοήσετε το μοντέλο, τις ροές ελέγχου ταυτότητας και τις επιφάνειες στις οποίες καταλήγουν τα δεδομένα σας.

Σημαντικό

Η απευθείας προσέγγιση OTel είναι η εξαίρεση, όχι η προεπιλογή. Χρησιμοποιήστε το μόνο εάν έχετε ήδη διοχέτευση OpenTelemetry, το πλαίσιό σας δεν μπορεί να χρησιμοποιήσει το Agent 365 SDK ή ο παράγοντας σας είναι γραμμένος σε γλώσσα που το SDK δεν υποστηρίζει ακόμα (όπως Java). Για όλους τους άλλους, η προτεινόμενη διαδρομή είναι το Microsoft OpenTelemetry Distro, το οποίο παρέχει ένα ενοποιημένο SDK παρατηρησιμότητας σε Agent 365, Microsoft Foundry, Azure Monitor και άλλα. Το προηγούμενο Observability SDK συνεχίζει να λειτουργεί χωρίς σημαντικές αλλαγές, αλλά δεν συνιστάται πλέον για νέες ενσωματώσεις· θα ακολουθήσουν οδηγίες μετεγκατάστασης για τους υπάρχοντες χρήστες του SDK.

Προαπαιτούμενα στοιχεία

Βεβαιωθείτε ότι έχουν γίνει οι ακόλουθες ρυθμίσεις πριν ξεκινήσει οποιαδήποτε ροή τηλεμετρίας.

Ποιος Τι
Διαχειριστής μισθωτή Εγγραφείτε στο Agent 365 και παραχωρήστε συγκατάθεση για την εφαρμογή παράγοντα σας. Δείτε Εγγραφή στο Agent 365. Χωρίς μισθωτή με άδεια χρήσης, η εισαγωγή απορρίπτεται σιωπηλά - η αίτηση επιστρέφει 200 OK με partialSuccess: null αλλά τα δεδομένα δεν εμφανίζονται ποτέ στη συνέχεια.
Διαχειριστής μισθωτή Αναθέστε μια άδεια χρήσης Microsoft 365 E7 ή Microsoft Agent 365 σε τουλάχιστον έναν χρήστη στον μισθωτή. Η παρουσία του SKU δεν είναι αρκετή. Η ανάθεση σε έναν χρήστη ξεκινά τη διαδικασία παρασκηνίου του Defender που επιτρέπει την εισαγωγή. Χωρίς ανατεθειμένη άδεια, τα αιτήματα επιστρέφουν 200 OK με partialSuccess: null και τα δεδομένα απορρίπτονται σιωπηλά.
Διαχειριστής μισθωτή Παραχωρήστε τη συγκατάθεση του μισθωτή. Δείτε Παραχώρηση πρόσβασης σε παράγοντες σε πόρους του Microsoft 365. Χωρίς αυτό, τα διακριτικά εκδίδονται χωρίς τον ρόλο/πεδίο εφαρμογής και τα αιτήματα επιστρέφουν 403.
Η ομάδα προγραμματιστών σας Καταχωρήστε την εφαρμογή σας (τυπική εφαρμογή Microsoft Entra ή blueprint). Δείτε Ξεκινήστε με την ανάπτυξη του Agent 365.
Η ομάδα προγραμματιστών σας Προσθέστε Agent365.Observability.OtelWrite στην ενότητα Δικαιώματα API (ρόλος εφαρμογής για S2S, πεδίο για εκπροσώπηση). Για τα blueprints, δείτε Διαμόρφωση μεταβιβαζόμενων δικαιωμάτων. Συντονιστείτε με την ομάδα προσθήκης λογαριασμών του Agent 365 για να ενεργοποιήσετε την άδεια.

Συνταγές ελέγχου ταυτότητας

Και οι τέσσερις συνταγές χρησιμοποιούν το τυπικό τελικό σημείο διακριτικού Microsoft Entra:

Πεδίο Τιμή
Τελικό σημείο διακριτικού https://login.microsoftonline.com/{your-tenant-id}/oauth2/v2.0/token
Πόρος (aud στο επιστρεφόμενο διακριτικό) 9b975845-388f-4429-889e-eab1ef63949c (δέχεται επίσης το api://9b975845-388f-4429-889e-eab1ef63949c)
S2S πεδίου 9b975845-388f-4429-889e-eab1ef63949c/.default
OBO πεδίου 9b975845-388f-4429-889e-eab1ef63949c/Agent365.Observability.OtelWrite

Οι παρακάτω συνταγές δείχνουν ακατέργαστο HTTP για σαφήνεια. Στην παραγωγή, προτιμήστε το Microsoft.Identity.Web ή άλλη βιβλιοθήκη MSAL, η οποία διαχειρίζεται την ανανέωση διακριτικών και την προσωρινή αποθήκευση.

Ποια συνταγή χρειάζομαι;

Το μοντέλο της εφαρμογής μου Η ροή μου OAuth Μετάβαση σε
Τυπική καταχώρηση εφαρμογής Microsoft Entra S2S (διαπιστευτήρια πελάτη) S2S, Τυπική εφαρμογή Microsoft Entra
Τυπική καταχώρηση εφαρμογής Microsoft Entra OBO (πληρεξούσιος) OBO, Τυπική εφαρμογή Microsoft Entra
Ταυτότητα παράγοντα που προέρχεται από σχεδιάγραμμα S2S (διαπιστευτήρια πελάτη) S2S, Ταυτότητα παράγοντα που προέρχεται από σχεδιάγραμμα
Ταυτότητα παράγοντα που προέρχεται από σχεδιάγραμμα OBO / Συνεργάτης AI OBO, Ταυτότητα παράγοντα που προέρχεται από σχεδιάγραμμα

S2S, Τυπική εφαρμογή Microsoft Entra

Εκτελέστε ένα POST στο τελικό σημείο διακριτικού του μισθωτή με grant_type=client_credentials. Πραγματοποιήστε έλεγχο ταυτότητας της εφαρμογής χρησιμοποιώντας μυστικό πελάτη, πιστοποιητικό (υπογεγραμμένη διεκδίκηση JWT), διαχειριζόμενη ταυτότητα ή ομόσπονδα διαπιστευτήρια.

POST https://login.microsoftonline.com/{your-tenant-id}/oauth2/v2.0/token
Content-Type: application/x-www-form-urlencoded

client_id={your-app-id}
&scope=9b975845-388f-4429-889e-eab1ef63949c%2F.default
&client_secret={secret}
&grant_type=client_credentials

Το επιστρεφόμενο διακριτικό έχει appid/azp = {your-app-id}, roles που περιέχει Agent365.Observability.OtelWrite, και aud = 9b975845-.... Χρησιμοποιήστε το στη /observabilityService/.../traces διαδρομή.

Για αυθεντικοποίηση με πιστοποιητικό, αντικαταστήστε client_secret={secret} με client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer&client_assertion={signed-jwt}.

S2S, Ταυτότητα παράγοντα που προέρχεται από σχεδιάγραμμα

Οι ταυτότητες των παραγόντων δεν έχουν δικά τους διαπιστευτήρια. Το σχέδιο ταυτότητας παράγοντα κρατά τα διαπιστευτήρια (διαχειριζόμενη ταυτότητα FIC, πιστοποιητικό ή μυστικό πελάτη) και εκδίδει διακριτικά για λογαριασμό των ταυτοτήτων θυγατρικών παραγόντων μέσω μιας ανταλλαγής δύο βημάτων. Για περισσότερες πληροφορίες, δείτε τη ροή OAuth της αυτόνομης εφαρμογής.

  1. Το blueprint πιστοποιεί και λαμβάνει ένα ομοσπονδιακό διακριτικό ανταλλαγής ταυτότητας T1:

    • {blueprint-credential} είναι το διακριτικό MSI του σχεδιαγράμματος, το JWT υπογεγραμμένο από πιστοποιητικό ή η μυστική δήλωση ανταλλαγής διακριτικού — ανά διαμόρφωση σχεδιαγράμματος.
    POST https://login.microsoftonline.com/{your-tenant-id}/oauth2/v2.0/token
    Content-Type: application/x-www-form-urlencoded
    
    client_id={blueprint-app-id}
    &scope=api%3A%2F%2FAzureADTokenExchange%2F.default
    &fmi_path={agent-identity-app-id}
    &client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer
    &client_assertion={blueprint-credential}
    &grant_type=client_credentials
    
  2. Η ταυτότητα του παράγοντα ανταλλάσσει T1 με το διακριτικό πόρου παρατηρησιμότητας του Agent 365:

    POST https://login.microsoftonline.com/{your-tenant-id}/oauth2/v2.0/token
    Content-Type: application/x-www-form-urlencoded
    
    client_id={agent-identity-app-id}
    &scope=9b975845-388f-4429-889e-eab1ef63949c%2F.default
    &client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer
    &client_assertion={T1}
    &grant_type=client_credentials
    
    • Το επιστρεφόμενο διακριτικό έχει appid/azp = {agent-identity-app-id}, roles που περιέχει Agent365.Observability.OtelWrite, και aud = 9b975845-....
    • Χρησιμοποιήστε αυτό το διακριτικό στη διαδρομή /observabilityService/.../traces.
    • Το URL {agentId} είναι το appId της ταυτότητας παράγοντα, όχι το blueprint appId.

OBO, Τυπική εφαρμογή Microsoft Entra

Λάβετε το εισερχόμενο διακριτικό Tc του χρήστη από τον ανάντη καλούντα (Φορέας ή PFAT) και στη συνέχεια ανταλλάξτε το:

POST https://login.microsoftonline.com/{your-tenant-id}/oauth2/v2.0/token
Content-Type: application/x-www-form-urlencoded

client_id={your-app-id}
&scope=9b975845-388f-4429-889e-eab1ef63949c%2FAgent365.Observability.OtelWrite
&client_secret={secret}
&grant_type=urn:ietf:params:oauth:grant-type:jwt-bearer
&assertion={Tc}
&requested_token_use=on_behalf_of

Για έλεγχο ταυτότητας μέσω πιστοποιητικού, αντικαταστήστε το client_secret={secret} με το ίδιο ζεύγος client_assertion_type + client_assertion όπως στο S2S.

Το επιστρεφόμενο διακριτικό έχει appid/azp = {your-app-id}, scp που περιέχει Agent365.Observability.OtelWrite, και aud = 9b975845-.... Χρησιμοποιήστε το στη /observability/.../traces διαδρομή. Ένα διακριτικό ανανέωσης επιστρέφεται ταυτόχρονα· αποθηκεύστε το και επαναχρησιμοποιήστε το αντί να εκτελείτε ξανά την ανταλλαγή σε κάθε κλήση.

OBO, ταυτότητα παράγοντα που προέρχεται από το Blueprint (συμπεριλαμβανομένου του συνεργάτη AI)

Υπάρχουν τρία βασικά βήματα στη ροή On-Behalf-Of. Για περισσότερες πληροφορίες, δείτε Ροές OAuth του παράγοντα: ροή On-Behalf-Of.

  1. Λάβετε το διακριτικό χρήστη Tc. Για έναν συνεργάτη AI, αυτό το διακριτικό αντιπροσωπεύει τον λογαριασμό χρήστη του ίδιου του παράγοντα· διαφορετικά, αντιπροσωπεύει τον ανθρώπινο χρήστη.

  2. Το blueprint αυθεντικοποιείται και λαμβάνει T1, όπως στη ροή ταυτότητας παράγοντα που προέρχεται από το S2S blueprint.

  3. Η ταυτότητα του παράγοντα ανταλλάσσει T1 και Tc με ένα διακριτικό πόρου με ανάθεση:

    POST https://login.microsoftonline.com/{your-tenant-id}/oauth2/v2.0/token
    Content-Type: application/x-www-form-urlencoded
    
    client_id={agent-identity-app-id}
    &scope=9b975845-388f-4429-889e-eab1ef63949c%2FAgent365.Observability.OtelWrite
    &client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer
    &client_assertion={T1}
    &grant_type=urn:ietf:params:oauth:grant-type:jwt-bearer
    &assertion={Tc}
    &requested_token_use=on_behalf_of
    

Το επιστρεφόμενο διακριτικό έχει appid/azp = {agent-identity-app-id}, scp που περιέχει Agent365.Observability.OtelWrite, και αντιπροσωπεύει τον χρήστη του παράγοντα. Χρησιμοποιήστε το στη /observability/.../traces διαδρομή. Το URL {agentId} είναι το appId της ταυτότητας παράγοντα, όχι το blueprint appId. Ένα διακριτικό ανανέωσης επιστρέφεται μαζί· αποθηκεύστε το και επαναχρησιμοποιήστε το.

Απαιτούμενες αξιώσεις για το επιστρεφόμενο διακριτικό

Διαδρομή S2S (/observabilityService/...) - διακριτικό μόνο για εφαρμογή:

Ισχυρισμός Απαιτούμενη τιμή
aud 9b975845-388f-4429-889e-eab1ef63949capi://9b975845-...)
roles Πρέπει να περιέχει Agent365.Observability.OtelWrite
appid (v1) ή azp (v2) Πρέπει να είναι ίσο με το URL {agentId}
scp Πρέπει να απουσιάζει

Διαδρομή με ανάθεση (/observability/...) - διακριτικό με ανάθεση χρήστη (Φορέας ή PFAT):

Ισχυρισμός Απαιτούμενη τιμή
aud 9b975845-388f-4429-889e-eab1ef63949capi://9b975845-...)
scp Πρέπει να περιέχει Agent365.Observability.OtelWrite
appid / azp Πρέπει να είναι ίσο με το URL {agentId}

Η διαδρομή ανάθεσης δέχεται τόσο τα Bearer όσο και τα MSAuth1.0 PFAT διακριτικά. Οι άμεσοι καλούντες θα πρέπει να χρησιμοποιούν Bearer. Εάν δεν ξέρετε ποιο έχετε, χρησιμοποιήστε Bearer.

Τελικά σημεία

Δύο διαδρομές· επιλέξτε με βάση το πώς η υπηρεσία σας πραγματοποιεί έλεγχο ταυτότητας, όχι με βάση το τι κάνει ο χρήστης:

POST https://agent365.svc.cloud.microsoft/observabilityService/tenants/{tenantId}/otlp/agents/{agentId}/traces?api-version=1   # S2S
POST https://agent365.svc.cloud.microsoft/observability/tenants/{tenantId}/otlp/agents/{agentId}/traces?api-version=1          # OBO

Κεφαλίδες:

Authorization: Bearer <token>      # or MSAuth1.0 ... for delegated PFAT
Content-Type: application/json

Παράμετροι διεύθυνσης URL

  • {tenantId} - το GUID του μισθωτή πελάτη. Ο διακομιστής το θεωρεί ως αυθεντική πηγή· αν τα spans σας ορίσουν microsoft.tenant.id και υπάρχει διαφωνία, το αίτημα απορρίπτεται.
  • {agentId} - της καλούσας εφαρμογής appId (επίσης το OAuth client_id). Για ταυτότητες που προέρχονται από blueprint, αυτό είναι το appId της ταυτότητας παράγοντα, όχι το appId του blueprint. Πρέπει να ισούται με τον ισχυρισμό appid / azp του διακριτικού σας.
  • api-version=1 - απαιτείται.

Κωδικοποίηση σώματος αιτήματος

Το σώμα έχει το τυπικό σχήμα OTLP/HTTP+JSON: ένα ExportTraceServiceRequest με resourceSpansscopeSpansspans. Λάβετε υπόψη τις ακόλουθες λεπτομέρειες:

  • traceId (16 byte) και spanId (8 byte) αποστέλλονται ως πεζές δεκαεξαδικές συμβολοσειρές.
  • startTimeUnixNano / endTimeUnixNano είναι συμβολοσειρές που αντιστοιχούν σε νανοδευτερόλεπτα της εποχής Unix.
  • το kind είναι η ακέραια τιμή απαρίθμησης OTLP (για παράδειγμα 1 για INTERNAL). Το status.code είναι η ακέραια τιμή απαρίθμησης (για παράδειγμα 1 για OK, 2 για ERROR).
  • Όλες οι τιμές χαρακτηριστικών αποστέλλονται ως stringValue.

Σχήμα απόκρισης

Μια επιτυχημένη κλήση επιστρέφει 200 OK:

{ "partialSuccess": null }

Εάν κάποια spans απορρίφθηκαν από το φίλτρο ανά span:

{
  "partialSuccess": {
    "rejectedSpans": 2,
    "errorMessage": "Dropped 2 non-A365 span(s) ..."
  }
}

Τα ονόματα των πεδίων είναι σε camelCase στη μετάδοση. Πάντα να ελέγχετε partialSuccess: ένα 200 με όλα τα spans απορριφθέντα είναι ένα πραγματικό αποτέλεσμα που πρέπει να αναφέρετε. Τα όρια και οι περιπτώσεις πτώσης παραθέτουν τις σιωπηλές περιπτώσεις πτώσης όπου επιστρέφεται 200 με partialSuccess: null αν και δεν εμφανίζονται δεδομένα κατάντη.

Το μικρότερο δυνατό αίτημα

Η απλούστερη ολοκληρωμένη δοκιμή στέλνει ένα μόνο invoke_agent span. Αυτό το span είναι το μικρότερο σώμα που καταχωρείται στο Microsoft Defender.

Βήμα 1. Αποκτήστε ένα διακριτικό φορέα. Για S2S, χρησιμοποιήστε διαπιστευτήρια πελάτη με πεδίο εφαρμογής 9b975845-388f-4429-889e-eab1ef63949c/.default (βλ. Οδηγίες ελέγχου ταυτότητας για την πλήρη διαδικασία).

Βήμα 2. Κάντε POST ενός μόνο span:

TOKEN="$(./get-token.sh)"
TENANT_ID="<customer-tenant-guid>"
AGENT_ID="<your-agent-app-id>"

curl -i -X POST \
  "https://agent365.svc.cloud.microsoft/observabilityService/tenants/${TENANT_ID}/otlp/agents/${AGENT_ID}/traces?api-version=1" \
  -H "Authorization: Bearer ${TOKEN}" \
  -H "Content-Type: application/json" \
  --data @- <<EOF
{
  "resourceSpans": [{
    "scopeSpans": [{
      "scope": { "name": "my-instrumentation", "version": "1.0.0" },
      "spans": [{
        "traceId": "0102030405060708090a0b0c0d0e0f10",
        "spanId":  "1111111111111111",
        "parentSpanId": "",
        "name": "invoke_agent",
        "kind": 1,
        "startTimeUnixNano": "1736175600000000000",
        "endTimeUnixNano":   "1736175601500000000",
        "status": { "code": 1 },
        "attributes": [
          { "key": "gen_ai.operation.name", "value": { "stringValue": "invoke_agent" } },
          { "key": "gen_ai.agent.id",       "value": { "stringValue": "${AGENT_ID}" } },
          { "key": "gen_ai.agent.name",     "value": { "stringValue": "MyAgent" } },
          { "key": "microsoft.a365.agent.blueprint.id", "value": { "stringValue": "${AGENT_ID}" } },
          { "key": "gen_ai.conversation.id","value": { "stringValue": "conv-001" } },
          { "key": "microsoft.channel.name","value": { "stringValue": "web" } },
          { "key": "user.id",               "value": { "stringValue": "<entra-user-objectid>" } },
          { "key": "client.address",        "value": { "stringValue": "10.1.2.80" } },
          { "key": "server.address",        "value": { "stringValue": "myagent.example.com" } },
          { "key": "server.port",           "value": { "stringValue": "443" } },
          { "key": "gen_ai.input.messages", "value": { "stringValue": "[{\"role\":\"user\",\"content\":\"hi\"}]" } },
          { "key": "gen_ai.output.messages","value": { "stringValue": "[{\"role\":\"assistant\",\"content\":\"hello\"}]" } }
        ]
      }]
    }]
  }]
}
EOF

Βήμα 3. Αναμένετε 200 OK με αυτό το σώμα:

{ "partialSuccess": null }

Βήμα 4. Επιβεβαιώστε ότι τα δεδομένα έφτασαν πράγματι. Ένα 200 OK δεν αποτελεί απόδειξη εισαγωγής· η ενότητα Επαλήθευση εισαγωγής περιγράφει τη ροή επαλήθευσης. Για να κάνετε POST ένα αποθηκευμένο αρχείο σώματος, αντικαταστήστε το --data @- <<EOF ... EOF με το --data @./otlp-request.json.

Παράδειγμα εκτέλεσης παράγοντα

Ένας χρήστης στο Microsoft Teams ρωτά "Τι καιρό κάνει στο Σιάτλ;". Ο παράγοντάς σας καλεί μια συνάρτηση GetWeather, ζητά από ένα LLM να μορφοποιήσει την απάντηση και απαντά. Αυτή η ενιαία διαδρομή είναι τέσσερα spans:

graph TD
    A["<b>invoke_agent</b> · spanId=A · parentSpanId=∅<br/><i>root - the run itself</i>"]
    B["<b>chat</b> · spanId=B · parentSpanId=A<br/><i>LLM picks the tool / formats reply</i>"]
    C["<b>execute_tool</b> · spanId=C · parentSpanId=A<br/><i>the GetWeather call</i>"]
    D["<b>output_messages</b> · spanId=D · parentSpanId=A<br/><i>final reply emitted to the user</i>"]
    A --> B
    A --> C
    A --> D

Χαρακτηριστικά σε όλη την εκτέλεση που έχουν οριστεί σε κάθε span:

Χαρακτηριστικό Παράδειγμα τιμής
traceId 0102030405060708090a0b0c0d0e0f10
gen_ai.conversation.id 19:abc@thread.tacv2
microsoft.session.id session-1234
microsoft.channel.name msteams
gen_ai.agent.id <AGENT_APP_ID>
gen_ai.agent.name WeatherBot
microsoft.a365.agent.blueprint.id <BLUEPRINT_APP_ID>
user.id <entra-user-objectid>
client.address 10.1.2.80
server.address weatherbot.example.com
server.port 443

Σημαντικό

Αυτά τα χαρακτηριστικά σε όλη την εκτέλεση δεν μεταδίδονται αυτόματα. Πρέπει να ρυθμίσετε gen_ai.conversation.id, microsoft.channel.name, και microsoft.session.id σε κάθε span μόνοι σας.

Span A: invoke_agent (ρίζα)

{
  "traceId": "0102030405060708090a0b0c0d0e0f10",
  "spanId": "1111111111111111",
  "parentSpanId": "",
  "name": "invoke_agent",
  "kind": 1,
  "startTimeUnixNano": "1736175600000000000",
  "endTimeUnixNano":   "1736175601500000000",
  "status": { "code": 1 },
  "attributes": [
    { "key": "gen_ai.operation.name",   "value": { "stringValue": "invoke_agent" } },
    { "key": "gen_ai.execution.type",   "value": { "stringValue": "HumanToAgent" } },
    { "key": "gen_ai.input.messages",   "value": { "stringValue": "[{\"role\":\"user\",\"content\":\"What's the weather in Seattle?\"}]" } },
    { "key": "gen_ai.output.messages",  "value": { "stringValue": "[{\"role\":\"assistant\",\"content\":\"It's 65F and partly cloudy in Seattle.\"}]" } },
    { "key": "user.email",              "value": { "stringValue": "alice@contoso.com" } }
    /* plus all the run-wide attributes listed above */
  ]
}

Span B: chat (κλήση LLM)

{
  "traceId": "0102030405060708090a0b0c0d0e0f10",
  "spanId": "2222222222222222",
  "parentSpanId": "1111111111111111",
  "name": "chat",
  "kind": 1,
  "startTimeUnixNano": "1736175600200000000",
  "endTimeUnixNano":   "1736175600900000000",
  "status": { "code": 1 },
  "attributes": [
    { "key": "gen_ai.operation.name",      "value": { "stringValue": "chat" } },
    { "key": "gen_ai.request.model",       "value": { "stringValue": "gpt-4o" } },
    { "key": "gen_ai.provider.name",       "value": { "stringValue": "openai" } },
    { "key": "gen_ai.usage.input_tokens",  "value": { "stringValue": "42" } },
    { "key": "gen_ai.usage.output_tokens", "value": { "stringValue": "23" } }
    /* plus all the run-wide attributes */
  ]
}

Span C: execute_tool

{
  "traceId": "0102030405060708090a0b0c0d0e0f10",
  "spanId": "3333333333333333",
  "parentSpanId": "1111111111111111",
  "name": "execute_tool",
  "kind": 1,
  "startTimeUnixNano": "1736175600950000000",
  "endTimeUnixNano":   "1736175601200000000",
  "status": { "code": 1 },
  "attributes": [
    { "key": "gen_ai.operation.name",      "value": { "stringValue": "execute_tool" } },
    { "key": "gen_ai.tool.name",           "value": { "stringValue": "GetWeather" } },
    { "key": "gen_ai.tool.type",           "value": { "stringValue": "function" } },
    { "key": "gen_ai.tool.call.id",        "value": { "stringValue": "call-001" } },
    { "key": "gen_ai.tool.call.arguments", "value": { "stringValue": "{\"location\":\"Seattle\"}" } },
    { "key": "gen_ai.tool.call.result",    "value": { "stringValue": "{\"tempF\":65,\"condition\":\"partly cloudy\"}" } }
    /* plus all the run-wide attributes */
  ]
}

Span D: output_messages

{
  "traceId": "0102030405060708090a0b0c0d0e0f10",
  "spanId": "4444444444444444",
  "parentSpanId": "1111111111111111",
  "name": "output_messages",
  "kind": 1,
  "startTimeUnixNano": "1736175601400000000",
  "endTimeUnixNano":   "1736175601500000000",
  "status": { "code": 1 },
  "attributes": [
    { "key": "gen_ai.operation.name",  "value": { "stringValue": "output_messages" } },
    { "key": "gen_ai.output.messages", "value": { "stringValue": "[{\"role\":\"assistant\",\"content\":\"It's 65F and partly cloudy in Seattle.\"}]" } }
    /* plus all the run-wide attributes */
  ]
}

Αποστολή τηλεμετρίας

Χρησιμοποιώντας OTel SDK

Οι περισσότεροι συνεργάτες στέλνουν ίχνη μέσω OTel SDK αντί για χειροποίητο HTTP. Το SDK χειρίζεται την ομαδοποίηση, την επανάληψη και την κωδικοποίηση OTLP/HTTP+JSON για εσάς. Ρυθμίστε το endpoint εξαγωγής και εισάγετε την κεφαλίδα Authorization.

Το τελικό σημείο εξαγωγής είναι η ίδια η διεύθυνση URL δρομολόγησης, συμπεριλαμβανομένης της συμβολοσειράς ερωτήματος:

https://agent365.svc.cloud.microsoft/observabilityService/tenants/{tenantId}/otlp/agents/{agentId}/traces?api-version=1

(Χρησιμοποιήστε το /observability/... αντί του /observabilityService/... για την ανατεθειμένη διαδρομή.)

Python

from opentelemetry.exporter.otlp.proto.http.trace_exporter import OTLPSpanExporter

exporter = OTLPSpanExporter(
    endpoint="https://agent365.svc.cloud.microsoft/observabilityService/tenants/{tenantId}/otlp/agents/{agentId}/traces?api-version=1",
    headers={"Authorization": f"Bearer {token}"},
)

Πακέτο: opentelemetry-exporter-otlp-proto-http.

Node.js / TypeScript

import { OTLPTraceExporter } from "@opentelemetry/exporter-trace-otlp-http";

const exporter = new OTLPTraceExporter({
  url: "https://agent365.svc.cloud.microsoft/observabilityService/tenants/{tenantId}/otlp/agents/{agentId}/traces?api-version=1",
  headers: { Authorization: `Bearer ${token}` },
});

Πακέτο: @opentelemetry/exporter-trace-otlp-http.

.NET

using OpenTelemetry.Exporter;

services.AddOpenTelemetry().WithTracing(b => b
    .AddOtlpExporter(o =>
    {
        o.Endpoint = new Uri("https://agent365.svc.cloud.microsoft/observabilityService/tenants/{tenantId}/otlp/agents/{agentId}/traces?api-version=1");
        o.Headers = $"Authorization=Bearer {token}";
        o.Protocol = OtlpExportProtocol.HttpJson;
    }));

Πακέτο: OpenTelemetry.Exporter.OpenTelemetryProtocol.

Μη αυτόματο HTTP

Αν δεν μπορείτε ή δεν θέλετε να χρησιμοποιήσετε ένα OTel SDK, δημιουργήστε μόνοι σας το αίτημα OTLP/HTTP+JSON και στείλτε το με POST. Η δομή του σώματος ορίζεται από την προδιαγραφή OTLP/HTTP+JSON του OpenTelemetry:

{
  "resourceSpans": [{
    "resource":  { "attributes": [ ... ] },          // optional
    "scopeSpans": [{
      "scope":  { "name": "<your-instrumentation>", "version": "1.0.0" },
      "spans":  [ <span>, <span>, ... ]
    }]
  }]
}

Κάθε <span> είναι ένα αντικείμενο με τα απαιτούμενα πεδία traceId, spanId, name, kind, startTimeUnixNano, endTimeUnixNano, attributes και (για μη κύρια spans) parentSpanId. Δείτε τις ενότητες Τελικά σημεία και Κωδικοποίηση σώματος αιτήματος για τους κανόνες κωδικοποίησης (χρόνοι ως συμβολοσειρές, δεκαεξαδικές τιμές traceId / spanId, ακέραιες τιμές kind / status.code, όλες οι τιμές ιδιοτήτων ως stringValue).

Το σύνολο των χαρακτηριστικών που πρέπει να οριστούν σε κάθε span καθορίζεται στα Συμβόλαια μηνυμάτων. Δείτε την Αναφορά χαρακτηριστικών για τον πλήρη κατάλογο χαρακτηριστικών. Ανατρέξτε στο παράδειγμα εκτέλεσης παράγοντα για ένα ολοκληρωμένο λειτουργικό παράδειγμα με το διακριτικό φορέα στην κεφαλίδα και το σώμα εντός της αίτησης.

Μπορείτε να στείλετε όλα τα spans μιας εκτέλεσης σε ένα μόνο σώμα POST (προτιμάται – ένα αίτημα, ένα trace) ή σε πολλά σώματα POST. Ο διακομιστής ανακατασκευάζει την εκτέλεση από το traceId + parentSpanId + gen_ai.conversation.id, έτσι ώστε κάθε διάστημα να φέρει αρκετά ώστε να συσχετιστεί με κάθε τρόπο.

Συμβάσεις μηνυμάτων

Αυτή η ενότητα ορίζει ποια spans μπορείτε να εκπέμψετε και ποια χαρακτηριστικά πρέπει να περιέχει το καθένα. Για την πλήρη προδιαγραφή ανά χαρακτηριστικό, δείτε την Αναφορά χαρακτηριστικών.

Τύποι λειτουργιών

Κάθε span που αποστέλλετε πρέπει να έχει το gen_ai.operation.name ορισμένο σε μία από αυτές τις τέσσερις τιμές (χωρίς διάκριση πεζών-κεφαλαίων). Όποιο span με τιμή που λείπει ή δεν αναγνωρίζεται απορρίπτεται σιωπηλά και προσμετράται στο partialSuccess.rejectedSpans.

gen_ai.operation.name Νόημα Το πιο γκουγκλαρισμένο gotcha
invoke_agent Επίκληση ενός παράγοντα. Η «ρίζα» μιας εκτέλεσης παράγοντα. Απαιτείται για να εμφανιστεί η εκτέλεση στις προβολές δραστηριότητας παράγοντα στο Microsoft Defender ή στο Κέντρο διαχείρισης Microsoft 365. Χωρίς αυτό, τα δεδομένα τηλεμετρίας καταλήγουν μόνο στην προηγμένη αναζήτηση του Microsoft Defender (CloudAppEvents).
execute_tool Κλήση εργαλείου ή συνάρτησης που εκτελείται από έναν παράγοντα. --
chat Μια κλήση συμπερασμάτων LLM. Χρησιμοποιήστε την λεκτική σταθερά chat, ΟΧΙ inference.
output_messages Ένα τελικό εκπεμπόμενο μήνυμα εξόδου. --

Ιεραρχία των span και ομαδοποίηση ανά εκτέλεση

Ο Agent 365 ανασυνθέτει μια εκτέλεση από το τυπικό γράφημα span OTLP (traceId, spanId, parentSpanId) καθώς και τα χαρακτηριστικά που ισχύουν για ολόκληρη τη σειρά από την αναφορά χαρακτηριστικών.

Έξι κανόνες:

  1. Ρυθμίστε πάντα parentSpanId σε κάθε μη root span. Χωρίς αυτό, η δενδρική δομή της εκτέλεσης δεν μπορεί να ανακατασκευαστεί.
  2. Επαναχρησιμοποιήστε το ίδιο traceId σε κάθε span σε μια εκτέλεση.
  3. Ορίστε gen_ai.conversation.id σε κάθε span με την ίδια τιμή. Αυτό είναι το κύριο κλειδί συσχέτισης για «όλα τα spans σε αυτήν την εκτέλεση». Δεν μεταδίδεται αυτόματα.
  4. Ορίστε microsoft.channel.name σε κάθε span με την ίδια τιμή. Τα spans εργαλείων που δεν έχουν το κανάλι / τη συνομιλία μπορούν να τα κληρονομήσουν από το γονικό στοιχείο τους invoke_agentμόνο αν το γονικό στοιχείο βρίσκεται στο ίδιο αίτημα OTLP, οπότε πρέπει να τα ορίσετε σε κάθε span εσείς οι ίδιοι.
  5. Ρυθμίστε microsoft.session.id σε κάθε span όταν έχετε μια λογική περίοδο λειτουργίας.
  6. Για κλήσεις παράγοντα προς παράγοντα όπου ο θυγατρικός παράγοντας βρίσκεται σε ξεχωριστό αίτημα, επαναχρησιμοποιήστε το ίδιο gen_ai.conversation.id και χρησιμοποιήστε τα χαρακτηριστικά microsoft.a365.caller.agent.* (βλ. Αναφορά χαρακτηριστικών) για να καταγράψετε το πλαίσιο του παράγοντα-καλούντα.

Το δέντρο τεσσάρων span στο παράδειγμα εκτέλεσης του παράγοντα αποτελεί το τυπικό σχήμα.

Κοινά σχήματα εκτέλεσης

Σχήμα Spans για εκπομπή Σημειώσεις
Bot συνομιλίας με έναν παράγοντα (χωρίς εργαλεία, χωρίς LLM span) Ένα invoke_agent μόνο Ορίστε τα χαρακτηριστικά που ισχύουν για όλη την εκτέλεση, συν gen_ai.input.messages και gen_ai.output.messages. Πανομοιότυπο με το μικρότερο δυνατό αίτημα.
παράγοντας με εργαλεία (συνηθέστερο) invoke_agent ρίζα + chat, execute_tool, output_messages θυγατρικά Όλα τα θυγατρικά μοιράζονται το χαρακτηριστικό traceId της ρίζας και ορίζουν το parentSpanId = root.spanId. Όλα έχουν τα ίδια χαρακτηριστικά για ολόκληρη την εκτέλεση. Δείτε παράδειγμα εκτέλεσης παράγοντα για ένα πλήρες παράδειγμα.
Παράγοντας σε παράγοντα Κάθε παράγοντας εκπέμπει το δικό του invoke_agent Επαναχρησιμοποιήστε το ίδιο gen_ai.conversation.id και στους δύο παράγοντες. Στο invoke_agent του στόχου, ορίστε τα χαρακτηριστικά gen_ai.execution.type = "Agent2Agent" και microsoft.a365.caller.agent.* (όνομα του καλούντος παράγοντα appId, blueprint appId, αναγνωριστικό χρήστη και email). Εάν ο καλών παράγοντας δεν έχει εγγραφή στο Entra, χρησιμοποιήστε το microsoft.a365.caller.agent.platform.id και το gen_ai.caller.agent.type αντ' αυτού.

Λίστα ελέγχου προσθήκης λογαριασμών

Ελέγξτε αυτή τη λίστα πριν τη μετάβαση σε παραγωγική λειτουργία.

Κατηγορία Έλεγχος
Έλεγχος ταυτότητας Η εφαρμογή Entra σας (ή το blueprint) έχει καταχωρηθεί και μπορείτε να εκδώσετε διακριτικά για αυτή.
Έλεγχος ταυτότητας Στην εφαρμογή σας έχει εκχωρηθεί Agent365.Observability.OtelWrite (ρόλος εφαρμογής για S2S, πεδίο εφαρμογής για εξουσιοδότηση).
Έλεγχος ταυτότητας Κάθε παράγοντας έχει το δικό του Entra appId όπως {agentId} στη διεύθυνση URL. Για τις ταυτότητες που προέρχονται από blueprint, το συγκεκριμένο appId είναι το appId της ταυτότητας του παράγοντα, και όχι το appId του blueprint. Εάν ο παράγοντας δεν έχει εγγραφή στο Entra, ανατρέξτε στην ενότητα Επιλογή τιμών.
Έλεγχος ταυτότητας Ένας διαχειριστής του μισθωτή έχει παραχωρήσει συγκατάθεση για Agent365.Observability.OtelWrite. Χωρίς συγκατάθεση, τα διακριτικά εκδίδονται χωρίς τον ρόλο/πεδίο εφαρμογής και τα αιτήματα απορρίπτονται με 403.
Παραχώρηση αδειών χρήσης Τουλάχιστον ένας χρήστης στον μισθωτή πελάτη διαθέτει εκχωρημένη άδεια χρήσης Microsoft 365 E7 ή Microsoft Agent 365 (πρόκειται για εκχώρηση και όχι απλώς για την ύπαρξη του SKU στον μισθωτή). Χωρίς εκχωρημένη άδεια, η εισαγωγή δεδομένων αγνοείται σιωπηλά. Δείτε Προϋποθέσεις.
Spans Κάθε span ορίζει τα βασικά στοιχεία εκτέλεσης (ιεραρχία εύρους και ομαδοποίηση εκτέλεσης).
Spans invoke_agent σύνολο spans gen_ai.input.messages και gen_ai.output.messages.
Spans execute_tool σύνολο spans gen_ai.tool.name, gen_ai.tool.type, gen_ai.tool.call.id, gen_ai.tool.call.arguments, gen_ai.tool.call.result.
Spans chat σύνολο spans gen_ai.request.model και gen_ai.provider.name (και ιδανικά gen_ai.usage.input_tokens / gen_ai.usage.output_tokens - κωδικοποιημένο ως συμβολοσειρά).
Spans Όλα τα spans που δεν είναι ριζικά θέτουν parentSpanId· όλα τα spans σε μια εκτέλεση μοιράζονται το ίδιο traceId.
Ωφέλιμο φορτίο Το σώμα αιτήματος είναι ≤ 1 MB.
Επαλήθευση Αναλύετε το partialSuccess σε κάθε απάντηση και καταγράφετε τις απορρίψεις.
Επαλήθευση Εκτελέσατε τη διαδικασία επαλήθευσης στην ενότητα Επαλήθευση εισαγωγής έναντι των πρώτων εκτελέσεών σας.

Επόμενα βήματα