AngularJS: как реализовать простую загрузку файлов с помощью составной формы?
Я хочу сделать простой составной пост формы от AngularJS до узла.сервер JS,
форма должна содержать объект JSON в одной части и изображение в другой части,
(В настоящее время я публикую только объект JSON с $resource)
Я решил, что должен начать с типа ввода="файл", но затем обнаружил, что AngularJS не может привязаться к этому..
все примеры, которые я могу найти, предназначены для обертывания плагинов jQuery для перетаскивания. Я хочу простую загрузку одного файл.
Я новичок в AngularJS и не чувствую себя комфортно с написанием собственных директив.
8 ответов:
реальный рабочий раствор без других зависимостей, чем в AngularJS (проверено с В. 1.0.6)
html
<input type="file" name="file" onchange="angular.element(this).scope().uploadFile(this.files)"/>Angularjs (1.0.6) не поддерживает ng-model на тегах "input-file", поэтому вы должны сделать это" родным способом", который передает все (в конечном итоге) выбранные файлы от пользователя.
контроллер
$scope.uploadFile = function(files) { var fd = new FormData(); //Take the first selected file fd.append("file", files[0]); $http.post(uploadUrl, fd, { withCredentials: true, headers: {'Content-Type': undefined }, transformRequest: angular.identity }).success( ...all right!... ).error( ..damn!... ); };крутая часть-это undefined тип контента и transformRequest: угловой.идентичность которые дают в $http возможность выбрать правильный "тип контента" и управлять границей, необходимой при обработке составных данных.
Вы можете использовать простой/легкий ng-file-upload
У меня просто была эта проблема. Так что есть несколько подходов. Во-первых, новые браузеры поддерживают
var formData = new FormData();перейдите по этой ссылке в блог с информацией о как поддержка ограничена современными браузерами, но в остальном она полностью решает эту проблему.
в противном случае вы можете разместить форму в iframe, используя целевой атрибут. При публикации формы обязательно установите целевой объект в iframe со свойством отображения, равным none. Цель - это имя фрейм. (Просто чтобы вы знали.)
надеюсь, это поможет
это более эффективно, чтобы отправить файл напрямую.
The кодировка base64 на
Content-Type: multipart/form-dataдобавляет дополнительные 33% накладных расходов. Если сервер поддерживает его, это более эффективно отправлять файлы напрямую:$scope.upload = function(url, file) { var config = { headers: { 'Content-Type': undefined }, transformResponse: angular.identity }; return $http.post(url, file, config); };при отправке сообщения с помощью File object важно установить
'Content-Type': undefined. Элемент XHR отправить метод затем обнаружит File object и автоматически установить содержание тип.для отправки нескольких файлов см. Делаешь Несколько
$http.postзапросы непосредственно из списка файлов
я решил, что должен начать с типа ввода="файл", но затем обнаружил, что AngularJS не может привязаться к этому..
The
<input type=file>элемент по умолчанию не работает с директива ng-model. Он нуждается в пользовательские директивы:рабочая демонстрация "select-ng-files" Директива, которая работает с
ng-model1angular.module("app",[]); angular.module("app").directive("selectNgFiles", function() { return { require: "ngModel", link: function postLink(scope,elem,attrs,ngModel) { elem.on("change", function(e) { var files = elem[0].files; ngModel.$setViewValue(files); }) } } });<script src="//unpkg.com/angular/angular.js"></script> <body ng-app="app"> <h1>AngularJS Input `type=file` Demo</h1> <input type="file" select-ng-files ng-model="fileArray" multiple> <h2>Files</h2> <div ng-repeat="file in fileArray"> {{file.name}} </div> </body>
$http.postтип содержимогоmultipart/form-dataесли нужно отправить
multipart/form-data:<form role="form" enctype="multipart/form-data" name="myForm"> <input type="text" ng-model="fdata.UserName"> <input type="text" ng-model="fdata.FirstName"> <input type="file" select-ng-files ng-model="filesArray" multiple> <button type="submit" ng-click="upload()">save</button> </form>$scope.upload = function() { var fd = new FormData(); fd.append("data", angular.toJson($scope.fdata)); for (i=0; i<$scope.filesArray.length; i++) { fd.append("file"+i, $scope.filesArray[i]); }; var config = { headers: {'Content-Type': undefined}, transformRequest: angular.identity } return $http.post(url, fd, config); };при отправке сообщения с помощью FormData API важно установить
'Content-Type': undefined. Элемент XHR отправить метод затем обнаружитFormDataобъект и автоматически установить заголовок типа контента multipart / form-data С правильная граница.
Я знаю, что это поздно, но я создал простую директиву загрузки. Что вы можете получить работу в кратчайшие сроки!
<input type="file" multiple ng-simple-upload web-api-url="/api/post" callback-fn="myCallback" />ng-simple-upload подробнее на Github с примером использования веб-API.
вы можете загрузить через
$resourceпутем присвоения данных params атрибут resourceactionsвот так:$scope.uploadFile = function(files) { var fdata = new FormData(); fdata.append("file", files[0]); $resource('api/post/:id', { id: "@id" }, { postWithFile: { method: "POST", data: fdata, transformRequest: angular.identity, headers: { 'Content-Type': undefined } } }).postWithFile(fdata).$promise.then(function(response){ //successful },function(error){ //error }); };
Я просто написал простую директиву (из существующего курса) для простого загрузчика в AngularJs.
(точный плагин jQuery uploader -https://github.com/blueimp/jQuery-File-Upload)
простой загрузчик с помощью AngularJs (с реализацией CORS)
(хотя на стороне сервера для PHP, вы можете просто изменить его узел также)
Я хотел бы добавить альтернативу. Используя угловую загрузку файлов. Вы можете найти объяснение:
вы можете найти подробное объяснение здесь:https://github.com/nervgh/angular-file-upload Пример:https://github.com/nervgh/angular-file-upload/tree/master/examples/simple
Comments