Before_filter chains and halting at an arbitrary filter

Hi–I’m trying to implement a 2-level authentication system, where I
have one before_filter which does general user authentication, and
another which does further authorization for a specific controller. I
have it set up as follows:

before_filter :authorize_level_2
prepend_before_filter :authorize_level_1

which causes authorize_level_1() to run, and then authorize_level_2().

However, the problem is that I want, if authorize_level_1 decides to
redirect someone back to the login page, to not run authorize_level_2.
Unfortunately it looks like this is what happens, and since
authorize_level_2 needs to assume information only available when
authorize_level_1 has succeeded, I get errors.

Is there any way to halt execution of further filters if some condition
is satisfied? I would have though redirect_to() would have this effect,
but it appears that code is still executed after a redirect_to()

“Jonathan L.” [email protected] wrote in
message news:[email protected]

However, the problem is that I want, if authorize_level_1 decides to
Posted via http://www.ruby-forum.com/.
Hi Jonathan

if you return false from a before filter, it stops the execution of
subsequent filters. So returning false after your call to redirect_to
should
do the trick

hth
alan

On 7/18/06, Jonathan L. [email protected] wrote:

Is there any way to halt execution of further filters if some condition
is satisfied? I would have though redirect_to() would have this effect,
but it appears that code is still executed after a redirect_to()

redirect_to …
return false

Thanks to everyone for kindly responding. Sorry I didn’t know the
question had been answered recently (search for the mailing list appears
to be down).

You’d think a simple behavior for filters like this would be included in
the RoR docs! My code works wonderfully now.

-Jonathan

On 7/18/06, Jonathan L. [email protected] wrote:

Thanks to everyone for kindly responding. Sorry I didn’t know the
question had been answered recently (search for the mailing list appears
to be down).

You’d think a simple behavior for filters like this would be included in
the RoR docs! My code works wonderfully now.

http://api.rubyonrails.org/classes/ActionController/Filters/ClassMethods.html

Look under “Filter chain ordering”.

– James

http://api.rubyonrails.org/classes/ActionController/Filters/ClassMethods.html

Look under “Filter chain ordering”.

– James

Ah, thanks. I know I looked at that section 5 or 6 times; must have
breezed over the last two sentences assuming they were talking more
about ordering per se and not about breaking the order. My fault!

Jonathan L. wrote:

However, the problem is that I want, if authorize_level_1 decides to
redirect someone back to the login page, to not run authorize_level_2.
Unfortunately it looks like this is what happens, and since
authorize_level_2 needs to assume information only available when
authorize_level_1 has succeeded, I get errors.

Is there any way to halt execution of further filters if some condition
is satisfied? I would have though redirect_to() would have this effect,
but it appears that code is still executed after a redirect_to()

I had the exact same problem a few weeks ago. I blogged about the
solution here
http://blog.mattmargolis.net/articles/2006/07/02/halting-before_filter-chains
In short you basically just need to return false.

Matthew M.
blog.mattmargolis.net