Скачать файл и сохранить на диск не работает - PullRequest
1 голос
/ 26 апреля 2019

Мне нужно загрузить файл с сервера, поэтому я использую модификацию и этот метод для сохранения файла на диск.

Вот мой код

    @GET
    Call<ResponseBody> downloadFileWithDynamicUrlSync(@Url String fileUrl);

Метод для загрузки файла

 private void dowloadFile(String url, FileListItem item) {

        Call<ResponseBody> callb = RestClient.getInstance().getService().downloadFileWithDynamicUrlSync(url);

        callb.enqueue(new Callback<ResponseBody>() {
            @Override
            public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
                if (response.isSuccessful()) {
                    Log.d(TAG, "server contacted and has file");
                    boolean writtenToDisk = writeResponseBodyToDisk(response.body(), item);
                    if(writtenToDisk){
                        MdocUtil.showToastShort(context, context.getString(R.string.file_dowloaded_succ));
                    }else{
                        MdocUtil.showToastShort(context, context.getString(R.string.error_download));
                    }
                    Log.d(TAG, "file download was a success? " + writtenToDisk);
                } else {
                    Log.d(TAG, "server contact failed");
                    APIError error = ErrorUtils.parseError(response);
                    MdocUtil.showToastShort(context, error.getMessage());
                }
            }

            @Override
            public void onFailure(Call<ResponseBody> call, Throwable t) {
                Log.e(TAG, "error");
            }
        });
    }

Метод записи файла на диск

 private boolean writeResponseBodyToDisk(ResponseBody body, FileListItem item) {
        try {
            File file = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) + File.separator + item.getName());

            InputStream inputStream = null;
            OutputStream outputStream = null;

            try {
                byte[] fileReader = new byte[4096];

                long fileSize = body.contentLength();
                long fileSizeDownloaded = 0;

                inputStream = body.byteStream();
                outputStream = new FileOutputStream(file);

                while (true) {
                    int read = inputStream.read(fileReader);

                    if (read == -1) {
                        break;
                    }

                    outputStream.write(fileReader, 0, read);

                    fileSizeDownloaded += read;

                    Log.d(TAG, "file download: " + fileSizeDownloaded + " of " + fileSize);
                }

                outputStream.flush();

                return true;
            } catch (IOException e) {
                return false;
            } finally {
                if (inputStream != null) {
                    inputStream.close();
                }

                if (outputStream != null) {
                    outputStream.close();
                }
            }
        } catch (IOException e) {
            return false;
        }

Этот код отлично работает при загрузке изображения, но не работает для файлов .pdf и .docx, в этом случае записанный ToDisk имеет значение trueно на телефоне нет файла.

ОБНОВЛЕНИЕ: Проблема в том, что я не установил токен доступа в заголовке, который запрашивается сервером для файлов, но не для изображений.

1 Ответ

2 голосов
/ 26 апреля 2019

Почему бы вам не использовать собственный менеджер загрузок Android? Вы можете увидеть здесь утилиту менеджера загрузок, которую можно использовать в качестве примера ниже:

downloadManager = new DownloadManager(new DownloadManager.DownloadCompleteListener(){
    @Override
    public void getProgress(double progress, long downloadedBytes, long sizeInBytes){

    }

    @Override
    public void onDownloadComplete(Uri fileLocalUri, long downloadedFileId){

    }
});
downloadManager.download(Uri uri, String fileName, String description);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...