אתם צופים במסמכי התיעוד של Apigee Edge.
אפשר לעבור אל מסמכי התיעוד של Apigee X. מידע
יכולות להיות הרבה שגיאות כשפרוקסי של API מטפל בבקשות מאפליקציות. לדוגמה, יכול להיות שיהיו בעיות ברשת כשמתקשרים עם שירותי קצה עורפיים, שאפליקציות יציגו פרטי כניסה שתוקפם פג, שפורמט הודעות הבקשה יהיה שגוי וכו'.
כשמתרחשת שגיאה אחרי שאפליקציית לקוח קוראת ל-API Proxy, הודעת שגיאה מוחזרת ללקוח. כברירת מחדל, הלקוח מקבל הודעת שגיאה לא ברורה ללא פרטים או הנחיות. אבל אם רוצים להחליף את הודעות השגיאה שמוגדרות כברירת מחדל בהודעות מותאמות אישית שימושיות יותר, ואפילו להוסיף להן דברים כמו כותרות HTTP נוספות, צריך להגדיר טיפול מותאם אישית בשגיאות ב-Edge.
טיפול בשגיאות בהתאמה אישית מאפשר לכם גם להוסיף פונקציונליות כמו רישום הודעות ביומן בכל פעם שמתרחשת שגיאה.
לפני שנדבר על הטמעה של טיפול בשגיאות בהתאמה אישית בשרתי proxy של API, כדאי להבין איך שגיאות מתרחשות ואיך שרתי proxy של API מגיבים להן.
סרטונים
כדי לקבל מידע נוסף על טיפול בתקלות, כדאי לצפות בסרטונים הבאים.
| וידאו | תיאור |
|---|---|
| מבוא לטיפול בשגיאות ולזרימות שגיאות | מידע על טיפול בשגיאות ומה קורה כשמתרחשת שגיאה ב-API Proxy. |
| טיפול בשגיאות באמצעות כללי שגיאה | איך מטפלים בתקלות באמצעות כללי תקלות |
| העלאת תקלות מותאמות אישית באמצעות מדיניות RaiseFault | אפשר להעלות תקלות מותאמות אישית במהלך זמן הריצה של ה-API באמצעות מדיניות RaiseFault. |
| הגדרת כללי תקלות בשרת proxy ל-API ובנקודות קצה של יעד | להגדיר כללי תקלות בשרת ה-proxy ל-API ובנקודות הקצה של היעד, ולהבין את ההבדלים. |
| הסבר על סדר הביצוע של כללי תקלות | הסבר על סדר הביצוע של כללי תקלות ב-API Proxy ובנקודות הקצה של היעד. |
| הגדרת כלל ברירת מחדל | הגדרת כלל ברירת מחדל לטיפול בשגיאות כלליות ב-API. |
איך מתרחשות שגיאות
קודם נסביר איך מתרחשות שגיאות. הבנה של אופן התרחשות השגיאות עוזרת לתכנן את המצבים השונים שבהם רוצים להטמיע טיפול מותאם אישית בשגיאות.
שגיאות אוטומטיות
שרת proxy של API יציג שגיאה באופן אוטומטי במקרים הבאים:
- מדיניות מחזירה שגיאה. לדוגמה, אם קריאה ל-API שולחת מפתח שפג תוקפו, מדיניות VerifyAPIKey מעלה שגיאה באופן אוטומטי. או אם מספר הקריאות ל-API חורג ממגבלה מסוימת, מדיניות Quota או מדיניות SpikeArrest מעלות שגיאה. (בהפניה לשגיאות במדיניות מפורטים סוגי השגיאות שמדיניות יכולה להחזיר).
- יש בעיה בזרימת ההודעות של ה-API proxy, כמו שגיאת ניתוב.
- יש כשל בקצה העורפי, כמו שגיאת HTTP בגלל כשלים ברמת הפרוטוקול, שגיאות TLS/SSL או שירות יעד לא זמין.
- יש כשל ברמת המערכת, כמו חריגה של חוסר זיכרון.
מידע נוסף על השגיאות האלה מופיע בקטע טקסונומיה של תקלות במאמר הזה.
שגיאות מותאמות אישית
במקרים שבהם לא מתרחשת שגיאה אוטומטית, יכול להיות שתרצו להפעיל שגיאה מותאמת אישית. לדוגמה, אם תגובה מכילה את המילה unavailable (לא זמין), או אם קוד הסטטוס של HTTP גדול מ-201. כדי לעשות את זה, מוסיפים מדיניות RaiseFault למקום המתאים בתהליך של שרת proxy ל-API.
אפשר להוסיף מדיניות RaiseFault לזרימת API Proxy בדיוק כמו שמוסיפים כל מדיניות אחרת. בדוגמה הבאה להגדרת שרת proxy, המדיניות Raise-Fault-1 מצורפת לתגובה של TargetEndpoint. אם המילה unavailable (לא זמין) מופיעה בתשובה משירות היעד, המדיניות RaiseFault מופעלת ומוצגת שגיאה.
<TargetEndpoint name="default">
...
<Response>
<Step>
<Name>Raise-Fault-1</Name>
<Condition>(message.content Like "*unavailable*")</Condition>
</Step>
</Response>הדוגמה הזו נועדה רק להראות שאפשר להציג שגיאות בהתאמה אישית. בקטע FaultRules לעומת המדיניות RaiseFault יש פרטים נוספים על המדיניות RaiseFault.
דוגמאות נוספות זמינות בפוסטים האלה בפורומים של קהילת Apigee:
מה קורה כשמתרחשות שגיאות בשרתי proxy של API
מה קורה כשמתרחשת שגיאה בשרת proxy.
יציאה מצינור עיבוד הנתונים של שרת ה-proxy
כשמתרחשת שגיאה ב-API Proxy, לא משנה איך היא מתרחשת, הוא יוצא מצינור התהליך הרגיל, עובר למצב שגיאה ומחזיר הודעת שגיאה לאפליקציית הלקוח. אחרי ש-API Proxy עובר למצב שגיאה, הוא לא יכול להחזיר את העיבוד לצינור התהליך הרגיל.
לדוגמה, נניח שלפרוקסי API יש מדיניות בסדר הבא בבקשה של ProxyEndpoint:
- אימות מפתח API
- מכסה
- JSON ל-XML
אם מתרחשת שגיאה במהלך אימות מפתח ה-API, פרוקסי ה-API עובר למצב שגיאה. הכללים Quota ו-JSON to XML לא מופעלים, ה-proxy לא ממשיך אל TargetEndpoint, והודעת שגיאה מוחזרת לאפליקציית הלקוח.
בדיקה של FaultRules
במצב שגיאה, שרתי proxy של API בודקים גם את הנוכחות של הפריטים הבאים (לפי הסדר) בהגדרת שרת ה-proxy של ה-API לפני שהם מחזירים הודעת שגיאה שמוגדרת כברירת מחדל לאפליקציית הלקוח:
- קטע
<FaultRules>, שמכיל את הלוגיקה להפעלת הודעות שגיאה מותאמות אישית (ומדיניות אחרת) על סמך תנאים ספציפיים שאתם מגדירים. - קטע
<DefaultFaultRule>, שמפעיל הודעת שגיאה שמוגדרת כברירת מחדל במצבים הבאים:- לא הוגדרו
<FaultRules>. - לא מופעלות
<FaultRules>קיימות. - הרכיב
<AlwaysEnforce>מוגדר כ-true.
- לא הוגדרו
בעצם, פרוקסי ה-API מאפשר לכם להחזיר הודעת שגיאה מותאמת אישית ולהפעיל לוגיקה אחרת. אם ה-proxy לא מוצא את שני החלקים האלה, או שהם קיימים אבל לא הופעלה שגיאה מותאמת אישית, ה-proxy שולח הודעת ברירת מחדל משלו שנוצרה ב-Edge.
דוגמה פשוטה לטיפול בשגיאות
נתחיל עם דוגמה פשוטה, שבה קריאה ל-API proxy לא מכילה מפתח API נדרש. כברירת מחדל, התגובה שמוחזרת לאפליקציית הלקוח היא:
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"}}}
יכול להיות שהמשתמשים ב-API יצליחו להבין את הודעת השגיאה, אבל יכול להיות שלא. הרבה שגיאות שמוגדרות כברירת מחדל הן יותר מורכבות וקשה לפענח אותן.
מפתחי API צריכים לשנות את ההודעה הזו כך שתתאים לצרכים של מי שיקבל אותה בסופו של דבר, בין אם מדובר במפתח אפליקציות ל-iOS או בקבוצת בדיקות פנימית שיש לה דרישות משלה לגבי פורמט הודעות השגיאה.
הנה דוגמה בסיסית לאופן שבו יוצרים הודעת שגיאה בהתאמה אישית כדי לטפל בשגיאה הזו. כדי לעשות את זה, צריך 1) מדיניות שמגדירה את ההודעה המותאמת אישית, ו-2) FaultRule שמפעיל את המדיניות כשה-proxy עובר למצב שגיאה.
1. יצירת מדיניות שמגדירה את ההודעה המותאמת אישית
קודם כול, יוצרים מדיניות שמגדירה את הודעת השגיאה המותאמת אישית. אפשר להשתמש בכל סוג של מדיניות, כמו מדיניות AssignMessage, שיכולה להגדיר מטען ייעודי (payload) וכותרות HTTP אופציונליות כמו קוד סטטוס ומשפט סיבה. האפשרות 'הקצאת הודעה' מתאימה לכך. הוא מאפשר לכם לשלוט במטען הייעודי (payload) של ההודעה, להגדיר קוד מצב HTTP שונה, להגדיר משפט סיבה שונה של HTTP ולהוסיף כותרות HTTP.
אל תצרפו את המדיניות לזרימה כלשהי ב-API Proxy. מספיק שהוא פשוט קיים בחבילת ה-proxy. כדי לעשות את זה בכלי לעריכת שרת proxy בממשק הניהול, עוברים לכרטיסייה Develop (פיתוח), ובחלונית Navigation (ניווט) לוחצים על סמל הפלוס בסרגל Policies (מדיניות).

כך תוכלו ליצור מדיניות בלי לצרף אותה לזרימה בשרת ה-proxy של ה-API. מדיניות שלא מצורפת לאף תהליך מסומנת בסמל 'מנותק' ברשימת המדיניות, כמו שמוצג ליד מדיניות ההודעות של מפתח ה-API באיור הקודם.
הדוגמה הבאה היא של מדיניות AssignMessage ש:
- הפונקציה מחזירה הודעת JSON.
- הגדרת קוד סטטוס HTTP (911, שהוא קוד סטטוס ברור שלא קיים, רק כדי להמחיש את הגמישות שיש לכם). קוד הסטטוס מופיע בכותרת ה-HTTP.
- מגדיר משפט סיבה של HTTP (כדי להחליף את משפט הסיבה 'לא מורשה' שמוגדר כברירת מחדל לשגיאה הזו של מפתח API חסר). הסיבה מופיעה לצד קוד הסטטוס בכותרת ה-HTTP.
- יוצרת כותרת HTTP חדשה בשם
invalidKeyומאכלסת אותה.
<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> <ReasonPhrase>Rejected by API Key Emergency Services</ReasonPhrase> </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>
כשהמדיניות הזו מופעלת, התגובה לאפליקציית הלקוח תיראה כך: משווים אותה לתשובה שמופיעה כברירת מחדל שמוצגת קודם.
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."}
כן, זה קצת טיפשי, אבל זה מראה לכם מה אפשר לעשות. לפחות עכשיו המפתח שמקבל את ההודעה יודע שהוא שכח לכלול מפתח API כפרמטר של שאילתה.
אבל איך המדיניות הזו מיושמת? בקטע הבא נסביר איך עושים את זה.
2. יוצרים את הרכיב <FaultRule> שיפעיל את המדיניות
בקטעים <ProxyEndpoint> או <TargetEndpoint> בהגדרת ה-proxy, מוסיפים <FaultRules> בלוק XML שמכיל קטע <FaultRule> אחד או יותר. כל רכיב FaultRule מייצג שגיאה שונה שרוצים לטפל בה. בדוגמה הפשוטה הזו נשתמש רק ב-FaultRule אחד כדי להראות לכם ממה הוא מורכב.
כדאי גם להוסיף <DefaultFaultRule> כדי לספק הודעת שגיאה כללית מותאמת אישית אם אף אחד מהכללים FaultRule לא מופעל.
דוגמה
<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>נקודות עיקריות:
- הכללים FaultRules מוגדרים ב-ProxyEndpoint. זה חשוב. בהמשך נסביר יותר על מיקום של FaultRules ב-ProxyEndpoint לעומת TargetEndpoint.
-
<Name>– שם המדיניות להפעלה. השם מגיע מהמאפייןnameשל המדיניות ברכיב ההורה, כפי שמוצג בדוגמה למדיניות שמופיעה למעלה. -
<Condition>– Edge מעריך את התנאי ומבצע את המדיניות רק אם התנאי הוא true. אם יש כמה רכיבי FaultRule שהערך שלהם הוא true, Edge מפעיל את הראשון שהערך שלו הוא true. (חשוב: סדר ההערכה של FaultRule, מלמעלה למטה או מלמטה למעלה, שונה בין TargetEndpoint לבין ProxyEndpoint, כפי שמתואר בקטע Multiple FaultRules and execution logic). אם לא מציינים תנאי, הערך של FaultRule הוא true באופן אוטומטי. אבל זו לא שיטה מומלצת. לכל רכיב FaultRule צריך להיות תנאי משלו. -
<DefaultFaultRule>– אם לא מופעל FaultRule מותאם אישית, מופעל<DefaultFaultRule>ונשלחת הודעה מותאמת אישית כללית יותר במקום הודעת ברירת המחדל המסתורית שנוצרת על ידי Edge. A<DefaultFaultRule>יכול לכלול גם<Condition>, אבל ברוב המקרים לא תרצו לכלול אותו, כי אתם רוצים שהפעולה תתבצע בכל מקרה כמוצא אחרון.בדרך כלל משתמשים ב-DefaultFaultRule כדי להחזיר הודעת שגיאה גנרית לכל שגיאה בלתי צפויה. לדוגמה, הודעה שמכילה פרטים ליצירת קשר עם תמיכה טכנית. תשובת ברירת המחדל הזו משמשת למטרה כפולה: היא מספקת מידע ידידותי למפתחים, וגם מסתירה כתובות URL של קצה עורפי או מידע אחר שאפשר להשתמש בו כדי לפגוע במערכת.
כללי FaultRule מרובים ולוגיקת ביצוע
בקטע דוגמה פשוטה לטיפול בשגיאות השתמשנו בדוגמה פשוטה של תנאי ו-FaultRule יחידים. בפרויקט API בעולם האמיתי, עם כל השגיאות האפשריות שיכולות להתרחש, סביר להניח שיהיו לכם כמה רכיבי FaultRule ורכיב DefaultFaultRule גם ב-<ProxyEndpoint> וגם ב-<TargetEndpoint>. בסופו של דבר, רק כלל FaultRule אחד מופעל כשמתרחשת שגיאה ב-API proxy.
בקטע הזה מתואר הלוגיקה שבה Edge משתמש בטיפול ב-FaultRules, החל מהאופן שבו הוא מגיע ל-FaultRule יחיד לביצוע ועד לאופן שבו מטופלים תנאי Step 'פנימיים' כשמופעל FaultRule שלהם. בקטע הזה יש גם הנחיות לגבי המקרים שבהם כדאי להגדיר FaultRules ב-<ProxyEndpoint> לעומת <TargetEndpoint>, ומוסבר הקשר בין FaultRules לבין המדיניות RaiseFault.
ביצוע של FaultRules
בקצרה, הנה הלוגיקה שבה Edge משתמש כששרת proxy של API עובר למצב שגיאה. שימו לב שיש הבדל קל בין ההערכה של FaultRules ב-ProxyEndpoint לבין ההערכה ב-TargetEndpoint.
- Edge מעריך את FaultRules ב-ProxyEndpoint או ב-TargetEndpoint, בהתאם למיקום שבו השגיאה התרחשה:
- ProxyEndpoint – Edge מתחיל עם התחתון
<FaultRule>ב-XML של ההגדרה, וממשיך כלפי מעלה, תוך הערכה של<Condition>בכל<FaultRule>(התנאי 'החיצוני', לא התנאים 'הפנימיים'<Step>). - TargetEndpoint – Edge מתחיל עם החלק העליון
<FaultRule>ב-XML של ההגדרה, וממשיך למטה, תוך הערכת<Condition>של כל<FaultRule>(התנאי "החיצוני", לא התנאים "הפנימיים"<Step>).
- ProxyEndpoint – Edge מתחיל עם התחתון
- מבצעת את first FaultRule שהתנאי שלה הוא true. אם ל-FaultRule אין תנאי, ברירת המחדל היא true.
- כשמפעילים FaultRule, כל השלבים בתוך FaultRule מוערכים לפי הסדר, מלמעלה למטה בהגדרת ה-XML. שלבים ללא תנאים מבוצעים באופן אוטומטי (המדיניות מופעלת), ושלבים עם תנאי
<Condition>שמקבל את הערך true מבוצעים (תנאים שמקבלים את הערך false לא מבוצעים). -
אם מופעל FaultRule, אבל לא מופעלים Steps ב-FaultRule (כי התנאים שלהם מוערכים כ-false), הודעת השגיאה שמוגדרת כברירת מחדל שנוצרת על ידי Edge מוחזרת לאפליקציית הלקוח. התג
<DefaultFaultRule>לא מופעל, כי Edge כבר הפעיל את ה-FaultRule שלו.
- כשמפעילים FaultRule, כל השלבים בתוך FaultRule מוערכים לפי הסדר, מלמעלה למטה בהגדרת ה-XML. שלבים ללא תנאים מבוצעים באופן אוטומטי (המדיניות מופעלת), ושלבים עם תנאי
- אם אף FaultRule לא מופעל, Edge מפעיל את
<DefaultFaultRule>, אם הוא קיים.
בהמשך מופיעות דוגמאות עם הערות מוטבעות.
ביצוע של ProxyEndpoint
ההערכה של ProxyEndpoint FaultRules מתבצעת מלמטה למעלה, לכן כדאי להתחיל לקרוא את FaultRule האחרון בדוגמה הבאה ולעבור למעלה. כדאי לבדוק את DefaultFaultRule בסוף.
<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), Edge
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, Edge looks at this FaultRule
first. But let's say this FaultRule is FALSE. A policy did not
throw a FailedToResolveAPIKey error. Edge 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 Edge has already
executed its one FaultRule). -->
<DefaultFaultRule name="default-fault">
<Step>
<Name>Default-message</Name>
</Step>
</DefaultFaultRule>ביצוע של TargetEndpoint
ההערכה של FaultRules ב-TargetEndpoint מתבצעת מלמעלה למטה, לכן כדאי להתחיל לקרוא את ה-FaultRule הראשון בדוגמה הבאה ולעבור למטה. כדאי לבדוק את DefaultFaultRule בסוף.
<TargetEndpoint name="default">
...
<FaultRules>
<!-- 1. Because this is the TargetEndpoint, Edge looks at this FaultRule
first. Let's say this FaultRule is FALSE.
A policy did not throw a FailedToResolveAPIKey error.
Edge 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), Edge
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 Edge has already
executed its one FaultRule). -->
<DefaultFaultRule name="default-fault">
<Step>
<Name>Default-message</Name>
</Step>
</DefaultFaultRule>סדר כללי התקלה
כפי שאפשר לראות בדוגמה הקודמת, הסדר שבו מציבים את רכיבי FaultRule חשוב, בהתאם לשאלה אם השגיאה מתרחשת ב-ProxyEndpoint או ב-TargetEndpoint.
לדוגמה:
| סדר של ProxyEndpoint | סדר של TargetEndpoint |
|---|---|
|
בדוגמה הבאה, מכיוון שההערכה מתבצעת מלמטה למעלה, מופעלת FaultRule 3, מה שאומר שלא מתבצעת הערכה של FaultRules 2 ו-1. 5. FaultRule 1: FALSE 4. FaultRule 2: TRUE 3. FaultRule 3: TRUE 2. FaultRule 4: FALSE 1. FaultRule: 5 FALSE |
בדוגמה הבאה, מכיוון שההערכה מתבצעת מלמעלה למטה, מופעלת FaultRule 2, מה שאומר שהמערכת לא מעריכה את FaultRule 3, 4 ו-5. 1. FaultRule 1: FALSE 2. FaultRule 2: TRUE 3. FaultRule 3: TRUE 4. FaultRule 4: FALSE 5. FaultRule: 5 FALSE |
כללי המדיניות שצריך לכלול
אפשר להריץ כל מדיניות מ-FaultRule על ידי הוספתה ל-Steps. לדוגמה, אפשר להפעיל מדיניות AssignMessage כדי לעצב תגובה לאפליקציית הלקוח, ואז לרשום הודעה ביומן באמצעות מדיניות MessageLogging. המדיניות מופעלת לפי הסדר שבו היא מופיעה (מלמעלה למטה בקובץ ה-XML).
כללי תקלות מופעלים רק במצב שגיאה (מידע על continueOnError)
יכול להיות שהכותרת הזו נראית כמו חזרה על דברים שכבר נאמרו, אבל יש ניואנס ספציפי שחשוב להכיר בנוגע לשגיאת proxy שגורמת ל-API proxy להיכנס למצב שגיאה – או ליתר דיוק, לא להיכנס למצב שגיאה: המאפיין continueOnError במדיניות.
לסיכום: שרת proxy של API בודק את <FaultRules> ואת <DefaultFaultRule> רק אם ה-proxy נכנס למצב שגיאה. כלומר, גם אם תנאי של FaultRule מחזיר את הערך true, הוא לא יופעל אם ה-proxy לא נמצא במצב שגיאה.
עם זאת, הנה דוגמה לשגיאה שמתרחשת והפרוקסי לא נכנס למצב שגיאה. בכל מדיניות אפשר להגדיר מאפיין ברכיב ההורה שנקרא continueOnError.
המאפיין הזה חשוב מאוד בכל הנוגע לטיפול בשגיאות, כי הוא קובע אם ה-proxy נכנס למצב שגיאה אם המדיניות נכשלת. ברוב המקרים, כדאי להשאיר את ברירת המחדל continueOnError="false", שגורמת לכך שה-proxy עובר למצב שגיאה אם המדיניות נכשלת, והטיפול בשגיאות המותאם אישית מופעל. עם זאת, אם continueOnError="true" (לדוגמה, אם אתם לא רוצים שכישלון של Service Callout יגרום להפסקת הביצוע של ה-proxy), ה-proxy לא יעבור למצב שגיאה אם המדיניות הזו תיכשל, וה-proxy לא יבדוק את FaultRules.
מידע על רישום שגיאות ביומן כשמשתמשים ב-continueOnError="true" זמין במאמר טיפול בשגיאות מדיניות בתהליך הנוכחי.
איפה להגדיר FaultRules: ProxyEndpoint או TargetEndpoint
כשמתרחשת שגיאה ב-API proxy, השגיאה מתרחשת ב-<ProxyEndpoint> (בקשה מאפליקציית לקוח או תגובה לאפליקציית לקוח) או ב-<TargetEndpoint> (בקשה לשירות היעד או תגובה משירות היעד). בכל מקום שבו השגיאה הזו מתרחשת, Edge מחפש את FaultRules.
לדוגמה, אם שרת היעד לא זמין (קוד סטטוס HTTP 503), פרוקסי ה-API יעבור למצב שגיאה בתגובה <TargetEndpoint>, והזרימה הרגילה של פרוקסי ה-API לא תמשיך אל <ProxyEndpoint>. אם הגדרתם FaultRules רק ב-<ProxyEndpoint>, הן לא יטפלו בשגיאה הזו.
דוגמה נוספת: אם מדיניות RaiseFault בתגובה <ProxyEndpoint> מפעילה שגיאה, לא תתבצע הפעלה של FaultRule ב-<TargetEndpoint>.
ההבדל בין FaultRules לבין המדיניות RaiseFault
יכול להיות שכללי תקלות ומדיניות RaiseFault נשמעים כמו דרכים חלופיות לטיפול בתקלות, ובמובנים מסוימים זה נכון. אבל הם גם פועלים יחד. בסעיף הזה מוסבר הקשר בין השניים. הבנת הקשר הזה תעזור לכם לתכנן את הטיפול בשגיאות, במיוחד אם אתם רוצים להשתמש בשניהם.
בקצרה:
- כללי תקלות נבדקים תמיד כשמתרחשת שגיאה בשרת proxy של API.
-
המדיניות RaiseFault מאפשרת להעביר שרת proxy של API למצב שגיאה כששגיאה לא הייתה מתרחשת אחרת.
לדוגמה, אם רוצים להציג שגיאה אם קוד הסטטוס של HTTP בתגובה משירות היעד גדול מ-200, מוסיפים מדיניות RaiseFault לזרימת התגובה. כתוב האתר שלך תיראה כך:
<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>המדיניות RaiseFault שולחת גם הודעת שגיאה לאפליקציית הלקוח.
מה קורה כשמדיניות RaiseFault מפעילה שגיאה, שמעבירה את ה-proxy למצב שגיאה, שעלול להפעיל FaultRule? כאן הדברים יכולים להיות קצת מסובכים. אם מדיניות RaiseFault מחזירה הודעת שגיאה ומופעל FaultRule ומחזירה הודעת שגיאה, מה מוחזר לאפליקציית הלקוח?
- מכיוון שהכלל FaultRule או DefaultFaultRule מופעלים אחרי המדיניות RaiseFault, נתוני התגובה של FaultRule הם אלה שקובעים.
- הנתונים של התגובה של מדיניות RaiseFault (קוד סטטוס, צירוף מילים לתיאור הסיבה או מטען ייעודי של הודעה) משמשים אם הנתונים האלה לא מוגדרים על ידי FaultRule או DefaultFaultRule.
- אם גם מדיניות RaiseFault וגם FaultRule מוסיפות כותרות HTTP מותאמות אישית, שתיהן נכללות בתגובה. שמות כפולים של כותרות יוצרים כותרת עם כמה ערכים.
בדוגמה הבאה אפשר לראות מה מוגדר על ידי מדיניות RaiseFault ו-FaultRule, ומה מוחזר לאפליקציית הלקוח. הדוגמאות נועדו להיות תמציתיות, ולא להציג שיטות מומלצות.
|
|
||
|
אפליקציית הלקוח מקבלת: Status Code: 468 Reason Phrase: Something happened Payload: {"Whoa":"Sorry."} Header: errorNote: woops,gremlins |
<- Fault rules policy sets this: Status Code: [none] Reason Phrase: Something happened Payload: {"Whoa":"Sorry."} Header: errorNote: gremlins |
<- מדיניות RaiseFault מגדירה את הערך הזה: Status Code: 468
Reason Phrase: Can't do that
Payload: {"DOH!":"Try again."}
Header:
errorNote: woops
|
יצירת תנאים
התנאים הם המפתח להפעלת FaultRule. יוצרים תנאים של FaultRule באותו אופן שבו יוצרים תנאים אחרים ב-Edge, כמו תנאים של זרימות מותנות או תנאים של RaiseFault.
כדי להבין את שאר החלק הזה, הנה דוגמה לכלל שגיאה עם תנאי FaultRule חיצוני ותנאי Step פנימי.
<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>משתנים ספציפיים לשגיאות במדיניות
המשתנים fault.name ו-{policy_namespace}.{policy_name}.failed זמינים כשמדיניות מחזירה שגיאה.
fault.name
אם מדיניות נכשלת, אפשר לזהות את השגיאה בתנאי באמצעות המשתנה fault.name. לדוגמה:
<Condition>(fault.name = "policy_error_name")</Condition>
שם השגיאה מופיע בהודעת השגיאה שמוגדרת כברירת מחדל. לדוגמה, בשגיאה הבאה, השם הוא FailedToResolveAPIKey. במקרה הזה, משתנה של זרימת נתונים בשם fault.name מוגדר לערך FailedToResolveAPIKey.
{"fault":{"faultstring":"Failed to resolve API Key variable request.queryparam.apikey","detail":{"errorcode":"steps.oauth.v2.FailedToResolveAPIKey"}}}
התנאי ייראה כך:
<Condition>(fault.name = "FailedToResolveAPIKey")</Condition>
רשימת שגיאות שקשורות למדיניות זמינה בדף העזר בנושא שגיאות שקשורות למדיניות.
{policy_namespace}.{policy_name}.failed
המשתנה *.failed זמין כשהמדיניות נכשלת. בהמשך מופיעות דוגמאות למשתני *.failed עבור מדיניות שונה.
לגבי מרחבי שמות של מדיניות, אפשר לעיין במשתני ה-Flow בכל נושא של הפניה למדיניות.
- RaiseFault policy:
raisefault.failed(זהה לכל כללי RaiseFault) - מדיניות VerifyAPIKey:
oauthV2.{policy_name}.failed, לדוגמה,oauthV2.Verify-API-Key-1.failed - מדיניות בנושא מכסות ומדיניות בנושא מניעת עליות פתאומיות בתנועה:
ratelimit.{policy_name}.failed, לדוגמה,ratelimit.Quota-1.failed
משתנים זמינים אחרים
כששרת Proxy של API עובר למצב שגיאה, המשתנים היחידים שזמינים לשימוש בתנאים הם:
- המשתנים של המדיניות שנכשלה.
- משתני הודעת ה-HTTP שקיימים בנקודת הכשל. לדוגמה, אם מוצגת שגיאה בתגובה, FaultRule ב-
<TargetEndpoint>יכול להשתמש בנתוני HTTPresponse.status.code,message.content,error.contentוכן הלאה. או אם מדיניות מכסת השימוש נכשלה, אפשר להשתמש במשתנהratelimit.{quota_policy_name}.exceed.count. כדי להבין אילו משתנים ונתוני HTTP זמינים, אפשר להשתמש בכלי המעקב ובנושאי העזרה בנושא מדיניות.
מידע נוסף
-
תנאים: הפניה לתנאים ומשתני Flow ותנאים
- שגיאות: המשמעות של שגיאות מדיניות
- משתנים: הפניה למשתנים, ודפי הפניה למדיניות ספציפית שבהם מפורטים המשתנים שזמינים בכל מדיניות.
שיטות מומלצות לטיפול בתקלות
טיפול בתקלות הוא משימה חשובה בתכנון הארכיטקטורה של פיתוח שרתי proxy של API. חשוב להקדיש זמן כדי להבין איך ומתי לטפל בשגיאות, לקבוע מה יהיה כתוב בהודעות השגיאה ולעצב את הפורמטים של הודעות השגיאה. אחרי (או תוך כדי) שתבינו את הדברים האלה, תוכלו להשתמש בשיטות המומלצות האלה כדי ליישם את הטיפול בשגיאות.
ריכזנו כאן כמה שיטות מומלצות לעיצוב ולבנייה של טיפול בשגיאות:
- לכל FaultRule, צריך לספק תג
<Condition>חיצוני (באותה רמה כמו התג<Step>). כללי תקלות ללא תנאי חיצוני מוערכים אוטומטית כ-true. תנאי שלב מסוג Inner לא משמשים כדי לקבוע אם FaultRule הוא true או false. תנאי השלב מוערכים רק אחרי ש-Edge מפעיל את FaultRule שמכיל אותם. ב-FaultRule, בדרך כלל יש כמה רכיבי Step עם מדיניות Assign Message (או מדיניות אחרת), כל אחד עם תנאי Step. -
כדי לטפל בשגיאות בכמה מדיניות מאותו סוג (למשל, כמה מדיניות של Quota), צריך ליצור FaultRule אחד לכל שגיאת מדיניות שסביר שתקבלו. לדוגמה, צריך ליצור FaultRule לכל שגיאה סבירה במדיניות בנושא מכסות, כמו
QuotaViolation,InvalidMessageWeightו-StartTimeNotSupported. (מידע על שגיאות שקשורות למדיניות זמין בדף העזר בנושא שגיאות שקשורות למדיניות). אם תגלו שגיאות נוספות שצריך לטפל בהן, תוכלו לחזור מאוחר יותר ולהוסיף אותן ל-FaultRules. אפשר לבצע שינויים חוזרים, אבל צריך לפרוס מחדש את ה-proxy.) הגישה הזו מאפשרת לכם לזהות את אותו סוג שגיאה בלי קשר למדיניות שגרמה לה, וכך קובץ ה-XML של FaultRules יהיה יעיל.אחר כך אפשר להשתמש בתנאים פנימיים של שלבים אם רוצים שליטה מדויקת יותר בשגיאות. לדוגמה, אם אתם אוכפים גם מכסה לכל מפתח וגם מכסה גלובלית באמצעות שתי מדיניות בזרימת הבקשות, צריך להגדיר את התנאי של FaultRule החיצוני כך שיופעל בשגיאה
QuotaViolation(שמוחזרת כשחורגים מהמכסה בכל אחד מהמקרים). לאחר מכן, מגדירים תנאים לשלב כדי להעריך את המשתניםexceed.countבשתי מדיניות המכסות. רק השגיאה הרלוונטית נשלחת ללקוח (חריגה ממכסת המפתחים או חריגה ממכסה גלובלית). דוגמה להגדרה כזו:<FaultRule name="over_quota"> <!-- This condition catches a QuotaViolation in *any* Quota policy --> <Condition>(fault.name = "QuotaViolation")</Condition> <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> </FaultRule>דוגמה נוספת אפשר לראות בשרשור הזה בפורום הקהילה של Apigee.
-
כדי לטפל בשגיאות כשמשתמשים במדיניות יחידה מסוג מסוים, אפשר להשתמש בכלל יחיד לטיפול בשגיאות שמופעל כשהמדיניות הזו נכשלת, ולכלול בו כמה שלבים שמתאימים לכל שגיאה אפשרית. כך קובץ ה-XML נשאר יעיל כי משתמשים ב-FaultRule אחד במקום בכמה FaultRule (אחד לכל סוג שגיאה). לדוגמה:
<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>Generic-Key-Fault</Name> </Step> <Step> <Name>Assign-Message-Raise-Fault-1</Name> <Condition>(fault.name = "FailedToResolveAPIKey")</Condition> </Step> <Step> <Name>Assign-Message-Raise-Fault-2</Name> <Condition>(fault.name = "InvalidApiKey")</Condition> </Step> </FaultRule> - מוסיפים FaultRules במקומות שבהם השגיאות יתרחשו (בצד הלקוח
<ProxyEndpoint>או בצד היעד<TargetEndpoint>). כוללים FaultRules לכל מדיניות שמופיעה בכל מיקום. - ב-FaultRules, אפשר להפעיל כל סוג של מדיניות שיכולה להחזיר הודעה לאפליקציית הלקוח. מדיניות AssignMessage היא אידיאלית למטרה הזו. כדאי גם לשקול לרשום הודעה באמצעות המדיניות MessageLogging אם רוצים לעקוב אחרי שגיאות.
- כשמשתמשים במדיניות RaiseFault בשילוב עם FaultRules, צריך לתאם את נתוני התגובה שנשלחים בחזרה כשגם מדיניות RaiseFault וגם FaultRule מחזירות נתונים. לדוגמה, אם מדיניות RaiseFault מאפסת את קוד הסטטוס HTTP, אל תאפסו את קוד הסטטוס באמצעות FaultRule. התרחיש הכי גרוע הוא שקוד הסטטוס שמוגדר כברירת מחדל יוחזר לאפליקציית הלקוח.
-
<DefaultFaultRule>execution:- אם רוצים ש-
<DefaultFaultRule>תמיד יופעל כשלא מופעל אף FaultRule אחר, לא כוללים בו<Condition>. - אם רוצים ש-
<DefaultFaultRule>תמיד יופעל גם כש-FaultRule אחר הופעל, מוסיפים את רכיב הצאצא<AlwaysEnforce>true</AlwaysEnforce>.
- אם רוצים ש-
תבנית לטיפול מרכזי בשגיאות שאפשר לעשות בו שימוש חוזר
בפוסט הבא בקהילת Apigee מתואר דפוס לטיפול מרכזי בשגיאות ללא שכפול קוד:
דפוס לטיפול בשגיאות בשרתי proxy של Apigee
יצירת רכיבי FaultRule
כדי להוסיף FaultRule, צריך לערוך את הגדרת ה-XML של ProxyEndpoint או TargetEndpoint. אפשר להשתמש בממשק המשתמש של Edge כדי לבצע את העריכה הזו בחלונית Code בתצוגה Develop של שרת proxy של API, או לערוך את קובץ ה-XML שמגדיר את ProxyEndpoint או TargetEndpoint.
אם יוצרים FaultRules בממשק המשתמש לניהול, קודם יוצרים את כללי המדיניות שרוצים להפעיל, ואז מוסיפים אותם להגדרות של FaultRule. (אם תנסו לשמור FaultRule שמפנה למדיניות שעדיין לא נוצרה, תופיע שגיאה בממשק המשתמש).
הוספת מדיניות ל-FaultRule
אפשר להוסיף כל מדיניות ל-FaultRule, אבל בדרך כלל משתמשים במדיניות AssignMessage כדי ליצור הודעת תגובה מותאמת אישית למצב שגיאה. האלמנט AssignMessage מאפשר לכם להגדיר תגובת HTTP עם מטען ייעודי (payload), קוד סטטוס HTTP, כותרות וביטוי לציון הסיבה.
בדוגמה הבאה מוצגת הגדרה אופיינית של מדיניות AssignMessage:
<AssignMessage name="fault_invalidkey"> <Set> <Payload contentType="text/plain">Contact support at support@mycompany.com.</Payload> <StatusCode>401</StatusCode> <ReasonPhrase>Unauthorized</ReasonPhrase> </Set> <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables> </AssignMessage>
עכשיו אפשר להשתמש במדיניות הזו ב-FaultRule. שימו לב לאופן שבו אתם מפנים למדיניות AssignMessage לפי שם ב-FaultRule:
<ProxyEndpoint name="default">
...
<FaultRules>
<FaultRule name="invalid_key_rule">
<Step>
<Name>fault_invalidkey</Name>
</Step>
<Condition>(fault.name = "InvalidApiKey")</Condition>
</FaultRule>
</FaultRules>
</ProxyEndpoint>כשפורסים את ההגדרה שלמעלה, שרת ה-proxy של ה-API יפעיל את מדיניות AssignMessage שנקראת fault_invalidkey בכל פעם שאפליקציה מציגה מפתח API לא תקין.
אפשר להפעיל כמה כללי מדיניות ב-FaultRule, כמו בדוגמה הבאה:
<ProxyEndpoint name="default">
...
<FaultRules>
<FaultRule name="invalid_key_rule">
<Step>
<Name>policy1</Name>
</Step>
<Step>
<Name>policy2</Name>
</Step>
<Step>
<Name>policy3</Name>
</Step>
<Condition>(fault.name = "InvalidApiKey")</Condition>
</FaultRule>
</FaultRules>
</ProxyEndpoint>הפעלת כללי המדיניות מתבצעת לפי הסדר שמוגדר. לדוגמה, אפשר להשתמש במדיניות MessageLogging, במדיניות ExtractVariables, במדיניות AssignMessage או בכל מדיניות אחרת ב-FaultRule. שימו לב: העיבוד של FaultRule נעצר באופן מיידי אם מתרחש אחד מהמצבים הבאים:
- כל מדיניות ב-FaultRule גורמת לשגיאה
- אחד מכללי המדיניות ב-FaultRule הוא מסוג RaiseFault
הגדרת הודעת השגיאה המותאמת אישית שמוחזרת מ-FaultRule
מומלץ להגדיר תגובות ברורות לשגיאות מממשקי ה-API. כך תוכלו לספק ללקוחות מידע עקבי ומועיל.
בדוגמה הבאה של מדיניות AssignMessage נעשה שימוש בתגים <Payload>, <StatusCode> ו-<ReasonPhase> כדי להגדיר את תגובת השגיאה המותאמת אישית שנשלחת בחזרה ללקוח בשגיאה InvalidApiKey (ראו את הדוגמה הקודמת של FaultRules).
<AssignMessage name="fault_invalidkey"> <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> <ReasonPhrase>Unauthorized</ReasonPhrase> </Set> <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables> </AssignMessage>
התשובה הזו כוללת:
- מטען ייעודי (payload) שמכיל את הודעת השגיאה וכתובת אימייל ליצירת קשר עם התמיכה.
- קוד הסטטוס של HTTP שמוחזר בתגובה.
- הסיבה, שהיא תיאור קצר של השגיאה.
יצירת DefaultFaultRule
DefaultFaultRule פועל כרכיב handler של חריגים לכל שגיאה שלא מטופלת באופן מפורש על ידי FaultRule אחר. אם התנאים של כל כללי FaultRule לא תואמים לשגיאה, השגיאה מטופלת על ידי DefaultFaultRule. כדי להפעיל טיפול בשגיאות שמוגדר כברירת מחדל, מוסיפים את התג <DefaultFaultRule> כרכיב צאצא של ProxyEndpoint או TargetEndpoint.
לדוגמה, בהגדרת TargetEndpoint שלמטה מוגדר DefaultFaultRule שמפעיל מדיניות בשם ReturnGenericError:
<TargetEndpoint name="default">
...
<FaultRules>
...
</FaultRules>
<DefaultFaultRule name="fault-rule">
<Step>
<Name>ReturnGenericError</Name>
</Step>
</DefaultFaultRule>
<HTTPTargetConnection>
<URL>http://mocktarget.apigee.net</URL>
</HTTPTargetConnection>
</TargetEndpoint>בדרך כלל משתמשים ב-DefaultFaultRule כדי להחזיר הודעת שגיאה גנרית לכל שגיאה לא צפויה, כמו הודעה שמכילה פרטי קשר לתמיכה טכנית. תגובת ברירת המחדל הזו משרתת שתי מטרות: היא מספקת מידע שנוח למפתחים להשתמש בו, וגם מסתירה כתובות URL של קצה עורפי או מידע אחר שאפשר להשתמש בו כדי לפגוע במערכת.
לדוגמה, מגדירים את מדיניות AssignMessage הבאה כדי להחזיר שגיאה כללית:
<AssignMessage name="ReturnGenericError"> <Set> <Payload type="text/plain">SERVICE UNAVAILABLE. PLEASE CONTACT SUPPORT: support@company.com.</Payload> </Set> </AssignMessage>
כדי להפעיל את DefaultFaultRule לכל שגיאה, גם אם כבר הופעל FaultRule אחר, צריך לכלול את הרכיב <AlwaysEnforce> בתג <DefaultFaultRule>. האלמנט DefaultFaultRule תמיד מופעל אחרון:
<DefaultFaultRule name="fault-rule">
<Step>
<Name>ReturnGenericError</Name>
</Step>
<AlwaysEnforce>true</AlwaysEnforce>
</DefaultFaultRule>אחד השימושים ב-DefaultFaultRule הוא לקבוע את סוג השגיאה שמתרחשת כשאין אפשרות לקבוע אותו בדרך אחרת. לדוגמה, שרת ה-proxy של ה-API נכשל בגלל שגיאה שלא הצלחתם לזהות. משתמשים ב-DefaultFaultRule כדי להפעיל את מדיניות AssignMessage הבאה. המדיניות הזו כותבת את הערך fault.name לכותרת בשם DefaultFaultHeader בתגובה:
<AssignMessage async="false" continueOnError="false" enabled="true" name="DefaultFaultRule"> <DisplayName>DefaultFaultRule</DisplayName> <Set> <Headers> <Header name="DefaultFaultHeader">{fault.name}</Header> </Headers> </Set> <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables> <AssignTo createNew="false" transport="http" type="response"/> </AssignMessage>
אחר כך אפשר לראות את הכותרת בכלי המעקב של Edge או בתגובה כדי להבין מה גרם לשגיאה.
הוספת רישום ביומן של הודעות ל-PostClientFlow
PostClientFlow הוא הרצף היחיד שמופעל אחרי שה-proxy עובר למצב שגיאה. אפשר לצרף לזרימה הזו רק את המדיניות MessageLogging, שמופעלת אחרי שהתשובה נשלחת בחזרה ללקוח. למרות שצירוף מדיניות MessageLogging לזרימה הזו לא נחשב מבחינה טכנית לטיפול בשגיאות, אפשר להשתמש בה כדי לרשום מידע ביומן במקרה של שגיאה. היא מופעלת בלי קשר להצלחה או לכישלון של ה-proxy, ולכן אפשר להציב מדיניות של רישום הודעות ב-PostClientFlow ולהבטיח שהיא תמיד תופעל.
טיפול בתקלות שקשורות למדיניות בתהליך הנוכחי
בדוגמאות שמוצגות עד עכשיו נעשה שימוש ב-FaultRule ב-ProxyEndpoint או ב-TargetEndpoint כדי לטפל בשגיאות מדיניות כחלק ממצב השגיאה. הסיבה לכך היא שערך ברירת המחדל של
האלמנט continueOnError של מדיניות הוא false, כלומר כשמתרחשת שגיאה במדיניות, השליטה מועברת למצב השגיאה. אחרי שהאפליקציה נכנסת למצב שגיאה, אי אפשר להחזיר את השליטה לצינור הרגיל, ובדרך כלל מוחזרת הודעת שגיאה כלשהי לאפליקציה שקוראת לפונקציה.
עם זאת, אם מגדירים את הרכיב continueOnError לערך true במדיניות, השליטה נשארת בתהליך הנוכחי והמדיניות הבאה בצינור מופעלת אחרי המדיניות שגרמה לשגיאה. היתרון בטיפול בשגיאה בתהליך הנוכחי הוא שאולי יש לך דרך לשחזר את השגיאה כדי להשלים את עיבוד הבקשה.
בדוגמה הבאה מוצגת מדיניות VerifyAPIKey בשם verify-api-key עם הרכיב continueOnError שהערך שלו הוא true:
<VerifyAPIKey async="false" continueOnError="true" enabled="true" name="verify-api-key"> <DisplayName>Verify API Key</DisplayName> <APIKey ref="request.queryparam.apikey"/> </VerifyAPIKey>
אם מפתח ה-API חסר או לא תקין, המדיניות VerifyAPIKey מגדירה את המשתנה oauthV2.verify-api-key.failed לערך true, אבל העיבוד ממשיך בתהליך הנוכחי.
לאחר מכן מוסיפים את מדיניות VerifyAPIKey כשלב ב-PreFlow של ProxyEndpoint:
<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>שימו לב איך השלב הבא ב-PreFlow משתמש בתנאי כדי לבדוק אם קיימת שגיאה. אם התרחשה שגיאה במדיניות VerifAPIKey, המדיניות בשם
FaultInFlow policy מופעלת. אחרת, המדיניות FaultInFlow לא תופעל. מדיניות FaultInFlow יכולה לבצע פעולות רבות, כמו רישום השגיאה ביומן, ניסיון לתקן את השגיאה או ביצוע פעולה אחרת.
הפעלת שגיאה באמצעות המדיניות RaiseFault
אפשר להשתמש במדיניות RaiseFault בכל שלב בתהליך כדי להפעיל שגיאה. כשמדיניות RaiseFault מופעלת, היא מסיימת את התהליך הנוכחי ומעבירה את השליטה למצב השגיאה.
אחד מהשימושים במדיניות RaiseFault הוא בדיקה של תנאי ספציפי שמדיניות אחרת לא יכולה לזהות. בדוגמה שלמעלה, הוספתם תג <Condition> לתג <Step> PreFlow שגרם להפעלת המדיניות FaultInFlow אם התנאי מתקיים. אם FaultInFlow היא מדיניות RaiseFault, השליטה מועברת למצב השגיאה. אפשר גם להוסיף מדיניות RaiseFault לזרימת נתונים כדי לנפות באגים ולבדוק את ה-FaultRules.
כשמדיניות RaiseFault מפעילה שגיאה, אפשר להשתמש ב-FaultRule ובתנאי הבאים כדי לעבד אותה:
<FaultRule name="raisefault_rule">
<Step>
<Name>{policy_name}</Name>
</Step>
<Condition>(fault.name = "RaiseFault")</Condition>
</FaultRule>שימו לב שהתנאי בודק אם יש תקלה בשם RaiseFault. המדיניות RaiseFault
תמיד מגדירה את הערך של fault.name ל-RaiseFault.
טיפול מותאם אישית בקודי שגיאה של HTTP משרת היעד
הדוגמאות שמוצגות בקטעים הקודמים רלוונטיות לשגיאות שנוצרות על ידי כללי מדיניות. עם זאת, אפשר גם ליצור תגובה מותאמת אישית לשגיאות ברמת התעבורה, כלומר שגיאות HTTP שמוחזרות משרת היעד. כדי לשלוט בתגובה משגיאת HTTP, צריך להגדיר TargetEndpoint לעיבוד קודי תגובה של HTTP.
כברירת מחדל, Edge מתייחס לקודי תגובה של HTTP בטווח 1xx-3xx כאל 'הצלחה', ולקודי תגובה של HTTP בטווח 4xx-5xx כאל 'כישלון'. כלומר, כל תגובה משירות הקצה העורפי עם קוד תגובת HTTP 4xx-5xx מפעילה באופן אוטומטי את מצב השגיאה, ואז מוחזרת הודעת שגיאה ישירות ללקוח ששלח את הבקשה.
אפשר ליצור פונקציות לטיפול בשגיאות בהתאמה אישית לכל קודי התגובה של HTTP. לדוגמה, יכול להיות שלא תרצו להתייחס לכל קודי התגובה של HTTP בטווח 4xx-5xx כאל 'כישלון', אלא רק לקודי 5xx, או שתרצו להחזיר הודעות שגיאה מותאמות אישית לקודי התגובה של HTTP 400 ו-500.
בדוגמה הבאה, משתמשים במאפיין success.codes כדי להגדיר את TargetEndpoint כך שיטפל בקודי תגובה מסוג HTTP 400 ו-500 כהצלחה, בנוסף לקודי ה-HTTP שמוגדרים כברירת מחדל. אם הקודים האלה נחשבים כהצלחה, TargetEndpoint משתלט על עיבוד הודעת התגובה, במקום להפעיל את מצב השגיאה:
<TargetEndpoint name="default">
...
<HTTPTargetConnection>
<Properties>
<Property name="success.codes">1xx,2xx,3xx,400,500</Property>
</Properties>
<URL>http://weather.yahooapis.com</URL>
</HTTPTargetConnection>
</TargetEndpoint>כפי שאפשר לראות בדוגמה הזו, אפשר להשתמש בתווים כלליים לחיפוש כדי להגדיר את המאפיין success.codes לטווח של ערכים.
הגדרת המאפיין success.codes מחליפה את ערכי ברירת המחדל. לכן, אם רוצים להוסיף את קוד ה-HTTP 400 לרשימת קודי ההצלחה שמוגדרים כברירת מחדל, צריך להגדיר את המאפיין הזה כך:
<Property name="success.codes">1xx,2xx,3xx,400</Property>
אבל אם רוצים שקוד HTTP 400 ייחשב כקוד הצלחה, צריך להגדיר את המאפיין כך:
<Property name="success.codes">400</Property>
עכשיו אפשר להגדיר handlers מותאמים אישית לקודי תגובה 400 ו-500 של HTTP כדי להחזיר הודעת תגובה מותאמת אישית לאפליקציה ששלחה את הבקשה. ב-TargetEndpoint הבא נעשה שימוש במדיניות בשם ReturnError כדי לטפל בקודי תגובה 400 ו-500 של HTTP:
<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>ההגדרה הזו של TargetEndpoint גורמת לכך שהמדיניות שנקראת ReturnError תטפל בתגובה בכל פעם ש-TargetEndpoint נתקל בקוד תגובה מסוג HTTP 400 או 500.
טקסונומיה של תקלות
שירותי API מארגנים את התקלות בקטגוריות ובקטגוריות משנה הבאות.
| קטגוריה | קטגוריית משנה | שם התקלה | תיאור |
|---|---|---|---|
| העברת הודעות | כשלים שמתרחשים במהלך זרימת ההודעות (לא כולל כשלים שקשורים למדיניות) | ||
| תקלות בהתאמה אישית | {fault_name} | תקלות שטופלו באופן מפורש על ידי שרת ה-proxy של ה-API באמצעות מדיניות RaiseFault | |
| קודי תגובה | InternalServerError, NotFound | קודי שגיאה של HTTP 5xx, 4xx | |
| בעיות בקביעת מסלול | NoRoutesMatched | הבחירה של TargetEndpoint עם שם עבור בקשה נכשלה | |
| כשלים בסיווג | NotFound | כשלים שנגרמים מ-URI של בקשה שלא תואם לאף BasePath באף הגדרה של ProxyEndpoint (כלומר, אין פרוקסי API שתואם לכתובת ה-URL בבקשה של אפליקציית הלקוח) | |
| Transport | שגיאות ברמת התעבורה של HTTP | ||
| קישוריות | ConnectionRefused, ConnectionReset, ConnectionTimeout | כשלים מתרחשים בזמן יצירת חיבורים ברמת הרשת או התעבורה | |
| בקשת אימותים | ContentLengthMissing, HostHeaderMissing | תקלות מתרחשות במהלך בדיקות סמנטיות בכל בקשה | |
| אימות תשובות | תקלות מתרחשות במהלך בדיקות סמנטיות בכל תגובה | ||
| שגיאות IO | SSLHandshakeError, ReadTimeout, ReadError, WriteTimeout, WriteError, ChunkError | שגיאות קריאה/כתיבה בנקודות קצה של לקוח או יעד, פסק זמן, שגיאות TLS/SSL ושגיאות חלוקה למקטעים | |
| מערכת | שגיאות לא מוגדרות בזמן ריצה | ||
| זיכרון | OutOfMemory, GCOverLimit | כשלים שקשורים לזיכרון | |
| חוט תפירה | RogueTaskTerminated | כשלים כמו סיום של משימות שרצות ללא הפסקה | |
| מדיניות | התקלות בכל סוג מדיניות מוגדרות בחומר העזר בנושא מדיניות. | ||
לכל שגיאה מצורף תיאור טקסט של הסיבה לכישלון. כשהמערכת מעלה תקלה, קבוצה של מאפיינים מאוכלסת כדי לסייע בפתרון הבעיה. תקלה כוללת את הפרטים הבאים:
- סיבה
- מאפיינים מותאמים אישית שהוגדרו על ידי המשתמש
