Freigeben über


Nutzen von Microsoft Graph in SharePoint-Framework

Die Verarbeitung von REST-APIs, die durch Azure Active Directory (Azure AD) und Open Authorization (OAuth 2.0) in einer clientseitigem SharePoint-Framework-Webpart oder einer Erweiterung gesichert sind, sind ein gängiges Geschäftsszenario auf Unternehmensebene.

Sie können das SharePoint-Framework (ab v.1.4.1) verwenden, um Microsoft Graph REST-APIs oder eine beliebige andere REST-API zu nutzen, die in Azure AD registriert ist.

In diesem Artikel erfahren Sie, wie Sie eine SharePoint-Framework-Lösung erstellen können, die die Microsoft Graph-API mit einem benutzerdefinierten Satz von Berechtigungen verwendet. Eine konzeptionelle Übersicht über diese Technologie finden Sie unter Herstellen einer Verbindung mit durch Azure AD gesicherten APIs in SharePoint-Framework-Lösungen.

Wichtig

Sie können die Microsoft Graph-API mit Versionen von SharePoint-Framework vor v1.4.1 nutzen, entweder über den nativen GraphHttpClient oder durch direkte Verwendung des impliziten OAuth-Flusses der Microsoft-Identitätsplatfomr-Authentifizierungsbibliotheken. Der frühere Ansatz ist jedoch an einen vordefinierten Satz von Berechtigungen gebunden, die einige Einschränkungen beinhalten, und der zweite ist aus Entwicklungsperspektive recht komplex. Details zur Implementierung eines impliziten OAuth-Flusses finden Sie unter Herstellen einer Verbindung zu einer mit Azure Active Directory gesicherten API.

Die Lösung im Überblick

In den Schritten in diesem Artikel wird veranschaulicht, wie Sie ein clientseitiges Webpart erstellen können, mit dem Benutzer im aktuellen Mandanten gesucht werden können, wie im folgenden Screenshot gezeigt. Die Suche basiert auf Microsoft Graph und erfordert mindestens die Berechtigung User.ReadBasic.All.

Ein clientseitiger Webpart, der ein Textfeld und eine Suchen-Schaltfläche für die Suche nach Benutzern innerhalb eines Mandanten enthält.

Mit dem clientseitigen Webpart können Sie anhand des Namens nach Benutzern suchen, außerdem werden alle übereinstimmenden Benutzer über eine DetailsList-Komponente der Office UI Fabric bereitgestellt. Das Webpart verfügt über eine Option im Eigenschaftenbereich, mit der ausgewählt werden kann, wie auf Microsoft Graph zugegriffen werden soll. Ab SharePoint-Framework v1.4.1 können Sie entweder mithilfe des nativen Graph-Client (MSGraphClient) oder über den allgemeinen Typ, der für den Zugriff auf mit Azure AD gesicherte REST-APIs verwendet wird (AadHttpClient), auf Microsoft Graph zugreifen.

Hinweis

Den Quellcode für diese Lösung finden Sie im GitHub-Repository api-scopes.

Wenn Sie bereits mit dem Erstellen von SharePoint-Framework-Lösungen vertraut sind, können Sie mit Konfigurieren der API-Berechtigungsanforderungen fortfahren.

Erstellen der ersten Lösung

Wenn Sie eine ältere Version des SharePoint-Framework-Generators verwenden, müssen Sie ihn als Erstes auf Version 1.4.1 oder höher aktualisieren. Führen Sie dazu den folgenden Befehl aus, um die aktuellste Version des Pakets global zu installieren.

npm install -g @microsoft/generator-sharepoint

Erstellen Sie als Nächstes eine neue SharePoint Framework-Lösung:

  1. Ersrtellen Sie einen Ordner in Ihrem Dateisystem. Speichern Sie den Quellcode der Lösung und verschieben Sie den aktuellen Pfad in diesen Ordner.

  2. Führen Sie den Yeoman-Generator aus, um eine neue Lösung mit einem Gerüst zu versehen.

    yo @microsoft/sharepoint
    
  3. Wenn Sie dazu aufgefordert werden, geben Sie die folgenden Werte ein (wählen Sie für alle unten nicht aufgeführten Eingabeaufforderungen die Standardoption aus):

    • Wie lautet der Name Ihrer Lösung?: spfx-api-scopes-tutorial
    • Welche Basisplanpakete möchten Sie für Ihre Komponente(n) als Ziel festlegen? Nur SharePoint Online (aktuellste)
    • Welchen Typ von clientseitiger Komponente möchten Sie erstellen? Webpart
    • Wie lautet der Name Ihres Webparts? GraphConsumer
    • Welches Framework möchten Sie verwenden? React
  4. Starten Sie Visual Studio Code (oder Ihren bevorzugten Quellcode-Editor) im Kontext des aktuellen Ordners.

    code .
    

Konfigurieren der grundlegenden Webpartelemente

Konfigurieren Sie als Nächstes die anfänglichen Elemente des clientseitigen Webparts.

Konfigurieren der benutzerdefinierten Eigenschaften

  1. Erstellen Sie eine neue Quellcodedatei im Ordner ./src/webparts/graphConsumer/components der Lösung.

    Nennen Sie die neue Datei ClientMode.ts, und verwenden Sie sie, um ein TypeScript-enum-Element mit den verfügbaren Optionen für die ClientMode-Eigenschaft des Webparts zu deklarieren.

    export enum ClientMode {
      aad,
      graph,
    }
    
  2. Öffnen Sie die Datei GraphConsumerWebPart.ts im Ordner ./src/webparts/graphConsumer der Lösung.

    Ändern Sie die Definition der IGraphConsumerWebPartProps-Schnittstelle so, dass ein Wert vom Typ ClientMode akzeptiert wird.

    export interface IGraphConsumerWebPartProps {
      clientMode: ClientMode;
    }
    
  3. Aktualisieren Sie die getPropertyPaneConfiguration()-Methode des clientseitigen Webparts, sodass die Auswahl im Eigenschaftenbereich unterstützt wird. Im folgenden Beispiel wird die neue Implementierung der Methode veranschaulicht.

    protected getPropertyPaneConfiguration(): IPropertyPaneConfiguration {
      return {
        pages: [
          {
            header: {
              description: strings.PropertyPaneDescription
            },
            groups: [
              {
                groupName: strings.BasicGroupName,
                groupFields: [
                  PropertyPaneChoiceGroup('clientMode', {
                    label: strings.ClientModeLabel,
                    options: [
                      { key: ClientMode.aad, text: "AadHttpClient"},
                      { key: ClientMode.graph, text: "MSGraphClient"},
                    ]
                  }),
                ]
              }
            ]
          }
        ]
      };
    }
    
  4. Sie müssen die render()-Methode des clientseitigen Webparts aktualisieren, um eine ordnungsgemäß konfigurierte Instanz der React-Komponente für das Rendern zu erstellen. Der folgenden Code zeigt die aktualisierte Methodendefinition.

    public render(): void {
      const element: React.ReactElement<IGraphConsumerProps > = React.createElement(
        GraphConsumer,
        {
          clientMode: this.properties.clientMode,
          context: this.context,
        }
      );
    
      ReactDom.render(element, this.domElement);
    }
    
  5. Damit dieser Code funktioniert, müssen Sie einige Importanweisungen am Anfang der Datei GraphConsumerWebPart.ts hinzufügen, wie im folgenden Beispiel gezeigt. Beachten Sie den Import für das PropertyPaneChoiceGroup-Steuerelement sowie den Import der ClientMode-Enumeration.

    import * as React from "react";
    import * as ReactDom from "react-dom";
    import { Version } from "@microsoft/sp-core-library";
    import {
      BaseClientSideWebPart,
      IPropertyPaneConfiguration,
      PropertyPaneChoiceGroup,
    } from "@microsoft/sp-webpart-base";
    
    import * as strings from "GraphConsumerWebPartStrings";
    import GraphConsumer from "./components/GraphConsumer";
    import { IGraphConsumerProps } from "./components/IGraphConsumerProps";
    import { ClientMode } from "./components/ClientMode";
    

Aktualisieren der Ressourcenzeichenfolgen

Um die Lösung zu kompilieren, müssen Sie die Datei mystrings.d.ts im Ordner ./src/webparts/graphConsumer/loc der Lösung aktualisieren.

  1. Sie müssen die Schnittstelle zur Definition der Ressourcenzeichenfolgen mit dem folgenden Codeauszug neu schreiben.

    declare interface IGraphConsumerWebPartStrings {
      PropertyPaneDescription: string;
      BasicGroupName: string;
      ClientModeLabel: string;
      SearchFor: string;
      SearchForValidationErrorMessage: string;
    }
    
  2. Konfigurieren Sie geeignete Werte für die neu erstellten Ressourcenzeichenfolgen, indem Sie die Datei en-us.js in demselben Ordner aktualisieren.

    define([], function () {
      return {
        PropertyPaneDescription: "Description",
        BasicGroupName: "Group Name",
        ClientModeLabel: "Client Mode",
        SearchFor: "Search for",
        SearchForValidationErrorMessage: "Invalid value for 'Search for' field",
      };
    });
    

Aktualisieren der Formatvorlage für das clientseitige Webpart

Außerdem müssen Sie die SCSS-Formatvorlagendatei aktualisieren.

Öffnen Sie dazu die Datei GraphConsumer.module.scss im Ordner ./src/webparts/graphConsumer/components der Lösung. Fügen Sie die folgenden Formatklassen direkt nach der .title-Klasse hinzu:

.form {
  @include ms-font-l;
  @include ms-fontColor-white;
}

label {
  @include ms-fontColor-white;
}

Aktualisieren der React-Komponente, die das Webpart rendert

Jetzt können Sie die React-Komponente GraphConsumer im Ordner ./src/webparts/graphConsumer/components der Lösung aktualisieren.

  1. Aktualisieren Sie die Datei IGraphConsumerProps.ts so, dass sie die von der Webpartimplementierung benötigten benutzerdefinierten Eigenschaften akzeptiert. Das folgenden Beispiel zeigt den aktualisierten Inhalt der Datei IGraphConsumerProps.ts. Beachten Sie den Import der ClientMode-Enumerationsdefinition sowie den Import des WebPartContext-Typs. Er wird später verwendet.

    import { WebPartContext } from "@microsoft/sp-webpart-base";
    import { ClientMode } from "./ClientMode";
    
    export interface IGraphConsumerProps {
      clientMode: ClientMode;
      context: WebPartContext;
    }
    
  2. Erstellen Sie eine neue Schnittstelle zum Speichern des Zustands der React-Komponente. Erstellen Sie eine neue Datei im Ordner ./src/webparts/graphConsumer/components, und nennen Sie sie IGraphConsumerState.ts. Im Folgenden sehen Sie die Schnittstellendefinition.

    import { IUserItem } from "./IUserItem";
    
    export interface IGraphConsumerState {
      users: Array<IUserItem>;
      searchFor: string;
    }
    
  3. Definieren Sie die IUserItem-Schnittstelle (in einer Datei namens IUserItem.ts im Ordner ./src/webparts/graphConsumer/components). Diese Schnittstelle wird in die Statusdatei importiert. Die Schnittstelle dient zum Definieren der Gliederung der Benutzer, die aus dem aktuellen Mandanten abgerufen und an die DetailsList in der Benutzeroberfläche gebunden werden.

    export interface IUserItem {
      displayName: string;
      mail: string;
      userPrincipalName: string;
    }
    
  4. Aktualisieren Sie die Datei GraphConsumer.tsx. Fügen Sie zuerst einige Importanweisungen hinzu, um die zuvor definierten Typen zu importieren. Beachten Sie den Import für IGraphConsumerProps, IGraphConsumerState, ClientMode und IUserItem. Darüber hinaus gibt es einige Importe für die Office UI Fabric-Komponenten, mit denen die Benutzeroberfläche der React-Komponente gerendert wird.

    import * as strings from "GraphConsumerWebPartStrings";
    import {
      BaseButton,
      Button,
      CheckboxVisibility,
      DetailsList,
      DetailsListLayoutMode,
      PrimaryButton,
      SelectionMode,
      TextField,
    } from "office-ui-fabric-react";
    import * as React from "react";
    
    import { AadHttpClient, MSGraphClient } from "@microsoft/sp-http";
    import { escape } from "@microsoft/sp-lodash-subset";
    
    import { ClientMode } from "./ClientMode";
    import styles from "./GraphConsumer.module.scss";
    import { IGraphConsumerProps } from "./IGraphConsumerProps";
    import { IGraphConsumerState } from "./IGraphConsumerState";
    import { IUserItem } from "./IUserItem";
    
  5. Definieren Sie nach den Importen die Gliederung der Spalten für die DetailsList-Komponente der Office UI Fabric.

    // Configure the columns for the DetailsList component
    let _usersListColumns = [
      {
        key: "displayName",
        name: "Display name",
        fieldName: "displayName",
        minWidth: 50,
        maxWidth: 100,
        isResizable: true,
      },
      {
        key: "mail",
        name: "Mail",
        fieldName: "mail",
        minWidth: 50,
        maxWidth: 100,
        isResizable: true,
      },
      {
        key: "userPrincipalName",
        name: "User Principal Name",
        fieldName: "userPrincipalName",
        minWidth: 100,
        maxWidth: 200,
        isResizable: true,
      },
    ];
    

    Dieses Array wird in den Einstellungen der DetailsList-Komponente verwendet, wie Sie in der render()-Methode der React-Komponente sehen können.

  6. Ersetzen Sie diese Komponente durch den nachstehenden Code.

    public render(): React.ReactElement<IGraphConsumerProps> {
      return (
        <div className={ styles.graphConsumer }>
          <div className={ styles.container }>
            <div className={ styles.row }>
              <div className={ styles.column }>
                <span className={ styles.title }>Search for a user!</span>
                <p className={ styles.form }>
                  <TextField
                      label={ strings.SearchFor }
                      required={ true }
                      onChange={ this._onSearchForChanged }
                      onGetErrorMessage={ this._getSearchForErrorMessage }
                      value={ this.state.searchFor }
                    />
                </p>
                <p className={ styles.form }>
                  <PrimaryButton
                      text='Search'
                      title='Search'
                      onClick={ this._search }
                    />
                </p>
                {
                  (this.state.users != null && this.state.users.length > 0) ?
                    <p className={ styles.form }>
                    <DetailsList
                        items={ this.state.users }
                        columns={ _usersListColumns }
                        setKey='set'
                        checkboxVisibility={ CheckboxVisibility.hidden }
                        selectionMode={ SelectionMode.none }
                        layoutMode={ DetailsListLayoutMode.fixedColumns }
                        compact={ true }
                    />
                  </p>
                  : null
                }
              </div>
            </div>
          </div>
        </div>
      );
    }
    
  7. Aktualisieren Sie die Typdeklaration der React-Komponente, und fügen Sie einen Konstruktor hinzu, wie im folgenden Beispiel gezeigt:

    export default class GraphConsumer extends React.Component<IGraphConsumerProps, IGraphConsumerState> {
    
      constructor(props: IGraphConsumerProps, state: IGraphConsumerState) {
        super(props);
    
        // Initialize the state of the component
        this.state = {
          users: [],
          searchFor: ""
        };
      }
    

    Es gibt einige Gültigkeitsprüfungsregeln und zu behandelnde Ereignisse, um in der TextField-Komponente die Suchkriterien zu sammeln. Im Folgenden werden die Methoden-Implementierungen gezeigt.

    Fügen Sie diese beiden Methoden am Ende der Klasse GraphConsumer hinzu:

    private _onSearchForChanged = (event: React.FormEvent<HTMLInputElement | HTMLTextAreaElement>, newValue?: string): void => {
    
      // Update the component state accordingly to the current user's input
      this.setState({
        searchFor: newValue,
      });
    }
    
    private _getSearchForErrorMessage = (value: string): string => {
      // The search for text cannot contain spaces
      return (value == null || value.length == 0 || value.indexOf(" ") < 0)
        ? ''
        : `${strings.SearchForValidationErrorMessage}`;
    }
    

    PrimaryButton löst eine \_search()-Funktion aus, die bestimmt, welche Clienttechnologie verwendet wird, um Microsoft Graph zu nutzen. Fügen Sie diese Methode am Ende der Klasse GraphConsumer hinzu:

    private _search = (event: React.MouseEvent<HTMLAnchorElement | HTMLButtonElement | HTMLDivElement | BaseButton | Button, MouseEvent>) : void => {
      console.log(this.props.clientMode);
    
      // Based on the clientMode value search users
      switch (this.props.clientMode)
      {
        case ClientMode.aad:
          this._searchWithAad();
          break;
        case ClientMode.graph:
        this._searchWithGraph();
        break;
      }
    }
    

Die DetailsList-Komponenteninstanz wird in der render()-Methode gerendert, falls die users-Eigenschaft des Komponentenstatus Elemente enthält.

Konfigurieren der API-Berechtigungsanforderungen

Damit sowohl Microsoft Graph als auch andere Drittanbieter-REST-APIs verwendet werden können, müssen Sie im Manifest der Lösung explizit deklarieren, welche Berechtigungsanforderungen aus Sicht von OAuth bestehen.

In SharePoint-Framework Version 1.4.1 oder höher können Sie dazu die webApiPermissionRequests-Eigenschaft in package-solution.json im Ordner config der Lösung konfigurieren. Im Folgenden sehen Sie einen Beispielauszug der Datei für die aktuelle Lösung.

Kopieren Sie die Deklaration der webApiPermissionRequests-Eigenschaft.

{
  "$schema": "https://developer.microsoft.com/json-schemas/spfx-build/package-solution.schema.json",
  "solution": {
    "name": "spfx-api-scopes-tutorial-client-side-solution",
    "id": "841cd609-d821-468d-a6e4-2d207b966cd8",
    "version": "1.0.0.0",
    "includeClientSideAssets": true,
    "skipFeatureDeployment": true,
    "webApiPermissionRequests": [
      {
        "resource": "Microsoft Graph",
        "scope": "User.ReadBasic.All"
      }
    ]
  },
  "paths": {
    "zippedPackage": "solution/spfx-api-scopes-tutorial.sppkg"
  }
}

Beachten Sie die webApiPermissionRequests-Eigenschaft, bei der es sich um ein Array von webApiPermissionRequest-Elementen handelt. Jedes Element definiert die resource und den scope der Berechtigungsanforderung.

Die resource kann der Name oder die Objekt-ID (in Azure AD) der Ressource sein, für die Sie die Berechtigungsanforderung konfigurieren möchten. Für Microsoft Graph lautet der Name Microsoft Graph. Die ObjectId ist nicht eindeutig und variiert je nach Mandant.

Der scope kann der Name der Berechtigung oder die eindeutige ID der Berechtigung sein. Den Berechtigungsnamen finden Sie in der API-Dokumentation. Die Berechtigungs-ID finden Sie in der API-Manifestdatei.

Hinweis

Eine Liste der Berechtigungen, die in Microsoft Graph zur Verfügung stehen, finden Sie unter Referenz zu Microsoft Graph-Berechtigungen.

Standardmäßig werden dem Dienstprinzipal keine expliziten Berechtigungen zum Zugriff auf Microsoft Graph erteilt. Wenn Sie jedoch ein Zugriffstoken für Microsoft Graph anfordern, erhalten Sie ein Token mit der user_impersonation-Berechtigung, die Sie zum Lesen von Informationen über Benutzer (User.Read.All) verwenden können. Sie können zusätzliche Berechtigungen von Mandantenadministratoren anfordern. Weitere Informationen finden Sie unter Herstellen einer Verbindung mit durch Azure AD gesicherten APIs in SharePoint-Framework-Lösungen.

Für die Suche nach Benutzern und zum Abrufen ihres displayName, ihrer mail und ihres userPrincipalName genügt die Berechtigung User.ReadBasic.All.

Wenn Sie Ihre Lösung packen und bereitstellen, müssen Sie (oder ein Administrator) die erforderlichen Berechtigungen für Ihre Lösung gewähren. Einzelheiten hierzu finden Sie unter Bereitstellen der Lösung und Gewähren von Berechtigungen.

Nutzen von Microsoft Graph

Sie können jetzt die Methoden zur Nutzung von Microsoft Graph implementieren. Sie haben zwei Möglichkeiten:

  • Verwenden des AadHttpClient-Clientobjekts
  • Verwenden des MSGraphClient-Clientobjekts

Das AadHttpClient-Clientobjekt eignet sich für die Verarbeitung einer beliebigen REST-API. Daher können Sie hiermit Microsoft Graph- oder eine beliebige andere REST-API von einem Drittanbieter (oder Erstanbieter) nutzen.

Das MSGraphClient-Clientobjekt kann nur Microsoft Graph verarbeiten. Es verwendet intern das AadHttpClient-Clientobjekt und unterstützt die Fluent-Syntax des Microsoft Graph-SDK.

Verwenden von AadHttpClient

Um eine REST-API mithilfe des AadHttpClient-Clientobjekts zu nutzen, erstellen Sie eine neue Instanz des Typs AadHttpClient, indem Sie die context.aadHttpClientFactory.getClient()-Methode aufrufen und den URI des Zieldiensts angeben.

Das erstellte Objekt stellt Methoden für die folgenden Anforderungen bereit:

  • get(): führt eine HTTP GET-Anforderung aus
  • post(): führt eine HTTP POST-Anforderung aus
  • fetch(): führt alle anderen Arten von HTTP-Anforderung aus basierend auf den angegebenen HttpClientConfiguration- und IHttpClientOptions-Argumenten.

Da alle diese Methoden das asynchrone Entwicklungsmodell von JavaScript/TypeScript unterstützen, können Sie ihre Ergebnisse mit Zusagen behandeln.

Das folgende Beispiel zeigt die \_searchWithAad()-Methode für die Beispiellösung.

private _searchWithAad = (): void => {
  // Log the current operation
  console.log("Using _searchWithAad() method");

  // Using Graph here, but any 1st or 3rd party REST API that requires Azure AD auth can be used here.
  this.props.context.aadHttpClientFactory
    .getClient("https://graph.microsoft.com")
    .then((client: AadHttpClient) => {
      // Search for the users with givenName, surname, or displayName equal to the searchFor value
      return client
        .get(
          `https://graph.microsoft.com/v1.0/users?$select=displayName,mail,userPrincipalName&$filter=(givenName%20eq%20'${escape(this.state.searchFor)}')%20or%20(surname%20eq%20'${escape(this.state.searchFor)}')%20or%20(displayName%20eq%20'${escape(this.state.searchFor)}')`,
          AadHttpClient.configurations.v1
        );
    })
    .then(response => {
      return response.json();
    })
    .then(json => {

      // Prepare the output array
      var users: Array<IUserItem> = new Array<IUserItem>();

      // Log the result in the console for testing purposes
      console.log(json);

      // Map the JSON response to the output array
      json.value.map((item: any) => {
        users.push( {
          displayName: item.displayName,
          mail: item.mail,
          userPrincipalName: item.userPrincipalName,
        });
      });

      // Update the component state accordingly to the result
      this.setState(
        {
          users: users,
        }
      );
    })
    .catch(error => {
      console.error(error);
    });
}

Die get()-Methode ruft die URL der OData-Anforderung als Eingabeargument ab. Eine erfolgreiche Anforderung gibt in der Antwort ein JSON-Objekt zurück.

Verwenden von MSGraphClient

Wenn Sie Microsoft Graph als Ziel verwenden, können Sie das MSGraphClient-Clientobjekt nutzen, das eine flüssigere Syntax bietet.

Das folgende Beispiel zeigt die Implementierung der _searchWithGraph()-Methode für die Beispiellösung.

private _searchWithGraph = () : void => {

  // Log the current operation
  console.log("Using _searchWithGraph() method");

  this.props.context.msGraphClientFactory
    .getClient()
    .then((client: MSGraphClient) => {
      // From https://github.com/microsoftgraph/msgraph-sdk-javascript sample
      client
        .api("users")
        .version("v1.0")
        .select("displayName,mail,userPrincipalName")
        .filter(`(givenName eq '${escape(this.state.searchFor)}') or (surname eq '${escape(this.state.searchFor)}') or (displayName eq '${escape(this.state.searchFor)}')`)
        .get((err, res) => {

          if (err) {
            console.error(err);
            return;
          }

          // Prepare the output array
          var users: Array<IUserItem> = new Array<IUserItem>();

          // Map the JSON response to the output array
          res.value.map((item: any) => {
            users.push( {
              displayName: item.displayName,
              mail: item.mail,
              userPrincipalName: item.userPrincipalName,
            });
          });

          // Update the component state accordingly to the result
          this.setState(
            {
              users: users,
            }
          );
        });
    });
}

Sie erhalten eine Instanz des Typs MSGraphClient, indem Sie die context.msGraphClientFactory.getClient()-Methode aufrufen.

Sie verwenden dann die Fluent-API des Microsoft Graph-SDK, um die OData-Abfrage zu definieren, die für den Microsoft Graph-Zielendpunkt ausgeführt wird.

Das Ergebnis ist eine JSON-Antwort, die Sie decodieren und dem typisierten Ergebnis zuordnen müssen.

Hinweis

Sie können einen vollständig typisierten Ansatz unter Nutzung der Microsoft Graph-TypeScript-Typen verwenden.

Bereitstellen der Lösung und Gewähren von Berechtigungen

Jetzt sind Sie bereit, die Lösung zu erstellen, zu bündeln, zu packen und bereitzustellen.

  1. Führen Sie die gulp-Befehle aus, um sicherzustellen, dass die Lösung korrekt erstellt wird.

    gulp build
    
  2. Führen Sie den folgenden Befehl aus, um die Lösung zu bündeln und zu packen.

    gulp bundle
    gulp package-solution
    
  3. Navigieren Sie zum App-Katalog Ihres Zielmandanten, und laden Sie das Lösungspaket hoch. Sie finden das Lösungspaket im Ordner sharepoint/solution der Lösung. Es ist die .sppkg-Datei. Nachdem Sie das Lösungspaket hochgeladen haben, erhalten Sie vom App-Katalog eine Eingabeaufforderung in Form eines Dialogfelds, das folgendem Screenshot ähnelt.

    Screenshot der App-Katalog-UI beim Hochladen der Paketlösung

    Eine Meldung im unteren Bereich des Bildschirms besagt, dass für das Lösungspaket Berechtigungen genehmigt werden müssen. Dies liegt an der webApiPermissionRequests-Eigenschaft in der Datei package-solution.json.

  4. Wählen Sie im modernen SharePoint Online Admin Center im linken Schnellstartmenü unter Erweitert das Menüelements API-Zugriff aus. Die Antwort sieht in etwa wie die folgende aus.

    Screenshot der Seite „WebApiPermission-Verwaltung“

    Auf dieser Seite können Sie (oder ein anderer Administrator Ihres SharePoint Online-Mandanten) alle ausstehenden Berechtigungsanforderungen genehmigen oder verweigern. Sie können nicht erkennen, welches Lösungspaket welche Berechtigung anfordert, da die Berechtigungen auf Mandantenebene und für eine eindeutige Anwendung definiert sind.

    Hinweis

    Weitere Informationen zur internen Funktionsweise der Berechtigungsbereiche auf Mandantenebene finden Sie in den Artikeln im Abschnitt Siehe auch.

  5. Wählen Sie die Berechtigung, die Sie in der Datei package-solution.json Ihrer Lösung angefordert haben, wählen die Option Zugriff genehmigen oder ablehnen und dann Genehmigen aus. Im folgenden Screenshot wird der Bereich in der Administrator-Benutzeroberfläche dargestellt.

    Screenshot der Verwaltungsseite für WebApiPermission während des Genehmigungsprozesses

Warnung

Wenn Sie bei dem Versuch, die Berechtigung zu genehmigen, eine unerwartete Ausnahme erhalten ([HTTP]:400 - [CorrelationId]), aktualisieren Sie das resource-Attribut in der Datei package-solution.json so, dass der Wert Microsoft.Azure.AgregatorService anstatt Microsoft Graph verwendet wird, wie zu einem früheren Zeitpunkt in diesem Lernprogramm angewiesen. Lehnen Sie die vorhandene Anforderung ab und aktualisieren Sie das Lösungspaket im App-Katalog mit dem aktualisierten Wert.

Testen der Lösung

  1. Führen Sie die Lösung mithilfe des folgenden gulp-Befehls aus.

    gulp serve --nobrowser
    
  2. Öffnen Sie den Browser, und navigieren Sie zur Seite mit der SharePoint-Framework Workbench, die unter der folgenden URL zu finden ist:

    https://<your-tenant>.sharepoint.com/_layouts/15/Workbench.aspx
    
  3. Fügen Sie das clientseitige Webpart GraphConsumer hinzu, konfigurieren Sie Client Mode, und suchen Sie nach Benutzern.

    Wenn Sie Ihre erste Anforderung vornehmen, wird ein Popupfenster angezeigt und anschließend wieder ausgeblendet. Das ist das Anmeldefenster von ADAL JS, das vom SharePoint-Framework intern zum Abrufen des Zugriffstokens von Azure AD mit einem internen OAuth-Fluss verwendet wird.

    Screenshot der Benutzeroberfläche der Beispielanwendung

Und das war‘s! Sie können jetzt Lösungen auf Unternehmensniveau erstellen, die REST-APIs verwenden, die mithilfe von Azure Active Directory gesichert sind.

Weitere Artikel