我正在使用亚马逊 SNS。通知运行良好,但有时我会收到此错误:
{
"message": "Endpoint is disabled",
"code": "EndpointDisabled",
"name": "EndpointDisabled",
"statusCode": 400,
"retryable": false
}
也许你知道为什么。
我正在使用亚马逊 SNS。通知运行良好,但有时我会收到此错误:
{
"message": "Endpoint is disabled",
"code": "EndpointDisabled",
"name": "EndpointDisabled",
"statusCode": 400,
"retryable": false
}
也许你知道为什么。
您可以创建一个新的 SNS 主题push-notification-failures
,然后将您的 APNS/APNS_SANDBOX 应用程序的“交付失败”事件与其关联。通过电子邮件订阅事件(并确认),您将获得有关失败的有用调试信息。这一切都可以通过 SNS 控制台完成,并且不需要执行 API 调用。
订阅此 SNS 主题的 HTTP 端点并记录所有交付失败可能是值得的,这样您就可以处理历史数据并调试生产问题。
例如FailureMessage
,“与端点关联的平台令牌无效”的传递意味着您正在从 APNS_SANDBOX 向 APNS 注册设备发送消息,反之亦然。这可能意味着您的构建系统有错误的 APNS 设置。(我们有一个令人沮丧的问题,即开发人员使用 APNS_SANDBOX 构建二进制文件,而 TestFlight 使用 APNS 构建二进制文件进行本地测试和 QA,这正是导致我走上这条道路的原因。)
到目前为止,我发现了 3 个原因:
这些是关于 Iphons/Ipads 的。
可以禁用端点的原因很少。我没有在任何地方看到它的记录(可能错过了它),这是我从支持中得到的:
您推送到端点,但令牌无效/过期。令牌在以下情况下无效:
它属于设备上不再安装的应用程序。
如果设备已从备份中恢复。这会使令牌无效,您的应用应请求新令牌并相应地更新 SNS 端点令牌。
应用程序已重新安装在同一设备上。在 Android 的情况下,应用程序被分配了一个新的令牌。APN 也会发生这种情况,但 Android 更常见。
对于 APN,在 xCode 中选择了错误的配置文件。在这种情况下,通知会失败,并且稍后会在 APNs 反馈后禁用设备。
如果错误地将 IOS 开发代币用于 IOS 生产应用程序,反之亦然。
如果 Apple 出于任何原因使您的 IOS 推送证书无效或有人从 iTunes 连接门户撤销推送证书。这需要几个小时才能禁用设备。
如果您从 Google 开发人员控制台更新 API 密钥而不更新 SNS 中的平台应用程序凭据,则与 GCM 相同。
您推送到 APNs 设备端点,但由于推送证书过期,应用程序已被禁用。
您推送到 GCM 设备端点,但 API 密钥已在 Google 开发人员控制台中更新,但 SNS 平台应用程序凭据未相应更新。
有关详细信息,我推荐这篇解决我问题的优秀文章
根据http://docs.aws.amazon.com/sns/latest/APIReference/API_Publish.html这意味着端点被禁用。
已启用——启用/禁用向端点传递的标志。当通知服务向 SNS 指示端点无效时,消息处理器会将其设置为 false。用户可以将其设置回 true,通常在更新 Token 之后。
在这种情况下,“通知服务”指的是谷歌的 GCM、苹果的 APNS 或亚马逊的 ADM。
我遇到过同样的问题。这就是我所做的:
将私钥从 Keychange Access 导出到 *private.p12 文件
将 openssl 与下载的 .cer 文件(来自 iOS Developer MemberCenter)一起使用以创建公共 .pem 证书
将 openssl 与生成的 *private.p12 文件一起使用以创建私有 .pem 密钥文件
从带有 .p12 扩展名的 Keychain Access 中选择 FULL CERTIFICATE,然后输入您在从 Keychain Access 导出时选择的密码 将公共 CERTIFICATE .pem 文件的内容复制到标有“Certificate”的文本区域,包括开始行和结束行:
-----BEGIN CERTIFICATE-----
-----END CERTIFICATE-----
仅将私钥 .pem 文件中以下列行开头和结尾的部分复制到标记为“Private Key”的文本区域:
-----BEGIN RSA PRIVATE KEY-----
-----END RSA PRIVATE KEY-----
我将 Cordova 与 phonegap-plugin-push 1.4.4 一起使用,但我的问题与 phonecap 无关。除了对上面的一些困惑之外,最终对我有用的是,在 XCode 中打开我的项目,找到我的项目的目标,然后启用推送通知。这会自动将“推送通知”权利添加到应用程序 ID。下次在您的设备上安装应用程序时,推送通知应该可以工作。至少它对我有用。
我希望这可以为遇到与我相同问题的人节省 1/2 天的工作时间!:)
采取严厉措施之前的快速清单:
就我而言,我使用第三方 SSL 工具生成了 CSR。我从 Apple 开发者门户获得了有效证书,但没有私钥。然后我尝试了 Windows 的证书工具来导出,但没有成功。浪费时间。启动你的 Mac。
然后我使用 AmazonMobilePush 示例应用程序来获取设备令牌。因为演示的包标识符与我的证书不匹配,所以端点无效。在每个发送端点的 SNS 上都被禁用 (false)。最后原因很明显,但我仍然失去了宝贵的时间。
如果您收到错误End Point is Disabled
消息,请使用以下代码启用端点,然后使用 Amazon 凭证推送通知:
*//Enable Device*
var sns = new AmazonSimpleNotificationServiceClient("AwsAccesskeyId", "AwsSecrteAccessKey", RegionEndpoint.USWest1);
Dictionary<string, string> objDictCheckEndpointEnable = new Dictionary<string, string>();
objDictCheckEndpointEnable.Add("Enabled", "False");
sns.SetEndpointAttributes(new SetEndpointAttributesRequest
{
Attributes = objDictCheckEndpointEnable,
EndpointArn = "AwsEndPointArn" //This is Device End Point Arn
});
*//End*
对我来说,我收到“与端点关联的平台令牌无效”,因为我的 SNS 平台应用程序端点设置不正确。具体来说,即使它包含正确的证书和私钥,SNS 控制台也没有从我的 .p12 文件中正确读取凭据。基于这篇文章的解决方案是创建第二个 .p12 文件,其中包含证书但没有密钥。我从第一个 .p12 文件加载了凭据,然后加载了第二个 .p12 文件的凭据。当我这样做时,我可以看到证书字符串发生了变化,之后我就没有问题了。
如果您正在创建生产端点,SNS 会警告您有关不匹配的证书,但它不会对开发端点进行此类检查。您知道端点被破坏的唯一方法是当您收到平台令牌错误时。
我当然希望这对那里的人有所帮助,因为它让我分心。
我正在使用这个。如果获取终端节点响应发现 NotFound 错误,它会创建一个终端节点(这绝不应该发生,但见鬼,它在 AWS SNS 文档网站上)。如果这没有发生,则意味着您正在获取端点的信息。它可以是好的(令牌匹配并且启用是真的),或者相反(在这种情况下你需要更新它)。
- (void)getEndpointDetailsWithResponse:(void(^)(AWSSNSGetEndpointAttributesResponse *response, AWSTask *))handleResponse {
NSString * deviceTokenForAWS = [self deviceTokenForAWS];
AWSSNS *manager = [AWSSNS SNSForKey:@"EUWest1SNS"];
AWSSNSGetEndpointAttributesInput *input = [AWSSNSGetEndpointAttributesInput new];
input.endpointArn = self.endpointArn;
AWSTask *getEndpointAttributesTask = [manager getEndpointAttributes:input];
[getEndpointAttributesTask continueWithBlock:^id(AWSTask *task) {
NSLog(@"%@ Error: %@", task.result, task.error);
AWSSNSGetEndpointAttributesResponse *result = task.result;
NSError *error = task.error;
if (error.code == AWSSNSErrorNotFound) {
[self createEndpointWithResponse:^(AWSSNSCreateEndpointResponse *createResponse) {
dispatch_async(dispatch_get_main_queue(), ^{
if (handleResponse != nil) {
handleResponse(result, task);
}
});
}];
} else {
NSLog(@"response for get endpoint attributes : %@", result);
NSString *token = [result.attributes valueForKey:@"Token"];
NSString *enabled = [result.attributes valueForKey:@"Enabled"];
NSLog(@"token : %@, enabled : %@", token, enabled);
BOOL wasSuccessful = [token isEqualToString:deviceTokenForAWS] && ([enabled localizedCaseInsensitiveCompare:@"true"] == NSOrderedSame);
if (!wasSuccessful) {
NSLog(@"device token does not match the AWS token OR it is disabled!");
NSLog(@"Need to update the endpoint");
AWSSNSSetEndpointAttributesInput *seai = [AWSSNSSetEndpointAttributesInput new];
seai.endpointArn = self.endpointArn;
NSDictionary *attributes = [NSDictionary dictionaryWithObjectsAndKeys:deviceTokenForAWS, @"Token", @"true", @"Enabled", nil];
seai.attributes = attributes;
AWSTask *setEndpointAttributesTask = [manager setEndpointAttributes:seai];
[setEndpointAttributesTask continueWithBlock:^id(AWSTask *task) {
NSLog(@"response : %@, error: %@", task.result, task.error);
dispatch_async(dispatch_get_main_queue(), ^{
if (handleResponse != nil) {
handleResponse(result, task);
}
});
return nil;
}];
} else {
NSLog(@"all is good with the endpoint");
dispatch_async(dispatch_get_main_queue(), ^{
if (handleResponse != nil) {
handleResponse(result, task);
}
});
}
}
return nil;
}];
}
这是此处找到的 AWS SNS 令牌管理文档的确切副本:https ://mobile.awsblog.com/post/Tx223MJB0XKV9RU/Mobile-token-management-with-Amazon-SNS
如果需要,我可以附上我的实现的其余部分,但这部分是最重要的部分。