实现对话Webhook作为Azure功能应用程序

时间:2017-05-26 19:03:16

标签: actions-on-google

我有一个天蓝色的功能应用程序,我用作google助手操作的webhook。我试图按照文档进行正确的响应,但在测试我的webhook时,我不断在模拟器中收到以下错误。我的回复消息中有什么东西看起来不对吗?

无法从http_response解析SDKResponse:

HTTP/1.1 200 OK
Cache-Control: no-cache
Pragma: no-cache
Content-Length: 451
Content-Type: application/json; charset=utf-8
Content-Encoding: gzip
Expires: -1
Vary: Accept-Encoding
Server: Microsoft-IIS/8.0
X-AspNet-Version: 4.0.30319
X-Powered-By: ASP.NET
Date: Sun, 28 May 2017 19:00:13 GMT

{"conversationToken":"cee44ab4-97dd-4e18-99c7-2b8613eb7584","expectUserResponse":true,"expectedInputs":[{"inputPrompt":{"richInitialPrompt":{"items":[{"simpleResponse":{"textToSpeech":"So, you want to become a great swordsman? First, you must learn the proper technique of insult sword fighting. The current difficulty level is Easy. Say 'Tutorial' for some quick instructions. Say 'Start Game' to start the game. Say 'Options' for more options. "}}]}}}]}

这是为了可读性而格式化的json:

{
  "conversationToken": "cee44ab4-97dd-4e18-99c7-2b8613eb7584",
  "expectUserResponse": true,
  "expectedInputs": [
    {
      "inputPrompt": {
        "richInitialPrompt": {
          "items": [
            {
              "simpleResponse": {
                "textToSpeech": "So, you want to become a great swordsman? ... "
              }
            }
          ]
        }
      }
    }
  ]
}

通过我的最新测试,我尝试发送在Fulfillment页面说明中给出的确切示例响应,但仍然失败:https://developers.google.com/actions/components/fulfillment

 {
  "conversationToken": "{\"state\":null,\"data\":{}}",
  "expectUserResponse": true,
  "expectedInputs": [
    {
      "inputPrompt": {
        "richInitialPrompt": {
          "items": [
            {
              "simpleResponse": {
                "textToSpeech": "Howdy! I can tell you fun facts about almost any number, like 42. What do you have in mind?",
                "displayText": "Howdy! I can tell you fun facts about almost any number. What do you have in mind?"
              }
            }
          ],
          "suggestions": []
        }
      },
      "possibleIntents": [ { "intent": "actions.intent.TEXT" } ]
    }
  ]
}

1 个答案:

答案 0 :(得分:1)

您的haskell-src-exts条目似乎略有无效。 Item对象被定义为联合字段,表示必须设置三个属性之一(import Data.List import Control.Monad import qualified Language.Haskell.Interpreter as I import Language.Haskell.Interpreter (Interpreter, GhcError(..), InterpreterError(..)) import qualified Language.Haskell.Exts as H import Language.Haskell.Exts.SrcLoc main :: IO () main = do r <- I.runInterpreter interpreterTest case r of Left err -> putStrLn $ errorString err Right () -> return () errorString :: InterpreterError -> String errorString (WontCompile es) = intercalate "\n" (header : map unbox es) where header = "ERROR: Won't compile:" unbox (GhcError e) = e errorString e = show e p :: String -> Interpreter () p = I.liftIO . putStrLn emptyLine :: Interpreter () emptyLine = p "" interpreterTest :: Interpreter () interpreterTest = do p "Finding out what the module exports are." p "To do this, we grab the text of the src/TestModule.hs" moduleContents <- I.liftIO . readFile $ "src/TestModule.hs" emptyLine p "Next, we find what the import module names are, so we can load them" p "To do that, we'll parse the contents of src/TestModule.hs as AST" let parseResult = H.parseModule moduleContents parsedModuleDeclE = case parseResult of H.ParseOk parsed -> Right parsed H.ParseFailed _ errorReason -> Left errorReason (moduleDeclarations, moduleImports) = case parsedModuleDeclE of Left _ -> ([], []) Right (H.Module _ _ _ _ _ importDecls decls) -> (decls, importDecls) p $ show moduleImports emptyLine p "Now we can pull the module names out of the ImportDecl values:" let moduleNames = do H.ModuleName s <- fmap H.importModule moduleImports return s p $ show moduleNames emptyLine p "After this we can obtain a list of the module exports for each of these modules and join them together:" I.loadModules ["src/TestModule.hs"] I.setTopLevelModules ["TestModule"] topLevelImportDecls <- fmap concat $ mapM I.getModuleExports moduleNames -- p $ show $ do { I.Fun f <- topLevelImportDecls ; return f } -- filter for functions only p $ show $ fmap I.name topLevelImportDecls emptyLine p "Then, we can get the top level declarations of the initial module and add them, too:" -- p $ show moduleDeclarations -- AST in haskell types let localDeclaractions = do (H.PatBind _ (H.PVar (H.Ident declName)) _ _) <- moduleDeclarations return declName availableDeclarations = localDeclaractions ++ fmap I.name topLevelImportDecls p $ show localDeclaractions emptyLine p "Finally, we have our big list:" p $ show availableDeclarations emptyLine p "Now, what about we get all of their types, just for fun?" typesOfAll <- sequence $ fmap (\n -> fmap ((n ++ " :: ") ++) (I.typeOf n)) availableDeclarations p $ Data.List.intercalate "\n" typesOfAll return () itemssimpleResponse)及其各自的值。< / p>

因此,basicCard属性不应直接位于structuredResponse之下,而是应该具有textToSpeech属性,并且在此下属于richInitialPrompt.item属性(或其中之一)对SimpleResponse对象有意义的其他属性。你必须至少有一个SimpleResponse(它必须是第一个),你可能不会超过两个。

但是,在这种背景下,第二个回复所附的文字没有意义。两个回复都将被显示/显示 - 如果用户操作有延迟,则不会回复。

v1协议有一种方法可以支持重新提示的细节,但我在v2中看不到相同的内容。

所以JSON应该看起来更像:

simpleResponse