【问题标题】:Uploading File in Request Body using AngularJS and $http PUT使用 AngularJS 和 $http PUT 在请求正文中上传文件
【发布时间】:2017-07-26 21:00:57
【问题描述】:

我正在通过 API 调用上传文件,该调用需要将文件放入请求正文并使用 PUT。使用以下代码,我可以上传创建文件并返回 200 状态的内容。 rawData 长度正是基于初始文件大小的预期长度。但是,创建的文件有一些额外的字节,无法打开。例如,我上传的 234 kb 的 jpg 文件上传后有 352 kb,而 12 kb 开头的 docx 文件上传后有 17 kb。

        var contentType = file.type;
        var reader = new FileReader();
        reader.onload = function (e) {
            var rawData = reader.result;

            $http({
                url: appSettings.serverPath + '/File/' + fileId + '/Content',
                method: 'PUT',
                headers: { 'Content-Type': undefined },
                data: rawData,
                transformRequest: []
            }).success(function (data, status, headers, config) {
                deferred.resolve(data);
            }).error(function (error) {
                deferred.reject(error);
            });

        };

        reader.readAsBinaryString(file);

除了使用未定义的“内容类型”之外,我还使用了文件的内容类型,但我遇到了同样的问题。

我尝试在 FileReader 上调用 readAsArrayBuffer 方法并传入 rawData 的 Uint8Array,但这不会传入 Request 上的任何数据并创建一个 0 字节的文件。

我还尝试在 FileReader 上调用 readAsDataURL 方法,该方法对数据进行完全不同的编码,因此我的 rawData 和生成的文件对于 jpg 为 313 kb。该文件仍然损坏,无法打开。

为了发送正确的数据,我应该做一些额外的编码等吗?

提前致谢!!

【问题讨论】:

    标签: javascript angularjs file upload


    【解决方案1】:

    无需使用 FileReader API 来读取文件。 XHR Send Method 自动序列化文件对象,因为它们是 Blob object 的一种特殊类型。

        //var contentType = file.type;
        //var reader = new FileReader();
        //reader.onload = function (e) {
        //    var rawData = reader.result;
    
        return $http({
            url: appSettings.serverPath + '/File/' + fileId + '/Content',
            method: 'PUT',
            headers: { 'Content-Type': undefined },
            //data: rawData,
            data: file
            //transformRequest: []
        };
        /*  }).success(function (data, status, headers, config) {
                deferred.resolve(data);
            }).error(function (error) {
                deferred.reject(error);
            });
        */
    
        //reader.readAsBinaryString(file);
    

    此外,由于 $http 服务已经返回了一个承诺,因此无需使用 $q.defer 制造承诺。

    .success.error 方法也是 deprecated and removed from Angular V1.6.


    FileReader.readAsBinaryString() 已弃用

    rawData 长度正是基于初始文件大小的预期长度。但是,创建的文件有一些额外的字节,无法打开。比如我上传的234kb的jpg文件上传后有352kb,而从12kb开始的docx文件上传后有17kb。

    //reader.readAsBinaryString(file);
    
    reader.readAsArrayBuffer(file)
    

    XHR Send Method 将二进制字符串 (DOMstring) 转换为 UTF-8。这意味着 128-255 范围内的数据字节被编码为 2 个字节。不要将二进制数据转换为 DOMstrings。使用ArrayBuffer API

    FileReader.readAsBinaryString()

    非标准

    此功能是非标准的,不在标准轨道上。不要在面向 Web 的生产站点上使用它:它不适用于每个用户。实现之间也可能存在很大的不兼容性,并且行为可能会在未来发生变化。

    根据 W3C 2012 年 7 月 12 日的工作草案,[It] 现在已弃用。

    — MDN Developer Reference - Web APIs - FileReader.readAsBinaryString()

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2011-08-30
      • 2022-01-11
      • 2019-09-27
      • 1970-01-01
      • 2011-11-02
      • 1970-01-01
      • 2016-09-18
      相关资源
      最近更新 更多