我已经使用AWS API Gateway设置了一个基本API,我想将我的端点链接到我在EC2实例上运行的服务(使用" HTTP代理"集成类型)。我已经读过为了锁定我的EC2服务器只接受来自API网关的流量,我基本上有以下两种选择之一:
我想使用#2的变体,而不是在EC2服务实例本身上验证证书,我想在另一个运行Haproxy的实例上进行验证。我已经使用Haproxy设置了第二个EC2实例,并将其指向我的另一个实例作为后端。我已经锁定了我的服务实例,因此它只接受来自Haproxy实例的请求。这一切都有效。我一直在努力弄清楚的是如何在Haproxy机器上验证AWS Gateway Client证书(我已生成)。我已经完成了大量的谷歌搜索,并且令人惊讶地没有关于如何做到这一点的零信息。几个问题:
这里有任何帮助吗?
解决方案更新
-----BEGIN PRIVATE KEY----- # private key I generated locally... -----END PRIVATE KEY----- -----BEGIN CERTIFICATE----- # cert from gandi... -----END CERTIFICATE----- # two certs from file in the above link
我保存了这个新的PEM文件(如haproxy.pem)并在我的HAproxy前端绑定语句中使用它,如下所示:
bind :443 ssl crt haproxy.pem verify required ca-file api-gw-cert.pem
上述绑定语句中的api-gw-cert.pem是一个文件,其中包含我在API网关控制台中生成的客户端证书。现在,HAproxy机器可以正确阻止来自除网关之外的任何流量。
答案 0 :(得分:1)
我所做的阅读建议我需要生成一个CA,然后使用该CA生成服务器和客户端证书。
这是一种方法,但在这种情况下并不适用。
您的HAProxy需要配置由受信任的CA签署的有效SSL证书 - 而不是签署客户端证书的证书,而不是您创建的证书。它必须是由公共可信CA签名的证书,其根证书位于API网关后端系统的信任库中... 应与您的Web基本相同浏览器信任,但可能是一个子集。
正如您的网络浏览器不会向拥有自签名证书的服务器发送SSL而不会发出必须绕过的警告,但API网关的后端不会与不受信任的证书进行协商(以及没有旁路)。
我只想说,在试图让它使用客户端证书之前,您需要让API Gateway通过TLS 与您的HAProxy通信,否则您将引入太多未知数。另请注意,您无法使用Amazon Certificate Manager证书,因为这些证书仅适用于CloudFront和ELB,它们都不会直接支持客户端证书。
HAProxy使用API网关后,您需要将其配置为对客户端进行身份验证。
您的ssl
声明中需要verify required
和bind
,但无法验证SSL客户端证书
我只能从我能说的内容中访问客户端证书。
这就是你所需要的一切。
bind ... ssl ... verify required ca-file /etc/haproxy/api-gw-cert.pem
。
SSL证书本质上是一个信任层次结构。树顶部的信任是明确的。通常,CA是明确信任的,并且它已签名的任何内容都是隐式信任的。 CA"担保"它签署的证书......对于证书,它使用CA属性集进行签名,CA属性集也可以在其下签署证书,从而扩展了隐含的信任。
但是,在这种情况下,您只需将客户端证书作为CA文件放入,然后将客户端证书"保证为" ...本身。呈现相同证书的客户端是受信任的,其他任何人都是断开连接的。当然,仅拥有证书对于客户端与您的代理进行通信是不够的 - 客户端还需要API网关所具有的匹配私钥。
因此,请考虑这两个单独的要求。首先通过TLS获取API网关与您的代理进行通信...之后,根据客户端证书进行身份验证实际上是更容易的部分。
答案 1 :(得分:0)
我认为您正在混淆服务器证书和客户端证书。在这种情况下,API Gateway是客户端,HAProxy是服务器。您希望HAProxy验证API Gateway发送的客户端证书。 API Gateway将为您生成证书,您只需配置HAProxy即可验证其处理的每个请求中是否存在证书。
我猜你可能正在查看他们告诉你生成客户端证书的this tutorial,然后配置HAProxy以验证该证书。由于API Gateway正在为您生成证书,因此可以跳过该教程的“生成证书”部分。
您只需单击API网关中的“生成”按钮,然后复制/粘贴它所呈现的证书的内容,并将其保存为HAProxy服务器上的.pem文件。现在我不是一个大的HAProxy用户,但我认为从该教程中获取HAProxy配置的示例如下所示:
case IS_BOOL:
if (type != BP_VAR_UNSET && Z_LVAL_P(container)==0) {
goto convert_to_array;
}
/* break missing intentionally */
default:
if (type == BP_VAR_UNSET) {
zend_error(E_WARNING, "Cannot unset offset in a non-array variable");
result->var.ptr_ptr = &EG(uninitialized_zval_ptr);
PZVAL_LOCK(EG(uninitialized_zval_ptr));
} else { // Gets here when boolean value equals true.
zend_error(E_WARNING, "Cannot use a scalar value as an array");
result->var.ptr_ptr = &EG(error_zval_ptr);
PZVAL_LOCK(EG(error_zval_ptr));
}
break;