Umgang mit Fehlern

Diese Seite gilt für Apigee und Apigee Hybrid.

Apigee Edge-Dokumentation aufrufen

Viele Fehlerbedingungen können auftreten, während API-Proxys Anfragen von Anwendungen verarbeiten. API-Proxys können zum Beispiel bei der Kommunikation mit Back-End-Diensten Netzwerkprobleme verursachen. Anwendungen können abgelaufene Anmeldedaten enthalten, die Anfragenachrichten sind falsch formatiert usw.

Wenn ein Fehler auftritt, nachdem eine Client-App einen API-Proxy aufgerufen hat, wird eine Fehlermeldung an den Client zurückgegeben. Standardmäßig erhält der Client häufig eine kryptografische Fehlermeldung ohne Details oder Anweisungen. Wenn Sie jedoch Standardfehler durch nützlichere benutzerdefinierte Meldungen ersetzen und diese auch mit zusätzlichen HTTP-Headern erweitern möchten, müssen Sie in Apigee eine benutzerdefinierte Fehlerbehandlung einrichten.

Mit der benutzerdefinierten Fehlerbehandlung können Sie auch Funktionen wie Nachrichten-Logging hinzufügen, wenn ein Fehler auftritt.

Bevor wir über die Implementierung einer benutzerdefinierten Fehlerbehandlung in Ihre API-Proxys sprechen, sollten Sie verstehen, wie Fehler auftreten und wie API-Proxys darauf reagieren.

Videos

In den folgenden Videos erhalten Sie weitere Informationen zur Fehlerbehandlung.

Video Beschreibung
Einführung in die Fehlerbehandlung und Fehlerabläufe Weitere Informationen über die Fehlerbehandlung und was geschieht, wenn ein Fehler in einem API-Proxy auftritt.
Fehler mit Fehlerregeln behandeln Informationen zur Fehlerbehandlung mithilfe von Fehlerregeln
Benutzerdefinierte Fehler mithilfe der RaiseFault-Richtlinie auslösen Benutzerdefinierte Fehler während der API-Laufzeit mithilfe der RaiseFault-Richtlinie auslösen.
Fehlerregeln im API-Proxy und in Zielendpunkten definieren Definieren Sie Fehlerregeln im API-Proxy und den Zielendpunkten und machen Sie sich mit den Unterschieden vertraut.
Informationen zur Ausführungsreihenfolge von Fehlerregeln Die Reihenfolge der Fehlerregeln im API-Proxy und in den Zielendpunkten verstehen.
Standardfehlerregel definieren Definieren Sie eine Standardfehlerregel zur Verarbeitung allgemeiner Fehler in Ihrer API.

Fehlerursachen

Zuerst besprechen wir, wie Fehler auftreten. Wenn Sie wissen, wie Fehler auftreten, können Sie die verschiedenen Situationen planen, in denen Sie die benutzerdefinierte Fehlerbehandlung implementieren möchten.

Automatische Fehler

Ein API-Proxy gibt in den folgenden Situationen automatisch einen Fehler aus:

  • Eine Richtlinie gibt einen Fehler aus. Wenn beispielsweise ein API-Aufruf einen abgelaufenen Schlüssel sendet, löst die VerifyAPIKey-Richtlinie automatisch einen Fehler aus. Wenn die Anzahl der API-Aufrufe ein bestimmtes Limit überschreitet, löst die Kontingentrichtlinie oder SpikeArrest-Richtlinie einen Fehler aus. In der Referenz zu Richtlinienfehlern finden Sie Informationen zu den Fehlertypen, die ausgelöst werden können.
  • Im Nachrichtenfluss des API-Proxys ist ein Problem aufgetreten, z. B. ein Routingfehler.
  • Ein Back-End-Fehler ist aufgetreten, z. B. ein HTTP-Fehler aufgrund von Fehlern auf Protokollebene, TLS/SSL-Fehlern oder eines nicht verfügbaren Zieldienstes.
  • Es liegt ein Fehler auf Systemebene vor, z. B. eine Ausnahme aufgrund fehlenden Speichers.

Weitere Informationen zu diesen Fehlern finden Sie unter Fehlertoleranz.

Benutzerdefinierte Fehler

Wenn kein automatischer Fehler vorliegt, können Sie einen benutzerdefinierten Fehler ausgeben, beispielsweise wenn eine Antwort das Wort unavailable enthält oder der HTTP-Statuscode größer als 201 ist. Dazu fügen Sie eine RaiseFault-Richtlinie an der entsprechenden Stelle in einem API-Proxy-Ablauf ein.

Sie können einem API-Proxy-Ablauf eine RaiseFault-Richtlinie hinzufügen, wie jede andere Richtlinie auch. Im folgenden Beispiel für die Proxykonfiguration wird die Richtlinie Raise-Fault-1 an die TargetEndpoint-Antwort angehängt. Wenn das Wort unavailable in der Antwort des Zieldienstes vorhanden ist, wird die RaiseFault-Richtlinie ausgeführt und gibt einen Fehler aus.

<TargetEndpoint name="default">
...
  <Response>
    <Step>
      <Name>Raise-Fault-1</Name>
      <Condition>message.content Like "*unavailable*"</Condition>
    </Step>
  </Response>

Dies dient nur dazu, dass Sie benutzerdefinierte Fehler ausgeben können. Weitere Informationen zur RaiseFault-Richtlinie finden Sie im Abschnitt FaultRules und RaiseFault-Richtlinie.

Weitere Beispiele finden Sie in den Beiträgen der Apigee-Community:

Wie funktionieren API-Proxys, wenn Fehler auftreten?

Wenn ein Proxy einen Fehler ausgibt, geschieht Folgendes:

Proxy-Pipeline beenden

Wenn ein API-Proxy auf einen Fehler stößt, unabhängig davon, wie er auftritt, verlässt er die normale Ablauf-Pipeline, tritt in einen Fehlerzustand ein und gibt eine Fehlermeldung an die Client-Anwendung zurück. Sobald der API-Proxy in den Fehlerzustand tritt, kann er die Verarbeitung nicht wieder in die normale Ablauf-Pipeline zurückführen.

Angenommen, ein API-Proxy hat Richtlinien in der folgenden Reihenfolge in der ProxyEndpoint-Anfrage:

  1. Verify API Key
  2. Kontingent
  3. JSON to XML

Wenn während der API-Schlüsselüberprüfung ein Fehler auftritt, wechselt der API-Proxy in einen Fehlerzustand. Die Richtlinien "Quota" und "JSON to XML" werden nicht ausgeführt, der Proxy geht nicht über den TargetEndpoint auf und eine Fehlermeldung wird an die Client-App zurückgegeben.

Auf FaultRules prüfen

Im Fehlerzustand prüfen API-Proxys auch das Vorhandensein der folgenden Punkte (in der Reihenfolge) in der API-Proxy-Konfiguration, bevor eine Standardfehlermeldung an die Client-Anwendung zurückgegeben wird:

  1. Ein <FaultRules>-Abschnitt, der die Logik zum Auslösen benutzerdefinierter Fehlermeldungen (und anderer Richtlinien) basierend auf bestimmten von Ihnen definierten Bedingungen enthält.
  2. Der Abschnitt <DefaultFaultRule>, der in den folgenden Situationen eine Standard-Fehlermeldung auslöst:
    • Keine <FaultRules> sind definiert.
    • Keine vorhandenen <FaultRules> werden ausgeführt.
    • Das Element <AlwaysEnforce> ist auf "true" gesetzt.

Im Wesentlichen bietet der API-Proxy die Möglichkeit, eine benutzerdefinierte Fehlermeldung zurückzugeben und eine weitere Logik auszulösen. Wenn der Proxy keinen dieser Abschnitte findet oder sie da sind, aber kein benutzerdefinierter Fehler ausgelöst wurde, sendet der Proxy seine eigene von Apigee generierte Standardnachricht.

Einfaches Beispiel für die Fehlerbehandlung

Beginnen wir mit einem einfachen Beispiel, in dem ein Aufruf an einen API-Proxy keinen erforderlichen API-Schlüssel enthält. Standardmäßig wird die folgende Antwort an die Client-App zurückgegeben:

HTTP/1.1 401 Unauthorized
Date: Wed, 20 Jul 2016 19:19:32 GMT
Content-Type: application/json
Content-Length: 150
Connection: keep-alive
Server: Apigee Router

* Connection #0 to host myorg-test.apigee.net left intact
{"fault":{"faultstring":"Failed to resolve API Key variable request.queryparam.apikey","detail":{"errorcode":"steps.oauth.v2.FailedToResolveAPIKey"}}}

Ihre API-Nutzer können die Fehlermeldung möglicherweise verstehen, vielleicht aber auch nicht. Außerdem sind viele Standardfehler subtiler und schwieriger zu entziffern.

Als API-Entwickler können Sie diese Nachricht an die Anforderungen des Empfängers der iOS-App oder an eine interne Testgruppe mit eigenen Formatanforderungen für Fehlermeldungen anpassen.

Hier ist ein einfaches Beispiel dafür, wie Sie eine benutzerdefinierte Fehlermeldung erstellen, um diesen Fehler zu beheben. Dies erfordert 1) eine Richtlinie, die die benutzerdefinierte Nachricht definiert, und 2) eine FaultRule, die die Richtlinie ausführt, wenn der Proxy in einen Fehlerzustand wechselt.

1. Richtlinie erstellen, in der die benutzerdefinierte Nachricht definiert wird

Erstellen Sie zuerst eine Richtlinie, in der die benutzerdefinierte Fehlermeldung definiert wird. Sie können jede Art von Richtlinie verwenden, z. B. eine AssignMessage-Richtlinie, die eine Nutzlast und optionale HTTP-Header wie Statuscode und Begründung festlegen kann. Hierfür eignet sich die AssignMessage-Richtlinie. Sie können hier die Nachrichtennutzlast steuern, einen anderen HTTP-Statuscode festlegen, eine andere HTTP-Grundphrase festlegen und HTTP-Header hinzufügen.

Sie müssen die Richtlinie nicht an einen Ablauf anhängen. Erstellen Sie sie einfach, wie unter Richtlinie erstellen beschrieben.

Im Folgenden finden Sie ein Beispiel für AssignMessage-Richtlinie, die:

  • eine JSON-Nachricht zurückgibt
  • einen HTTP-Statuscode festlegt (911, also ein offensichtlich nicht vorhandener Statuscode, um die Flexibilität zu veranschaulichen); der Statuscode wird im HTTP-Header angezeigt
  • eine HTTP-Grundlage festlegt, um die Standardformulierung Unauthorized für diesen fehlenden API-Schlüsselfehler zu ersetzen; die Begründung wird neben dem Statuscode im HTTP-Header angezeigt
  • einen neuen HTTP-Header mit dem Namen invalidKey erstellt und befüllt
<AssignMessage async="false" continueOnError="false" enabled="true" name="invalid-key-message">
    <DisplayName>Invalid key message</DisplayName>
    <Set>
        <Payload contentType="application/json">{"Citizen":"Where's your API key? I don't see it as a query parameter"}</Payload>
        <StatusCode>911</StatusCode>
    </Set>
    <Add>
        <Headers>
            <Header name="invalidKey">Invalid API key! Call the cops!</Header>
        </Headers>
    </Add>
    <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables>
    <AssignTo createNew="false" transport="http" type="request"/>
</AssignMessage>

Wenn diese Richtlinie ausgeführt wird, sieht die Antwort an die Clientanwendung so aus. Vergleichen Sie sie mit der zuvor gezeigten Standardantwort.

HTTP/1.1 911 Rejected by API Key Emergency Services
Date: Wed, 20 Jul 2016 18:42:36 GMT
Content-Type: application/json
Content-Length: 35
Connection: keep-alive
invalidKey: Invalid API key! Call the cops!
Server: Apigee Router

* Connection #0 to host myorg-test.apigee.net left intact
{"Citizen":"Where's your API key? I don't see it as a query parameter."}

Ja, dies scheint ein bisschen albern, aber es zeigt, was möglich ist. Zumindest weiß jetzt der Entwickler, der die Nachricht erhält, dass er vergessen hat, einen API-Schlüssel als Abfrageparameter anzugeben.

Aber wie wird diese Richtlinie ausgeführt? Im nächsten Abschnitt erfahren Sie, wie das geht.

2. <FaultRule> erstellen, die die Richtlinie auslöst

In den Abschnitten <ProxyEndpoint> oder <TargetEndpoint> der Proxykonfiguration fügen Sie einen <FaultRules>-XML-Block hinzu, der einen oder mehrere einzelne <FaultRule>-Abschnitte enthält. Jede FaultRule stellt einen anderen Fehler dar, den Sie behandeln möchten. In diesem einfachen Beispiel verwenden wir nur eine FaultRule, um Ihnen zu zeigen, woraus sie besteht.

Sie sollten auch eine <DefaultFaultRule> hinzufügen, um eine benutzerdefinierte allgemeine Fehlermeldung anzugeben, wenn keine Ihrer FaultRules ausgeführt wird.

Beispiel

<ProxyEndpoint name="default">
...
    <FaultRules>
       <FaultRule name="invalid_key_rule">
            <Step>
                <Name>invalid-key-message</Name>
            </Step>
            <Condition>(fault.name = "FailedToResolveAPIKey")</Condition>
        </FaultRule>
    </FaultRules>
    <DefaultFaultRule name="default-fault">
        <Step>
            <Name>Default-message</Name>
        </Step>
    </DefaultFaultRule>

Wichtige Fakten:

  • Die FaultRules sind im ProxyEndpoint definiert. Das ist sehr wichtig. Weitere Informationen zum Einfügen von FaultRules in den ProxyEndpoint und TargetEndpoint finden Sie weiter unten.
  • <Name>: Der Name der auszuführenden Richtlinie. Dieser stammt aus dem Attribut name der Richtlinie für das übergeordnete Element, wie im Beispiel oben gezeigt.
  • <Condition>: Apigee wertet die Bedingung aus und führt die Richtlinie nur aus, wenn die Bedingung zutrifft. Wenn es mehrere FaultRules gibt, die als wahr ausgewertet werden, führt Apigee die erste zutreffende aus. (Wichtig: Die Reihenfolge, in der die FaultRules von oben nach unten oder von unten nach oben ausgewertet werden, unterscheidet sich zwischen TargetEndpoint und ProxyEndpoint, wie im Abschnitt Mehrere FaultRules und Ausführungslogik beschrieben.) Wenn Sie keine Bedingung angeben, ist die FaultRule automatisch "true". Das ist aber nicht empfehlenswert. Jede FaultRule sollte eine eigene Bedingung haben.

  • <DefaultFaultRule>: Wenn keine benutzerdefinierte FaultRule ausgeführt wird, wird <DefaultFaultRule> ausgeführt. Dabei wird eine allgemeinere benutzerdefinierte Nachricht anstelle der von Apigee generierten Standardnachricht gesendet. Eine <DefaultFaultRule> kann auch eine <Condition> haben. In den meisten Fällen hat sie jedoch keine, da Sie die Richtlinie in jeden Fall ausführen möchten, egal was passiert.

    Die DefaultFaultRule wird in der Regel verwendet, um für jeden unerwarteten Fehler eine allgemeine Fehlermeldung zurückzugeben. Ein Beispiel wäre eine Nachricht mit Kontaktdaten für technischen Support. Diese Standardantwort dient dem doppelten Zweck, Entwicklerinformationen bereitzustellen und gleichzeitig Back-End-URLs oder andere Informationen zu verschleiern, mit denen das System manipulieren werden könnten.

Mehrere FaultRules und Ausführungslogik

Im Abschnitt Beispiel für einfache Fehlerbehandlung haben wir ein einfaches Beispiel einer einzelnen FaultRule und einer Bedingung verwendet. In einem realen API-Projekt mit all den möglichen Fehlern, die auftreten können, werden Sie wahrscheinlich mehrere FaultRules und eine DefaultFaultRule sowohl in Ihrem <ProxyEndpoint> als auch in Ihrem <TargetEndpoint> haben. Letztendlich wird jedoch nur eine FaultRule ausgeführt, wenn ein API-Proxy in einen Fehlerzustand versetzt wird.

In diesem Abschnitt wird die Logik beschrieben, die Apigee bei der Verarbeitung von FaultRules verwendet, von der Ausführung einer einzelnen FaultRule bis hin zur Verarbeitung interner Schrittbedingungen beim Auslösen der FaultRule. Dieser Abschnitt enthält auch Hinweise dazu, wann FaultRules im <ProxyEndpoint> gegenüber dem <TargetEndpoint> definiert werden sollten, und beschreibt die Beziehung zwischen FaultRules und der RaiseFault-Richtlinie.

FaultRules-Ausführung

Kurz gesagt, hier ist die Logik, die Apigee verwendet, wenn ein API-Proxy in einen Fehlerzustand geht. Beachten Sie, dass es einen Unterschied zwischen FaultRules-Bewertung im ProxyEndpoint und dem TargetEndpoint gibt.

  1. Apigee wertet die FaultRules entweder im ProxyEndpoint oder TargetEndpoint aus, je nachdem, wo der Fehler aufgetreten ist:
    • ProxyEndpoint: Apigee beginnt mit der untersten <FaultRule> in der Konfigurations-XML und arbeitet sich nach oben, wobei es die <Condition> jeder <FaultRule> (die externe-Bedingung, nicht die internen <Step>-Bedingungen) auswertet.
    • TargetEndpoint: Apigee beginnt mit der obersten <FaultRule> in der XML-Konfiguration und arbeitet sich nach unten, wobei es die <Condition> jeder <FaultRule> (die externe Bedingung, nicht die internen <Step>-Bedingungen) auswertet.
  2. Führt die erste FaultRule aus, deren Bedingung "true" ist. Wenn für eine FaultRule keine Bedingung angegeben ist, gilt sie standardmäßig als "true".
    • Beim Ausführen einer FaultRule werden alle Schritte innerhalb der FaultRule in der Reihenfolge von oben nach unten in der XML-Konfiguration ausgewertet. Schritte ohne Bedingungen werden automatisch ausgeführt (die Richtlinien werden ausgeführt) und Schritte, bei denen eine <Condition> als "true" ausgewertet wird, werden ausgeführt. Als code ausgewertete Bedingungen werden nicht ausgeführt.
    • Wenn eine FaultRule ausgeführt wird, aber keine Schritte in der FaultRule ausgeführt werden, da ihre Bedingungen mit code ausgewertet werden, wird die von Apigee generierte Standardfehlermeldung an die Client-App zurückgegeben. Die <DefaultFaultRule> wird nicht ausgeführt, da Apigee bereits eine FaultRule ausgeführt hat.

  3. Wenn keine FaultRule ausgeführt wird, führt Apigee, falls vorhanden, <DefaultFaultRule> aus.

Im Folgenden finden Sie Beispiele für Inline-Kommentare.

ProxyEndpoint-Ausführung

Die Auswertung von ProxyEndpoint FaultRules ist von unten nach oben. Lesen Sie also die letzte FaultRule im folgenden Beispiel und arbeiten Sie nach oben. Sehen Sie sich die DefaultFaultRule zuletzt an.

<ProxyEndpoint name="default">
...
    <FaultRules>
<!-- 3. This FaultRule is automatically TRUE, because there's no outer
     condition. But because the FaultRule just below this got
     executed (bottom-to-top evaluation in a ProxyEndpoint), Apigee
     doesn't even evaluate this FaultRule.
     Note that it's not a best practice to have a FaultRule without 
     an outer condition, which automatically makes the FaultRule true. -->
        <FaultRule name="random-error-message">
            <Step>
                <Name>Random-fault</Name>
            </Step>
        </FaultRule>
<!-- 2. Let's say this fault is TRUE. The Quota policy threw a QuotaViolation
     error. This is the first FaultRule to be TRUE, so it's executed. 
     Now the Steps are evaluated, and for the ones whose conditions
     evaluate to TRUE, their policies are executed. Steps without
     conditions are automatically true. -->
<FaultRule name="over_quota">
            <Step>
                <Name>developer-over-quota-fault</Name>
                <Condition>(ratelimit.developer-quota-policy.exceed.count GreaterThan "0")</Condition>
            </Step>
            <Step>
                <Name>global-over-quota-fault</Name>
                <Condition>(ratelimit.global-quota-policy.exceed.count GreaterThan "0")</Condition>
            </Step>
            <Step>
                <Name>log-error-message</Name>
            </Step>
            <Condition>(fault.name = "QuotaViolation")</Condition>
        </FaultRule>
<!-- 1. Because this is the ProxyEndpoint, Apigee looks at this FaultRule
     first. But let's say this FaultRule is FALSE. A policy did not 
     throw a FailedToResolveAPIKey error. Apigee moves UP to check
     the next FaultRule. -->
        <FaultRule name="invalid_key_rule">
            <Step>
                <Name>invalid-key-message</Name>
            </Step>
            <Condition>(fault.name = "FailedToResolveAPIKey")</Condition>
        </FaultRule>
    </FaultRules>

<!-- If no <FaultRule> is executed, the <DefaultFaultRule> is executed. 
     If a FaultRule is executed, but none of its Steps are executed,
     The DefaultFaultRule is not executed (because Apigee has already
     executed its one FaultRule). -->
    <DefaultFaultRule name="default-fault">
        <Step>
            <Name>Default-message</Name>
        </Step>
    </DefaultFaultRule>

TargetEndpoint-Ausführung

Die Auswertung der TargetEndpoint FaultRules erfolgt von oben nach unten. Beginnen Sie also mit dem Lesen der ersten FaultRule im folgenden Beispiel und arbeiten Sie sich nach unten. Sehen Sie sich die DefaultFaultRule zuletzt an.

<TargetEndpoint name="default">
...
    <FaultRules>
<!-- 1. Because this is the TargetEndpoint, Apigee looks at this FaultRule
     first. Let's say this FaultRule is FALSE. 
     A policy did not throw a FailedToResolveAPIKey error. 
     Apigee moves down to the next FaultRule. -->
        <FaultRule name="invalid_key_rule">
            <Step>
                <Name>invalid-key-message</Name>
            </Step>
            <Condition>(fault.name = "FailedToResolveAPIKey")</Condition>
        </FaultRule>
<!-- 2. Let's say this fault is TRUE. The Quota policy threw a QuotaViolation
     error. This is the first FaultRule to be TRUE, so it's executed. 
     Now the Steps are evaluated, and for the ones whose conditions
     evaluate to TRUE, their policies are executed. Steps without
     conditions are automatically true. -->
        <FaultRule name="over_quota">
            <Step>
                <Name>developer-over-quota-fault</Name>
                <Condition>(ratelimit.developer-quota-policy.exceed.count GreaterThan "0")</Condition>
            </Step>
            <Step>
                <Name>global-over-quota-fault</Name>
                <Condition>(ratelimit.global-quota-policy.exceed.count GreaterThan "0")</Condition>
            </Step>
            <Step>
                <Name>log-error-message</Name>
            </Step>
            <Condition>(fault.name = "QuotaViolation")</Condition>
        </FaultRule>
<!-- 3. This FaultRule is automatically TRUE, because there's no outer
     condition. But because the FaultRule just above this got
     executed (top-to-bottom evaluation in a TargetEndpoint), Apigee
     doesn't even evaluate this FaultRule.
     Note that it's not a best practice to have a FaultRule without 
     an outer condition, which automatically makes the FaultRule true. -->
        <FaultRule name="random-error-message">
            <Step>
                <Name>Random-fault</Name>
            </Step>
        </FaultRule>
    </FaultRules>

<!-- If no <FaultRule> is executed, the <DefaultFaultRule> is executed. 
     If a FaultRule is executed, but none of its Steps are executed,
     The DefaultFaultRule is not executed (because Apigee has already
     executed its one FaultRule). -->
    <DefaultFaultRule name="default-fault">
        <Step>
            <Name>Default-message</Name>
        </Step>
    </DefaultFaultRule>

Reihenfolge der Fehlerregeln

Wie Sie im vorherigen Beispiel sehen können, ist die Reihenfolge, in der Sie Ihre FaultRules einfügen, wichtig, je nachdem, ob der Fehler im ProxyEndpoint im Vergleich zum TargetEndpoint auftritt.

Beispiel:

ProxyEndpoint-Reihenfolge TargetEndpoint-Reihenfolge

Im folgenden Beispiel wird die FaultRule 3 ausgeführt, da die Bewertung von unten nach oben erfolgt. Das bedeutet, dass FaultRules 2 und 1 nicht ausgewertet werden.

5. FaultRule 1: FALSE

4. FaultRule 2: TRUE

3. FaultRule 3: TRUE

2. FaultRule 4: FALSE

1. FaultRule 5: FALSE

Da im folgenden Beispiel die Auswertung von oben nach unten erfolgt, wird FaultRule 2 ausgeführt. Dies bedeutet, dass die FaultRule 3, 4 und 5 nicht ausgewertet werden.

1. FaultRule 1: FALSE

2. FaultRule 2: TRUE

3. FaultRule 3: TRUE

4. FaultRule 4: FALSE

5. FaultRule 5: FALSE

Aufzunehmende Richtlinien

Sie können jede Richtlinie aus einer FaultRule ausführen, indem Sie sie in Schritte einfügen. Sie können beispielsweise eine AssignMessage-Richtlinie ausführen, um eine Antwort an die Client-App zu formatieren und dann eine Nachricht mit der MessageLogging-Richtlinie zu loggen. Richtlinien werden in der Reihenfolge ausgeführt, in der Sie sie einfügen (in der XML-Datei von oben nach unten).

Fault-Regeln werden NUR im Fehlerzustand ausgelöst (über continueOnError).

Die Überschrift mag den Anschein erwecken, als würden wir uns wiederholen, aber im Hinblick auf einen Proxy-Fehler, der dazu führt, dass ein API-Proxy in einen Fehlerzustand oder besser gesagt, in keinen Fehlerzustand eintritt, ist eine besondere Nuance zu beachten: das continueOnError-Attribut einer Richtlinie.

Kurz gesagt: Ein API-Proxy wertet <FaultRules> und <DefaultFaultRule> nur aus, wenn der Proxy in einen Fehlerzustand getreten ist. Dies bedeutet, dass eine FaultRule-Bedingung auch dann nicht ausgelöst wird, wenn sich der Proxy in einem Fehlerzustand befindet.

Hier ist jedoch ein Beispiel für einen Fehler. Der Proxy ist in keinen Fehlerzustand getreten. In jeder Richtlinie können Sie ein Attribut für das übergeordnete Element mit dem Namen continueOnError festlegen. Dieses Attribut ist im Hinblick auf die Fehlerbehandlung sehr wichtig, da es bestimmt, ob der Proxy in den Fehlerzustand wechselt, wenn die Richtlinie fehlschlägt. In den meisten Fällen empfiehlt es sich, den Standardwert continueOnError="false" beizubehalten, bei dem der Proxy in den Fehlerzustand versetzt wird, wenn die Richtlinie fehlschlägt und Ihre benutzerdefinierte Fehlerbehandlung ausgelöst wird. Wenn jedoch continueOnError="true"continueOnError="true" (z. B. wenn Sie nicht möchten, dass die Proxy-Ausführung durch den Ausfall eines Service-Callouts gestoppt wird), geht der Proxy nicht in einen Fehlerzustand über, wenn diese Richtlinie fehlschlägt und der Proxy sieht sich Ihre FaultRules nicht an.

Informationen zum Logging von Fehlern bei continueOnError="true" finden Sie unter Umgang mit Richtlinienfehlern im aktuellen Ablauf.

Wo FaultRules definiert sein sollen: ProxyEndpoint oder TargetEndpoint

Wenn bei einem API-Proxy ein Fehler auftritt, tritt der Fehler entweder im <ProxyEndpoint> (Anfrage von oder an die Clientanwendung) oder im <TargetEndpoint> (Anfrage an oder vom Zieldienst) auf. Wo immer dieser Fehler auftritt, sucht Apigee nach FaultRules.

Ist beispielsweise ein Zielserver nicht verfügbar (HTTP-Statuscode 503), würde der API-Proxy in der <TargetEndpoint>-Antwort in einen Fehlerzustand gehen und der normale API-Proxy-Fluss würde nicht bis zum <ProxyEndpoint> weitergehen. Wenn Sie FaultRules nur im <ProxyEndpoint> definiert haben, wird dieser Fehler nicht behandelt.

Ein weiteres Beispiel: Wenn eine RaiseFault-Richtlinie für die <ProxyEndpoint>-Antwort einen Fehler auslöst, wird eine FaultRule im <TargetEndpoint> nicht ausgeführt.

FaultRules-Richtlinie im Vergleich zur RaiseFault-Richtlinie

Fehlerregeln und die RaiseFault-Richtlinie mögen oberflächlich betrachtet nach alternativen Wegen zur Fehlerbehandlung klingen; und in gewisser Weise stimmt das auch. Sie funktionieren aber auch zusammen. In diesem Abschnitt wird die Beziehung zwischen den beiden erläutert. Ein gutes Verständnis dieser Beziehung sollte Ihnen beim Entwerfen der Fehlerbehandlung helfen, insbesondere, wenn Sie beide verwenden möchten.

Kurz gesagt bedeutet das:

  • Fehlerregeln werden immer ausgewertet, wenn ein API-Proxy in einen Fehlerzustand wechselt.
  • Mit der RaiseFault-Richtlinie kann ein API-Proxy in einen Fehlerzustand versetzt werden, wenn sonst kein Fehler aufgetreten wäre.

    Wenn Sie z. B. einen Fehler auslösen möchten, wenn der HTTP-Statuscode in der Antwort vom Zieldienst größer als 200 ist, fügen Sie eine RaiseFault-Richtlinie in Ihren Antwortablauf ein. Dies würde in etwa so aussehen:

    <TargetEndpoint name="default">
        <PreFlow name="PreFlow">
    ...
            <Response>
                <Step>
                    <Name>Raise-Fault-1</Name>
    <!-- If the condition is true, the Raise-Fault-1 policy gets executed -->
                    <Condition>(response.status.code GreaterThan "200")</Condition>
                </Step>
            </Response>

    Die RaiseFault-Richtlinie sendet auch eine Fehlermeldung an die Client-App.

Was passiert, wenn eine RaiseFault-Richtlinie einen Fehler auslöst, durch den der Proxy in einen Fehlerzustand versetzt wird, wodurch möglicherweise eine FaultRule ausgelöst wird? Hier kann es etwas knifflig werden. Wenn die RaiseFault-Richtlinie eine Fehlermeldung zurückgibt und eine FaultRule ausgelöst und eine Fehlermeldung zurückgegeben wird, was wird dann an die Client-App zurückgegeben?

  • Da die FaultRule oder DefaultFaultRule nach der RaiseFault-Richtlinie ausgeführt wird, gewinnen die FaultRule-Antwortdaten.
  • Die Antwortdaten der RaiseFault-Richtlinie (Statuscode, Grundphase oder Nachrichtennutzlast) werden verwendet, wenn diese Daten nicht durch die FaultRule oder DefaultFaultRule eingestellt sind.
  • Wenn sowohl die RaiseFault-Richtlinie und die FaultRule HTTP-Header hinzufügen, sind beide in der Antwort enthalten. Doppelte Header-Namen erstellen einen Header mit mehreren Werten.

Hier ein Beispiel dafür, was durch eine RaiseFault-Richtlinie und eine FaultRule festgelegt wird und was an die Client-App zurückgegeben wird. Die Beispiele sind einfach und nicht als Best Practices gedacht.

Was durch eine RaiseFault-Richtlinie und eine FaultRule festgelegt wird.

Client-App empfängt:

Status Code: 468
Reason Phrase: Something happened
Payload: {"Whoa":"Sorry."}
Header:
  errorNote: woops,gremlins

<- Richtlinie für Fehlerregeln legt Folgendes fest:

Status Code: [none] 
Reason Phrase: Something happened
Payload: {"Whoa":"Sorry."}
Header:
  errorNote: gremlins

<- RaiseFault-Richtlinie legt Folgendes fest:

Status Code: 468
Reason Phrase: Can't do that
Payload: {"DOH!":"Try again."}
Header: 
  errorNote: woops

Bedingungen erstellen

Bedingungen sind der Schlüssel zur Ausführung von FaultRules. FaultRule-Bedingungen werden auf dieselbe Weise wie für andere Bedingungen in Apigee erstellt, z. B. für bedingte Abläufe oder RaiseFault-Bedingungen.

Um den Rest dieses Abschnitts im Kontext zu stellen, finden Sie hier eine Beispielfehlerregel, die eine äußere FaultRule-Bedingung und eine interne Schrittbedingung hat.

<FaultRule name="invalid_key_rule">
    <Step>
        <Name>invalid-key-message</Name>
        <Condition>oauthV2.Verify-API-Key-1.failed = true</Condition>
    </Step>
    <Condition>fault.name = "FailedToResolveAPIKey"</Condition>
</FaultRule>

Für Richtlinienfehler spezifische Variablen

Die Variablen fault.name und {policy_namespace}.{policy_name}.failed sind verfügbar, wenn eine Richtlinie einen Fehler ausgibt.

fault.name

Wenn eine Richtlinie fehlschlägt, fangen Sie den Fehler mithilfe der Variable fault.name in einer Bedingung ab. Beispiel:

<Condition>fault.name = "policy_error_name"</Condition>

Der Fehlername wird in der Standardfehlermeldung angezeigt. Im folgenden Beispiel lautet der Fehlername FailedToResolveAPIKey. In diesem Fall wird eine Ablaufvariable namens fault.name auf den Wert FailedToResolveAPIKey festgelegt.

{"fault":{"faultstring":"Failed to resolve API Key variable request.queryparam.apikey","detail":{"errorcode":"steps.oauth.v2.FailedToResolveAPIKey"}}}

Die Bedingung sieht dann so aus:

<Condition>fault.name = "FailedToResolveAPIKey"</Condition>

Eine Liste der Richtlinienfehler finden Sie in der Referenz zu Richtlinienfehlern.

{policy_namespace}.{policy_name}.failed

Die Variable *.failed ist verfügbar, wenn eine Richtlinie fehlschlägt. Im Folgenden finden Sie Beispiele für *.failed-Variablen für verschiedene Richtlinien. Informationen zu Richtlinien-Namespaces finden Sie in den Ablaufvariablen in den einzelnen Referenzthemen.

Andere verfügbare Variablen

Wenn ein API-Proxy in einen Fehlerzustand versetzt wird, sind nur die folgenden Variablen zur Verwendung verfügbar:

  • Die Variablen der Richtlinie, die fehlgeschlagen sind.
  • Die HTTP-Nachrichtenvariablen, die zum Zeitpunkt des Fehlers vorhanden sind. Wenn zum Beispiel in der Antwort ein Fehler ausgelöst wird, könnte eine FaultRule im <TargetEndpoint> HTTP-Daten response.status.code, message.content, error.content usw. verwenden, sodass der Fehler nicht mehr auftritt. Wenn eine Kontingentrichtlinie fehlschlägt, können Sie die Variable ratelimit.{quota_policy_name}.exceed.count verwenden. Mit dem Debug-Tool und der Richtlinienreferenz können Sie herausfinden, welche Variablen und HTTP-Daten verfügbar sind.

Weitere Informationen

Best Practices für die Fehlerbehandlung

Die Fehlerbehandlung ist eine wichtige Architekturaufgabe für die API-Proxy-Entwicklung. Es ist wichtig, herauszufinden, wie und wann Fehler behoben werden, welche Fehlermeldungen ausgegeben werden und wie Fehlermeldungen formatiert werden. Nachdem (oder sobald) Sie diese Punkte herausgefunden haben, können Sie mithilfe der Best Practices Ihre Fehlerbehandlung implementieren.

Im Folgenden finden Sie einige Best Practices für das Entwerfen und Erstellen von Fehlerbehandlungen:

  • In FaultRules können Sie jede Art von Richtlinie angeben. Das gängigste Muster ist die Verwendung der AssignMessage-Richtlinie, um bestimmte Elemente in der ausstehenden Fehlerantwort festzulegen. Sie können AssignMessage auch verwenden, um Variablen für andere Zwecke festzulegen, z. B. für Variablen, auf die von Logging-Richtlinien verwiesen wird, die im PostClientFlow oder in FlowHooks ausgeführt werden. Sie können auch eine Nachricht loggen, z. B. mit der MessageLogging-Richtlinie oder der ServiceCallout-Richtlinie, wenn Sie bestimmte Fehler in bestimmten Fehlerbedingungen loggen möchten.
  • Geben Sie RaiseFault-Richtlinien nicht als Schritte innerhalb einer FaultRule an. Es ist besser, AssignMessage-Richtlinien zu verwenden, um Nachrichtenelemente wie Nutzlast, Header oder Statuscode festzulegen oder zu ändern.
  • Geben Sie für jede FaultRule oder für alle außer der zuletzt ausgewerteten FaultRule eine externe <Condition> an, die als untergeordnetes Element des <FaultRule>-Elements angehängt wird. Die Ausführungsbedingung für eine FaultRule ohne angegebene explizite Bedingung wird implizit als true ausgewertet. Ein <Condition>-Element, das als untergeordnetes Element eines <Step>-Elements angehängt wird, wird nicht verwendet, um zu bestimmen, ob die Ausführungsbedingung für die FaultRule als true oder false ausgewertet wird. Die Schrittbedingungen werden erst ausgewertet, wenn Apigee die FaultRule ausführt, die sie enthalten. In einer FaultRule sind normalerweise mehrere Schritte mit AssignMessage-Richtlinien oder anderen Richtlinien mit jeweils einer Schrittbedingung enthalten.
  • Um Fehler in mehreren Richtlinien desselben Typs zu verarbeiten (z. B. mehrere Quota-Richtlinien), erstellen Sie eine FaultRule pro Richtlinienfehler, den Sie wahrscheinlich erhalten werden, und unterscheiden Sie dann zwischen separaten Fehlern mithilfe von Bedingungen, die an Schritte angehängt sind. Erstellen Sie beispielsweise eine FaultRule, um einen Fehler in den Kontigentrichtlinien zu behandeln, z. B. QuotaViolation, und eine separate FaultRule für InvalidApiKey. Informationen zu Richtlinienfehlern finden Sie in der Referenz zu Richtlinienfehlern. Wenn Sie zusätzliche Fehler entdecken, die behoben werden müssen, können Sie sie später noch einmal Ihren FaultRules-Regeln hinzufügen. Sie können iterativ ausgeführt werden, allerdings ist eine neue Proxy-Bereitstellung erforderlich. Mit diesem Ansatz können Sie den gleichen Fehlertyp ermitteln, unabhängig davon, welche Richtlinie ihn auslöst, was zu einer effizienten FaultRules-XML führt.

    Die internen Schrittbedingungen bieten Ihnen eine genauere Kontrolle. Wenn Sie z. B. sowohl das einzelne Entwicklerkontingent als auch das globale Kontingent mit zwei Richtlinien in Ihrem Anfrageablauf durchsetzen, stellen Sie die externe FaultRule-Bedingung so ein, dass sie beim QuotaViolation-Fehler ausgelöst wird (der in beiden Fällen beim Überschreiten des Kontingents ausgelöst wird). Legen Sie dann Schrittbedingungen fest, um die spezifischen exceed.count-Variablen in beiden Kontingentrichtlinien auszuwerten. Nur der relevante Fehler wird an den Client gesendet (Entwickler- oder globale Kontingentüberschreitung). Hier ein Beispiel für diese Konfiguration:

    <FaultRule name="over_quota">
      <!-- This condition catches a QuotaViolation in *any* Quota policy -->
      <Condition>fault.name = "QuotaViolation"</Condition>
      <Step>
        <Name>AM-developer-over-quota-fault</Name>
        <Condition>ratelimit.developer-quota-policy.exceed.count GreaterThan 0</Condition>
      </Step>
      <Step>
        <Name>AM-global-over-quota-fault</Name>
        <Condition>ratelimit.global-quota-policy.exceed.count GreaterThan 0</Condition>
      </Step>
    </FaultRule>

    Ein weiteres Beispiel finden Sie in dieser Diskussion zur Richtlinienfehlerbehandlung.

  • Zur Behandlung von Fehlern sollten Sie, wenn Sie eine einzelne Richtlinie eines Typs verwenden, eine einzelne Fehlerregel in Betracht ziehen, die ausgeführt wird, wenn diese eine Richtlinie fehlschlägt, und mehrere Schritte einbinden, die jedem möglichen Fehler zugeordnet sind. Dies vereinfacht die XML-Datei, indem eine einzelne FaultRule anstelle mehrerer FaultRules verwendet wird (eine für jeden Fehlertyp). Sie können beispielsweise angeben, dass verschiedene Schritte der AssignMessage-Richtlinie unter verschiedenen Bedingungen ausgeführt werden:

    <FaultRule name="raise-fault-3">
      <!-- This condition catches *any* error in the Verify-API-Key-1 policy. -->
      <Condition>oauthV2.Verify-API-Key-1.failed = "true"</Condition>
      <!-- This first step always executes, which handles errors you haven't mapped with inner conditions. -->
      <Step>
        <Name>AM-Generic-Key-Fault</Name>
      </Step>
      <Step>
        <Name>AM-API-Key-NotFound</Name>
        <Condition>fault.name = "FailedToResolveAPIKey"</Condition>
      </Step>
      <Step>
        <Name>AM-API-Key-Invalid</Name>
        <Condition>fault.name = "InvalidApiKey"</Condition>
      </Step>
    </FaultRule>
  • Fügen Sie FaultRules hinzu, bei denen die Fehler auftreten (clientseitiger <ProxyEndpoint> oder Zielseiten-<TargetEndpoint>). Fügen Sie FaultRules für jede Richtlinie hinzu, die an den einzelnen Standorten angezeigt wird.
  • Wenn Sie RaiseFault-Richtlinien zusammen mit FaultRules verwenden, koordinieren Sie die Antwortdaten, die zurückgegeben werden, wenn sowohl die RaiseFault-Richtlinie als auch eine FaultRule Daten zurückgeben. Wenn Sie beispielsweise eine RaiseFault-Richtlinie haben, die den HTTP-Statuscode festlegt, konfigurieren Sie nicht zusätzlich einen AssignMessage-Schritt innerhalb einer FaultRule, die den Statuscode zurückgesetzt. Das Schlimmste, was passieren kann, ist, dass der Standardstatuscode an die Clientanwendung zurückgegeben wird.
  • Das Element <DefaultFaultRule> ergänzt das Element <FaultRules>, um Ihnen mehr Kontrolle über die Richtlinien zu geben, die der Proxy ausführt, wenn er einen Fehlerzustand verarbeitet. Wenn Sie einen <DefaultFaultRule> angeben, wird er ausgeführt, wenn eine oder beide der folgenden Bedingungen erfüllt sind:

    • Es wurde keine andere FaultRule ausgeführt. Ein Sonderfall ist, wenn überhaupt kein <FaultRules>-Element konfiguriert ist.
    • Wenn das untergeordnete Element <AlwaysEnforce> von <DefaultFaultRule> true ist.

    Sie können auch ein <Condition>-Element in einem <DefaultFaultRule> angeben. Sie können dies tun, um die Ausführung anhand eines bestimmten Status der Anfrage oder der ausstehenden Fehlermeldung auszuschließen, z. B. wenn ein bestimmter Header vorhanden ist oder fehlt.

    Verwenden Sie einen <DefaultFaultRule> mit <AlwaysEnforce> auf truegesetzt, wenn Sie eine oder mehrere Richtlinien haben, die der Proxy immer ausführen soll, unabhängig davon, ob eine vorherige FaultRule ausgeführt wurde. Ein mögliches Szenario: Angenommen, Sie möchten in allen Fällen einen Header in die Antwort einfügen, egal ob die Proxyanfrage zu einem Fehler geführt hat oder nicht und egal ob der Fehler zuvor verarbeitet wurde oder nicht. Sie würden dann eine entsprechende AssignMessage-Richtlinie im Abschnitt <PostFlow>/<Response> anhängen und dieselbe Richtlinie im <DefaultFaultRule> mit <AlwaysEnforce> festgelegt auf true anhängen.

Muster für die zentralisierte, wiederverwendbare Fehlerbehandlung

Unter Fehlerbehandlungsmuster für Apigee-Proxys wird ein Muster für die zentrale Fehlerbehandlung ohne Codeduplizierung beschrieben.

FaultRules erstellen

Zum Hinzufügen einer FaultRule müssen Sie die XML-Konfiguration des ProxyEndpoint oder TargetEndpoint bearbeiten. Sie können die Apigee-Benutzeroberfläche verwenden, um diese Bearbeitung im Bereich Code der Ansicht Entwickeln für einen API-Proxy vorzunehmen, oder die XML-Datei bearbeiten, die den ProxyEndpunkt oder TargetEndpunkt definiert.

Wenn Sie in der Apigee-Benutzeroberfläche FaultRules erstellen, erstellen Sie zuerst die Richtlinien, die Sie ausführen möchten, und fügen Sie sie dann der FaultRule-Konfiguration hinzu. (Wenn Sie versuchen, eine FaultRule zu speichern, die auf eine noch nicht erstellte Richtlinie verweist, wird eine Fehlermeldung in der Benutzeroberfläche angezeigt.)

Richtlinien zu einer FaultRule hinzufügen

Sie können einer FaultRule eine beliebige Richtlinie hinzufügen. Normalerweise verwenden Sie jedoch die AssignMessage-Richtlinie, um eine benutzerdefinierte Antwortnachricht für eine Fehlerbedingung zu generieren. Mit AssignMessage können Sie eine HTTP-Antwort mit Nutzlast, HTTP-Statuscode, Kopfzeilen und Grund-Phrasen konfigurieren.

Das folgende Beispiel zeigt eine typische Konfiguration einer AssignMessage-Richtlinie:

<AssignMessage name="AM-Invalid-Key">
  <Set>
      <Payload contentType="text/plain">That is an error.</Payload>
      <StatusCode>401</StatusCode>
  </Set>
  <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables>
</AssignMessage>

Beachten Sie, dass kein <AssignTo>-Element angegeben ist. Das bedeutet, dass der Umgebungsnachricht zugewiesen wird, je nachdem, wo die Richtlinie angehängt ist.

Sie können diese Richtlinie jetzt in Ihrer FaultRule verwenden. Beachten Sie, wie Sie die AssignMessage-Richtlinie in der FaultRule nach Namen referenzieren:

<ProxyEndpoint name="default">
  ...
  <FaultRules>
    <FaultRule name="invalid_key_rule">
      <Step>
        <Name>AM-Invalid-Key</Name>
      </Step>
      <Condition>fault.name = "InvalidApiKey"</Condition>
    </FaultRule>
  </FaultRules>
</ProxyEndpoint>

Wenn Sie die obige Konfiguration bereitstellen, führt der API-Proxy die Zuweisungsrichtlinie AM-Invalid-Key aus, wenn eine Anwendung einen ungültigen API-Schlüssel anzeigt.

Sie können mehrere Richtlinien in einer FaultRule ausführen, wie das folgende Beispiel zeigt:

<ProxyEndpoint name="default">
  ...
  <FaultRules>
    <FaultRule name="invalid_key_rule">
      <Step>
        <Name>AM-Invalid-Key</Name>
      </Step>
      <Step>
        <Name>policy2</Name>
      </Step>
      <Step>
        <Name>policy3</Name>
      </Step>
      <Condition>fault.name = "InvalidApiKey"</Condition>
    </FaultRule>
  </FaultRules>
</ProxyEndpoint>

Die Richtlinien werden in der angegebenen Reihenfolge ausgeführt. Sie können beispielsweise die MessageLogging-Richtlinie, die ExtractVariables-Richtlinie, die AssignMessage-Richtlinie oder eine beliebige andere Richtlinie in der FaultRule verwenden. Beachten Sie, dass die Verarbeitung der FaultRule sofort beendet wird, wenn eine der folgenden Situationen eintritt:

  • Jede Richtlinie in der FaultRule verursacht einen Fehler
  • Alle Richtlinien in der FaultRule sind vom Typ RaiseFault

Benutzerdefinierte Fehlermeldung definieren, die von einer FaultRule zurückgegeben wird

Als Best Practice sollten Sie klare Fehlerantworten aus Ihren APIs definieren. Auf diese Weise bieten Sie Ihren Kunden konsistente und nützliche Informationen.

Im folgenden Beispiel für AssignMessage-Richtlinie werden die Tags <Payload> und <StatusCode> verwendet, um die benutzerdefinierte Fehlerantwort zu definieren, die an den Client zu einem InvalidApiKey-Fehler gesendet wird (siehe vorheriges FaultRules-Beispiel).

<AssignMessage name="AM-Invalid-Key">
  <Set>
    <Payload contentType="text/plain">You have attempted to access a resource without the correct authorization.
       Contact support at support@mycompany.com.</Payload>
    <StatusCode>401</StatusCode>
  </Set>
  <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables>
</AssignMessage>

Diese Antwort enthält:

  • Die Nutzlast mit der Fehlermeldung und eine E-Mail-Adresse, über die Sie den Support kontaktieren können.
  • Den in der Antwort zurückgegebene HTTP-Statuscode.
  • Die Begründung, die eine kurze Beschreibung des Fehlers darstellt.

DefaultFaultRule erstellen

Eine DefaultFaultRule agiert als Ausnahme-Handler für jeden Fehler, der nicht explizit von einer anderen FaultRule behandelt wird. Wenn die Bedingungen für alle FaultRules nicht mit dem Fehler übereinstimmen, übernimmt die DefaultFaultRule den Fehler. Aktivieren Sie die standardmäßige Fehlerbehandlung, indem Sie das <DefaultFaultRule>-Tag als untergeordnetes Element eines ProxyEndpoint oder TargetEndpoint hinzufügen.

Die folgende TargetEndpoint-Konfiguration definiert beispielsweise eine DefaultFaultRule, die eine Richtlinie namens AM-Return-Generic-Error aufruft:

<TargetEndpoint name="default">
  ...
  <FaultRules>
    ...
  </FaultRules>

  <DefaultFaultRule name="fault-rule">
    <Step>
      <Name>AM-Return-Generic-Error</Name>
    </Step>
  </DefaultFaultRule>

  <HTTPTargetConnection>
    <URL>https://mytarget.example.net</URL>
  </HTTPTargetConnection>
</TargetEndpoint>

Die DefaultFaultRule wird in der Regel verwendet, um für jeden unerwarteten Fehler eine generische Fehlermeldung zurückzugeben, z. B. eine Nachricht mit Kontaktinformationen für den technischen Support. Diese Standardantwort dient dem Zweck, entwicklerfreundliche Informationen bereitzustellen und gleichzeitig Back-End-URLs oder andere Informationen zu verschleiern, die möglicherweise das System gefährden könnten.

Sie definieren beispielsweise die folgende AssignMessage-Richtlinie, um einen allgemeinen Fehler zurückzugeben:

<AssignMessage name="AM-Return-Generic-Error">
  <Set>
    <Payload type="text/plain">SERVICE UNAVAILABLE. PLEASE CONTACT SUPPORT: support@company.com.</Payload>
  </Set>
</AssignMessage>

Fügen Sie das Element <AlwaysEnforce> in das Tag <DefaultFaultRule> ein, um die DefaultFaultRule für jeden Fehler auszuführen, auch wenn bereits eine andere FaultRule ausgeführt wurde. Die DefaultFaultRule ist immer die letzte FaultRule, die ausgeführt werden soll:

  <DefaultFaultRule name="fault-rule">
    <Step>
      <Name>AM-Return-Generic-Error</Name>
    </Step>
    <AlwaysEnforce>true</AlwaysEnforce>
  </DefaultFaultRule>

Mithilfe einer DefaultFaultRule können Sie beispielsweise die Art des auftretenden Fehlers ermitteln, wenn Sie ihn sonst nicht bestimmen können. Wenn Ihr API-Proxy beispielsweise aufgrund eines Fehlers fehlschlägt, den Sie nicht ermitteln können, können Sie die DefaultFaultRule verwenden, um die folgende AssignMessage-Richtlinie aufzurufen. Diese Richtlinie schreibt den fault.name-Wert in einen Antwortwert in den Header Unhandled-Fault:

<AssignMessage name="AM-Set-Fault-Header">
  <Set>
    <Headers>
      <Header name="Unhandled-Fault">{fault.name}</Header>
    </Headers>
  </Set>
  <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables>
</AssignMessage>

Sie können dann den Header im Debug-Tool oder in der Antwort aufrufen, um zu sehen, wodurch der Fehler verursacht wurde.

Nachrichten-Logging zu PostClientFlow hinzufügen

Der PostClientFlow ist der einzige Ablauf, der ausgeführt wird, wenn der Proxy in den Fehlerzustand wechselt. An diesen Ablauf kann nur die MessageLogging-Richtlinie angehängt werden, die ausgeführt wird, nachdem die Antwort an den Client zurückgesendet wurde. Obwohl das Anhängen der MessageLogging-Richtlinie an diesen Ablauf technisch keine Fehlerbehandlung ist, können Sie bei einem Fehler die Informationen loggen. Da sie unabhängig davon ausgeführt wird, ob der Proxy erfolgreich war oder fehlgeschlagen ist, können Sie Message Logging-Richtlinien in den PostClientFlow einfügen und so dafür sorgen, dass sie immer ausgeführt werden.

Richtlinienfehler im aktuellen Ablauf behandeln

Die bisher gezeigten Beispiele verwenden eine FaultRule auf dem ProxyEndpoint oder TargetEndpoint für die Verarbeitung von Richtlinienfehlern als Teil des Fehlerzustands. Dies liegt daran, dass der Standardwert des continueOnError-Elements einer Richtlinie false lautet. Das bedeutet, dass bei einem Fehler in einer Richtlinie die Steuerung an den Fehlerzustand weitergeleitet wird. Sobald der Fehlerzustand zurückgegeben wird, können Sie die Steuerung nicht mehr an die normale Pipeline zurückgeben. In der Regel wird irgendeine Form von Fehlermeldung an die aufrufende Anwendung zurückgegeben.

Wenn Sie jedoch das Element continueOnError für eine Richtlinie auf true setzen, bleibt die Steuerung im aktuellen Ablauf und die nächste Richtlinie in der Pipeline wird nach der Richtlinie ausgeführt, die den Fehler verursacht hat. Der Vorteil der Bearbeitung des Fehlers im aktuellen Ablauf besteht darin, dass Sie möglicherweise eine Möglichkeit haben, den Fehler zu beheben und die Verarbeitung der Anfrage abzuschließen.

Im Folgenden sehen Sie eine VerifyAPIKey-Richtlinie namens verify-api-key, wobei das continueOnError-Element auf true: gesetzt ist.

<VerifyAPIKey continueOnError="true" name="verify-api-key">
  <DisplayName>Verify API Key</DisplayName>
  <APIKey ref="request.queryparam.apikey"/>
</VerifyAPIKey>

Wenn der API-Schlüssel fehlt oder ungültig ist, setzt die VerifyAPIKey-Richtlinie die Variable oauthV2.verify-api-key.failed auf true. Die Verarbeitung wird jedoch im aktuellen Ablauf fortgesetzt.

Anschließend fügen Sie im PreFlow des ProxyEndpoint die Richtlinie "VerifyAPIKey" als Schritt hinzu:

<ProxyEndpoint name="default">
  ...
  <PreFlow name="PreFlow">
    <Request>
      <Step>
        <Name>verify-api-key</Name>
      </Step>
      <Step>
        <Name>FaultInFlow</Name>
        <Condition>oauthV2.verify-api-key.failed = "true"</Condition>
      </Step>
    </Request>
    <Response/>
  </PreFlow>      
</ProxyEndpoint>  

Beachten Sie, wie der nächste Schritt im PreFlow die Bedingung verwendet, um das Vorhandensein eines Fehlers zu testen. Wenn in der VerifyAPIKey-Richtlinie ein Fehler aufgetreten ist, wird die Richtlinie FaultInFlow ausgeführt. Andernfalls wird die Richtlinie FaultInFlow übersprungen. Die FaultInFlow-Richtlinie kann viele Aufgaben ausführen, z. B. den Fehler loggen, den Fehler beheben oder eine andere Aktion ausführen.

Fehler mithilfe der RaiseFault-Richtlinie auslösen

Sie können die RaiseFault-Richtlinie jederzeit verwenden, um einen Fehler auszulösen. Wenn eine RaiseFault-Richtlinie ausgeführt wird, beendet sie den aktuellen Ablauf und überträgt die Steuerung an den Fehlerzustand.

Eine Verwendung der BoostFault-Richtlinie ist es, eine bestimmte Bedingung zu testen, die von einer anderen Richtlinie möglicherweise nicht erkannt wird. Im obigen Beispiel haben Sie einem PreFlow-<Step>-Tag ein <Condition>-Tag hinzugefügt, das bewirkt, dass die Richtlinie FaultInFlow ausgeführt wird, wenn die Bedingung erfüllt ist. Wenn FaultInFlow eine RaiseFault-Richtlinie ist, dann geht die Steuerung in den Fehlerzustand über. Sie können auch eine RaiseFault-Richtlinie in einen Ablauf einfügen, um die FaultRules zu debuggen und zu testen.

Wenn eine RaiseFault-Richtlinie einen Fehler auslöst, können Sie die folgende FaultRule und diese Bedingung verwenden, um sie zu verarbeiten:

<FaultRule name="raisefault_rule">
  <Step>
    <Name>POLICY-NAME-HERE</Name>
  </Step>
  <Condition>fault.name = "RaiseFault"</Condition>
</FaultRule>

Beachten Sie, dass die Bedingung auf einen Fehler namens RaiseFault prüft. Die RaiseFault-Richtlinie legt immer den Wert von fault.name auf RaiseFault fest. Sie können auch benutzerdefinierte Variablen innerhalb einer RaiseFault-Richtlinie festlegen. In diesem Fall können Sie diese Variablen in den Bedingungselementen testen.

Benutzerdefinierte Behandlung von HTTP-Fehlercodes vom Zielserver

Die in den vorherigen Abschnitten gezeigten Beispiele gelten für Fehler, die von Richtlinien erstellt wurden. Sie können jedoch auch eine benutzerdefinierte Antwort auf Fehler der Transportebene erstellen, d. h. die vom Zielserver zurückgegebenen HTTP-Fehler. Konfigurieren Sie einen TargetEndpoint zur Verarbeitung von HTTP-Antwortcodes, um die Antwort von einem HTTP-Fehler zu steuern.

Standardmäßig behandelt Apigee HTTP-Antwortcodes im Bereich 1xx-3xx als Erfolg und HTTP-Antwortcodes im Bereich 4xx-5xx als Fehler. Das bedeutet, dass jede Antwort vom Back-End-Dienst mit dem HTTP-Antwortcode 4xx-5xx automatisch den Fehlerzustand aufruft und dann eine Fehlermeldung direkt an den anfordernden Client zurückgibt.

Sie können benutzerdefinierte Handler für alle HTTP-Antwortcodes erstellen. Beispielsweise möchten Sie vielleicht nicht alle HTTP-Antwortcodes im Bereich 4xx-5xx als "Fehler" behandeln, sondern nur 5xx, oder Sie möchten benutzerdefinierte Fehlermeldungen für die HTTP-Antwortcodes 400 und 500 zurückgeben.

Im nächsten Beispiel verwenden Sie das Attribut success.codes, um den TargetEndpoint so zu konfigurieren, dass die HTTP-Antwortcodes 400 und 500 zusammen mit den Standard-HTTP-Codes als Erfolg behandelt werden. Indem diese Codes als Erfolg behandelt werden, übernimmt der TargetEndpoint die Verarbeitung der Antwortnachricht, anstatt den Fehlerzustand aufzurufen:

<TargetEndpoint name="default">
  ...
  <HTTPTargetConnection>
    <Properties>
          <Property name="success.codes">1xx,2xx,3xx,400,500</Property>
    </Properties>
    <URL>http://weather.yahooapis.com</URL>
  </HTTPTargetConnection>
</TargetEndpoint>

Wie Sie in diesem Beispiel sehen, können Sie Platzhalter verwenden, um das Attribut success.codes auf einen Wertebereich festzulegen.

Wenn Sie das Attribut success.codes festlegen, werden die Standardwerte überschrieben. Wenn Sie also HTTP-Code 400 zur Liste der Standarderfolgscodes hinzufügen möchten, legen Sie dieses Attribut so fest:

<Property name="success.codes">1xx,2xx,3xx,400</Property>

Wenn Sie jedoch nur HTTP-Code 400 als Erfolgscode behandeln möchten, legen Sie das Attribut so fest:

<Property name="success.codes">400</Property>

Sie können nun benutzerdefinierte Handler für die HTTP-Antwortcodes 400 und 500 definieren, um eine benutzerdefinierte Antwortnachricht an die anfragende Anwendung zurückzugeben. Der folgende TargetEndpoint verwendet die Richtlinie ReturnError zur Verarbeitung der HTTP-Antwortcodes 400 und 500:

<TargetEndpoint name="default">
  <PreFlow name="PreFlow">
    <Request/>
    <Response>
      <Step>
        <Name>ReturnError</Name>
        <Condition>(response.status.code = 400) or (response.status.code = 500)</Condition>
      </Step>
    </Response>
  </PreFlow>

  <HTTPTargetConnection>
    <Properties>
      <Property name="success.codes">1xx,2xx,3xx,400,500</Property>
    </Properties>
    <URL>http://weather.yahooapis.com</URL>
  </HTTPTargetConnection>
</TargetEndpoint>

Bei dieser TargetEndpoint-Konfiguration verarbeitet die Richtlinie namens ReturnError die Antwort, wenn der TargetEndpoint einen HTTP-Antwortcode von 400 oder 500 meldet.

Fehlertaxonomie

API-Dienste teilen Fehler in die folgenden Kategorien und Unterkategorien auf.

Kategorie Unterkategorie Fehlername Beschreibung
Messaging Fehler, die während des Nachrichtenablaufs auftreten (ohne Richtlinienfehler)
Benutzerdefinierte Fehler {fault_name} Alle Fehler, die explizit vom API-Proxy mithilfe der RaiseFault-Richtlinie behandelt werden
Antwortcodes InternalServerError, NotFound HTTP-Fehlercodes 5xx, 4xx
Routingfehler NoRoutesMatched Fehler bei der Auswahl eines benannten TargetEndpoint für eine Anfrage
Klassifizierungsfehler NotFound Fehler, die durch einen Anfrage-URI verursacht werden, der mit keinem BasePath für eine ProxyEndpoint-Konfigurationen übereinstimmt (keine API-Proxys stimmen mit der URL in der Anfrage der Client-App überein)
Transport Fehler auf HTTP-Transportebene
Verbindung ConnectionRefused, ConnectionReset, ConnectionTimeout Fehler beim Herstellen von Verbindungen auf Netzwerk- oder Transportebene
Validierungen anfordern ContentLengthMissing, HostHeaderMissing Fehler treten bei der Semantikprüfung für jede Anfrage auf
Antwortvalidierungen Fehler treten während der Semantikprüfung für jede Antwort auf
E/A-Fehler SSLHandshakeError, ReadTimeout, ReadError, WriteTimeout, WriteError, ChunkError Lese-/Schreibfehler an Client- oder Zielendpunkten, Zeitüberschreitungen, TLS/SSL-Fehler und blockierte Fehler
System Nicht definierte Laufzeitfehler
Arbeitsspeicher OutOfMemory, GCOverLimit Speicherbezogene Fehler
Thread RogueTaskTerminated Fehler, z. B. das Beenden von Ausführungsaufgaben
Richtlinie Fehler für jeden Richtlinientyp werden in der Richtlinienreferenz definiert.

Zu einem Fehler gehört immer eine Textbeschreibung der Fehlerursache. Wenn das System einen Fehler auslöst, wird eine Reihe von Attributen ausgefüllt, um die Fehlerbehebung zu erleichtern. Ein Fehler enthält die folgenden Informationen:

  • Grund
  • Benutzerdefinierte Attribute