Ruby Forum Ferret > Multi select with conditions

Posted by Max Williams (max-williams)
on 17.04.2008 12:27
(Received via mailing list)
Hi

I'm doing a multi-model search like this, which works absolutely fine:

        @search_results = ActsAsFerret::find( "trumpet", [Resource, 
Lesson,
Course],
                                    #(ferret) options
                                    { :page => 1,
                                      :per_page => 20,
                                      :sort =>
Ferret::Search::SortField.new(:name, :reverse => false)
                                    },
                                    #find options
                                    {}
                                 )

My new problem is that the results need to be restricted: basically any 
user
has only limited access to certain lessons, resources and courses, 
depending
on their shared priveleges.  I have methods to produce arrays of ids of 
each
that the user is allowed to see, eg

@user.allowed_lessons
  => array of ids of all lessons the user has access to

Can anyone show me how to incorporate this into my search?  I have the
feeling that i can do something with the :conditions options, which can 
be
passed through in the find options hash.  But i can't work it out:  i 
tried
this:

:conditions => ["lesson.id in (?) or course.id in (?) or resource.id in
(?)", @user.allowed_lessons, @user.allowed_courses, 
@user.allowed_resources]

But it doesn't work:  it says 'no such field as lesson.id in resources'. 
I
feel like this should be possible - can anyone help?

thanks
max
Posted by Nicolas Escobar (nejrb)
on 31.05.2008 18:28
I have the same problem Max, did you solve it?

Regards!
Posted by Adam Hill (ado)
on 12.06.2008 03:00
Hi Max,

Try this:


@search_results = ActsAsFerret::find("trumpet", [Resource, Lesson, 
Course],
                                    #(ferret) options
                                    { :page => 1,
                                      :per_page => 20,
                                      :sort => 
Ferret::Search::SortField.new(:name, :reverse => false)
                                    },
                                    #find options - note this assumes 
it's a flat array of allowed id numbers:
                                    { :lesson   => "lessons.id IN 
(#{@user.allowed_lessons.join(',')})",
                                      :course   => "courses.id IN 
(#{@user.allowed_courses.join(',')})",
                                      :resource => "resources.id IN 
(#{@user.allowed_resources.join(',')})"
                                    }
                                 )
Posted by Adam Hill (ado)
on 12.06.2008 05:31
Sorry, I missed the :conditions key in the last hash
{ :conditions => {:lesson   => "lessons.id IN
(#{@user.allowed_lessons.join(',')})",
                  :course   => "courses.id IN
(#{@user.allowed_courses.join(',')})",
                  :resource => "resources.id IN
(#{@user.allowed_resources.join(',')})"
                 }
}
Posted by Max Williams (max-williams)
on 13.06.2008 11:31
Thanks all

On the way to solving this i found a bug in acts_as_ferret - it seems 
that if i try to sort, paginate and use conditions at the same time then 
the sorting breaks down:  instead of being sorted and then paginated, 
the results are paginated (ordered simply by id) and then sorted within 
each page.

I let Jens Kraemer (and the acts as ferret mailing list) know about it 
but as far as i know it's not been fixed.

I ended up doing a ferret search to get the ids of the results (with 
unallowed records filtered out), and then doing an AR find to get those 
results, sort and paginate them.  So, it's a little inelegant but it 
works, at least.

thanks
max