Export Security Incidents to Microsoft Sentinel
Send security incidents to your Microsoft Sentinel workspace as OCSF Detection Findings. AIControls gets a short-lived Microsoft Entra token with a client secret or a certificate and posts each incident to a data collection rule (DCR) stream. No gateway is needed.
Before you start
- You need the admin role in AIControls, and in Azure the rights to create a custom table, a data collection endpoint (DCE) and a DCR in the Log Analytics workspace that Sentinel uses, and to register an application in Microsoft Entra ID.
- AIControls must be able to reach
login.microsoftonline.comand your DCE over HTTPS. Sovereign clouds (US Government, China) are not supported: the Entra authority and the*.ingest.monitor.azure.comendpoint host are fixed. - The event is the same OCSF 1.9.0 Detection Finding as the OCSF JSON format, wrapped in a one-element JSON array. Know which data leaves the product: see what is never exported. The same Redact actors and Include finding summaries options apply.
Create the table, endpoint and rule
- Create the custom table. The columns are listed in the Sentinel table and rule schema, with a ready
az monitor log-analytics workspace table createcommand. The table name must end in_CL, for exampleAIControlsFindings_CL. - Create a data collection endpoint in the same region as the workspace. Copy its Logs Ingestion URI, for example
https://aicontrols-ab12.eastus-1.ingest.monitor.azure.com. - Create a data collection rule that uses the endpoint, declares the stream
Custom-AIControlsFindings_CLwith the columns in the schema reference, and sends it to the workspace table with the transformsource | extend TimeGenerated = unixtime_milliseconds_todatetime(time). The reference has the full rule definition. - Open the rule's JSON view and copy its
immutableId, which starts withdcr-.
Register the application
- In Microsoft Entra ID, go to App registrations → New registration. Copy the Application (client) ID and the Directory (tenant) ID.
- Under Certificates & secrets, create a client secret and copy its value. Choose a short expiry and set a reminder to rotate it; the destination reports
token_invalid_client_7000222after it expires. To use a certificate instead, upload its public part under Certificates on the same page, and keep its unencrypted RSA private key (2048 bits or more) in PEM form for the next section. Elliptic-curve keys are not supported. - On the data collection rule, open Access control (IAM) and assign the role Monitoring Metrics Publisher to the application. This is the least privilege that Logs Ingestion needs; assign it on the rule only, not on the workspace or the subscription. A new role assignment can take up to 30 minutes to apply.
Configure the destination
- Go to Integrations → Security export and select Add destination.
- Enter a unique Name and set Format to Microsoft Sentinel (Logs Ingestion).
- Enter the Tenant ID and Client ID, then choose the Credential: a Client secret, or a Certificate with its Private key, both in PEM form. Use one, not both. The secret and the private key are hidden after you save; leave the masked value to keep the saved one. The form checks that the key matches the certificate and shows the certificate's expiry.
- Enter the Data collection endpoint URL, the Rule immutable ID and the Stream name.
- Set the Severity filter, Event types, Automatic export, Redact actors and Include finding summaries as for any other destination.
- Turn the integration on, select Send Test, then Save. The test gets a token and posts one event titled
AIControls export testwith low severity, so it appears as a row in the table. A failure shows a short reason.
Rows can take a few minutes to appear in the workspace after the first post.
How delivery works
- Token. AIControls requests a client-credentials token, proving the app's identity with the secret or with a signed assertion (RFC 7523: valid for 10 minutes, signed RS256 with the private key, carrying the certificate's SHA-256 thumbprint), for the scope
https://monitor.azure.com/.defaultand reuses it until five minutes before it expires (halfway through its life for a token that lives under ten minutes). If Logs Ingestion answers 401, it gets a new token once per delivery and sends again; a second 401 fails the delivery. The token is never written to a log, the audit trail or an API response. - One event per request. Each incident is one request, far below the 1 MB request limit. An event larger than that is refused with the reason
payload_too_large. - Retries. A network error, 429 or 5xx, from Entra or from Logs Ingestion, is retried up to 3 attempts in total; an attempt is a token lookup (a request to Entra only when no valid token is cached) and one post. The wait is 1 then 2 seconds, or the
Retry-Aftervalue when the service sends one. ARetry-Afterlonger than 5 seconds is not cut short: the delivery fails with the reason of that response (http_429from Logs Ingestion,token_http_429ortoken_<error>from Entra) and automatic export tries again on its next run. - Automatic export. Works as for the other destinations: each incident is sent once per destination across all replicas, and a failed delivery is retried until it leaves the 24-hour window. A rejected credential stops the run, so it does not retry every incident: a failed token request, a 403, or a 401 that persists after the one new token. If you change the destination while an export is running, nothing more is sent to it under the old settings, and the incident goes to the saved destination on the next run. Automatic events carry a stable
metadata.uid; add a rule to deduplicate on it if a repeat after a crash matters to you.
Check what was sent
Every attempt is recorded in Security → Activity → Configuration as security_incident.exported, with the actor, the trigger, the destination name, the endpoint host, the event ID, the attempt count and the outcome. A failure carries a short reason. The attempt records never carry the tenant ID, client ID, client secret, private key, rule ID, tokens or response bodies. When you change the destination, the configuration audit records the change and redacts the client secret and the private key; the tenant ID, client ID, endpoint and rule ID are identifiers, not secrets, and appear in it. Scrape aicontrols_security_export_total to alert on failures.
Troubleshooting
| Reason | Check |
|---|---|
token_invalid_client_7000215 | The client secret value is wrong. Copy the secret value, not its ID. |
token_invalid_client_7000222 | The client secret expired. Create a new one and save it in the destination. |
token_invalid_client_700027 | With a certificate: the certificate is not uploaded to the app registration, or does not match the private key. |
invalid_certificate | The saved certificate or key could not be used, for example because the certificate expired. Replace it. |
token_invalid_client_700016 | The client ID is not an application in that tenant. |
token_invalid_request_90002 | The tenant ID is wrong. |
token_network_error, token_timeout | AIControls cannot reach login.microsoftonline.com. |
http_401, http_403 | The application has no Monitoring Metrics Publisher role on the rule, or the assignment is still applying. |
http_404 | The endpoint URL or the rule immutable ID is wrong, or the rule does not use that endpoint. |
http_400 | The stream name or the declared columns do not match the event. Compare with the schema reference. |
http_429, http_5xx | Throttled or unavailable. Automatic export retries. |
payload_too_large | The event exceeds 1 MB, so it cannot be delivered. |
See Sentinel table and rule schema for the columns, and Security Incident OCSF Mapping for every exported field.