websocket AWS.ApiGatewayManagementApi()postToConnection不工作

rmbxnbpk  于 2023-05-07  发布在  Pig
关注(0)|答案(5)|浏览(139)

我正在尝试使用**AWS.ApiGatewayManagementApi() postToConnection**方法向通过套接字连接的客户端发送消息。它在本地运行良好,但在ec2中不工作。唯一的区别是VPC。有问题吗?

var AWS = require('aws-sdk');

var awsGW = new AWS.ApiGatewayManagementApi({
    endpoint: "https://endpoint",
    accessKeyId: "accessKeyId",
    secretAccessKey: "secretAccessKey",
    region: "region"
});

awsGW.postToConnection({
    ConnectionId: 'ConnectionId',
    Data: '{"key1":"msg1","key2":"msg2"}'
}, (err, success) => {
    if (err) {
        console.log('Socket error', err);
    } else {
    }
});

错误:

{ ForbiddenException: Forbidden
    at Object.extractError (/home/ubuntu/git/backend/node_modules/aws-sdk/lib/protocol/json.js:51:27)
    at Request.extractError (/home/ubuntu/git/backend/node_modules/aws-sdk/lib/protocol/rest_json.js:55:8)
    at Request.callListeners (/home/ubuntu/git/backend/node_modules/aws-sdk/lib/sequential_executor.js:106:20)
    at Request.emit (/home/ubuntu/git/backend/node_modules/aws-sdk/lib/sequential_executor.js:78:10)
    at Request.emit (/home/ubuntu/git/backend/node_modules/aws-sdk/lib/request.js:683:14)
    at Request.transition (/home/ubuntu/git/backend/node_modules/aws-sdk/lib/request.js:22:10)
    at AcceptorStateMachine.runTo (/home/ubuntu/git/backend/node_modules/aws-sdk/lib/state_machine.js:14:12)
    at /home/ubuntu/git/backend/node_modules/aws-sdk/lib/state_machine.js:26:10
    at Request.<anonymous> (/home/ubuntu/git/backend/node_modules/aws-sdk/lib/request.js:38:9)
    at Request.<anonymous> (/home/ubuntu/git/backend/node_modules/aws-sdk/lib/request.js:685:12)
  message: 'Forbidden',
  code: 'ForbiddenException',
  time: 2019-06-10T07:40:02.214Z,
  requestId: 'f4caef03-8b52-11e9-9cc3-91bfe40b8eb0',
  statusCode: 403,
  retryable: false,
  retryDelay: 37.0834357877396 }
vs3odd8k

vs3odd8k1#

我遇到了一个类似的问题,这是因为我使用了错误的端点。我是从event对象生成的,但是是在一个普通的API请求上,所以我得到了一个不同服务的端点(普通的API,而不是WebSocket)。
如果你的websockets服务被部署到一个类似wss://abcd的URL,那么你的端点应该是https://abcd

q5lcpyga

q5lcpyga2#

在我的例子中,在我用来示例化

new AWS.ApiGatewayManagementApi({
    endpoint,
    region,
})

注:终点可提供2种形式:

  • 自定义域名+基础路径Map,例如:wss.my-super-website-with-websocket.com/v1(其中v1是配置的基本路径Map)
  • 默认aws样式的url,如https://********.execute-api.us-east-5.amazonaws.com/prod,其中prod是API网关中配置的stage。

更重要的是,为了您的调试目的,如果您感到绝望,我发现您可以很容易地记录aws-sdk发出的请求,以确保您正在发出正确的请求(使用aws cli尝试请求也是一个好主意):node_modules\aws-sdk\lib\event_listeners.js

function executeSend() {
  var http = AWS.HttpClient.getInstance();
  var httpOptions = resp.request.service.config.httpOptions || {};
  try {
    console.log('event listener execute send', resp.request.httpRequest); // only this line is added
    ...
3pvhb19x

3pvhb19x3#

403听起来您需要为调用postToConnection的IAM角色更新策略
在我的例子中,我有明确的缺失规则,因此我必须附加ExecuteAPI的授权

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "VisualEditor0",
            "Effect": "Allow",
            "Action": "execute-api:*",
            "Resource": "arn:aws:execute-api:eu-west-1:###########:*/*/*/*"
        }
    ]
}
o3imoua4

o3imoua44#

我遇到了同样的问题-我在私有子网中的VPC内有Lambda,并且有API网关的VPC端点,但它总是返回403 Forbidden
这很奇怪,但在将VPC端点替换为NAT网关后,问题消失了。

xn1cxnb4

xn1cxnb45#

这就是我的工作来源:https://docs.aws.amazon.com/AWSJavaScriptSDK/v3/latest/clients/client-apigatewaymanagementapi/classes/posttoconnectioncommand.html

import { PostToConnectionCommand } from "@aws-sdk/client-apigatewaymanagementapi";

const input = {
   Data: response,
   ConnectionId: connectId,
};
const command = new PostToConnectionCommand(input);
await client.send(command);

相关问题