SitePoint Sponsor

User Tag List

Results 1 to 5 of 5

Hybrid View

  1. #1
    SitePoint Member
    Join Date
    Apr 2006
    Posts
    18
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)

    acts_as_list sort by multiple items

    I have a Person model and I'm using acts_as_list so I can have drag/drop positioning of people. The only thing is, I want to be able to differentiate between male and female, ie. sort males separately from females. It seems completely useless to have two separate models since all the other attributes of a person are the same (name, address etc) Does acts_as_list allow ordering by, say, position and sex so I can just keep one model and have some males positioned from 0-x and females positioned from 0-y ? x&y being the # of males/females respectively

    In writing this, I also just thought, maybe I can create a person model and have a male/female model extend from this with attribute sex, then use acts_as_list on the male/female model. I'm not sure i would know how to design the db for that.

    Any thoughts on this?

  2. #2
    SitePoint Member
    Join Date
    Apr 2006
    Posts
    18
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    So i'm thinking of implementing the following:
    Code:
    class Person > ActiveRecord:Base #has name, details, sex, position
    then having
    Code:
    class Male > Person
    and
    Code:
    class Female > Person
    From an OO perspective, this makes sense. but in rails I'm not so sure. I don't want a separate db table for male/female, so it all has to be stored in Person. The whole point is to not use two separate db tables for male and female. But in my controller, if I create a new Person, i can check params[:sex] and either create Male or Female depending. I still don't know if this will work as far as the sorting. I'll have acts_as_list for each male/female but if I make a sort function in my male controller, and I call Male.update_all I can't visualize how rails could possibly only select the males from the Person db given that the Male class is basically just virtual. Ugh, i'm pretty confused here, if anyone has insight, it's greatly appreciated

  3. #3
    SitePoint Evangelist
    Join Date
    Feb 2006
    Location
    Worcs. UK
    Posts
    404
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    If the only difference is the entry in the "sex" field, then I really think creating separate classes is just making things difficult - especially if you want to keep all the data in the same table.

    If it were me, I'd create Person methods that return male and female. A simple solution would be something like this:

    Code:
    class Person < ActiveRecord:Base
      def self.find_all_male
        find(:all, :conditions => " sex = 'male' ")
      end
    
      def self.find_all_female
        find(:all, :conditions => " sex = 'female' ")
      end
    end
    Usage would be:
    Code:
    @men = Person.find_all_male
    However, a more flexible approach is to do something like this:
    Code:
    class Person < ActiveRecord:Base
      def self.find_male(options = Hash.new)
        new_condition = " sex = 'male' "
        find(:all, options_plus_new_condition(options, new_condition)
      end
    
      def self.find_female(options = Hash.new)
        new_condition = " sex = 'female' "
        find(:all, options_plus_new_condition(options, new_condition)
      end
    
      private
        def self.options_plus_new_condition(options, new_condition)
        if options[:conditions]
          if options[:conditions].kind_of? Array
            options[:conditions][0] << " AND #{new_condition}"
          else
            options[:conditions] << " AND #{new_condition}"
          end
        else
          options[:conditions] = new_condition
        end
        return options
      end
    end
    Usage would be
    Code:
    #get all men
    men = Person.find_male
    
    #get all women with blue eyes and sort by name
    blue_eyed_women = Person.find_female({:conditions => ["eye_colour = ?", 'blue'], :order => 'name'})

  4. #4
    SitePoint Member
    Join Date
    Apr 2006
    Posts
    18
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Hi, thanks for the response. I had no problems retrieving separate male/female columns, the problem was that acts_as_list automatically adds the new position as the max of all items in the scope.

    I ended up using one class as I wanted. and i just didnt use acts_as_list at all. I made my own function to get count of males and females, so when I create a male or female, it sets the position appropriately

    Don't know why I didn't just think of that in the first place, it's pretty simple Likewise I wrote my own delete function to update all positions appropriately

  5. #5
    SitePoint Member flover21's Avatar
    Join Date
    Feb 2009
    Location
    Prague
    Posts
    15
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    2ReggieB
    great advice. I'd never did like this


Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •