Comparing lists of field-hashes with equivalent AR-objects.

Posted by Tim Snowhite on Stack Overflow See other posts from Stack Overflow or by Tim Snowhite
Published on 2010-04-30T21:29:28Z Indexed on 2010/04/30 22:27 UTC
Read the original article Hit count: 160

Filed under:
|
|
|
|

I have a list of hashes, as such:

incoming_links = [
 {:title => 'blah1', :url => "http://blah.com/post/1"},
 {:title => 'blah2', :url => "http://blah.com/post/2"},
 {:title => 'blah3', :url => "http://blah.com/post/3"}]

And an ActiveRecord model which has fields in the database with some matching rows, say:

Link.all => 
[<Link#2 @title='blah2' @url='...post/2'>,
 <Link#3 @title='blah3' @url='...post/3'>,
 <Link#4 @title='blah4' @url='...post/4'>]

I'd like to do set operations on Link.all with incoming_links so that I can figure out that <Link#4 ...> is not in the set of incoming_links, and {:title => 'blah1', :url =>'http://blah.com/post/1'} is not in the Link.all set, like so:

#pseudocode #incoming_links = as above links = Link.all expired_links = links - incoming_links missing_links = incoming_links - links expired_links.destroy missing_links.each{|link| Link.create(link)}

One route I've tried:

I'd rather not rewrite Array#- and such, and I'm okay with converting incoming_links to a set of unsaved Link objects; so I've tried overwriting hash eql? and so on in Link so that it ignored the id equality that AR::Base provides by default. But this is the only place this sort of equality should be considered in the application - in other places the Link#id default identity is required. Is there some way I could subclass Link and apply the hash, eql?, etc overwriting there?

The other route I've tried is to pull out the attributes hash for each Link and doing a .slice('id',...etc) to prune the hashes down. But this requires writing seperate methods for keeping track of the Link objects while doing set operations on the hashes, or writing seperate Collection classes to wrap the incoming_links hash-list and Link-list which seems a bit overkill.

What is the best way to design this interaction? Extra credit for cleanliness.

© Stack Overflow or respective owner

Related posts about activerecord

Related posts about Identity