How to customize route controller with both selector and options?


#1

Thanks to Discover Meteor, I write this route.js. and I want to add a custom filter on selector.
Which means Posts.find({categoryId: 1, author, 'Tom'}) . And I could not get this right.
I’ve tried to add

categoryId: function() {
  return parseInt(this.params.categoryId);
},

in PostsListController, but not work. And tried in PostsByCategoryIdController, not working either. So, what is the proper way to do this? What is the common way to define a general filter on post metas like category or author? Thanks a lot!

  PostsListController = RouteController.extend({
  template: 'postsList',
  increment: 25,
  postsLimit: function() {
    return parseInt(this.params.postsLimit) || this.increment;
  },
  findOptions: function() {
    return {sort: this.sort, limit: this.postsLimit()};
  },
  subscriptions: function() {
    this.postsSub = Meteor.subscribe('posts', this.findOptions());
  },
  posts: function() {
    return Posts.find(this.selector, this.findOptions());
  },
  data: function() {
    var hasMore = this.posts().count() === this.postsLimit();
    return {
      posts: this.posts(),
      ready: this.postsSub.ready,
      nextPath: hasMore ? this.nextPath() : null
    };
  }
});

HotPostsController = PostsListController.extend({
  selector: {},
  sort: {commentsCount: -1, submitted: -1, _id: -1},
  nextPath: function() {
    return Router.routes.hotPosts.path({postsLimit: this.postsLimit() + this.increment})
  }
});

PostsByCategoryIdController = PostsListController.extend({
  selector: {categoryId: function() {return parseInt(this.params.categoryId)} },
  // selector: {categoryId: 1 }, // will work
  sort: {submitted: -1, _id: -1},
  nextPath: function() {
    return Router.routes.postsByCategory.path({postsLimit: this.postsLimit() + this.increment})
  }
});

#2

After so many attemps, I finally make it right. The code is here:
I still think there is so much redundancy in it. But I’m only know little js, gettting it work is all I can do for now.

PostsListController = RouteController.extend({
  template: 'postsList',
  increment: 25,
  postsLimit: function() {
    return parseInt(this.params.postsLimit) || this.increment;
  },
  getCategoryId: function() {
    return parseInt(this.params.categoryId);
  },
  getAuthorName: function() {
    return this.params.author || "";
  },
  findSelector: function() {
    cid = this.getCategoryId();
    name = this.getAuthorName();
    if (cid) {
      return {categoryId: cid};
    }
    else if (name) {
      return {author: name};
    }
    else {
      return {};
    }
  },

  findOptions: function() {
    return {sort: this.sort, limit: this.postsLimit()};
  },
  subscriptions: function() {
    this.postsSub = Meteor.subscribe('posts', this.findSelector() ,this.findOptions());
  },
  posts: function() {
    return Posts.find(this.findSelector(), this.findOptions());
  },
  data: function() {
    var hasMore = this.posts().count() === this.postsLimit();
    return {
      posts: this.posts(),
      ready: this.postsSub.ready,
      nextPath: hasMore ? this.nextPath() : null
    };
  }
});

PostsByCategoryIdController = PostsListController.extend({
  sort: {submitted: -1, _id: -1},
  nextPath: function() {
    return Router.routes.postsByCategoryId.path({postsLimit: this.postsLimit() + this.increment})
  }
});

Router.route('/posts/cid/:categoryId/:postsLimit?', {name: 'postsByCategoryId'});