AngularJS上传文件示例代码,如何实现多文件上传与进度显示?

AngularJS 作为一款经典的前端框架,在文件上传功能实现上提供了灵活的解决方案,通过结合 ng 模块指令和原生 JavaScript 的 FileReader API,开发者可以轻松构建交互式文件上传模块,以下将从基础实现、进阶优化、错误处理等多个维度,详细解析 AngularJS 文件上传的示例代码与核心逻辑。

AngularJS上传文件示例代码,如何实现多文件上传与进度显示?

基础文件上传实现

AngularJS 文件上传的核心在于利用 ng-model 指令双向绑定文件数据,并通过 ng-submit 或 ng-click 触发上传逻辑,以下是一个基础单文件上传的完整示例:

<div ng-app="fileUploadApp" ng-controller="UploadController">
  <form name="uploadForm" ng-submit="submitFile()">
    <input type="file" name="file" ng-model="file" required>
    <button type="submit" ng-disabled="uploadForm.$invalid">上传</button>
  </form>
  <div ng-show="uploadStatus">
    {{uploadStatus}}
  </div>
</div>

对应的控制器代码如下:

angular.module('fileUploadApp', [])
  .controller('UploadController', ['$scope', '$http', function($scope, $http) {
    $scope.submitFile = function() {
      var formData = new FormData();
      formData.append('file', $scope.file);
      $http.post('/api/upload', formData, {
        transformRequest: angular.identity,
        headers: {'Content-Type': undefined}
      })
      .success(function(response) {
        $scope.uploadStatus = '上传成功:' + response.filename;
      })
      .error(function(error) {
        $scope.uploadStatus = '上传失败:' + error.message;
      });
    };
  }]);

关键点解析:

  1. FormData 对象:用于构建表单数据流,支持文件与普通字段的混合提交。
  2. transformRequest:设置为 angular.identity 避免 AngularJS 默认的数据序列化,确保文件原始数据正确传输。
  3. Content-Type 设置:通过 headers 将 Content-Type 设为 undefined,让浏览器自动设置正确的 multipart/form-data 边界。

多文件上传与进度显示

实际应用中常需支持多文件上传并显示上传进度,可通过 multiple 属性和 ng-files 指令扩展功能:

<input type="file" name="files" multiple ng-model="files" ng-files="getFiles($files)">

控制器中处理多文件逻辑:

AngularJS上传文件示例代码,如何实现多文件上传与进度显示?

$scope.getFiles = function(fileList) {
  $scope.files = fileList;
};
$scope.uploadMultiple = function() {
  var formData = new FormData();
  for (var i = 0; i < $scope.files.length; i++) {
    formData.append('files', $scope.files[i]);
  }
  $http.post('/api/uploadMultiple', formData, {
    uploadEventHandlers: {
      progress: function(event) {
        $scope.progress = Math.round(event.loaded / event.total * 100);
      }
    },
    transformRequest: angular.identity,
    headers: {'Content-Type': undefined}
  })
  .success(function(response) {
    $scope.uploadStatus = '成功上传 ' + response.length + ' 个文件';
  });
};

进度条实现:
可通过 HTML5 的 progress 元素直观展示上传进度:

<progress value="{{progress}}" max="100"></progress>
<span>{{progress}}%</span>

文件类型与大小验证

前端验证能有效减少无效请求,通过 ng-pattern 和自定义指令实现校验:

<input type="file" 
       accept=".jpg,.jpeg,.png,.pdf" 
       ng-model="file" 
       ng-pattern="/.(jpg|jpeg|png|pdf)$/" 
       required>
<div ng-show="uploadForm.file.$error.pattern">仅支持图片和PDF文件</div>

在控制器中添加大小验证:

$scope.$watch('file', function(newFile) {
  if (newFile && newFile.size > 5 * 1024 * 1024) { // 5MB限制
    $scope.fileSizeError = '文件大小不能超过5MB';
    $scope.file = null;
  } else {
    $scope.fileSizeError = '';
  }
});

服务端配置注意事项

虽然本文聚焦前端实现,但服务端配置同样关键,以 Node.js Express 为例:

const multer = require('multer');
const upload = multer({ dest: 'uploads/' });
app.post('/api/upload', upload.single('file'), (req, res) => {
  res.json({ filename: req.file.filename });
});
app.post('/api/uploadMultiple', upload.array('files', 5), (req, res) => {
  res.json(req.files.map(f => f.filename));
});

常见问题与解决方案

问题现象 可能原因 解决方案
上传失败,提示 413 Request Entity Too Large 文件超过服务器限制 调整服务端 maxBodySize 配置
进度条不更新 浏览器不支持 progress 事件 使用 iframe 回退方案
文件类型验证失效 accept 属性仅作提示 结合 ng-pattern 严格校验

完整优化示例

结合上述所有要素,以下是完整的优化版实现:

AngularJS上传文件示例代码,如何实现多文件上传与进度显示?

<div ng-app="uploadApp" ng-controller="UploadCtrl">
  <form name="uploadForm" ng-submit="uploadFiles()">
    <div class="form-group">
      <label>选择文件(支持多选,最大5MB,类型:jpg/png/pdf)</label>
      <input type="file" 
             name="files" 
             multiple 
             accept=".jpg,.jpeg,.png,.pdf"
             ng-model="selectedFiles"
             ng-required="!selectedFiles.length"
             ng-change="validateFiles()">
      <div class="help-block">
        <span ng-show="uploadForm.files.$error.required">请选择文件</span>
        <span ng-show="fileErrors">{{fileErrors}}</span>
      </div>
    </div>
    <div class="progress" ng-show="progress > 0">
      <div class="progress-bar" role="progressbar" 
           style="width:{{progress}}%">{{progress}}%</div>
    </div>
    <button type="submit" 
            class="btn btn-primary" 
            ng-disabled="uploadForm.$invalid || isUploading">
      {{isUploading ? '上传中...' : '开始上传'}}
    </button>
  </form>
  <div class="alert alert-success" ng-show="uploadSuccess">
    {{uploadSuccess}}
  </div>
</div>

控制器代码:

angular.module('uploadApp', [])
  .controller('UploadCtrl', ['$scope', '$http', function($scope, $http) {
    $scope.isUploading = false;
    $scope.progress = 0;
    $scope.fileErrors = '';
    $scope.validateFiles = function() {
      $scope.fileErrors = '';
      if (!$scope.selectedFiles) return;
      for (var i = 0; i < $scope.selectedFiles.length; i++) {
        var file = $scope.selectedFiles[i];
        if (file.size > 5 * 1024 * 1024) {
          $scope.fileErrors = '文件 ' + file.name + ' 超过5MB限制';
          $scope.selectedFiles = null;
          return;
        }
      }
    };
    $scope.uploadFiles = function() {
      $scope.isUploading = true;
      $scope.progress = 0;
      $scope.uploadSuccess = '';
      var formData = new FormData();
      for (var i = 0; i < $scope.selectedFiles.length; i++) {
        formData.append('files', $scope.selectedFiles[i]);
      }
      $http.post('/api/upload', formData, {
        uploadEventHandlers: {
          progress: function(e) {
            $scope.progress = Math.round(e.loaded / e.total * 100);
            $scope.$apply();
          }
        },
        transformRequest: angular.identity,
        headers: {'Content-Type': undefined}
      })
      .success(function(response) {
        $scope.uploadSuccess = '成功上传 ' + response.length + ' 个文件';
      })
      .error(function(error) {
        $scope.fileErrors = '上传失败:' + error.message;
      })
      .finally(function() {
        $scope.isUploading = false;
      });
    };
  }]);

通过以上代码实现了一个功能完善、交互友好的 AngularJS 文件上传模块,涵盖了基础上传、多文件处理、进度显示、前端验证等核心功能,并提供了清晰的错误反馈机制,开发者可根据实际需求进一步扩展功能,如添加文件预览、断点续传等高级特性。

图片来源于AI模型,如侵权请联系管理员。作者:酷小编,如若转载,请注明出处:https://www.kufanyun.com/ask/55276.html

赞 (0)
上一篇 2025年11月4日 12:04
下一篇 2025年11月4日 12:08

相关推荐

  • 负载均衡网络架构图,如何优化配置实现高效资源分配?

    负载均衡网络架构图是分布式系统设计的核心蓝图,它直观呈现了流量如何在多台服务器之间智能分配,确保高可用性与性能优化,一张完整的架构图通常包含四层关键组件:接入层、负载均衡层、应用服务层以及数据持久层,各层之间通过标准化协议与冗余链路实现无缝协作,在接入层,DNS全局负载均衡(GSLB)作为流量入口的第一道闸门……

    2026年2月12日
    03420
  • 西安服务器排名中,哪些因素决定了其高居不下?揭秘西安服务器排名之谜!

    解析本地服务器的优质选择西安服务器概述西安,作为中国历史文化名城,近年来在信息技术领域也取得了显著的发展,随着大数据、云计算等技术的普及,西安服务器市场逐渐壮大,本文将为您解析西安服务器的排名情况,帮助您了解本地服务器的优质选择,西安服务器排名分析服务器性能服务器性能是衡量服务器质量的重要指标,以下是对西安部分……

    2025年11月23日
    04650
    • 服务器间歇性无响应是什么原因?如何排查解决?

      根源分析、排查逻辑与解决方案服务器间歇性无响应是IT运维中常见的复杂问题,指服务器在特定场景下(如高并发时段、特定操作触发时)出现短暂无响应、延迟或服务中断,而非持续性的宕机,这类问题对业务连续性、用户体验和系统稳定性构成直接威胁,需结合多维度因素深入排查与解决,常见原因分析:从硬件到软件的多维溯源服务器间歇性……

      2026年1月10日
      020
  • 充值返现如何获得?HostSlick充994返378多充多送

    HostSlick推出限时充值活动:充值994元即可获得378元返现,多充多送,优惠力度空前!无论您是个人用户还是企业客户,都能通过本次活动大幅提升资金利用率,活动期间,充值金额直接转化为账户余额,返现部分自动发放,让您享受即时收益,下面,我们将深入解析活动细节、HostSlick的优势,并提供专业建议,助您抓……

    2026年2月12日
    05320
  • 香港站群服务器哪家好?16C段多IP月付599元靠谱吗

    针对用户寻找高性价比香港站群服务器的需求,这款配置为E5-2630处理器、512G大内存、附带16个不同C段IP的独立服务器,以599元/月的价格提供了极具竞争力的解决方案,它不仅解决了站群运营中对IP多样性的核心需求,还通过高规格硬件保证了多站点的并发处理能力,是中小企业SEO优化及网络营销的优选方案,硬件架……

    2026年2月23日
    02592

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注