views:

45

answers:

4

I'm wondering if theres a best practice for what I'm trying to accomplish...

First we have the model categories, categories, has_many posts.

Now lets say, users add posts.


Now, I have a page, that I want to display only the current user's posts by category.


Lets say we have the following categories: A, B, and C

User 1, has posted in Categories A and B.


In my view I have something like:

@categories.each do |category|

   category.name

   @posts.each do |post|
   if post.category_id==category.id

     post content here

    end
    end


end

The problem with this, is I'm going to show the empty category, as well as the categories that do have content.

Is there a more efficient way of going about this? As I don't want to show the empty categories.

Best, Elliot


UPDATE:

So I've been trying to use this code:

<% @categories.select {|cat| cat.posts.count > 0}.each do |category| %> <%= category.name %>
<% category.posts.select {|post| post.user == current_user}.each do |post| %> <%= post.content %>
<% end %> <% end %>

For the most part its almost there. The issue is, it will still show an empty category if any posts have been entered in it at all (even if the current user has not input posts into that category.

So the question boils down to:

How do I make the following loop only count posts in the category from the current user?

<% @categories.select {|cat| cat.posts.count > 0}.each do |category| %>

A: 
@categories.select do |category|
  category.posts.any? {|post| post.user == current_user }
end

Will filter out the categories to have only categories with posts by the current_user. I guess it would be more efficient doing this in the db, use this if you're fetching the @categories anyway.

Jakub Hampl
+1  A: 
<% @categories.select {|cat| cat.posts.count > 0}.each do |category| %>
  <%= category.name %><br/>
  <% category.posts.select {|post| post.user == current_user}.each do |post| %>
    <%= post.content %><br/>
  <% end %>
<% end %>

This renders each category with any posts, then the content for each post within the category belonging to the current user. You'd probably want to do the initial selection in the controller though, to keep the view clean.

zetetic
Hey zetetic, thanks for a great answer!How would I be able to do this selection in the controller?
Elliot
A: 

Hi Elliot,

As per my concern you need to have an intermediate table for users who publish posts for a given category that table might have following fields

user_id,post_id, category_id by this way you will be having a table which has category id's and for each category there is a post.

then you can do the following

get the distinct categories (from above table) loop through the categories get posts for those categories

** then you will not get any categories without posts

cheers, sameera

sameera207
+1  A: 

Adding to zetetic's answer, perhaps the lookup of the posts of a user in a given category would be done the opposite way. Instead of querying "All the posts for the category where the author is the current user", ask for "all the posts for the user where it is in given category"

<% @categories.select {|cat| cat.posts.count > 0}.each do |category| %>
  <%= category.name %><br/>
  <% current_user.posts_in_category(category).each do |post| %>
    <%= post.content %><br/>
  <% end %>
<% end %>

And throw a scoped search User#posts_in_category

EDIT: Probably you should also set the @categories variable already filtered from your controller, if you're not showing them somewhere else in your view. Also, if the category has no posts, it will not enter the cycle, so maybe the select is not needed.

Chubas
Hi Chubas,How would I be able to filter the categories variable in my controller?
Elliot