Ответ веб-перехватчика Google Actions API на Heroku nodejs

Вопрос: всегда ли Google Actions запускает сообщение веб-перехватчика при каждом вводе пользователя, и мне просто нужно работать с логикой, чтобы каждый раз анализировать json и реагировать только в том случае, если мой интересующий параметр найден? Или есть способ контролировать публикацию веб-перехватчика, созданную Google Actions API, чтобы она была сделана только тогда, когда действие полностью заполнено, содержащее значение для интересующего параметра?

#

Подробности: у меня есть приложение nodejs, развернутое на Heroku: https://github.com/quique123/myjsonparser/blob/master/app.js

Я использую его как перехватчик для примера Google Actions API (Number Genie). В Number Genie пользователь начинает игру с "Talk to Number Genie". Джинн отвечает, что я думаю о числе ... угадай. Пользователь отвечает числом, а затем (и только тогда) запускается логика для сравнения предположения с ответом.

Но у меня есть вызов api для каждого почтового запроса из дома Google. Другими словами, публикация веб-перехватчика создается каждый раз, когда пользователь взаимодействует с API беседы. Это можно увидеть здесь, где тело не содержит параметров ввода пользователя, а Heroku отвечает на «поговорить с джинном числа»:

2017-04-30T18:59:19.480900+00:00 heroku[router]: at=info method=POST path="/API/switches/sw1?password=123456" host=myjsonparser.herokuapp.com request_id=64d51b1c-3253-4a64-b7f5-a29a7750945b fwd="54.224.155.160" dyno=web.1 connect=1ms service=35ms status=200 bytes=254 protocol=https
2017-04-30T18:59:19.473973+00:00 app[web.1]: headers: {"host":"myjsonparser.herokuapp.com","connection":"close","accept":"*/*","content-type":"application/json; charset=UTF-8","cache-control":"no-cache","pragma":"no-cache","user-agent":"Java/1.8.0_112","x-request-id":"64d51b1c-3253-4a64-b7f5-a29a7750945b","x-forwarded-for":"54.224.155.160","x-forwarded-proto":"https","x-forwarded-port":"443","via":"1.1 vegur","connect-time":"1","x-request-start":"1493578759443","total-route-time":"0","content-length":"575"}
2017-04-30T18:59:19.474002+00:00 app[web.1]: body: {"id":"14797289-b0b8-492a-b030-bf9f05c7ea17","timestamp":"2017-04-30T18:59:19.413Z","lang":"en","result":{"source":"agent","resolvedQuery":"talk to number genie","speech":"","action":"generate_answer","actionIncomplete":false,"parameters":{},"contexts":[],"metadata":{"intentId":"688b0da5-547e-4c7a-8adc-189844834bcc","webhookUsed":"true","webhookForSlotFillingUsed":"false","intentName":"start_game"},"fulfillment":{"speech":"","messages":[{"type":0,"speech":""}]},"score":0.61},"status":{"code":200,"errorType":"success"},"sessionId":"ff2e0c97-552b-40d3-8f06-32e612476897"}
2017-04-30T18:59:19.477116+00:00 app[web.1]: postSwitch {"id":"sw1","state":"off","name":"Koko's Lamp"}

И когда я тестирую его с помощью числа в Google Actions API, вы можете видеть в ответе Heroku на «44», что включен check_guess:

2017-04-30T19:00:31.901297+00:00 app[web.1]: headers: {"host":"myjsonparser.herokuapp.com","connection":"close","accept":"*/*","content-type":"application/json; charset=UTF-8","cache-control":"no-cache","pragma":"no-cache","user-agent":"Java/1.8.0_112","x-request-id":"5a7a2c31-9ce5-4b02-9bac-bcef55ad6818","x-forwarded-for":"54.224.155.160","x-forwarded-proto":"https","x-forwarded-port":"443","via":"1.1 vegur","connect-time":"1","x-request-start":"1493578831899","total-route-time":"0","content-length":"573"}
2017-04-30T19:00:31.901347+00:00 app[web.1]: body: {"id":"5478dfb5-54f3-451d-b975-4f984d1ce3cb","timestamp":"2017-04-30T19:00:31.858Z","lang":"en","result":{"source":"agent","resolvedQuery":"44","speech":"","action":"check_guess","actionIncomplete":false,"parameters":{"check_guess":"44"},"contexts":[],"metadata":{"intentId":"c863e1e2-c850-45d8-9b96-b57e0b1ee77e","webhookUsed":"true","webhookForSlotFillingUsed":"false","intentName":"provide_guess"},"fulfillment":{"speech":"","messages":[{"type":0,"speech":""}]},"score":1},"status":{"code":200,"errorType":"success"},"sessionId":"ff2e0c97-552b-40d3-8f06-32e612476897"}
2017-04-30T19:00:31.903553+00:00 app[web.1]: postSwitch {"id":"sw1","state":"on","name":"Koko's Lamp"}
2017-04-30T19:00:31.907017+00:00 heroku[router]: at=info method=POST path="/API/switches/sw1?password=123456" host=myjsonparser.herokuapp.com request_id=5a7a2c31-9ce5-4b02-9bac-bcef55ad6818 fwd="54.224.155.160" dyno=web.1 connect=1ms service=5ms status=200 bytes=253 protocol=https

Проблема в том, что postSwitch {} происходит в обоих случаях.

Всегда ли так Google Actions будет работать, и мне просто нужно работать с логикой, чтобы каждый раз анализировать json и реагировать только в случае обнаружения check_guess? Или есть способ контролировать публикацию веб-перехватчика, созданную Google Actions API, чтобы она была сделана только тогда, когда действие полностью заполнено, содержащее значение для параметра check_guess?


person marciokoko    schedule 30.04.2017    source источник
comment
Вы используете API.AI? Можете ли вы также добавить скриншоты намерений, которые запускают это? Если вы не используете API.AI, можете ли вы добавить пакет действий, который вы используете.   -  person Prisoner    schedule 30.04.2017
comment
На данный момент в их статье есть МНОГО ошибок. Они обновили пример кода, не обновив полностью руководство. Однако, если у вас есть другие проблемы, их лучше всего задать в дополнительных вопросах SO. Этого лучше всего оставить, чтобы попытаться решить ваш вопрос о маршрутизации.   -  person Prisoner    schedule 01.05.2017
comment
Пакеты действий предназначены только для использования не -API.AI метода реализации действий. Не беспокойтесь об этом, если вы используете API.AI.   -  person Prisoner    schedule 01.05.2017


Ответы (1)


Вы можете установить только один веб-перехватчик (один статический URL-адрес), который будет вызываться для всех действий, запускаемых с помощью API.AI. Хотя вам нужно будет проанализировать JSON (вы используете node.js, JSON.parse () не НАСТОЛЬКО сложный), вы должны использовать поле result.action вместо того, чтобы пытаться выяснить, какие параметры установлены. Это будет соответствовать полю Action, которое вы установили в API.AI.

Это, конечно, предполагает, что у вас установлен флажок веб-перехватчика для вашего действия. В противном случае вы вообще не получите вызова веб-перехватчика.

Так, например, с начальным намерением, настроенным следующим образом:

введите здесь описание изображения

Он отправит этот JSON на ваш веб-перехватчик.


{
 "originalRequest": {
  "source": "google",
  "data": {
   "surface": {
    "capabilities": [
     {
      "name": "actions.capability.AUDIO_OUTPUT"
     }
    ]
   },
   "inputs": [
    {
     "arguments": [],
     "intent": "assistant.intent.action.MAIN",
     "raw_inputs": [
      {
       "query": "talk to number genie",
       "input_type": 2,
       "annotation_sets": []
      }
     ]
    }
   ],
   "user": {
    "user_id": "kQmX8nX9ovcS9jfb3WKmwLk9YFlHGZH05YGbc8muNI8=",
    "permissions": []
   },
   "device": {
    "locale": "en-US"
   },
   "is_in_sandbox": true,
   "conversation": {
    "conversation_id": "1493637016599",
    "type": 1
   }
  }
 },
 "id": "9444bfe4-3c23-487a-84e7-fcbf1708d9e3",
 "timestamp": "2017-05-01T11:10:16.694Z",
 "lang": "en",
 "result": {
  "source": "agent",
  "resolvedQuery": "GOOGLE_ASSISTANT_WELCOME",
  "speech": "",
  "action": "generate_answer",
  "actionIncomplete": false,
  "parameters": {},
  "contexts": [
   {
    "name": "game",
    "parameters": {},
    "lifespan": 5
   },
   {
    "name": "google_assistant_welcome",
    "parameters": {},
    "lifespan": 0
   },
   {
    "name": "actions_capability_audio_output",
    "parameters": {},
    "lifespan": 0
   }
  ],
  "metadata": {
   "intentId": "56da4637-0419-46b2-b851-d7bf726b1b1b",
   "webhookUsed": "true",
   "webhookForSlotFillingUsed": "false",
   "intentName": "start_game"
  },
  "fulfillment": {
   "speech": "",
   "messages": [
    {
     "type": 0,
     "speech": ""
    }
   ]
  },
  "score": 1
 },
 "status": {
  "code": 200,
  "errorType": "success"
 },
 "sessionId": "1493637016599"
}

Хотя намерение provide_guess может быть настроено следующим образом

provide_guess снимок экрана

и предоставьте этот JSON веб-перехватчику:


{
 "originalRequest": {
  "source": "google",
  "data": {
   "surface": {
    "capabilities": [
     {
      "name": "actions.capability.AUDIO_OUTPUT"
     }
    ]
   },
   "inputs": [
    {
     "arguments": [
      {
       "raw_text": "42",
       "text_value": "42",
       "name": "text"
      }
     ],
     "intent": "assistant.intent.action.TEXT",
     "raw_inputs": [
      {
       "query": "42",
       "input_type": 2,
       "annotation_sets": []
      }
     ]
    }
   ],
   "user": {
    "user_id": "kQmX8nX9ovcS9jfb3WKmwLk9YFlHGZH05YGbc8muNI8=",
    "permissions": []
   },
   "device": {
    "locale": "en-US"
   },
   "is_in_sandbox": true,
   "conversation": {
    "conversation_token": "[\"_actions_on_google_\",\"game\"]",
    "conversation_id": "1493637749915",
    "type": 2
   }
  }
 },
 "id": "09997ef5-5c0f-4c60-a69f-af06d6e4e3f5",
 "timestamp": "2017-05-01T11:22:34.377Z",
 "lang": "en",
 "result": {
  "source": "agent",
  "resolvedQuery": "42",
  "speech": "",
  "action": "check_guess",
  "actionIncomplete": false,
  "parameters": {
   "guess": "42"
  },
  "contexts": [
   {
    "name": "game",
    "parameters": {
     "guess.original": "42",
     "guess": "42"
    },
    "lifespan": 5
   },
   {
    "name": "_actions_on_google_",
    "parameters": {
     "guessCount": 0,
     "printed": "Welcome back to Number Genie. I'm thinking of a number from %s to %s. What's your first guess?",
     "guess.original": "42",
     "answer": 74,
     "guess": "42",
     "lastPrompt": "Welcome back to Number Genie. I'm thinking of a number from %s to %s. What's your first guess?",
     "steamSoundCount": 0,
     "fallbackCount": 0
    },
    "lifespan": 99
   },
   {
    "name": "actions_capability_audio_output",
    "parameters": {
     "guess.original": "42",
     "guess": "42"
    },
    "lifespan": 0
   }
  ],
  "metadata": {
   "intentId": "1e46ffc2-651f-4ac0-a54e-9698feb88880",
   "webhookUsed": "true",
   "webhookForSlotFillingUsed": "false",
   "intentName": "provide_guess"
  },
  "fulfillment": {
   "speech": "",
   "messages": [
    {
     "type": 0,
     "speech": ""
    }
   ]
  },
  "score": 1
 },
 "status": {
  "code": 200,
  "errorType": "success"
 },
 "sessionId": "1493637749915"
}

В своем коде вы должны проверить значение result.action в своем postSwitch() методе и затем выбрать точные операции на своей стороне на основе этого действия (либо generateAnswer(), либо checkGuess() в зависимости от закомментированного кода).

person Prisoner    schedule 01.05.2017
comment
Хорошо, итак, result.action используется для проверки конкретного результата намерения, поэтому он называется действием намерения в console.api.ai. Хорошо поигравшись с ним вчера вечером, я получил значение, выполнив Assistant.getArgument ('check_guess'), и я смог получить его в Heroku с моим последним кодом на github. - person marciokoko; 01.05.2017
comment
Это правильный способ получить доступ к этим значениям? - person marciokoko; 02.05.2017
comment
Какие ценности? result.action? - person Prisoner; 02.05.2017
comment
Я пытаюсь получить доступ к вводу пользователя, который в примере number genie будет параметром check_guess, который также является именем действия в result.action. Это будет что-то вроде result.action.check_guess: 65. Но вместо того, чтобы разбирать json как словарь, я использовал образец кода let guess = parseInt(assistant.getArgument('check_guess')); из учебника Google Actions Number Genie. - person marciokoko; 03.05.2017
comment
Похоже, вы задаете другой вопрос. Хороший вопрос - но отличный от того, который задан здесь. Поднимите его в новом вопросе SO, чтобы его можно было правильно сохранить для других, у кого есть такой же вопрос. - person Prisoner; 03.05.2017