{"id":18754042,"url":"https://github.com/dcavar/alexa_https","last_synced_at":"2026-05-15T08:34:15.888Z","repository":{"id":69903834,"uuid":"113127245","full_name":"dcavar/alexa_https","owner":"dcavar","description":"Alexa HTTPS server interface in Go","archived":false,"fork":false,"pushed_at":"2017-12-08T03:25:35.000Z","size":16,"stargazers_count":2,"open_issues_count":0,"forks_count":0,"subscribers_count":5,"default_branch":"master","last_synced_at":"2024-12-29T00:55:14.877Z","etag":null,"topics":["amazon-alexa","chatbot","golang"],"latest_commit_sha":null,"homepage":"http://damir.cavar.me/","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/dcavar.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2017-12-05T03:28:48.000Z","updated_at":"2019-06-09T22:01:45.000Z","dependencies_parsed_at":"2023-05-23T09:30:59.534Z","dependency_job_id":null,"html_url":"https://github.com/dcavar/alexa_https","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/dcavar%2Falexa_https","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/dcavar%2Falexa_https/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/dcavar%2Falexa_https/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/dcavar%2Falexa_https/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/dcavar","download_url":"https://codeload.github.com/dcavar/alexa_https/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":239644166,"owners_count":19673578,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["amazon-alexa","chatbot","golang"],"created_at":"2024-11-07T17:27:54.525Z","updated_at":"2025-10-30T09:13:03.468Z","avatar_url":"https://github.com/dcavar.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Alexa HTTPS Server in Go\n\n(C) 2017 by [Damir Cavar], [Rashmi Bidanta], [Prateek Srivastava]\n\nThis is an example implementation of an\n\u003ca href=\"https://developer.amazon.com/docs/custom-skills/host-a-custom-skill-as-a-web-service.html\"\u003eHTTPS Amazon Alexa Skill\u003c/a\u003e\ninterface (or\n\u003ca href=\"https://developer.amazon.com/docs/custom-skills/host-a-custom-skill-as-a-web-service.html\"\u003eCustom Skill\u003c/a\u003e)\nto process\n\u003ca href=\"https://developer.amazon.com/docs/custom-skills/request-and-response-json-reference.html\"\u003eAlexa JSON requests\u003c/a\u003e\nand generate a response programmed in \u003ca href=\"https://golang.org/\"\u003eGo\u003c/a\u003e.\n\n\n## The HTTPS Server\n\nIn the *main* function you will find the following lines that basically fire up the HTTPS server:\n\n    http.HandleFunc(\"/\", MyServer)\n\terr := http.ListenAndServeTLS(\":443\", \"certificate.pem\", \"privatekey.pem\", nil)\n\tif err != nil {\n\t\tlog.Fatal(\"ListenAndServe: \", err)\n\t}\n\nYou will have to make sure that you either use existing keys (*certificate.pem* and *privatekey.pem*) or create\nself-signed keys by following for example the instructions on the\n[Amazon Alexa *Test a Custom Skill*](https://developer.amazon.com/docs/custom-skills/test-a-custom-skill.html#create-a-private-key-and-self-signed-certificate-for-testing)\npage.\n\nThe implementation of\n\n    func MyServer(w http.ResponseWriter, req *http.Request) {\n    ...\n    }\n\ncontains code to process the HTTP header:\n\n\tvar header map[string]string\n\theader = make(map[string]string)\n\tfor _, element := range []string{\"Content-Type\",\n\t                                 \"Host\",\n\t                                 \"From\",\n\t                                 \"Content-Language\",\n\t                                 \"Content-Encoding\",\n\t                                 \"Server\",\n\t                                 \"Date\",\n\t                                 \"User-Agent\"} {\n\t\tv := req.Header.Get(element)\n\t\tif v != \"\" {\n\t\t\theader[element] = v\n\t\t}\n\t}\n\nYou can extend the header elements by adding your own keywords for HTTP headers. See the\n[Wikipedia page on HTTP-header fields](https://en.wikipedia.org/wiki/List_of_HTTP_header_fields)\nfor more details.\n\nYou can read the content of the HTTP-message body using the following code:\n\n\tb, err := ioutil.ReadAll(req.Body)\n\tif err != nil {\n\t\tfmt.Println(err)\n\t\terr = req.Body.Close()\n\t\tif err != nil {\n\t\t\tfmt.Println(err)\n\t\t}\n\t} else {\n\t\t// Process the body of the message here\n\t}\n\nAssuming that you set up all necessary structs in *AlexaRequest.go*, you can *unmarshal* the JSON data transmitted from\nthe Amazon Alexa server using the following code:\n\n\tjdata := \u0026AlexaRequest{\n\t\tSession: \u0026Session{},\n\t\tContext: \u0026Context{},\n\t\tRequest: \u0026Request{},\n\t}\n\terr := json.Unmarshal(b, jdata)\n\nWe generate a response to the Amazon Alexa server using the following code:\n\n\tw.Header().Set(\"Content-Type\", \"application/json; charset=UTF-8\")\n\tw.WriteHeader(http.StatusOK)\n    w.Write([]byte(`{\"version\": \"1.0\", \"response\": {\"outputSpeech\": {\"type\": \"PlainText\", \"text\": \"This is an example response. Can I help you with anything else?\"}, \"shouldEndSession\": true}}`))\n\nYou can now replace the *w.Write* function call with the message that you generate using your particular response\nfunctions.\n\n\n\n\n## The JSON Parser\n\nVia the Alexa HTTPS Custom Client interface you receive a JSON Request object. In the code repo you will find a sample\n*AlexaRequest.json*. See above one possible way to process JSON data objects in Go. There are of course many more\nalternative ways.\n\n\n\n## The XML-RPC Interface\n\nOur implementation is part of a broader system of Microservices that communicate using\n\u003ca href=\"https://en.wikipedia.org/wiki/XML-RPC\"\u003eXML-RPC\u003c/a\u003e or\n\u003ca href=\"https://en.wikipedia.org/wiki/JSON-RPC\"\u003eJSON-RPC\u003c/a\u003e. We create a very simple\n\u003ca href=\"https://en.wikipedia.org/wiki/XML-RPC\"\u003eXML-RPC\u003c/a\u003e request establishing an\n\u003ca href=\"https://en.wikipedia.org/wiki/Hypertext_Transfer_Protocol\"\u003eHTTP\u003c/a\u003e-connection to our main Dispatcher module\nin an \u003ca href=\"https://en.wikipedia.org/wiki/Natural_language_processing\"\u003eNLP\u003c/a\u003e pipeline.\n\nWhatever the utterance is that Alexa sends to our server, we extract it and send it to the *callDispatcher* function.\n\n*callDispatcher* transfers the utterance to an HTTP-based XML-RPC server.\n\nInstead of recreating some XML-RPC package for Go, I took the simple solution to generate a simplified XML response and\ncommunicate it to the XML-RPC server using an\n\n\tvar buffer bytes.Buffer\n\tbuffer.WriteString(`\u003c?xml version=\"1.0\"?\u003e\u003cmethodCall\u003e\u003cmethodName\u003eparse\u003c/methodName\u003e\u003cparams\u003e\u003cparam\u003e\u003cvalue\u003e\u003cstring\u003e`)\n\tbuffer.WriteString(text)\n\tbuffer.WriteString(`\u003c/string\u003e\u003c/value\u003e\u003c/param\u003e\u003c/params\u003e\u003c/methodCall\u003e`)\n\nWe create an HTTP-client:\n\n\tclient := \u0026http.Client{}\n\nWe establish a new request for this client using the HTTP POST method:\n\n\thost := \"localhost\"\n\tport := \"1234\"\n\treq, err := http.NewRequest(http.MethodPost, \"http://\"+host+\":\"+port, strings.NewReader(buffer.String()))\n\tif err != nil {\n\t\tlog.Fatal(err)\n\t}\n\nWe create an HTTP header:\n\n\treq.Header.Add(\"Content-Type\", \"text/xml\")\n\tvar contLength = string(buffer.Len())\n\treq.Header.Add(\"Content-Length\", contLength)\n\nAnd, finally we submit the entire request to the XML-RPC server:\n\n\t_, err = client.Do(req)\n\tif err != nil {\n\t\tlog.Fatal(err)\n\t}\n\n\n\n\n[Damir Cavar]: http://damir.cavar.me/ \"Damir Cavar homepage\"\n[Rashmi Bidanta]: https://github.com/rbidanta \"Rashmi Bidanta GitHub page\"\n[Prateek Srivastava]: https://github.com/prateek22sri \"Prateek Srivastava GitHub page\"\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdcavar%2Falexa_https","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fdcavar%2Falexa_https","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdcavar%2Falexa_https/lists"}