2017-02-20 4 views
0

http応答からバイトを使用してpdfファイルを保存する必要があります。空白のPDFをokhttpから保存する場合

ファイルが小さい場合(約数百バイト、1k未満)はすべて問題ありませんが、ファイルが大きすぎる場合は、インテントで別のアプリケーションを使用して、すべてのページが白(ページ数が正しい)です。

ドキュメントを外部ストレージに保存し、URIをインテントに渡します。

これは、サーバーからファイルを取得し、外部記憶装置に保存するために私のコードです:

public static Observable<Integer> getDocument(final String id, final String service, final String filename){ 
    return Observable.create(new Observable.OnSubscribe<Integer>() { 
     @Override 
     public void call(Subscriber<? super Integer> subscriber) { 
      InputStream inputStream = null; 
      FileOutputStream outputStream = null; 
      OkHttpClient client = HypeHttpClientBuilder.getOkHttpClient(200); //timeout 
      RequestBody formBody = new FormEncodingBuilder() 
        .add("platform", HypeApplication.getDeviceType()) 
        .add("function", service) 
        .add("pdfid",id) 
        .build(); 

      Request requests = HttpRequestBuilder.getRequest(formBody); 
      try { 
       Response response = client.newCall(requests).execute(); 

       inputStream = response.body().byteStream(); 
       File dir = new File(Environment.getExternalStorageDirectory(),"Hype"); 
       if (!dir.mkdirs()) { 
        Log.e(TAG, "Directory not created"); 
       } 
       outputStream = new FileOutputStream(new File(dir, filename)); 
       int totalCount = inputStream.available(); 
       byte[] buffer = new byte[1024 * 1024]; 
       int len; 
       int readLen = 0; 
       while ((len = inputStream.read(buffer)) != -1) { 

        //System.out.println("download loop " + Thread.currentThread().getName()); 

        outputStream.write(buffer, 0, len); 
        readLen += len; 

       } 


       subscriber.onNext(readLen); 


      }catch (Exception e){ 
       subscriber.onError(e); 
      }finally { 
       try { 
        if (inputStream != null) { 
         inputStream.close(); 
        } 
        if (outputStream != null) { 
         outputStream.flush(); 
         outputStream.close(); 
        } 
       } catch (IOException e) { 
        e.printStackTrace(); 
       } 
      } 

      subscriber.onCompleted(); 


     } 
    }); 
} 

、これは別のアクティビティを開始するためのコードです:

Intent intent = new Intent(Intent.ACTION_VIEW); 
      intent.setDataAndType(FileProvider.getUriForFile(getActivity(),getActivity().getApplicationContext().getPackageName() + ".provider",f) 
        , "application/pdf"); 

      intent.setFlags(Intent.FLAG_ACTIVITY_NO_HISTORY); 
      intent.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); 

      startActivity(intent); 

UPDATE 私がしようとしましたプロキシを使用してhttpコールを傍受します。 プロキシからファイルを取得し、コードで生成したファイルを比較しました。いくつかの違いがあります。

私はUrlConnectionクラスを使用して簡単な解決策を得ました。

URL url = new URL(URLSetting.getOldUrl()); 
       HttpURLConnection conn = (HttpURLConnection)url.openConnection(); 
       conn.setReadTimeout(10000); 
       conn.setConnectTimeout(15000); 
       conn.setRequestMethod("POST"); 
       conn.setDoInput(true); 
       conn.setDoOutput(true); 
       conn.setRequestProperty("appversion","2.0.0"); 
       conn.setRequestProperty("Content-Type", 
         "application/x-www-form-urlencoded"); 


       Uri.Builder builder = new Uri.Builder() 
         .appendQueryParameter("platform", HypeApplication.getDeviceType()) 
         .appendQueryParameter("function", service) 
         .appendQueryParameter("deviceid",HypeApplication.getDeviceId()) 
         .appendQueryParameter("pdfid", id); 

       OutputStream os = conn.getOutputStream(); 
       BufferedWriter writer = new BufferedWriter(
         new OutputStreamWriter(os, "UTF-8")); 
       writer.write(builder.build().getEncodedQuery()); 
       writer.flush(); 
       writer.close(); 
       os.close(); 

       conn.connect(); 


       inputStream = conn.getInputStream(); 

したがって、okHttpがデフォルトのエンコードUTF-8として設定されているかどうかは分かりますか?

+0

あなたの 'FileOutputStream'で' flush() 'と' close() 'の間に' getFD()。sync() 'をお勧めします。それを超えて、デバイスからPDFをダウンロードし、それがOKかどうかを確認してください。 – CommonsWare

+0

いいえ、あなたが私に言ったように 'getFD.sync()'を入れましたが、ドキュメントの白いページが表示され続けます。 – hooloovoo

答えて

1

問題の原因がわかりませんが、Okio APIを使用してコードを単純化することができます。

BufferedSource source = response.body().source(); 

Sink out = Okio.sink(outputFile); 
try { 
    while (!source.exhausted()) { 
    Buffer buffer = source.buffer(); 
    out.write(buffer, buffer.size()); 
    } 
} finally { 
    out.close(); 
} 

変更があるかどうかを確認してください。

関連する問題