Zum Hauptinhalt springen

Setup

Diese Anleitung führt durch alles, was nötig ist, um ein Microsoft-365-Postfach aus OctoMesh abzufragen — zuerst im Azure Portal, dann die entsprechenden Azure-CLI-(az)- Befehle und schließlich die OctoMesh-Seite (Anmeldedaten, Pipeline, Deployment, Test).

Anders als der Teams-Bot verwendet diese Integration einen App-only- (Client-Credentials-)Flow: Es gibt keine Azure-Bot-Ressource und keine Benutzeranmeldung. Die App- Registrierung authentifiziert sich als sie selbst und liest/verschiebt E-Mails über die Application- Berechtigungen von Microsoft Graph.

Voraussetzungen​

  • Ein Azure-Abonnement und die Berechtigung, eine App-Registrierung in Microsoft Entra ID zu erstellen.
  • Ein Global Administrator (oder Privileged Role Administrator), um die Admin-Einwilligung (admin consent) für die Graph-Application-Berechtigung zu erteilen.
  • Ein Microsoft-365-Postfach, das abgefragt werden soll, und die Ordnerstruktur, die Sie als Arbeitswarteschlange verwenden möchten (z. B. ein ToDo- und ein Done-Ordner).
  • Ein laufender OctoMesh-Mesh Adapter für den Ziel-Tenant.
Nachfolgend verwendete Benennungen

Die Beispiele verwenden den App-Namen octo-mail-import, das Postfach accounting@company.com, den Quellordner Archive/Invoices/ToDo und den Erfolgsordner Archive/Invoices/Done. Ersetzen Sie sie durch Ihre eigenen Werte.


Schritt 1 — App-Registrierung + Client-Secret​

Die App-Registrierung ist die Identität, als die sich der Adapter authentifiziert. Ihre Client- ID/-Secret und Tenant-ID gehen in die OctoMesh-MicrosoftGraphConfiguration.

Portal​

  1. Microsoft Entra ID → App registrations → + New registration.
  2. Name: octo-mail-import.
  3. Supported account types: Accounts in this organizational directory only (Single tenant).
  4. Register, dann Application (client) ID und Directory (tenant) ID notieren.
  5. Certificates & secrets → + New client secret → eine Ablaufzeit festlegen → Add → den Value sofort kopieren (er wird nur einmal angezeigt).

Azure CLI​

# create a single-tenant app registration
az ad app create --display-name "octo-mail-import" --sign-in-audience AzureADMyOrg
# -> note the "appId" from the output

# add a client secret (prints the secret once)
az ad app credential reset --id <APP_ID> --append --display-name mail-import --years 1 \
--query password -o tsv

# your tenant id
az account show --query tenantId -o tsv

Bewahren Sie drei Werte für später auf: App (client) ID, Client-Secret, Tenant-ID.


Schritt 2 — Graph-Application-Berechtigung Mail.ReadWrite​

Der Trigger liest Nachrichten und verschiebt sie zwischen Ordnern, daher benötigt er die Application-Berechtigung Mail.ReadWrite (nicht die delegierte), gefolgt von einer Admin- Einwilligung.

Portal​

  1. In der App-Registrierung: API permissions → + Add a permission → Microsoft Graph → Application permissions.
  2. Nach Mail.ReadWrite suchen, ankreuzen, Add permissions.
  3. Auf Grant admin consent for <tenant> klicken und bestätigen — die Spalte Status muss ein grünes Granted-Häkchen anzeigen.

Azure CLI​

GRAPH=00000003-0000-0000-c000-000000000000 # Microsoft Graph resource appId
MAIL_RW=e2a3a72e-5f79-4c64-b1b1-878b674786c9 # Mail.ReadWrite (application) role id

# add the application permission
az ad app permission add --id <APP_ID> \
--api $GRAPH --api-permissions ${MAIL_RW}=Role

# grant admin consent (requires an admin)
az ad app permission admin-consent --id <APP_ID>

# verify the grant
az ad app permission list-grants --id <APP_ID> -o table
Umfang der Application-Berechtigung — schränken Sie ihn ein

Die Application-Berechtigung Mail.ReadWrite gewährt der App Zugriff auf jedes Postfach im Tenant, nicht nur auf das, das Sie konfigurieren. Bevor Sie dies in der Produktion verwenden, schränken Sie sie auf die konkrete(n) Mailbox(en) mit einer Application Access Policy in Exchange Online ein (erstellen Sie eine mail-fähige Sicherheitsgruppe, die nur die freizugebende(n) Mailbox(en) enthält, dann):

# Exchange Online PowerShell
New-ApplicationAccessPolicy -AppId <APP_ID> `
-PolicyScopeGroupId mail-import-scope@company.com `
-AccessRight RestrictAccess `
-Description "Restrict octo-mail-import to the accounting mailbox"

# confirm the app can access the target mailbox but not others
Test-ApplicationAccessPolicy -AppId <APP_ID> -Identity accounting@company.com

Schritt 3 — Die Postfachordner vorbereiten​

Der Trigger behandelt einen Ordner als Arbeitswarteschlange. Erstellen Sie den Quell- und (optional) den Erfolgs- ordner im Postfach, zum Beispiel:

Archive
└── Invoices
├── ToDo ← trigger polls this (folderPath)
└── Done ← messages moved here on success (moveToFolderPathOnSuccess)
Verwenden Sie die (nicht lokalisierten) Graph-Ordnernamen

folderPath-Segmente müssen den Graph-Anzeigenamen entsprechen, die nicht lokalisiert sind. Verwenden Sie Archive, nicht den lokalisierten Outlook-Namen (z. B. Archivieren). Wohlbekannte Ordner (inbox, archive, …) werden auch über ihren wohlbekannten Namen aufgelöst. Das Blatt (leaf) des Erfolgsordners wird automatisch erstellt, falls es fehlt, aber sein übergeordneter Pfad muss bereits existieren.

Leiten Sie eingehende Rechnungen nach Belieben in den ToDo-Ordner (eine Outlook-Regel, ein Workflow für gemeinsame Postfächer oder manuelle Ablage).


Schritt 4 — OctoMesh konfigurieren​

1. Anmeldedaten (MicrosoftGraphConfiguration)​

Geben Sie die Tenant-ID / Client-ID / das Secret als System.Communication/MicrosoftGraphConfiguration-Entität an. Speichern Sie das Secret außerhalb der Versionsverwaltung (eine lokale Secrets-Datei, ein Key Vault, …). Dies ist der gleiche Konfigurationstyp, den die Teams-Trigger verwenden.

- rtId: <config-rtId>
ckTypeId: System.Communication/MicrosoftGraphConfiguration
rtWellKnownName: MicrosoftGraphDocuments
attributes:
- id: System.Communication/AzureTenantId
value: "<tenant id>"
- id: System.Communication/ClientId
value: "<app (client) id>"
- id: System.Communication/ClientSecret
value: "<client secret>"

2. Pipeline mit FromMicrosoftGraphEmail@1​

Die Pipeline muss eine System.Communication/Uses-Assoziation zur MicrosoftGraphConfiguration tragen (die GlobalConfiguration wird nur aus Uses- Assoziationen aufgebaut — der Name allein wird nicht aufgelöst).

# on the Pipeline entity
associations:
- roleId: System.Communication/Uses
targetRtId: <config-rtId>
targetCkTypeId: System.Communication/MicrosoftGraphConfiguration

Eine minimale Pipeline-Definition, die jeden PDF-Anhang staged (der Trigger liefert eine Nachricht pro Lauf, daher iteriert das äußere ForEach@1 über ein einzelnes Element):

triggers:
- type: FromMicrosoftGraphEmail@1
serverConfiguration: MicrosoftGraphDocuments
mailbox: accounting@company.com
folderPath: Archive/Invoices/ToDo
moveToFolderPathOnSuccess: Archive/Invoices/Done
pollingIntervalSeconds: 120
transformations:
- type: ForEach@1
iterationPath: $.Emails
targetPath: $.emailResults
targetValueKind: Simple
targetValueWriteMode: Overwrite
transformations:
- type: ForEach@1
iterationPath: $.key.Attachments
targetPath: $.attachmentResults
targetValueKind: Simple
targetValueWriteMode: Overwrite
transformations:
- type: If@1
path: $.key.ContentType
operator: Equals
value: "application/pdf"
valueType: String
transformations:
# ... store $.key.Data, run OCR / AI, create entities ...

Die Nachrichten-Metadaten ($.key.Subject, $.key.FromAddress, $.key.Date, $.key.Body) sowie FileName / ContentType / Length / Data jedes Anhangs sind unter dem Element-Key des ForEach@1 verfügbar — siehe die vereinheitlichte Nachrichtenstruktur.

3. Deployment​

Importieren Sie die Konfiguration und die Pipeline und stellen Sie den Datenfluss mit dem octo-cli bereit (ImportRt, DeployDataFlow). Nach dem Deployment beginnt der Adapter, im konfigurierten Intervall abzufragen.


Schritt 5 — Test​

  1. Legen Sie eine Testnachricht mit einem PDF-Anhang in den Ordner Archive/Invoices/ToDo.
  2. Innerhalb eines Abfrageintervalls (Standard 120 s) läuft die Pipeline für diese Nachricht.
  3. Bei Erfolg verschwindet die Nachricht aus ToDo und erscheint in Done; bei einem Fehler bleibt sie in ToDo und wird bis zu maxAttemptsPerMessage Mal erneut versucht.

Beobachten Sie das Adapter-Log, um den Umlauf zu bestätigen — ein Token-Fehler, ein Berechtigungsfehler oder ein fehlender Ordner tauchen alle dort auf (siehe Fehlerbehebung).


Node-Referenz​

FromMicrosoftGraphEmail@1 (Trigger)​

PropertyDefaultBeschreibung
serverConfiguration—WellKnownName der MicrosoftGraphConfiguration (Tenant-ID + Client-ID/-Secret).
mailbox—Abzufragender Postfach-UPN (z. B. accounting@company.com).
folderPath—/-getrennter Ordnerpfad, aufgelöst vom Postfach-Root.
moveToFolderPathOnSuccess(none)Ordner, in den die Nachricht nach einem erfolgreichen Lauf verschoben wird (Blatt automatisch erstellt). Weggelassen → Nachricht bleibt am Platz.
pollingIntervalSeconds120Sekunden zwischen den Abfragezyklen.
maxMessagesPerPoll25Maximale Anzahl pro Zyklus abgerufener Nachrichten (älteste zuerst).
senderFilter(none)Nur Nachrichten verarbeiten, deren Absenderadresse diese Zeichenkette enthält.
maxAttemptsPerMessage3Wiederholungen für eine fehlschlagende Nachricht, bevor sie bis zum Neustart des Adapters übersprungen wird.

Ausgabe: $.Emails[] (ein Element pro Lauf) — siehe den Überblick. Siehe auch die kompakte FromMicrosoftGraphEmail@1-Node-Referenz.


Sicherheit​

  • App-only-Zugriff. Der Adapter authentifiziert sich als App-Registrierung über Client-Credentials; es gibt keinen Benutzerkontext. Behandeln Sie das Client-Secret wie ein Passwort — speichern Sie es außerhalb der Versionsverwaltung und rotieren Sie es vor Ablauf.
  • Minimale Rechte. Die Application-Berechtigung Mail.ReadWrite erstreckt sich über den gesamten Tenant. Schränken Sie sie mit einer Application Access Policy auf die Ziel-Mailbox(en) ein (siehe die Admonition in Schritt 2). Ohne sie legt ein geleaktes Secret jedes Postfach offen.
  • Lese-/Schreib-Fußabdruck. Der Trigger liest Nachrichten, lädt Anhänge herunter und verschiebt Nachrichten zwischen Ordnern. Er löscht oder sendet keine E-Mails.

Fehlerbehebung​

SymptomUrsache / Behebung
invalid_client / AADSTS7000215 beim Abrufen des TokensFalsches oder abgelaufenes Client-Secret oder falsche AzureTenantId. Setzen Sie das Secret zurück (Schritt 1) und prüfen Sie die Tenant-ID erneut.
ErrorAccessDenied / 403 von GraphDie Application-Berechtigung Mail.ReadWrite fehlt oder die Admin-Einwilligung wurde nicht erteilt (Schritt 2), oder eine Application Access Policy blockiert dieses Postfach. Prüfen Sie mit az ad app permission list-grants und Test-ApplicationAccessPolicy.
ErrorItemNotFound / Ordner nicht gefundenfolderPath verwendet einen lokalisierten Namen (z. B. Archivieren) oder einen nicht existierenden Pfad. Verwenden Sie die (nicht lokalisierten) Graph-Anzeigenamen; der übergeordnete Ordner des Erfolgsordners muss existieren.
Nichts wird abgefragt, obwohl E-Mail im Ordner liegtmailbox-UPN falsch, folderPath zeigt auf den falschen Ordner, oder senderFilter schließt die Nachrichten aus. Bestätigen Sie, dass der Ordner die Nachrichten tatsächlich enthält, und prüfen Sie das Adapter-Log.
Eine Nachricht wird wiederholt verarbeitetDer Pipeline-Lauf schlägt immer wieder fehl, sodass die Nachricht nie aus dem Quellordner verschoben wird. Beheben Sie den Pipeline-Fehler; nach maxAttemptsPerMessage Fehlschlägen wird die Nachricht bis zum Neustart des Adapters übersprungen.
Anhänge sind leerNur die Inhalte von fileAttachment werden heruntergeladen — Inline-/Item-/Reference-Anhänge werden übersprungen. Prüfen Sie ContentType/Length an $.Emails[0].Attachments[].
Überhaupt keine Abfrageaktivität im LogDer Datenfluss ist nicht bereitgestellt, oder der Adapter-Build ist älter als der Node — stellen Sie erneut bereit und starten Sie den Adapter neu.