使用google-api-java-clients批处理请求时,流式插入API会引发500错误

时间:2014-08-06 13:22:45

标签: google-bigquery

我们正在使用流式插入API以及google-api-java-clients批量请求。

最初一切都很好,但经过一段时间后,它开始抛出500多个错误:

{"code":500,"errors":[{"domain":"global","message":"Unexpected. Please try again.","reason":"internalError"}],"message":"Unexpected. Please try again."}

代码段如下:

val batch = client.batch()   
val request = new TableDataInsertAllRequest()
request.setRows(rows)
val insertAll = client.tabledata().insertAll(ProjectId, datasetId, tableId, request)
insertAll.queue(batch, new MyCallback(datasetId, tableId, rows, retryAttempt))   

有时我们也会 BackEndError

{"code":500,"errors":[{"domain":"global","message":"Backend Error","reason":"backendError"}],"message":"Backend Error"}

注意:在收到错误之前,我们收到了以下错误:

java.net.SocketTimeoutException: Read timed out
  at java.net.SocketInputStream.socketRead0(Native Method) ~[na:1.7.0_06]
    at java.net.SocketInputStream.read(SocketInputStream.java:150) ~[na:1.7.0_06]
    at java.net.SocketInputStream.read(SocketInputStream.java:121) ~[na:1.7.0_06]
    at sun.security.ssl.InputRecord.readFully(InputRecord.java:312) ~[na:1.7.0_06]
    at sun.security.ssl.InputRecord.read(InputRecord.java:350) ~[na:1.7.0_06]
    at sun.security.ssl.SSLSocketImpl.readRecord(SSLSocketImpl.java:927) ~[na:1.7.0_06]
    at sun.security.ssl.SSLSocketImpl.readDataRecord(SSLSocketImpl.java:884) ~[na:1.7.0_06]
    at sun.security.ssl.AppInputStream.read(AppInputStream.java:102) ~[na:1.7.0_06]
    at java.io.BufferedInputStream.fill(BufferedInputStream.java:235) ~[na:1.7.0_06]
    at java.io.BufferedInputStream.read1(BufferedInputStream.java:275) ~[na:1.7.0_06]
    at java.io.BufferedInputStream.read(BufferedInputStream.java:334) ~[na:1.7.0_06]
    at sun.net.www.http.HttpClient.parseHTTPHeader(HttpClient.java:633) ~[na:1.7.0_06]
    at sun.net.www.http.HttpClient.parseHTTP(HttpClient.java:579) ~[na:1.7.0_06]
    at sun.net.www.protocol.http.HttpURLConnection.getInputStream(HttpURLConnection.java:1322) ~[na:1.7.0_06]
    at java.net.HttpURLConnection.getResponseCode(HttpURLConnection.java:468) ~[na:1.7.0_06]
    at sun.net.www.protocol.https.HttpsURLConnectionImpl.getResponseCode(HttpsURLConnectionImpl.java:338) ~[na:1.7.0_06]
    at com.google.api.client.http.javanet.NetHttpResponse.<init>(NetHttpResponse.java:36) ~[google-http-client-1.18.0-rc.jar:1.18.0-rc]
    at com.google.api.client.http.javanet.NetHttpRequest.execute(NetHttpRequest.java:94) ~[google-http-client-1.18.0-rc.jar:1.18.0-rc]
    at com.google.api.client.http.HttpRequest.execute(HttpRequest.java:965) ~[google-http-client-1.18.0-rc.jar:1.18.0-rc]
    at com.google.api.client.googleapis.batch.BatchRequest.execute(BatchRequest.java:241) ~[google-api-client-1.18.0-rc.jar:1.18.0-rc]                 

问题

  • 这是什么原因?
  • 我们应该怎么做才能解决这个问题?

修改
  - 项目ID为 deft-virtue-628
  - 我们正在使用流式插入api执行,并且没有作业ID。

1 个答案:

答案 0 :(得分:0)

之前我们遇到过同样的问题。以下是我们的一些调查结果,希望他们能为您提供一些帮助。

  1. 关于java.net.SocketTimeoutException:读取超时:它很大的机会不是由于Bigquery方面,但可能是你的系统资源(JVM或网络套接字或相关的东西)变得疲惫不堪。我们最初在Windows Server 2008R2上的虚拟机上运行我们的程序,当时我们经历了这么多套接字超时。由于我们迁移到新服务器并在本机上运行我们的程序,因此我们几乎没有看到这种例外情况。此外,此超时有时会导致其他异常,例如在握手期间关闭SSL连接等等。

  2. 从Bigquery 500的错误:我们无法找到避免它的方法,因为它没有显示任何模式,Bigquery并不完全禁止或未能满足您的后续请求。简单地做退避无助于避免此错误,特别是如果您使用多线程,则很难准确地控制退避时间。所以,我们所做的是在发生500错误并重试时将数据放回队列,事实是在重试1-2次后平均成功。虽然我们仍然在等待处理这个错误的优化方法的建议,但我们现在只是继续重试。通过执行此操作,会发生500的错误,但我们仍然可以将所有数据流式传输到Bigquery。