2015-12-06 54 views
0

我正嘗試使用Lua與Cleverbot API進行交互。我有一個密鑰和一個用戶名,所以我測試了郵差,它的工作完美。然後我試圖用Lua做同樣的事情,但我有一個奇怪的錯誤。Lua - HTTPS/tlsv1警報內部錯誤

這是代碼:

local https = require("ssl.https") 
local string = require("string") 
local ltn12 = require ("ltn12") 
local funcs = (loadfile "./libs/functions.lua")() 

local function cleverbot(msg) 
    local params = { 
     ['user'] = 'SyR2nvN1cAxxxxxx', 
     ['key'] = 'ckym8oDRNvpYO95GmTD14O9PuGxxxxxx', 
     ['nick'] = 'cleverbot', 
     ['text'] = tostring(msg), 
    } 

    local body = funcs.encode_table(params) 
    local response = {} 
    ok, code, headers, status = https.request({ 
     method = "POST", 
     url = "https://cleverbot.io/1.0/ask/", 
     headers = { 
      ['Accept'] = '*/*', 
      ['content-type'] = 'application/x-www-form-urlencoded', 
      ['accept-encoding'] = 'gzip', 
      ['content-length'] = tostring(#body), 
     }, 
     print(tostring(ok)), 
     print(tostring(code)), 
     print(tostring(headers)), 
     print(tostring(status)), 

     source = ltn12.source.string(body), 
     sink = ltn12.sink.table(response) 
    }) 

    response = table.concat(response) 

    if code ~= 200 then 
     return 
    end 

    if response[1] ~= nil then 
     return tostring(response) 
    end 
end 

然而,當我把這個,這是那些4幅版畫顯示:

nil 
tlsv1 alert internal error 
nil 
nil 

我嘗試使用HTTP,而不是進行連接,但是這是什麼發生:

1 
301 
table: 0xe5f7d60 
HTTP/1.1 301 Moved Permanently 

response總是空的。請問我做錯了什麼? 謝謝!

+0

你調用https.request的方式肯定是錯誤的。爲什麼要將打印函數的結果傳遞給https.request參數表? – marsgpl

+0

哦,嘿@marsgpl,我不知道這可能會影響結果。我刪除了它,並在其外面放置了一個「打印(確定,代碼,標題,狀態)」。我也刪除了'funcs.encode_table(params)'的東西,我正在測試一個已經格式化的參數字符串。我也在裏面加了'protocol =「tlsv1」',但結果完全一樣。還有什麼錯誤? – bokirov

+0

好吧,試着檢查openssl庫的存在,確保它沒有過期。 – marsgpl

回答

0

我強烈的懷疑是,目標主機(cleverbot.io)堅持通過SNI(服務器名稱指示)獲取主機名,而您使用的ssl-library不會發送該主機名。通常,服務器會使用默認網站,但當然它們可以自由地讓握手失敗。看起來像這樣,什麼cloudflare(cleverbot.io託管或代理通過)。

不幸的是沒有簡單的方法來解決這個問題,除非底層ssl庫改爲使用sni與主機名cleverbot.io進行ssl握手。

參見

Fails: 
openssl s_client -connect cleverbot.io:443 -tls1_1 

Succeeds: 
openssl s_client -servername cleverbot.io -connect cleverbot.io:443 -tls1_1 

這意味着,不僅底層SSL庫必須支持SNI,而且還具備被告知,通過LUA結合層之間要使用的服務器名。例如Luasec目前沒有使用sni,afaik

+0

我找到了這個:https://github.com/brunoos/luasec/blob/master/samples/ sni/client.lua 我會試試看看它是否有效。否則,我會找到一種方法在js中做到這一點。感謝您的詳細解答! – bokirov