验证的方法代码:
function dbmethods:auth_scram_sha1(username, password)
local user = string.gsub(string.gsub(username, '=', '=3D'), ',' , '=2C')
local nonce = ngx.encode_base64(string.sub(tostring(math.random()), 3 , 14))
local first_bare = "n=" .. user .. ",r=" .. nonce
local sasl_start_payload = ngx.encode_base64("n,," .. first_bare)
r, err = self:cmd(attachpairs_start({
saslStart = 1 ;
mechanism = "SCRAM-SHA-1" ;
autoAuthorize = 1 ;
payload = sasl_start_payload ;
} , "saslStart" ) )
if not r then
return nil, err
end
local conversationId = r['conversationId']
local server_first = r['payload']
local parsed_s = ngx.decode_base64(server_first)
local parsed_t = {}
for k, v in string.gmatch(parsed_s, "(%w+)=([^,]*)") do
parsed_t[k] = v
end
local iterations = tonumber(parsed_t['i'])
local salt = parsed_t['s']
local rnonce = parsed_t['r']
if not string.sub(rnonce, 1, 12) == nonce then
return nil, 'Server returned an invalid nonce.'
end
local without_proof = "c=biws,r=" .. rnonce
local pbkdf2_key = pass_digest ( username , password )
local salted_pass = pbkdf2_hmac_sha1(pbkdf2_key, iterations, ngx.decode_base64(salt), 20)
local client_key = ngx.hmac_sha1(salted_pass, "Client Key")
local stored_key = ngx.sha1_bin(client_key)
local auth_msg = first_bare .. ',' .. parsed_s .. ',' .. without_proof
local client_sig = ngx.hmac_sha1(stored_key, auth_msg)
local client_key_xor_sig = xor_bytestr(client_key, client_sig)
local client_proof = "p=" .. ngx.encode_base64(client_key_xor_sig)
local client_final = ngx.encode_base64(without_proof .. ',' .. client_proof)
local server_key = ngx.hmac_sha1(salted_pass, "Server Key")
local server_sig = ngx.encode_base64(ngx.hmac_sha1(server_key, auth_msg))
r, err = self:cmd(attachpairs_start({
saslContinue = 1 ;
conversationId = conversationId ;
payload = client_final ;
} , "saslContinue" ) )
if not r then
return nil, err
end
parsed_s = ngx.decode_base64(r['payload'])
parsed_t = {}
for k, v in string.gmatch(parsed_s, "(%w+)=([^,]*)") do
parsed_t[k] = v
end
if parsed_t['v'] ~= server_sig then
return nil, "Server returned an invalid signature."
end
if not r['done'] then
r, err = self:cmd(attachpairs_start({
saslContinue = 1 ;
conversationId = conversationId ;
payload = ngx.encode_base64("") ;
} , "saslContinue" ) )
if not r then
return nil, err
end
if not r['done'] then
return nil, 'SASL conversation failed to complete.'
end
return 1
end
return 1
end
完整文件github的地址:
https://github.com/LuaDist2/l...
이 문제를 어떻게 해결하나요? 계정과 비밀번호를 추가한 후 각 쿼리 요청을 확인해야 하며 시간이 30ms에서 500ms로 늘어납니다
Openresty에는 연결 풀이 있으며, 데이터베이스와 처음 연결될 때만 인증이 수행되므로 큰 영향을 미치지 않습니다
매번 확인할 필요는 없겠죠?