Reputation: 8589
I have a big little issue with the filters on Angular, to be explicit: input search with a filter attached.
if you see this example, is exactly what I want
actually I did that Plnkr with the real information of my app. You can search through sports and his leagues, but in my app you can not, you can just search through the sports and once you try to search any leagues, the app returns a message "did not match any search criteria", below I will put all of the code regarding this issue, someone says it could be a routing issue or that I am missing a resolve or something like that, that's why I am here, because I need your help. Also I recorded a VIDEO for you to understand easier, as you see on the video if I put "college" the filter works, but below there are 2 leagues starting with "ncaa", if I type "ncaa" then the empty message shows up. It is weird because in the Plnkr example everything works properly.
sportsList.html
<input type="text"
placeholder="Sports finder..."
ng-model="query">
<div ng-repeat="sport in sportsFilter = (sports | filter:query)">
ng-if="sport.leagues.length">
<!--this filter works correctly-->
{{sport.name}}
<div ng-repeat="league in sport.leagues | filter:query">
<!--this filter do not any respond-->
{{league.name}}
</div>
</div>
app.js
.config(function($stateProvider, $urlRouterProvider) {
$stateProvider
.state('app.sports', {
url:'/sports',
views:{
menuContent:{
templateUrl:'templates/sportsList.html',
controller:'SportsController'
}
}
})
service.js
.factory('SportsFactory', function($http, $q, AuthFactory,
LocalForageFactory, LeaguesFactory, CONSTANT_VARS) {
return {
getSports: function(agent) {
var defer = $q.defer();
LocalForageFactory.retrieve(CONSTANT_VARS.LOCALFORAGE_SPORTS)
.then(function(sports) {
if (!_.isNull(sports)) {
defer.resolve(_.values(sports));
}else {
$http.get(CONSTANT_VARS.BACKEND_URL + '/lines/sports/' + agent)
.success(function(sports) {
//forcing array instead of object
sports = _.values(sports);
sports = _.sortBy(sports, function(sport) {
return sport.priority;
});
LocalForageFactory.set(CONSTANT_VARS.LOCALFORAGE_SPORTS, sports);
defer.resolve(sports);
})
.error(function(err) {
defer.reject(err);
});
}
});
return defer.promise;
},
getSportsWithLeagues: function(customer) {
var _this = this,
defer = $q.defer(),
rejection = function(err) {
defer.reject(err);
},
sportsLength;
LocalForageFactory.retrieve(CONSTANT_VARS.LOCALFORAGE_SPORTS_LEAGUES)
.then(function(sportLeagues) {
if (!_.isNull(sportLeagues)) {
//forcing array instead of object
sportLeagues = _.values(sportLeagues);
defer.resolve(sportLeagues);
}else {
_this.getSports(customer.agent).then(function(sports) {
sportsLength = sports.length;
LeaguesFactory.getLeagues({
sportIds: _.pluck(sports, 'id'),
lineProfile: customer.lineProfile,
betLimit: customer.betLimit
}).then(function(leagues) {
_.each(sports, function(sport) {
sport.leagues = _.filter(leagues, function(league) {
return sport.id === league.sport.id;
});
});
//forcing array instead of object
sports = _.values(sports);
LocalForageFactory.set(CONSTANT_VARS.LOCALFORAGE_SPORTS_LEAGUES, sports);
defer.resolve(sports);
}, rejection);
}, rejection);
}
}, rejection);
return defer.promise;
}
};
});
controller.js
.controller('SportsController', function($scope, $state,
AuthFactory, SportsFactory) {
$scope.sports = [];
$scope.customer = {};
AuthFactory.getCustomer().then(function(customer) {
$scope.customer = customer;
SportsFactory.getSportsWithLeagues(customer).then(function(sports) {
$ionicLoading.hide();
if (sports.length) {
$scope.sports = sports;
}else {
AuthFactory.logout();
}
}, function(err) {
$ionicLoading.hide();
console.log(err);
});
}, function(err) {
$ionicLoading.hide();
$state.go('app.login');
console.log(err);
});
what are your suggestions ?
Upvotes: 3
Views: 92
Reputation: 8589
Auto answering just for future issues, the proper way to do it and avoiding anti patterns:
.state('app.sports', {
url:'/sports',
views:{
menuContent:{
templateUrl:'templates/sportsList.html',
controller:'SportsController',
resolve: {
Customer: ['AuthFactory', function(AuthFactory) {
return AuthFactory.getCustomer();
}],
Sports: ['SportsFactory', 'Customer', function(SportsFactory, Customer) {
return SportsFactory.getSportsWithLeagues(Customer);
}],
Leagues: ['Sports', 'LeaguesFactory', function(Sports, LeaguesFactory) {
return LeaguesFactory.getLeagues(Sports);
}]
}
}
}
})
Upvotes: 1
Reputation: 56
maybe you should to resolve the service in the route, here is an example:
views:{
menuContent:{
templateUrl:'templates/sportsList.html',
controller:'SportsController',
resolve: {
Sports: function(sportsService, $q) {
var defer = $q.defer();
sportsService.getSports().then(function getAllSports(allSports) {
defer.resolve(allArticles);
});
return defer.promise;
}
}
}
}
Then just call Sports resolved in your controller
.controller('SportsController', function($scope, Sports) {
$scope.sports = Sports
Somethig like that, this just an example, you should to call the AuthFactory in the resolve as well.
Here is the documentation for resolve:
resolve documentation for ui-router
hope this help, cheers!
Upvotes: 1