0f9b6b2dd5ecff193f6dd78502ce1a13

I have a helper to show all my blog entries line by line. Now how can I convert them into day by day basis?

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
before:

def list_for_blogentries(user)
  user.blogentries.collect {|entry| link_for_entry entry}
end

after:

def list_for_blogentries(user)
  hash = user.blogentries.group_by {|entry| entry.created_at.to_s(:db).first(10)}
  hash.each {|date, entries| puts date; entries.each {|entry| link_for_entry entry}} # It seems doesn't work.
end

I wish to have results like:

2007-12-15
blah, blah, blah,
ok, I write my first blog.

2007-12-14
blah, blah...

Refactorings

No refactoring yet !

D16d53391068ff0830269149b060789d

Jason Dew

December 19, 2007, December 19, 2007 13:28, permalink

No rating. Login to rate!

See if this works for you. I would also consider moving the user.blogentries.group_by code into the association proxy -- so you would call user.blogentries.by_day instead. Check out "Association extensions" here: http://api.rubyonrails.org/classes/ActiveRecord/Associations/ClassMethods.html for more information.

Helper

1
2
3
4
5
6
7
8
9
10
11
def list_for_blogentries(user)
  blogentries_by_day = user.blogentries.group_by {|entry| entry.created_at.to_date }
  
  returning "" do |html|
    blogentries_by_day.each do |date, entries|
      html << date.to_s
      entries.each {|entry| html << link_for_entry(entry) }
    end
  end
end
5170ca260dbd2cdfd5a887a4dba7636f

Jeremy Weiskotten

December 19, 2007, December 19, 2007 14:48, permalink

No rating. Login to rate!

I'm not sure what your link_for_entry method does, but I think you need to puts the result of that method. Also, Hash#each_pair is a little more efficient than #each according to the Ruby docs.

You're also assuming that the order of the keys (in this case they are date strings) will be iterated in sorted order. This appears to be the case in my tests, but it's probably just a coincidence because the hash values happen to be in the same order. You should explicitly sort the keys and then iterate the hash in the order of the sorted keys.

1
2
3
4
def list_for_blogentries(user)
  hash = user.blogentries.group_by {|entry| entry.created_at.to_s(:db).first(10)}
  hash.each_pair {|date, entries| puts date; entries.each {|entry| puts link_for_entry entry}}
end
0f9b6b2dd5ecff193f6dd78502ce1a13

winson

December 19, 2007, December 19, 2007 16:25, permalink

No rating. Login to rate!

Hi, Jason,

I tried, it's wonderful. But it seems didn't sort by date very well. Any suggestion?

0f9b6b2dd5ecff193f6dd78502ce1a13

winson

December 19, 2007, December 19, 2007 16:43, permalink

No rating. Login to rate!

Hi, Jeremy,

There's nothing special in my link_for_entry helper. It just help me organize blog entry data, like entry title, entry author & publish date.

D16d53391068ff0830269149b060789d

Jason Dew

December 19, 2007, December 19, 2007 18:46, permalink

No rating. Login to rate!

I didn't consider sorting in the original refactoring so here's the updated version. Hope it helps,

Helper

1
2
3
4
5
6
7
8
9
10
11
12
def list_for_blogentries(user)
  blogentries_by_day = user.blogentries.group_by {|entry| entry.created_at.to_date }
  blogentries_sorted_by_day = blogentries_by_day.sort_by {|(date, entries)| date }.reverse
  
  returning "" do |html|
    blogentries_sorted_by_day.each do |date, entries|
      html << date.to_s
      entries.each {|entry| html << link_for_entry(entry) }
    end
  end
end
0f9b6b2dd5ecff193f6dd78502ce1a13

winson

December 20, 2007, December 20, 2007 01:05, permalink

No rating. Login to rate!

Hi, Jason,

It works like a wonderland, thank you. "blogentries_by_day and blogentries_sorted_by_day" seems can be refactored as:

1
blogentries_sorted_by_day = user.blogentries.group_by {|entry| entry.created_at.to_date }.sort.reverse
D16d53391068ff0830269149b060789d

Jason Dew

December 20, 2007, December 20, 2007 02:04, permalink

No rating. Login to rate!

very true :-)

Your refactoring





Format Copy from initial code

or Cancel