-1

このヘルパークラスを使用してJSONデータをしばらく解析していましたが、更新時にアプリが実行されている間にアプリケーションが2回目にクラッシュしました。なぜこれが起こっているのか分かりません。StringIndexOutOfBoundsException JSONの解析中にエラーが発生しました

アップデート2

問題がリダイレクトであるとクッキーとは何の関係もありませんが、私は私の問題を解決することができました。ソリューションのために私の答えをチェックしてください。

更新アーロンの提案した後、1

。私は実際に最初のリクエスト後にJSONを返さない。これがクッキーの問題である場合、なぜ最初に動作しますか?

HTTP/1.1 302 Moved Temporarily 
Content-Type: text/html; charset=UTF-8 
Cache-Control: no-cache, no-store, max-age=0, must-revalidate 
Pragma: no-cache 
Expires: Mon, 01 Jan 1990 00:00:00 GMT 
Date: Tue, 03 Jan 2017 13:31:59 GMT 
Location: https://docs.google.com/spreadsheets/d/I REMOVED THE KEY/gviz/tq 
P3P: CP="This is not a P3P policy! See https://support.google.com/accounts/answer/151657?hl=en for more info." 
P3P: CP="This is not a P3P policy! See https://support.google.com/accounts/answer/151657?hl=en for more info." 

MainActivity

new DownloadWebpageTask1(new AsyncResult1() { 
       @Override 
       public void onResult(JSONObject object) { 

        processJson(object); 
       } 
      }).execute("SOMEWEBSITE"); 

DownloadWebpageTask1.class

public class DownloadWebpageTask1 extends AsyncTask<String, Void, String> { 
    com.test.test.AsyncResult1 callback; 

    public DownloadWebpageTask1(com.test.test.AsyncResult1 callback) { 
     this.callback = callback; 
    } 

    @Override 
    protected String doInBackground(String... urls) { 

     // params comes from the execute() call: params[0] is the url. 
     try { 
      return downloadUrl(urls[0]); 
     } catch (IOException e) { 
      return "Unable to download the requested page."; 
     } 
    } 

    // onPostExecute displays the results of the AsyncTask. 
    @Override 
    protected void onPostExecute(String result) { 
     // remove the unnecessary parts from the response and construct a JSON 
     int start = result.indexOf("{", result.indexOf("{") + 1); 
     int end = result.lastIndexOf("}"); 
     String jsonResponse = result.substring(start, end); 
     Log.i("Error", jsonResponse); 
     try { 
      JSONObject table = new JSONObject(jsonResponse); 
      callback.onResult(table); 
     } catch (JSONException e) { 
      e.printStackTrace(); 
     } 
    } 

    private String downloadUrl(String urlString) throws IOException { 
     InputStream is = null; 

     try { 
      URL url = new URL(urlString); 
      HttpURLConnection conn = (HttpURLConnection) url.openConnection(); 
      conn.setReadTimeout(30000 /* milliseconds */); 
      conn.setConnectTimeout(30000 /* milliseconds */); 
      conn.setRequestMethod("GET"); 
      conn.setDoInput(true); 
      // Starts the query 
      conn.connect(); 
      int responseCode = conn.getResponseCode(); 
      is = conn.getInputStream(); 

      String contentAsString = convertStreamToString(is); 
      return contentAsString; 
     } finally { 
      if (is != null) { 
       is.close(); 
      } 
     } 
    } 

    private String convertStreamToString(InputStream is) { 
     BufferedReader reader = new BufferedReader(new InputStreamReader(is)); 
     StringBuilder sb = new StringBuilder(); 

     String line = null; 
     try { 
      while ((line = reader.readLine()) != null) { 
       sb.append(line + "\n"); 
      } 
     } catch (IOException e) { 
      e.printStackTrace(); 
     } finally { 
      try { 
       is.close(); 
      } catch (IOException e) { 
       e.printStackTrace(); 
      } 
     } 
     return sb.toString(); 
    } 
} 

JSON

/*O_o*/ 
google.visualization.Query.setResponse({"version":"0.6","reqId":"0","status":"ok","sig":"806967004","table":{"cols":[{"id":"A","label":"Date","type":"date","pattern":"M/d/yyyy"},{"id":"B","label":"Name","type":"string"},{"id":"C","label":"News","type":"string"},{"id":"D","label":"url","type":"string"},{"id":"E","label":"icon","type":"string"},{"id":"F","label":"picture","type":"string"}],"rows":[{"c":[{"v":"Date(2017,0,2)","f":"1/2/2017"},{"v":"Event 1"},{"v":"This is some event data for event 1"},{"v":""},{"v":"/icon1.png"},{"v":"Test"}]},{"c":[{"v":"Date(2017,0,2)","f":"1/2/2017"},{"v":"Event 2"},{"v":"This is some event data for event 2"},{"v":"https://www.google.com/"},{"v":"/icon2.png"},{"v":"test"}]},{"c":[{"v":"Date(2016,11,30)","f":"12/30/2016"},{"v":"Event 3"},{"v":"This is some event data for event 3"},{"v":""},{"v":"/icon3.png"},{"v":"test"}]},{"c":[{"v":"Date(2016,11,30)","f":"12/30/2016"},{"v":"Event 4"},{"v":"This is some event data for event 4"},{"v":""},{"v":"/icon4.png"},{"v":"test"}]},{"c":[{"v":"Date(2016,11,30)","f":"12/30/2016"},{"v":"Event 5"},{"v":"This is some event data for event 5"},{"v":"https://www.google.com/"},{"v":"/icon5.png"},{"v":"test"}]}]}}); 

エラー

W/System.err: java.net.SocketTimeoutException: Read timed out 
    W/System.err:  at org.apache.harmony.xnet.provider.jsse.NativeCrypto.SSL_read(Native Method) 
    W/System.err:  at org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl$SSLInputStream.read(OpenSSLSocketImpl.java:664) 
    W/System.err:  at libcore.net.http.UnknownLengthHttpInputStream.read(UnknownLengthHttpInputStream.java:41) 
    W/System.err:  at java.io.InputStreamReader.read(InputStreamReader.java:244) 
    W/System.err:  at java.io.BufferedReader.fillBuf(BufferedReader.java:130) 
    W/System.err:  at java.io.BufferedReader.readLine(BufferedReader.java:354) 
    W/System.err:  at com.test.test.DownloadWebpageTask1.convertStreamToString(DownloadWebpageTask1.java:84) 
    W/System.err:  at com.test.test.DownloadWebpageTask1.downloadUrl(DownloadWebpageTask1.java:69) 
    W/System.err:  at com.test.test.DownloadWebpageTask1.doInBackground(DownloadWebpageTask1.java:32) 
    W/System.err:  at com.test.test.DownloadWebpageTask1.doInBackground(DownloadWebpageTask1.java:20) 
    W/System.err:  at android.os.AsyncTask$2.call(AsyncTask.java:287) 
    W/System.err:  at java.util.concurrent.FutureTask.run(FutureTask.java:234) 
    W/System.err:  at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:230) 
    W/System.err:  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1080) 
    W/System.err:  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:573) 
    W/System.err:  at java.lang.Thread.run(Thread.java:856) 
    W/dalvikvm: threadid=1: thread exiting with uncaught exception (group=0xa6165908) 
    E/AndroidRuntime: FATAL EXCEPTION: main 
         java.lang.StringIndexOutOfBoundsException: length=1566; regionStart=-1; regionLength=0 
          at java.lang.String.startEndAndLength(String.java:583) 
          at java.lang.String.substring(String.java:1464) 
          at com.test.test.DownloadWebpageTask1.onPostExecute(DownloadWebpageTask1.java:44) 
          at com.test.test.DownloadWebpageTask1.onPostExecute(DownloadWebpageTask1.java:20) 
          at android.os.AsyncTask.finish(AsyncTask.java:631) 
          at android.os.AsyncTask.access$600(AsyncTask.java:177) 
          at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:644) 
          at android.os.Handler.dispatchMessage(Handler.java:99) 
          at android.os.Looper.loop(Looper.java:137) 
          at android.app.ActivityThread.main(ActivityThread.java:5041) 
          at java.lang.reflect.Method.invokeNative(Native Method) 
          at java.lang.reflect.Method.invoke(Method.java:511) 
          at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:793) 
          at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:560) 
          at dalvik.system.NativeStart.main(Native Method) 
+0

ポストJSON文字列だけでなく – Lino

+0

エラーがスローされたライン? –

+0

タイムアウトしたように見えますが、レスポンスが得られていないので、indexof( "{")は長さ0で-1を返しています。-1は文字列の一部ではないため例外をスローします。ブレークポイントを挿入し、結果の文字列をチェックします。正しくフォーマットされていない可能性があります。 – Aaron

答えて

0

これはリダイレクトに関係することの問題であるスロー含まれていないことを期待しています。 GoogleはJSONデータが取得されたURLを変更しました。あなたのURL要求の変化に

https://spreadsheets.google.com/tq?key=YOUR_KEY_HERE 

https://docs.google.com/spreadsheets/d/YOUR_KEY_HERE/gviz/tq 

そしてhttps://stackoverflow.com/a/40105282/6147989からいくつかのわずかに変更されたコードとすべてに起動して実行されます。

private String downloadUrl(String urlString) throws IOException { 
      String temp = ""; 
      try { 
       URL obj = new URL(urlString); 
       HttpURLConnection conn = (HttpURLConnection) obj.openConnection(); 
       conn.setReadTimeout(5000); 
       conn.addRequestProperty("Accept-Language", "en-US,en;q=0.8"); 
       conn.addRequestProperty("User-Agent", "Mozilla"); 
       conn.addRequestProperty("Referer", "google.com"); 

       System.out.println("Request URL ... " + urlString); 

       boolean redirect = false; 

       // normally, 3xx is redirect 
       int status = conn.getResponseCode(); 
       if (status != HttpURLConnection.HTTP_OK) { 
        if (status == HttpURLConnection.HTTP_MOVED_TEMP 
          || status == HttpURLConnection.HTTP_MOVED_PERM 
          || status == HttpURLConnection.HTTP_SEE_OTHER) 
         redirect = true; 
       } 

       System.out.println("Response Code ... " + status); 

       if (redirect) { 
        // get redirect url from "location" header field 
        String newUrl = conn.getHeaderField("Location"); 

        // get the cookie if need, for login 
        String cookies = conn.getHeaderField("Set-Cookie"); 

        // open the new connnection again 
        conn = (HttpURLConnection) new URL(newUrl).openConnection(); 
        conn.setRequestProperty("Cookie", cookies); 
        conn.addRequestProperty("Accept-Language", "en-US,en;q=0.8"); 
        conn.addRequestProperty("User-Agent", "Mozilla"); 
        conn.addRequestProperty("Referer", "google.com"); 

        System.out.println("Redirect to URL : " + newUrl); 
       } 

       BufferedReader in = new BufferedReader(
         new InputStreamReader(conn.getInputStream())); 
       String inputLine; 
       StringBuffer html = new StringBuffer(); 

       while ((inputLine = in.readLine()) != null) { 
        html.append(inputLine); 
       } 
       in.close(); 

       System.out.println("URL Content... \n" + html.toString()); 
       System.out.println("Done"); 

       temp = html.toString(); 

      } catch (Exception e) { 
       e.printStackTrace(); 
      } 
      return temp; 
     } 
2

私はこの問題は、JSON文字列(result変数)に関連していると思います。私はそれが{ '文字は、そのためのコード

int start = result.indexOf("{", result.indexOf("{") + 1); 
int end = result.lastIndexOf("}"); 
String jsonResponse = result.substring(start, end); 

のこの部分は例外

+0

はい、あなたは正しいです、そして、2回目の実行時にクラッシュします。私はこれがクッキーと関係があるかもしれないと思います〜更新を確認してください – Greg432

+0

@ Greg432何が問題でしたか? – Lino

+0

最初のリクエスト後に自分のコードがURLのリダイレクトを行っていないため、理由は十分にわかりませんが、リクエストされたURLアドレスを変更してリダイレクトする必要はなくなりました。再び変更を加えることにしました。 – Greg432

関連する問題