我在食谱中使用了这个http_request
块:
http_request 'some request' do
url 'https://'"#{node[:chef][:node_name]}"'/v1/xyz'
headers ({
'AUTHORIZATION' => "Basic #{Base64.encode64('#{node[\'user\']}:#{node[\'password\']')}",
})
action :get
end
但是当我尝试执行它时出现此错误:
[2017-05-12T21:39:04-04:00] ERROR: http_request[some request] (mi_activemq::default line 58) had an error: OpenSSL::SSL::SSLError: SSL Error connecting to https://... - SSL_connect returned=1 errno=0 state=error: certificate verify failed
如果我对username:password
进行硬编码,则按预期方式工作:
'AUTHORIZATION' => "Basic #{Base64.encode64('username:password')}",
答案 0 :(得分:1)
你那里有各种各样的转义字符,但错误与证书或网址中的错误名称有关。
只需将用户/传递放入网址
即可url "https://#{node['user']}:#{node['password']@#{node['fqdn']}/v1/xyz"
其中node['fqdn']
是证书中的名称。
答案 1 :(得分:1)
您需要学习如何将值插入字符串。从这个Hash定义开始:
node = {
chef: {
node_name: 'foo'
}
}
这个字符串定义:
'https://'"#{node[:chef][:node_name]}"'/v1/xyz'
# => "https://foo/v1/xyz"
Ruby会将相邻的字符串连接成一个字符串:
'foo'"bar"'baz' # => "foobarbaz"
但代码难以阅读,所以除非你有充分的理由,否则不要这样做。而只需写下来:
'foobarbaz' # => "foobarbaz"
或:
"foobarbaz" # => "foobarbaz"
请记住,代码越混乱,你或其他人在六个月内弄清楚它意味着什么就越难。
因此,请使用:
,而不是上面的字符串"https://#{node[:chef][:node_name]}/v1/xyz"
# => "https://foo/v1/xyz"
您的代码还有其他问题:
require 'base64'
"Basic #{Base64.encode64('#{node[\'user\']}:#{node[\'password\']')}"
# > "Basic I3tub2RlWyd1c2VyJ119OiN7bm9kZVsncGFzc3dvcmQnXQ==\n"
这是问题的症结所在:
'#{node[\'user\']}:#{node[\'password\']'
# => "\#{node['user']}:\#{node['password']"
代码运行时,传递给Base64.encode64
的值就是该字符串。您的变量未进行插值,因此您将始终获得:
# > "Basic I3tub2RlWyd1c2VyJ119OiN7bm9kZVsncGFzc3dvcmQnXQ==\n"
为结果字符串。它没有编码您的用户或密码。
潜在的第二个问题是,您的node
哈希可能没有'user'
或'password'
个密钥,但我们无法分辨,因为您没有提供足够的信息。
调用encode64
的更清晰,更清晰的方法是:
encoded_user_password = Base64.encode64(
node.values_at('user', 'password').join(':')
)
然后将其插入到字符串中:
"Basic #{encoded_user_password}"
我建议熟悉Ruby的URI类,因为它是构建和操作URI的首选方法。