Different permissions for resource and some of its privileges

classic Classic list List threaded Threaded
4 messages Options
Reply | Threaded
Open this post in threaded view
|

Different permissions for resource and some of its privileges

Dmitry Petrov
Greetings to all,

I'm building navigation on my site with Zend_Navigation and Zend_Acl. Each resource is connected to some controller, additionally I want to have an ability to set a custom access rights for every action ( they are associated with priveleges ) if needed.

I've found that if some privilege is denied for role, than the whole resource is considered "not allowed", even if role can access any other privileges.

Here is a testcase:

$test = new Zend_Acl();
$test->addRole( new Zend_Acl_Role( 'user' ) );
$test->addRole( new Zend_Acl_Role( 'admin' ) );
$test->addResource( new Zend_Acl_Resource( 'about' ) );

$test->allow( array( 'user', 'admin' ), 'about' );
$test->deny( array( 'user', 'admin' ), 'about', 'somestuff' );
$test->allow( array( 'admin' ), 'about', 'somestuff' );

var_dump( $test->isAllowed( 'user', 'about' ) ); //false :(
var_dump( $test->isAllowed( 'admin', 'about' ) ); //true
var_dump( $test->isAllowed( 'user', 'about', 'somestuff' ) ); //false
var_dump( $test->isAllowed( 'user', 'about', 'anyotherstuff' ) ); //true
var_dump( $test->isAllowed( 'admin', 'about', 'somestuff' ) ); //true


As you can see, even when I explictly allow access for all privilege for user role and deny only one, the whole resource is not allowed. As the consequence, this resource will not be shown in the menu for the user.

I've found the place in code, where it happens, and commented it out, and now everything works right as I've expected, but I'm not sure, that it's a correct way to solve the problem.

Can anyone correct me, if i'm doing the wrong thing, or the problem has other solutions?
Reply | Threaded
Open this post in threaded view
|

Re: Different permissions for resource and some of its privileges

Peter Sharp
That's actually pretty interesting.  At first glance I thought it might just be the way you're defining it, but it seems that denying access to a resource and permission pair actually blocks the entire resource.

About the best I could come up with would be to use something like:

$test->allow( array( 'user', 'admin' ), 'about' );
$test->removeAllow( 'user', 'about', 'somestuff');

But still, this seems like a bug to me.  It makes setting ACL permissions dynamically a much more difficult proposition.
Reply | Threaded
Open this post in threaded view
|

Re: Different permissions for resource and some of its privileges

Peter Sharp
Actually, now that I come to think about it, this behavior does make sense.

You're in effect setting two permissions for the same user on the same resource, and the ACL is deciding to take the most restrictive rule by default.

Better would be to say:

$test->addRole('user');
$test->addRole('admin', 'user');

$test->allow('user', 'about', array('index', 'anyotherstuff'));
$test->allow('admin', 'about', 'somestuff');

You also have to remember that if you're assigning the action as a permission then the default view for a controller would be 'index' for testing, not null.

So ...

var_dump($test->isAllowed('user', 'about', 'index'));
... etc
Reply | Threaded
Open this post in threaded view
|

Re: Different permissions for resource and some of its privileges

Dmitry Petrov
It's a big question, because  I restrict access to only one privilege.

However, your last note makes sense. Thanks!