יצירת webhook

במדריך הזה נסביר איך להשתמש ב-webhook כדי שהנציג יהיה דינמי יותר. בגלל הפשטות של Cloud Functions, משתמשים בהן כדי לארח את ה-webhook, אבל יש עוד הרבה דרכים לארח שירות webhook. הדוגמה מבוססת על שפת התכנות Go, אבל אפשר להשתמש בכל שפה שנתמכת ב-Cloud Functions. לא תצטרכו לערוך את הקוד במדריך הזה.

קוד ה-webhook לדוגמה מבצע את הפעולות הבאות:

  • קורא את ערכי הפרמטרים מהבקשה ל-webhook.
  • כותב ערך פרמטר לתגובת ה-webhook.
  • מספקת תשובת טקסט בתגובת ה-webhook.

לפני שמתחילים

אם אתם לא מתכננים להשתמש ב-webhooks, אתם יכולים לדלג על המדריך הזה.

לפני שתקראו את המדריך הזה:

  1. מידע בסיסי על תהליכים
  2. לבצע את השלבים להגדרה.
  3. מבצעים את השלבים במדריך למתחילים פיתוח סוכן באמצעות תהליכים. השלבים הבאים ממשיכים לעבוד על אותו נציג. אם הנציג כבר לא קיים, אתם יכולים להוריד את הנציג ולשחזר אותו.

יצירת הפונקציה של Cloud Functions

אפשר ליצור פונקציות של Cloud Functions באמצעות מסוף Google Cloud (למשאבי העזרה, לפתיחת המסוף). כדי ליצור פונקציה למדריך הזה:

  1. חשוב שהסוכן ב-Dialogflow CX והפונקציה יהיו באותו פרויקט. זו הדרך הקלה ביותר לתת ל-Dialogflow CX גישה מאובטחת לפונקציה. כניסה לדף לבחירת הפרויקט
  2. נכנסים לדף הסקירה הכללית של Cloud Functions.
  3. לוחצים על Create Function ומגדירים את השדות הבאים:
    • סביבה: דור ראשון
    • שם הפונקציה: shirts-agent-webhook
    • ‫Region: אם ציינתם אזור לסוכן, השתמשו באותו אזור.
    • HTTP Trigger type: ‏ HTTP
    • כתובת URL: לוחצים על כפתור ההעתקה כאן ושומרים את הערך. תצטרכו את כתובת ה-URL הזו כשתגדירו את ה-webhook.
    • אימות: דרישת אימות
    • דרישת HTTPS: מסומן
  4. לוחצים על Save.
  5. לוחצים על Next (אין צורך בהגדרות מיוחדות של זמן ריצה, build, חיבורים או אבטחה).
  6. מגדירים את השדות הבאים:
    • ‫Runtime: בוחרים את סביבת זמן הריצה העדכנית של Go.
    • קוד מקור: עורך בתוך השורה
    • נקודת כניסה: HandleWebhookRequest
  7. מחליפים את הקוד בקוד הבא:

    // Package cxwh contains an example Dialogflow CX webhook
    package cxwh
    
    import (
    	"encoding/json"
    	"fmt"
    	"log"
    	"net/http"
    )
    
    type fulfillmentInfo struct {
    	Tag string `json:"tag"`
    }
    
    type sessionInfo struct {
    	Session    string         `json:"session"`
    	Parameters map[string]any `json:"parameters"`
    }
    
    type text struct {
    	Text []string `json:"text"`
    }
    
    type responseMessage struct {
    	Text text `json:"text"`
    }
    
    type fulfillmentResponse struct {
    	Messages []responseMessage `json:"messages"`
    }
    
    // webhookRequest is used to unmarshal a WebhookRequest JSON object. Note that
    // not all members need to be defined--just those that you need to process.
    // As an alternative, you could use the types provided by the Dialogflow protocol buffers:
    // https://pkg.go.dev/google.golang.org/genproto/googleapis/cloud/dialogflow/cx/v3#WebhookRequest
    type webhookRequest struct {
    	FulfillmentInfo fulfillmentInfo `json:"fulfillmentInfo"`
    	SessionInfo     sessionInfo     `json:"sessionInfo"`
    }
    
    // webhookResponse is used to marshal a WebhookResponse JSON object. Note that
    // not all members need to be defined--just those that you need to process.
    // As an alternative, you could use the types provided by the Dialogflow protocol buffers:
    // https://pkg.go.dev/google.golang.org/genproto/googleapis/cloud/dialogflow/cx/v3#WebhookResponse
    type webhookResponse struct {
    	FulfillmentResponse fulfillmentResponse `json:"fulfillmentResponse"`
    	SessionInfo         sessionInfo         `json:"sessionInfo"`
    }
    
    // confirm handles webhook calls using the "confirm" tag.
    func confirm(request webhookRequest) (webhookResponse, error) {
    	// Create a text message that utilizes the "size" and "color"
    	// parameters provided by the end-user.
    	// This text message is used in the response below.
    	t := fmt.Sprintf("You can pick up your order for a %s %s shirt in 5 days.",
    		request.SessionInfo.Parameters["size"],
    		request.SessionInfo.Parameters["color"])
    
    	// Create session parameters that are populated in the response.
    	// The "cancel-period" parameter is referenced by the agent.
    	// This example hard codes the value 2, but a real system
    	// might look up this value in a database.
    	p := map[string]any{"cancel-period": "2"}
    
    	// Build and return the response.
    	response := webhookResponse{
    		FulfillmentResponse: fulfillmentResponse{
    			Messages: []responseMessage{
    				{
    					Text: text{
    						Text: []string{t},
    					},
    				},
    			},
    		},
    		SessionInfo: sessionInfo{
    			Parameters: p,
    		},
    	}
    	return response, nil
    }
    
    // handleError handles internal errors.
    func handleError(w http.ResponseWriter, err error) {
    	w.WriteHeader(http.StatusInternalServerError)
    	fmt.Fprintf(w, "ERROR: %v", err)
    }
    
    // HandleWebhookRequest handles WebhookRequest and sends the WebhookResponse.
    func HandleWebhookRequest(w http.ResponseWriter, r *http.Request) {
    	var request webhookRequest
    	var response webhookResponse
    	var err error
    
    	// Read input JSON
    	if err = json.NewDecoder(r.Body).Decode(&request); err != nil {
    		handleError(w, err)
    		return
    	}
    	log.Printf("Request: %+v", request)
    
    	// Get the tag from the request, and call the corresponding
    	// function that handles that tag.
    	// This example only has one possible tag,
    	// but most agents would have many.
    	switch tag := request.FulfillmentInfo.Tag; tag {
    	case "confirm":
    		response, err = confirm(request)
    	default:
    		err = fmt.Errorf("Unknown tag: %s", tag)
    	}
    	if err != nil {
    		handleError(w, err)
    		return
    	}
    	log.Printf("Response: %+v", response)
    
    	// Send response
    	if err = json.NewEncoder(w).Encode(&response); err != nil {
    		handleError(w, err)
    		return
    	}
    }
  8. לוחצים על Deploy.

  9. מחכים עד שאינדיקטור הסטטוס מראה שהפונקציה נפרסה בהצלחה. בזמן ההמתנה, בודקים את הקוד שפרסתם. הערות בקוד שמתארות פרטים חשובים.

יצירת ה-webhook

עכשיו, כשה-webhook קיים כפונקציה של Cloud Functions, אתם יכולים לשייך אותו לנציג שלכם. כדי ליצור את ה-webhook לסוכן:

  1. פותחים את מסוף Dialogflow CX.
  2. בוחרים את הפרויקט ב-Google Cloud.
  3. בוחרים את הסוכן.
  4. לוחצים על הכרטיסייה ניהול.
  5. לוחצים על Webhooks.
  6. לוחצים על יצירה.
  7. ממלאים את השדות הבאים:
    • שם לתצוגה: shirts-agent-webhook
    • ‫Webhook URL: מציינים את כתובת ה-URL של ה-webhook ששמרתם כשיצרתם את הפונקציה.
    • סוג משנה: רגיל.
    • בכל שאר השדות משתמשים בערכי ברירת המחדל.
  8. לוחצים על Save.

שימוש ב-webhook

עכשיו, כשה-webhook זמין לסוכן, אתם יכולים להשתמש בו ב-fulfillment. בדף Order Confirmation יש מילוי בקשה לכניסה, שכרגע יש לו תגובת טקסט סטטית. כדי לעדכן את מילוי הבקשה כך שישתמש ב-webhook:

  1. לוחצים על הכרטיסייה Build.
  2. לוחצים על הדף Order Confirmation כדי להרחיב את הדף בתרשים של Agent Builder.
  3. לוחצים על השדה Entry Fulfillment בדף כדי לפתוח את חלונית ה-fulfillment.
  4. מוחקים את התשובה הכתובה הקיימת שמתחת לכותרת Agent says. כשמעבירים את העכבר מעל הטקסט, מופיע כפתור המחיקה .
  5. לוחצים על הפעלת התגובה לפעולה מאתר אחר (Webhook).
  6. בוחרים באפשרות shirts-agent-webhook בתפריט הנפתח Webhook.
  7. מזינים confirm בשדה Tag (תג).
  8. לוחצים על Save.
  9. סוגרים את חלונית המילוי.

צילום מסך של תרשים הסוכן

קוד ה-webhook שנפרס שולח תגובה שיוצרת פרמטר בשם cancel-period. מעדכנים את הנציג כך שיפנה לפרמטר הזה בתשובה הסופית של הנציג באותו דף Order Confirmation:

  1. לוחצים על route של התנאי שמוצג עם התנאי true כדי לפתוח את חלונית הנתיב.
  2. גוללים למטה לקטע Fulfillment בחלונית המסלול, ומוסיפים את התשובה הכתובה הבאה מתחת לכותרת Agent says: You can cancel your order within $session.params.cancel-period days. Goodbye.
  3. לוחצים על Save.
  4. סוגרים את חלונית המסלול.

צילום מסך של תרשים הסוכן

בדיקת הנציג בסימולטור

הנציג וה-webhook מוכנים לבדיקה באמצעות הסימולטור:

  1. לוחצים על Test Agent.
  2. מזינים את I want to buy a large red shirt ומקישים על Enter.

מכיוון שציינתם גם מידה וגם צבע, סיפקתם לנציג את כל מה שצריך כדי ליצור הזמנה של חולצה, ולכן הוא עובר ישירות לדף אישור ההזמנה.

צילום מסך של תרשים הסוכן

התגובות של הנציג מתוארות בהמשך:

תשובה הסבר
בסדר, נתחיל הזמנה חדשה. כשהדף New Order הפך לפעיל, הופעל מילוי הבקשה של הכניסה. התגובה הופעלה מהמילוי הזה.
בחרת חולצה אדומה במידה L. אחרי שכל הפרמטרים של הטופס סופקו בדף New Order, מתבצעת קריאה לנתיב התנאי שבודק אם הטופס הושלם. התגובה הופעלה מהמילוי של הבקשה (fulfillment) של הנתיב הזה. המסלול הזה גם עובר לדף Order Confirmation (אישור ההזמנה).
ההזמנה שלך של חולצה אדומה במידה L תהיה מוכנה לאיסוף בעוד 5 ימים. מילוי הבקשה בכניסה לדף Order Confirmation קורא ל-webhook. מעיינים בפונקציה confirm בקוד ה-webhook. הפונקציה הזו יוצרת את התגובה הזו בטקסט, והיא משתמשת בפרמטרים שסופקו בבקשת ה-webhook.
אתם יכולים לבטל את ההזמנה תוך יומיים. להתראות. בדף Order Confirmation יש נתיב תנאי עם תנאי שתמיד נכון. התשובה הזו מופעלת על ידי מילוי הבקשה של המסלול הזה. שימו לב שהתשובה משתמשת בפרמטר שהוגדר על ידי ה-webhook בתגובת ה-webhook.