2012-08-09 73 views
1

我已经在客户端的服务器&上成功部署了GCM示例应用程序。我能够成功注册设备。但是,当我试图将消息发送到设备,正在显示以下异常在服务器日志:实施Google云消息传递时在Web服务器上的例外情况

Exception in thread "pool-1-thread-1" java.lang.IllegalArgumentException: argume 
nt cannot be null 
     at com.google.android.gcm.server.Sender.nonNull(Sender.java:553) 
     at com.google.android.gcm.server.Sender.getString(Sender.java:534) 
     at com.google.android.gcm.server.Sender.sendNoRetry(Sender.java:365) 
     at com.google.android.gcm.server.Sender.send(Sender.java:261) 
     at com.google.android.gcm.demo.server.SendAllMessagesServlet$1.run(SendA 
llMessagesServlet.java:119) 
     at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExec 
utor.java:886) 
     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor 
.java:908) 
     at java.lang.Thread.run(Thread.java:662) 
Exception in thread "pool-1-thread-2" java.lang.IllegalArgumentException: argume 
nt cannot be null 
     at com.google.android.gcm.server.Sender.nonNull(Sender.java:553) 
     at com.google.android.gcm.server.Sender.getString(Sender.java:534) 
     at com.google.android.gcm.server.Sender.sendNoRetry(Sender.java:365) 
     at com.google.android.gcm.server.Sender.send(Sender.java:261) 
     at com.google.android.gcm.demo.server.SendAllMessagesServlet$1.run(SendA 
llMessagesServlet.java:119) 
     at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExec 
utor.java:886) 
     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor 
.java:908) 
     at java.lang.Thread.run(Thread.java:662) 

在浏览器中,

下面的消息显示,但设备亘古不接收任何消息由于例外。

异步发送1个播报文到2个设备

任何提示/建议将是有益的。

回答

3

我得到了完全相同的错误。查看Sender.java的源代码,当发送者试图通过HttpURLConnection.getErrorStream()来找出错误的性质时,这看起来就会发生。

if (status != 200) { 
    // Exception on the line below due to getErrorStream() returning null 
    responseBody = getString(conn.getErrorStream()); 
    logger.finest("JSON error response: " + responseBody); 
    throw new InvalidRequestException(status, responseBody); 
} 

在我的情况下,错误是越来越触发由于GCM服务器返回401(我已经忘记了我是VPNed的工作,并没有白列出的IP在我的谷歌API帐户)。

您可能会从服务器获得非200状态。尝试看看是什么问题通过:

$ curl -D headers.txt --header "Authorization: key=$api_key" --header Content-Type:"application/json" https://android.googleapis.com/gcm/send -d "{\"registration_ids\":[\"$registrationID\"]}" && cat headers.txt 

其中$ api_key是您的apiKey和$ registrationID是目标注册ID。

发件人没有正确处理这个事实是一个不同的问题,但我不确定它是否与gcm库尝试读取错误的方式有关,或者它与jdk有关。 (1.6这里)。这是非常奇怪的,因为GCM文档mention this scenario明确地被抛出。

根据该文档,getErrorStream()将返回null:

如果没有出现过错误,连接未连接或 服务器发送无用的数据。

  • 我们知道有一个错误
  • 我们知道有一个连接(401在我的情况被退回)
  • 我们知道服务器发送有用的数据(状态码= 200检查!):

从未经授权的IP:

[[email protected] ~]$ curl -D headers.txt --header "Authorization: key=$api_key" --header Content-Type:"application/json" https://android.googleapis.com/gcm/send -d "{\"registration_ids\":[\"$registrationID\"]}" && cat headers.txt 

<HTML> 
<HEAD> 
<TITLE>Unauthorized</TITLE> 
</HEAD> 
<BODY BGCOLOR="#FFFFFF" TEXT="#000000"> 
<H1>Unauthorized</H1> 
<H2>Error 401</H2> 
</BODY> 
</HTML> 
HTTP/1.1 401 Unauthorized 
Content-Type: text/html; charset=UTF-8 
Date: Tue, 14 Aug 2012 00:30:47 GMT 
Expires: Tue, 14 Aug 2012 00:30:47 GMT 
Cache-Control: private, max-age=0 
X-Content-Type-Options: nosniff 
X-Frame-Options: SAMEORIGIN 
X-XSS-Protection: 1; mode=block 
Server: GSE 
Transfer-Encoding: chunked 

编辑: 这现在已经进入了作为一个问题来这里的GCM项目:http://code.google.com/p/gcm/issues/detail?id=7

编辑: 的问题已解决,并应可在gcm.jar辅助类的下一个版本。

0

对发件人的参数不能为空。如果您将空作为参数传递给发件人,请检入日志。 例如,如果您有类似:

Sender sender = new Sender(businessLayer.Helper.getAndroidAPIkey()); 

如果由于某种原因businessLayer.Helper.getAndroidAPIkey()为空,你会得到这个例外。

+0

如果您查看堆栈跟踪,执行会一直发送到sendNoRetry(),它在构造发件人之后调用(在调用send()之后调用)。如果您查看Sender.java,则“null”值将来自调用getErrorStream()而不是传递给发件人的参数。 – 2012-08-14 16:37:36