UNPKG

6.15 kBJavaScriptView Raw
1"use strict";
2/**
3 * Copyright 2018 Google Inc. All Rights Reserved.
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17Object.defineProperty(exports, "__esModule", { value: true });
18exports.dialogflow = void 0;
19const assistant_1 = require("../../assistant");
20const actionssdk_1 = require("../actionssdk");
21const common = require("../../common");
22const conv_1 = require("./conv");
23const google_auth_library_1 = require("google-auth-library");
24const isVerification = (verification) => typeof verification.headers === 'object';
25/**
26 * This is the function that creates the app instance which on new requests,
27 * creates a way to handle the communication with Dialogflow's fulfillment API.
28 *
29 * Supports Dialogflow v1 and v2.
30 *
31 * @example
32 * ```javascript
33 *
34 * const app = dialogflow()
35 *
36 * app.intent('Default Welcome Intent', conv => {
37 * conv.ask('How are you?')
38 * })
39 * ```
40 *
41 * @public
42 */
43const dialogflow = (options = {}) => assistant_1.attach({
44 _handlers: {
45 intents: {},
46 catcher: (conv, e) => {
47 throw e;
48 },
49 },
50 _middlewares: [],
51 intent(intents, handler) {
52 for (const intent of common.toArray(intents)) {
53 this._handlers.intents[intent] = handler;
54 }
55 return this;
56 },
57 catch(catcher) {
58 this._handlers.catcher = catcher;
59 return this;
60 },
61 fallback(handler) {
62 this._handlers.fallback = handler;
63 return this;
64 },
65 middleware(middleware) {
66 this._middlewares.push(middleware);
67 return this;
68 },
69 init: options.init,
70 verification: options.verification,
71 _client: options.clientId
72 ? new google_auth_library_1.OAuth2Client(options.clientId)
73 : undefined,
74 auth: options.clientId
75 ? {
76 client: {
77 id: options.clientId,
78 },
79 }
80 : undefined,
81 ordersv3: options.ordersv3 || false,
82 async handler(body, headers, metadata = {}) {
83 const { debug, init, verification, ordersv3 } = this;
84 if (verification) {
85 const { headers: verificationHeaders, status = 403, error = (e) => e, } = isVerification(verification)
86 ? verification
87 : { headers: verification };
88 for (const key in verification) {
89 const check = headers[key.toLowerCase()];
90 if (!check) {
91 return {
92 status,
93 body: {
94 error: typeof error === 'string'
95 ? error
96 : error('A verification header key was not found'),
97 },
98 };
99 }
100 const value = verificationHeaders[key];
101 const checking = common.toArray(check);
102 if (checking.indexOf(value) < 0) {
103 return {
104 status,
105 body: {
106 error: typeof error === 'string'
107 ? error
108 : error('A verification header value was invalid'),
109 },
110 };
111 }
112 }
113 }
114 let conv = new conv_1.DialogflowConversation({
115 body,
116 headers,
117 init: init && init(),
118 debug,
119 ordersv3,
120 });
121 if (conv.user.profile.token) {
122 await conv.user._verifyProfile(this._client, this.auth.client.id);
123 }
124 for (const middleware of this._middlewares) {
125 // tslint:disable-next-line:no-any genericize Conversation type
126 const result = middleware(conv, metadata);
127 conv = (result instanceof conv_1.DialogflowConversation
128 ? result
129 : (await result) || conv);
130 }
131 const log = debug ? common.info : common.debug;
132 log('Conversation', common.stringify(conv, 'request', 'headers', 'body'));
133 const { intent } = conv;
134 const traversed = {};
135 let handler = intent;
136 while (typeof handler !== 'function') {
137 if (typeof handler === 'undefined') {
138 if (!this._handlers.fallback) {
139 if (!intent) {
140 throw new Error('No intent was provided and fallback handler is not defined.');
141 }
142 throw new Error(`Dialogflow IntentHandler not found for intent: ${intent}`);
143 }
144 handler = this._handlers.fallback;
145 continue;
146 }
147 if (traversed[handler]) {
148 throw new Error(`Circular intent map detected: "${handler}" traversed twice`);
149 }
150 traversed[handler] = true;
151 handler = this._handlers.intents[handler];
152 }
153 try {
154 try {
155 await handler(conv, conv.parameters, conv.arguments.parsed.list[0], conv.arguments.status.list[0]);
156 }
157 catch (e) {
158 await this._handlers.catcher(conv, e);
159 }
160 }
161 catch (e) {
162 if (e instanceof actionssdk_1.UnauthorizedError) {
163 return {
164 status: 401,
165 headers: {},
166 body: {},
167 };
168 }
169 throw e;
170 }
171 return {
172 status: 200,
173 headers: {},
174 body: conv.serialize(),
175 };
176 },
177}, options);
178exports.dialogflow = dialogflow;
179//# sourceMappingURL=dialogflow.js.map
\No newline at end of file