我正在使用AngularJS(v1.6.7)和Parse Server(v2.3.3)开发电子商务Web应用程序。我在Parse Server中创建了类别和产品类。我正在尝试为每个类别提取一定数量的产品。例如,在主页中,每个类别将检索20个产品。其他页面中的产品数量发生变化。为此,我想创建一个工厂,在任何类别中获取给定数量的产品( amount 和 category 的产品将作为参数传递)。所以我将能够在其他控制器中重用它。我的工厂代码是这样的:
sebetimapp.factory('ProductsFactory', ['$q', function($q){
Parse.initialize('MY_APP_ID', 'JS_KEY');
Parse.serverURL = 'https://parseapi.back4app.com/';
var fac = {};
fac.getProducts = function(cat, lmt) {
var Category = Parse.Object.extend('Category'),
qr = new Parse.Query(Category);
qr.get(cat, {
success: function(res) {
var product_dfd = $q.defer(),
Product = Parse.Object.extend('Product'),
query = new Parse.Query(Product);
query.include('category');
query.equalTo('category', res);
if(lmt) {query.limit(lmt);}
query.find({
success: function(results) {
product_dfd.resolve(results);
},
error: function(err) {
product_dfd.reject(results);
}
});
return product_dfd.promise;
},
error: function(object, error) {
}
});
};
return fac;
}]);
这是我的控制器代码块:
sebetimapp.controller('productsCtrl', ['$scope','$log','$location','$q','ProductsFactory', function($scope, $log, $location, $q, ProductsFactory) {
var params = $location.search(); // I passed category ID as a parameter in url.
$scope.products = function(){
ProductsFactory.getProducts(params.cat, 20).then(function(response){
$log.log('Successfully retrieved products.');
}, function(error) {
$log.log('Unable to get products.');
});
};
$scope.products();
}]);
当我执行它时,会发生错误:TypeError: Cannot read property 'then' of undefined
但如果我不使用工厂并在我的控制器中定义getProducts()
功能,它就可以工作。
为什么会这样?我是AngularJS的新手。任何帮助将不胜感激。
答案 0 :(得分:1)
.then()
方法仅适用于Promises。您的函数似乎没有返回任何内容(因此.then()
不可用)。
这可能会有所帮助:
sebetimapp.factory('ProductsFactory', ['$q', function($q) {
Parse.initialize('MY_APP_ID', 'JS_KEY');
Parse.serverURL = 'https://parseapi.back4app.com/';
var fac = {};
fac.getProducts = function(cat, lmt) {
var Category = Parse.Object.extend('Category'),
qr = new Parse.Query(Category);
return qr.get(cat)
.then(function(res) {
var Product = Parse.Object.extend('Product'),
query = new Parse.Query(Product);
query.include('category');
query.equalTo('category', res);
if (lmt) {
query.limit(lmt);
}
return query.find();
});
};
return fac;
}]);

Parse JS API中的大多数方法都会返回promise。您可以直接使用它们(而不是使用success
和error
回调)。自从我在Parse工作以来已经很久了(我认为它已经不再可用了)所以你可能需要自己弄清楚细节.. Handy Link:http://docs.parseplatform.org/js/guide/#promises
TLDR;您的工厂函数需要返回一个承诺,但不返回任何内容,因此.then()
无法使用
sebetimapp.factory('ProductsFactory', ['$q', function($q) {
Parse.initialize('MY_APP_ID', 'JS_KEY');
Parse.serverURL = 'https://parseapi.back4app.com/';
var fac = {};
fac.getProducts = function(cat, lmt) {
var Category = Parse.Object.extend('Category'),
qr = new Parse.Query(Category),
// Move the deffered object out of the inner function
product_dfd = $q.defer();
qr.get(cat, {
success: function(res) {
var Product = Parse.Object.extend('Product'),
query = new Parse.Query(Product);
query.include('category');
query.equalTo('category', res);
if (lmt) {
query.limit(lmt);
}
query.find({
success: function(results) {
product_dfd.resolve(results);
},
error: function(err) {
product_dfd.reject(results);
}
});
},
error: function(object, error) {}
});
// Return the deferred object
return product_dfd.promise;
};
return fac;
}]);