Search code examples
javascriptangularjspromiseangular-promise

Angularjs how to get filename extension?


Hi I am developing angularjs application. I am doing file upload module. I am trying to validate the files. I want to upload only xlsx or xls files. I have developed directive and factory method to upload files as below.

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

Below is my controller.

 $scope.upload = function (filename) {
 fileUploadExcel.doUpload().success(function (success) {
 }).error(function (error) {
});

Below is my factory code.

myapp.factory('fileUploadExcel', ['$http', '$cookieStore', 'cfg', function ($http, $cookieStore, cfg) {
    var LoginID = $cookieStore.get("LoginID");
    var baseurl = cfg.Baseurl;
    var fileuploadurl = baseurl + 'api/Customer/BulkUploadVehicle/';

    var service = {
        uploadUrl: fileuploadurl,
        pendingFiles: {},
        doUpload: doUpload
    };
    return service;
    function doUpload() {
        var filename;
        var files = new FormData();
        files.append('LoginID', LoginID);
        angular.forEach(this.pendingFiles, function (value, index) {
            filename = value.name;
            files.append(index, value);
        });
        var extn = filename.split(".").pop();
        if (extn == 'xlsx' || extn == 'xls') {
            return $http.post(this.uploadUrl, files, {
                transformRequest: angular.identity,
                headers: {
                    'Content-Type': undefined
                }
            })
        }
        else
        {
            return false;
        } 
    }
}]);

I am able to get extn successfully. When my files are of type excel my code works fine. Whenever i upload other than excel i am getting error. I have wrote return false. This is not working here. I should return something else may be. May i know what i should write in else case? Can anyone help me out here? Any help would be appreciated. Thank you.


Solution

  • You return different type:

    on success, you return a $http promise in your factory, so you can call success & error function in your controller whith that:

    fileUploadExcel.doUpload().success() exist!

    but if error, you return false in your factory, in this case this is a boolean and is not a $http promise so you cant use success & error function.

    fileUploadExcel.doUpload().success() doesnt exist and return an error

    Of course a solution is to check if the returning value is not false and continue your code, but I suggest to return always a promise by resolving it if success and rejecting it on error, so the promise chain is a not broken.

    PS: $http is a modified promise why they have success & error, but I suggest using the vanilla promise and using .then()

    var deferred = $q.defer();
    
    if (extn === 'xlsx' || extn === 'xls') {
        $http.post(this.uploadUrl, files, {
            transformRequest: angular.identity,
             headers: {
                 'Content-Type': undefined
             }
        }).success(function(success) {
            deferred.resolve(success);
        }).error(function(error) {
            deferred.reject(error);
        });
    } else {
        deferred.reject('File format not supported');
    }
    return deferred.promise;
    

    and your controller:

    $scope.upload = function (filename) {
        fileUploadExcel.doUpload().then(function (success) {
            //success
        }, function (error) {
            //error
        });
    }