Android 角度:无法读取属性';然后';未定义的
在我使用Android 角度:无法读取属性';然后';未定义的,android,angularjs,cordova,amazon-s3,crosswalk-runtime,Android,Angularjs,Cordova,Amazon S3,Crosswalk Runtime,在我使用cordova文件传输插件与自己的后端签名后,我有一个服务上传图像到amazons3。 我在使用cordovacamera插件拍照后调用此服务,将拍摄的照片上传到s3存储桶。 应用程序使用我自己的后端正确签名,但当它触发函数upload时,我得到了我在标题中定义的错误。 这是服务,它在我的后端调用一个端点来签署文件,然后将图像上载到amazon s3: //Image upload Service .factory('S3Uploader', function($q, $window,
cordova
文件传输
插件与自己的后端签名后,我有一个服务上传图像到amazons3
。
我在使用cordova
camera
插件拍照后调用此服务,将拍摄的照片上传到s3存储桶
。
应用程序使用我自己的后端正确签名,但当它触发函数upload
时,我得到了我在标题中定义的错误。
这是服务
,它在我的后端调用一个端点来签署文件,然后将图像上载到amazon s3
:
//Image upload Service
.factory('S3Uploader', function($q, $window, $http, $ionicPopup, API_URL) {
var signingURI = API_URL + "s3signing";
function upload(imageURI, fileName) {
document.addEventListener('deviceready', function() {
console.log('Uploading ' + fileName + ' to S3');
var deferred = $q.defer(),
ft = new FileTransfer(),
options = new FileUploadOptions();
options.fileKey = "file";
options.fileName = fileName;
options.mimeType = "image/jpeg";
options.chunkedMode = false;
console.log('Requesting signed doc ' + signingURI);
$http.post(signingURI, {
"fileName": fileName
})
.success(function(data) {
console.log('Got signed doc: ' + JSON.stringify(data));
options.params = {
"auth": true,
"key": fileName,
"AWSAccessKeyId": data.awsKey,
"acl": "public-read",
"policy": data.policy,
"signature": data.signature,
"Content-Type": "image/jpeg"
};
ft.upload(imageURI, "https://" + data.bucket + ".s3.amazonaws.com/",
function(e) {
console.log("Upload succeeded");
console.log(JSON.stringify(e));
deferred.resolve(e);
$ionicPopup.alert({
title: 'great',
content: 'The image upload to amazon success'
});
},
function(e) {
deferred.reject(e);
$ionicPopup.alert({
title: 'Oops',
content: 'The image upload failed to amazon'
});
}, options);
})
.error(function(data, status, headers, config) {
console.log(JSON.stringify(data));
console.log(status);
$ionicPopup.alert({
title: 'Oops',
content: 'The image upload failed to sign with node'
});
});
return deferred.promise;
}, false); //device ready
}
return {
upload: upload
}
})
下面是控制器代码,在这里,我调用相机插件,在成功拍照时,我从S3Uploader服务调用上传功能:
.controller('newItemCtrl', function($scope, $http, $ionicPopup, $timeout, $cordovaCamera, API_URL, me, S3Uploader) {
$scope.selectPicture = function() {
document.addEventListener('deviceready', function() {
var options = {
destinationType: Camera.DestinationType.FILE_URI,
sourceType: Camera.PictureSourceType.CAMERA,
allowEdit: true,
encodingType: Camera.EncodingType.JPEG,
targetWidth: 300,
targetHeight: 300,
};
$cordovaCamera.getPicture(options).then(function(imageURI) {
$scope.imageSrc = imageURI;
// upload to Amazon s3 bucket
var fileName = new Date().getTime() + ".jpg";
S3Uploader.upload(imageURI, fileName).then(function() {
alert("upload to S3 successed");
});
}, function(err) {
alert(err);
});
}, false); // device ready
}; // Select picture
})
我在控制器的这一行中得到erorr:
S3Uploader.upload(imageURI, fileName).then(function() {
还有一点很重要,我在我的ionic应用程序中使用了crosswalk。您当前的
S3Uploader实现。upload
不会返回承诺,它不会返回任何东西。将您的声明和承诺的返回直接移动到S3Uploader.upload
函数中,而不是嵌套在文档中。addEventListener
code
将代码更改为类似以下内容:
.factory('S3Uploader', function($q, $window, $http, $ionicPopup, API_URL) {
var signingURI = API_URL + "s3signing";
function upload(imageURI, fileName) {
var deferred = $q.defer()
document.addEventListener('deviceready', function() {
// Removed for brevity
}, false);
return deferred.promise;
}
return {
upload: upload
}
})
您正在创建并从事件侦听器返回延迟对象及其承诺。不是上传工厂方法 您需要的就是这些方面:
.factory('S3Uploader', function($q) {
function upload() {
var deferred = $q.defer();
// listener logic
return deferred.promise;
}
return {
upload : upload
}
});
这会有问题,因为每次启动侦听器时都需要一个新的延迟对象。在我看来,向工厂方法添加侦听器来执行某些操作似乎是一种糟糕的模式。事件应该将工厂方法的调用包装起来。总是有人用同样的答案击败我:-)谢谢,您的回答修复了我的问题:我在控制台中没有收到此错误,但在调用上载函数几秒钟后,应用程序仍然崩溃。我不知道是插件、人行横道还是实现。@AhmadElmoualem为此提出了一个新问题。