从GAE到FCM的发布请求在getAccessToken()失败

时间:2018-01-07 09:55:48

标签: google-app-engine firebase firebase-cloud-messaging google-oauth2

我有以下代码来获取稍后用于对FCM的POST请求的访问令牌。以下代码在部署后立即生效,并在一段时间后失败。

FileInputStream serviceAccountCreds= new FileInputStream("path/to/serviceAccountKey.json");
        HttpTransport httpTransport = GoogleNetHttpTransport.newTrustedTransport();
        JsonFactory jsonFactory = JacksonFactory.getDefaultInstance();
        GoogleCredential credential = GoogleCredential
                .fromStream(serviceAccountCreds, httpTransport, jsonFactory)
                .createScoped(Arrays.asList(FIREBASE_SCOPE));
        credential.refreshToken();
        return credential.getAccessToken();

堆栈跟踪如下:

java.net.UnknownHostException: accounts.google.com
at java.net.AbstractPlainSocketImpl.connect (AbstractPlainSocketImpl.java:184)
at java.net.SocksSocketImpl.connect (SocksSocketImpl.java:392)
at java.net.Socket.connect (Socket.java:589)
at sun.security.ssl.SSLSocketImpl.connect (SSLSocketImpl.java:668)
at sun.net.NetworkClient.doConnect (NetworkClient.java:175)
at sun.net.www.http.HttpClient.openServer (HttpClient.java:432)
at sun.net.www.http.HttpClient.openServer (HttpClient.java:527)
at sun.net.www.protocol.https.HttpsClient.<init> (HttpsClient.java:264)
at sun.net.www.protocol.https.HttpsClient.New (HttpsClient.java:367)
at sun.net.www.protocol.https.AbstractDelegateHttpsURLConnection.getNewHttpClient (AbstractDelegateHttpsURLConnection.java:191)
at sun.net.www.protocol.http.HttpURLConnection.plainConnect0 (HttpURLConnection.java:1138)
at sun.net.www.protocol.http.HttpURLConnection.plainConnect (HttpURLConnection.java:1032)
at sun.net.www.protocol.https.AbstractDelegateHttpsURLConnection.connect (AbstractDelegateHttpsURLConnection.java:177)
at sun.net.www.protocol.http.HttpURLConnection.getOutputStream0 (HttpURLConnection.java:1316)
at sun.net.www.protocol.http.HttpURLConnection.getOutputStream (HttpURLConnection.java:1291)
at sun.net.www.protocol.https.HttpsURLConnectionImpl.getOutputStream (HttpsURLConnectionImpl.java:250)
at com.google.api.client.http.javanet.NetHttpRequest.execute (NetHttpRequest.java:77)
at com.google.api.client.http.HttpRequest.execute (HttpRequest.java:972)
at com.google.api.client.auth.oauth2.TokenRequest.executeUnparsed (TokenRequest.java:283)
at com.google.api.client.auth.oauth2.TokenRequest.execute (TokenRequest.java:307)
at com.google.api.client.googleapis.auth.oauth2.GoogleCredential.executeRefreshToken (GoogleCredential.java:384)

...

代码在Google App Engine应用程序中执行,因此GoogleCredential可能无法进行HTTPRequest吗? (我记得在GAE的文档中读过这些内容)。如果是这样,那么在这里使用正确的HTTP传输是什么?

1 个答案:

答案 0 :(得分:0)

我的猜测是正确的。 GoogleCredential发出的Http调用被Google App Engine阻止,因为它使用的是Socket API。将此行添加到appengine-web.xml中会强制Http(s)请求使用urlfetch。

应用服务引擎-web.xml中

<url-stream-handler>urlfetch</url-stream-handler>

参考:https://cloud.google.com/appengine/docs/standard/java/config/appref#url-stream-handler