1

Hi i am developing file upload module using Angularjs and api. I am following https://jsfiddle.net/JeJenny/vtqavfhf/. I have one list which contains document names such as passport,visa etc and so on. I am binding this list to array and looping inside ng-repeat. So based on the number of documents it generates file upload controls as below.

<div class="upload-button" ng-repeat="file in files">
                <div class="upload-button-icon">
                    <img src="images/folder-small.png">
                    <div class="upload-text">{{file}}</div>
                    <input type="file" id="file1" name="file1" file-model="{{file}}"  />
                </div>
</div>

Note: we can upload obly one document on one upload. So clearly if i have 4 documents in files array then 4 file upload controls will generate.

Finally i have one button which should save all the above files on click.

   <input type="submit" value="{{ 'NEXT' | translate }}" class="blue-button" ng-click="uploadFile(files)">

I have this function to save file(Taken from fiddler)

$scope.uploadFile = function(filename){
       //Here i want to save all the files. For example if there are three documents in array files then 3 documents at a time i want to send it to server.
    };

As you can see, fiddler will be having separate functions to save each file individually. I am trying to send all the files at a time.

May i get some help here? I am not sure what should be written inside $scope.uploadFile function? How can i collect here all files data? Thank you.

Niranjan Godbole
  • 2,135
  • 7
  • 43
  • 90
  • multipart form. See https://stackoverflow.com/questions/24443246/angularjs-how-to-upload-multipart-form-data-and-a-file – IamSilviu Jun 06 '17 at 07:56
  • Thanks. That will upload maultiple files but those multiple files will be selected on one file upload control. Please let me know if you did not understand the scenario. – Niranjan Godbole Jun 06 '17 at 07:59
  • If you want all files in one go (Ajax POST) then build multipart (concatenate all files in one form body) and submit. Else I didn't understand your scenario. – IamSilviu Jun 06 '17 at 08:07
  • Thanks. you are correct now. I am confused about concatenate all files in one form body. How can i concatenate files? – Niranjan Godbole Jun 06 '17 at 08:13
  • i have created var payload = new FormData(); How can i append file data to this? Any help would be appreciated. – Niranjan Godbole Jun 06 '17 at 08:17

2 Answers2

1

Here is a working example, hope it helps

var myApp = angular.module('myApp', []);

myApp.directive('fileModel', ['fileUpload', function(fileUpload) {
  return {
    restrict: 'A',
    link: function(scope, element, attrs) {
      element.bind("change", function(evt) {
        fileUpload.pendingFiles[attrs.fileModel] = evt.target.files[0];
      });
    }
  };
}]);

myApp.factory('fileUpload', ['$http', function($http) {

  var service = {
    uploadUrl: "https://httpbin.org/post",
    pendingFiles: [],
    doUpload: doUpload
  };

  return service;

  function doUpload() {
    var files = new FormData();
    angular.forEach(this.pendingFiles, function(value, key) {
      files.append('file', value);
    });

    return $http.post(this.uploadUrl, files, {
      transformRequest: angular.identity,
      headers: {
        'Content-Type': undefined
      }
    })
  }
}]);

myApp.controller('myCtrl', ['$scope', 'fileUpload', function($scope, fileUpload) {
  $scope.fileInputs = [1, 2, 3];
  $scope.upload = function(filename) {
    fileUpload.doUpload().success(function(success) {
      $scope.result = success
    });
  };
}]);
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>

<body ng-app="myApp">
  <div ng-controller="myCtrl">
    <div ng-repeat="fileInput in fileInputs">
      <input type="file" file-data="{{fileInput}}" file-model="{{fileInput}}" />
    </div>
    <br />
    <button ng-click="upload()">upload all</button>
  <br />
    <pre>{{result | json}}</pre>
  </div>
</body>
IamSilviu
  • 232
  • 2
  • 12
  • Thanks. This is what i am looking for. I can see function doUpload. It receives fileuploadurl parameter. But in ng-click="upload()" we are not sending any data. How it will work? – Niranjan Godbole Jun 06 '17 at 09:41
  • Hi IamSiviu. Hope you understood. – Niranjan Godbole Jun 06 '17 at 09:59
  • My major concern is when we click on upload all we should have all files data in array or formdata. How to get that? – Niranjan Godbole Jun 06 '17 at 10:11
  • via onChange event that we bind in drective on link phase. the pendingList array is populated on file select. I removed the uploadUrl as parameter, you can set it the way you want, I just want to demo how to create the multipart via forEach file you append to formdata – IamSilviu Jun 06 '17 at 10:24
  • Now i understood. but files are not appending in files.append('file', value); and this.pendingFiles this will be reflected with multiple files. Appening is not happening. – Niranjan Godbole Jun 06 '17 at 10:36
  • Console.log(files) always returns empty. So no file data? I am little confused. – Niranjan Godbole Jun 06 '17 at 10:43
  • Everything is working fine other than formdata.append. So my api receives empty always. Is there anything i should follow to work files.append('file', value); – Niranjan Godbole Jun 06 '17 at 11:07
  • Finally figure out problem. $scope.fileInputs = ["Passport","Visa"]; This is giving problem. I want to pass string rather than int. Is there any way to change this? – Niranjan Godbole Jun 06 '17 at 13:20
0

add multiple attribute to your input tag file <input type="file" multiple> this will allow multiple select of files

perseusl
  • 348
  • 1
  • 14
  • One file control should upload one file at a time. I dont want multiple. Finally i want to send all data(one go). – Niranjan Godbole Jun 06 '17 at 08:18
  • why not put them in one form then upload on submit of the form? – perseusl Jun 06 '17 at 08:19
  • i tried i tried var formdata = new FormData(); formdata.append("Image",$scope[filename]); console.dir(formdata); This will not append data to formdata. But console.dir($scope[filename]); will display the required file data. May i know how can i append file data to formdata? – Niranjan Godbole Jun 06 '17 at 08:36
  • this will help you use form data https://stackoverflow.com/questions/21044798/how-to-use-formdata-for-ajax-file-upload – perseusl Jun 06 '17 at 08:42