Cancel Angular File Upload - angularjs

I am not able to cancel an uploading file request from angular, I am using the below mentioned plugin to upload a file and according to the author it feels like it is way to simple, but I am not sure how should I implement it. This is how I am uploading the files, from Angular plugin files gets posted to php and php intern reads the entire file and streams it to java api through curl, so, now I have a Cancel button and once user clicks on that cancel upload button I need to be able to stop the upload from angular plugin, so once the upload is stopped I can make another call to clean up half streamed file....and other clean up stuff.
Plugin Link: https://github.com/danialfarid/ng-file-upload
$scope.uploadFiles = function(files) {
if(files != undefined){
$scope.currentFileUploadList = files;
$scope.$apply();
}
angular.forEach(files, function(file, key) {
if(isSpecialChar(file.name)){
//$scope.currentFileUploadList[key].status = false;
//$scope.$apply();
file.upload = Upload.upload({
url: $scope.BASE_FOLDER+'/sync/file/upload',
fields: {csrf_token: $('.csrf_token').html(), path: 'ParaBlu'},
file: file
});
file.upload.then(function (response) {
$timeout(function () {
file.result = response.data;
if(response.data.result == 'success'){
$('.status').hide();
toastr.success(response.data.file.fileName+' has been uploaded successfully', 'Successfully!!!', {allowHtml: true});
$scope.currentFileUploadList.forEach(function(value, key){
if(value.name.toString() == response.data.file.fileName.toString()){
$scope.currentFileUploadList.splice(key, 1);
}
});
if((files.length) == key){
$('#uploadFiles').modal('hide');
}
}else{
toastr.error(file.name, response.data.msg, 'Fail!!!', {allowHtml: true});
}
});
}, function (response) {
if (response.status > 0)
$scope.errorMsg = response.status + ': ' + response.data;
});
file.upload.progress(function (evt) {
file.progress = Math.min(100, parseInt(100.0 *
evt.loaded / evt.total));
});
}else{
$scope.currentFileUploadList.forEach(function(value, key){
if(value.name.toString() == file.name.toString()){
$scope.currentFileUploadList.splice(key, 1);
}
});
toastr.error('Special characters like ( * \ | : " < > ? / ) are not allowed, in a file name.', 'Fail!!!', {allowHtml: true});
}
});
};

It was not a problem with the plugin rather with the streaming, I had to cancel the php file streaming separately to cancel the upload, process, not sure y? I though setting user interruption to false in php.ini would stop the php curl request as well once the ajax request is cancelled but it did not happen, anyway thanks for your help.

Related

Video capture to not show in my gallery on phone

I am using ng-cordova's plugin capture to capture (https://github.com/apache/cordova-plugin-media-capture) videos inside of the ionic framework from a mobile phone.
$scope.captureVideo = function() {
var options = { limit: 1, duration: 10 };
$cordovaCapture.captureVideo(options).then(function(videoData) {
var i, path, len;
for (i = 0, len = videoData.length; i < len; i += 1) {
path = videoData[i].fullPath;
console.log("Path of the video is = " + path.toString());
}
}, function(err) {
// An error occurred. Show a message to the user
});
}
The problem is every video capture I take saves to my phones gallery which I do not want. If I capture an image it does NOT save to my phone's gallery which is what I would like with video capture. Is there a way to stop videos from being saved?
I tried deleting the file but apparently the video file is not saved
in cordovafile directories.
function DeleteFile() {
var filename = "20161024_095758.mp4";
var relativeFilePath = "file:/storage/C8F0-1207/DCIM/Camera";
console.log('data directory: '+cordova.file.dataDirectory);
window.resolveLocalFileSystemURL(relativeFilePath, function(dir) {
dir.getFile(filename, {create:false}, function(fileEntry) {
fileEntry.remove(function(){
alert('file removed');
// The file has been removed succesfully
},function(error){
alert('error'+JSON.stringify(error));
// Error deleting the file
},function(){
alert('file doesnt exist');
// The file doesn't exist
});
});
});
The code above to delete file results in Error Code:6. No modification allowed
Well, apparently WE CANNOT DELETE AND WRITE FILES FROM MICRO SD-CARD SINCE VERSION 4.4. It is read only now.. And, when the user deletes the file from the gallery, it would not be available for the project. Here is what i came up with.
I copied the video file to cordova's external directory from where i could read the file when wanted and delete as per the need. Plugins required are cordova-file-plugin and cordova-plugin-file-transfer
.controller('yourCtrl', function($scope,$cordovaCapture,$sce,$cordovaFile, $cordovaFileTransfer, $timeout) {
$cordovaCapture.captureVideo(options).then(function(videoData) {
console.log(JSON.stringify(videoData[0]));
console.log(cordova.file.externalDataDirectory);
$cordovaFileTransfer.download(videoData[0].fullPath, cordova.file.externalDataDirectory + 'my-video.mp4', {}, true).then(
function(result)
{
console.log('success: '+ result);
},
function (error)
{
console.log('error: '+ JSON.stringify(error));
},function (progress) {
$timeout(function () {
$scope.downloadProgress = (progress.loaded / progress.total) * 100;
});
},false);
$scope.clipSrc = $sce.trustAsResourceUrl(videoData[0].fullPath);
//$scope.videoSrc = videoData[0].fullPath;
}, function(err) {
alert('Err: <br />'+ JSON.stringify(videoData));
});
//delete the file according to filename.
$scope.deleteVideo= function(){
$cordovaFile.removeFile(cordova.file.externalDataDirectory, "my-video.mp4")
.then(function (result) {
console.log('Success: deleting videoData file' + JSON.stringify(result));
}, function (err) {
console.log('Error: deleting videoData file' + JSON.stringify(err));
});
}
})

------WebKitFormBoundary being added by AngularJS app

I built a Ruby/Sinatra backend for an angularjs app. I wrote a POST call to parse and upload a file from the request body to AWS S3. Now when I use Postman to upload a file. It works completely fine, the file gets uploaded and I can view it on S3. But the problem is that when I try to upload a file using the angular app, it adds the following to the file cause of which the file gets corrupted and a pdf file opens up as a text file within the browser.
------WebKitFormBoundaryuRzuSgC6oXxEgwa1
Content-Disposition: form-data; name="file"; filename="Application Form.pdf"
Content-Type: application/pdf
***FILE DATA HERE***
------WebKitFormBoundaryuRzuSgC6oXxEgwa1--
Can someone help me to either parse this data properly in the ruby or help me to avoid adding this extra code from the angular app.
This is the angular code to upload the file
$scope.uploadFiles = function(files, errFiles) {
$scope.all_files.push(files);
console.log($scope.all_files[0]);
$scope.files = files;
$scope.errFiles = errFiles;
angular.forEach(files, function(file) {
file.upload = Upload.upload({
url: 'http://api.company.com/upload',
data: {file: file}
});
file.upload.then(function (response) {
$timeout(function () {
file.result = response.data;
});
}, function (response) {
if (response.status > 0)
$scope.errorMsg = response.status + ': ' + response.data;
}, function (evt) {
file.progress = Math.min(100, parseInt(100.0 *
evt.loaded / evt.total));
});
});
};
And the following is the code in Ruby to parse and upload the file
post '/upload' do
request.body.rewind
body = request.body.read
res(200, {url: saveFile(body)})
end
def saveFile(body)
name = "random string here"
s3 = Aws::S3::Resource.new(region:'ap-southeast-1')
obj = s3.bucket('company-files').object(name)
obj.put(body: body, acl:'public-read')
saved_url = obj.public_url
return saved_url
end
You may need to manually set the Content-Type header to force your browser to use this upload mechanism, probably at this point:
file.upload = Upload.upload({
url: 'http://api.company.com/upload',
data: {file: file}
});
I don't know what's Upload object, so I can't say how to do it

Upload file in IE9 is failing using ng-file-upload + Spring MVC + OAuth2.0

I'm completely dummy in AngularJS and appreciate your help here.
I'm trying to implement a file upload page. It is very simple, user selects the file and pushes upload button and it has to be uploaded to back-end which is a Spring MVC REST web service. I'm trying to use ng-file-upload.
Here is my front-end code:
<form name="myForm">
<input type="file" ngf-select ng-model="picFile" name="file
accept="application/pdf" ngf-max-size="2MB" required
ngf-model-invalid="errorFiles">
<i ng-show="myForm.file.$error.required">*required</i><br>
<i ng-show="myForm.file.$error.maxSize">File too large
{{errorFiles[0].size / 1000000|number:1}}MB: max 2M</i>
<button ng-disabled="!myForm.$valid" ng-click="uploadFiles(picFile)">Submit</button>
and controller:
$scope.uploadFiles = function(file, errFiles) {
console.log("Uploading files");
$scope.f = file;
$scope.errFile = errFiles && errFiles[0];
if (file) {
file.upload = Upload.upload({
url: 'api/proposals/upload',
data: {file: file}
});
file.upload.then(function (response) {
$timeout(function () {
file.result = response.data;
});
}, function (response) {
if (response.status > 0)
$scope.errorMsg = response.status + ': ' + response.data;
}, function (evt) {
file.progress = Math.min(100, parseInt(100.0 *
evt.loaded / evt.total));
});
}
};
and my back-end:
#RequestMapping(value = "/proposals/upload",method = RequestMethod.POST)
#Timed
public ResponseEntity<TemporaryProposal>
uploadProposal(#RequestParam("file") MultipartFile agreementFile){
The error I'm getting in IE9 console is
TypeError: Unable to get value of the property 'error': object is null or undefined
and from back-end:
[DEBUG] com.iocs.portal.aop.logging.LoggingAspect - Enter: org.springframework.boot.actuate.audit.AuditEventRepository.add() with argument[s] = [AuditEvent [timestamp=Tue Mar 01 08:53:23 EST 2016, principal=anonymousUser, type=AUTHORIZATION_FAILURE, data={message=Access is denied, type=org.springframework.security.access.AccessDeniedException}]]
[DEBUG] com.iocs.portal.aop.logging.LoggingAspect - Exit: org.springframework.boot.actuate.audit.AuditEventRepository.add() with result = null
[DEBUG] com.iocs.portal.security.Http401UnauthorizedEntryPoint - Pre-authenticated entry point called. Rejecting access
I solved this problem by sending the authentication parameters along with the request from front-end. As I was using Auth2 authentication, it was OK to include the token in the request.

nodejs write simple image blob - Upload.dataUrltoBlob

Simple question. How do I save a image blob in Nodejs from angular.
AngularSide:
$scope.upload = function (dataUrl, picFile) {
Upload.upload({
url: 'http://test.dev:3000/register/user/uploads',
data: {
file: Upload.dataUrltoBlob(dataUrl, picFile.name)
},
}).then(function (response) {
$timeout(function () {
$scope.result = response.data;
});
}, function (response) {
if (response.status > 0) $scope.errorMsg = response.status
+ ': ' + response.data;
}, function (evt) {
$scope.progress = parseInt(100.0 * evt.loaded / evt.total);
});
}
nodejs side: Do I need middleware here? if so which one should I use?
router.post('/user/uploads', multipartMiddleware, function(req, resp) {
var newPath = "/Users/testUser/test_hold_files/" + req.files.file.originalFilename;
fs.writeFile(newPath, req.files.file, function(err) {
if (err) {
console.log("Data Error ");
return console.error(err);
}
});
res.status(200).jsonp({status: "status: success "});
});
right now this just writes out the file with correct name but its empty.
You used to be able to access the uploaded file through req.files.imageName and then you would fs.readFile from tmp and write it permanently, which is no longer the case in express 4.0
In Express 4, req.files is no longer available on the req object by default. To access uploaded files on the req.files object, use multipart-handling middleware like busboy, multer, formidable, multiparty, connect-multiparty, or pez.
Soooooooo, you can feel free to use which ever one of those middlewares names above and then follow their API for dealing with uploaded files like images. Hope this helps, enjoy.
Ok,
After a long time of messing with this stuff. I found an answer. It does load the file in my folder.
I feel this is only partial since it does not resize the actual file smaller. It is what is selected with https://github.com/danialfarid/ng-file-upload. I used the
Upload.upload({
url: 'http://test.dev:3000/register/user/uploads',
data: {
file: Upload.dataUrltoBlob(dataUrl, picFile.name)
},
This did zoom into the file on selected image. It did not make the actual file size smaller. I am still looking into this issue.
var formidable = require('formidable'),
util = require('util'),
fs_extra = require('fs-extra');
This is my post to accept images.
router.post('/user/uploads', function (req, res){
var form = new formidable.IncomingForm();
form.parse(req, function(err, fields, files) {
res.writeHead(200, {'content-type': 'text/plain'});
res.write('received upload:\n\n');
res.end(util.inspect({fields: fields, files: files}));
});
form.on('end', function(fields, files) {
/* Temporary location of our uploaded file */
var temp_path = this.openedFiles[0].path;
/* The file name of the uploaded file */
var file_name = this.openedFiles[0].name;
/* Location where we want to copy the uploaded file */
var new_location = "/Users/testUser/test_hold_files/";
fs_extra.copy(temp_path, new_location + file_name, function(err) {
if (err) {
console.error(err);
} else {
console.log("success!")
}
});
});
});
I have also noticed that I can view the file in chrome but not load it into gimp. Gimp gives me a file error.
Small steps I guess.
Maybe Datsik can give us some insight on what is going on here.
https://stackoverflow.com/users/2128168/datsik
Phil

How to show file upload progress for each file with AWS Javascript SDK?

I am trying to upload file to AWS S3 and its working fine. But when the file upload is going on for multiple files , how do i get the progress for each file. Below is my code in AngularJs
upload: function (file) {
options = {
accessKeyId : 'xxxxxxx',
secretAccessKey : 'xxxxxxxxxxxxxxxxxxxxxxx',
region : 'xxxxxx'
}
var s3 = new AWS.S3(options);
var params = {
Bucket : bucketStructure,
Key: file.name,
ContentType: file.type,
Body: file,
ServerSideEncryption: 'xxxx',
ACL : 'private'
};
s3.putObject(params, function(err, data) {
if(err) {
// There Was An Error With Your S3 Config
alert('AWS Error : '+err.message);
return false;
}
else {
// Success!
alert('Upload Done');
}
})
.on('httpUploadProgress',function(progress) {
//console.log(Math.round(progress.loaded / progress.total * 100) + '% done');
});
}
I am calling the above code which is in a service function, in a loop. So when the user clicks on form submit button, i get the two files to upload and in a loop below i am calling the above function:
angular.forEach($rootScope.awsfiles, function (file) {
FileFactory.Upload(file);
});
Now how do i get to know for which file the progress to show ?? Any other better ideas to get this working?? Thanks!

Resources