-
- 620 Posts
How can I determine if a user has the necessary permissions to access a given resource in a snippet?
I am writing a little plugin that uses the modx API [externally] to log in a user and grab various resources for use in a mobile app, now the only thing missing is restricting users from resources they do not have access to.
Best I can come up with [after searching through the API] is to getGroupsList on the resource they are trying to access & then compare it to the users group memberships...
Is there an easier way?
*** Not just websites, we also create signage, banners, print, trade show displays and more! ***
Sean Kimball CLP, CLS.
Technical Director / Sr. Developer | BigBlock Studios
._______________________________________________.
Bigblock Studios
http://www.bigblockstudios.ca Web site design & development.
27-1300 King Street East. Box 167 Oshawa, Ontario L1H8J4 Canada.
phone/fax: 905-426-5525
-
- 24,544 Posts
See these two tests, the first one checks the Context Access permissions, the second checks the Resource Group Access permissions. You can use either test or both and you can use any permission you like (see the Administrator policy for the hasPermission() test and the Resource policy for the checkPolicy() test.
if (!$this->modx->hasPermission('view_document') || !$this->resource->checkPolicy('view') ) {
/* user has permission */
}
Notice that hasPermission() is a method of $modx and checkPolicy is a method of the Resource object.
-
- 620 Posts
hmmm... no love:
this is the function I am using to retrieve the resource, it always denies access....
function getResource($id){
$templateVars = array();
$content = array();
$resource = $this->modx->getObject('modResource',$id);
if ($this->modx->hasPermission('view_document') || $resource->checkPolicy('view') ) {
$content = array('access'=>'denied');
return $content;
}
if($resource){
$fields = $this->modx->getFields('modResource');
foreach($fields as $key => $value){
$content[$key] = $resource->get($key);
}
$tvs = $resource->getMany('TemplateVars');
if (!empty($tvs)) {
foreach($tvs as $tv) {
$name = $tv->get('name');
$value = $tv->getValue($id);
//echo $name.' = '.$value.'<br>';
$templateVars[] = array($name => $value);
}
}
}
$content['template_variables'] = $templateVars;
return $content;
}
so what is the checkPolicy and hasPermission doing, are they just "assuming" the current user?
*** Not just websites, we also create signage, banners, print, trade show displays and more! ***
Sean Kimball CLP, CLS.
Technical Director / Sr. Developer | BigBlock Studios
._______________________________________________.
Bigblock Studios
http://www.bigblockstudios.ca Web site design & development.
27-1300 King Street East. Box 167 Oshawa, Ontario L1H8J4 Canada.
phone/fax: 905-426-5525
-
- 24,544 Posts
Yes, they assume the current user. BTW, your test is backwards. You're rejecting users who *have* either of the permissions.
if (! ($this->modx->hasPermission('view_document') && $resource->checkPolicy('view') )) {
-
- 620 Posts
oh yea - left that from fiddling with it - if I replace the exclamation marks, then it allows access to any resource - protected or not.
is it possible to explicitly pass the user & doc id to either function?
*** Not just websites, we also create signage, banners, print, trade show displays and more! ***
Sean Kimball CLP, CLS.
Technical Director / Sr. Developer | BigBlock Studios
._______________________________________________.
Bigblock Studios
http://www.bigblockstudios.ca Web site design & development.
27-1300 King Street East. Box 167 Oshawa, Ontario L1H8J4 Canada.
phone/fax: 905-426-5525
-
- 24,544 Posts
I don't think so. The permissions of the current user are in memory and both functions just check them.
If you need to check permissions for some other user, I think you'd need to query the access tables yourself, though you might be able to cheat by getting the user object and checking the user group(s) they belong to with $user->isMember('UserGroupName').
[update] FYI, isMember() will also take an array of user group names and return true if the user is a member of any of them.
-
- 620 Posts
hmmmm - I can't get this to work at all, I have the function:
function getResource($id){
$resource = $this->modx->getObject('modResource',$id);
echo $this->modx->getLoginUserID().'<br >';
echo '<br >view_document '.$this->modx->hasPermission('view_document');
echo '<br >load '.$this->modx->hasPermission('load');
echo '<br >view_category '.$this->modx->hasPermission('view_category');
echo '<br >view_plugin '.$this->modx->hasPermission('view_plugin');
echo '<br >view_snippet '.$this->modx->hasPermission('view_snippet');
echo '<br >view_template '.$this->modx->hasPermission('view_template');
if (!($this->modx->hasPermission('view_document') && $resource->checkPolicy('view')) ) {
$content = array('access'=>'granted');
//return $content;
}
$templateVars = array();
$content = array();
if($resource){
$fields = $this->modx->getFields('modResource');
foreach($fields as $key => $value){
$content[$key] = $resource->get($key);
}
$tvs = $resource->getMany('TemplateVars');
if (!empty($tvs)) {
foreach($tvs as $tv) {
$name = $tv->get('name');
$value = $tv->getValue($id);
//echo $name.' = '.$value.'<br>';
$templateVars[] = array($name => $value);
}
}
}
$content['template_variables'] = $templateVars;
return $content;
}
those first few 'echo' tests always return '1' even if there is no user logged in I've triple checked this & the user permissions, flushed sessions etc. no love.
any thoughts? actually the problem here is that the functions hasPermission and checkPolicy are acting on the current document, which the user will always have access to - I need to pass a different document id to the hasPermission/checkPolicy ... is this possible?
[ed. note: sean69 last edited this post 11 years, 1 month ago.]
*** Not just websites, we also create signage, banners, print, trade show displays and more! ***
Sean Kimball CLP, CLS.
Technical Director / Sr. Developer | BigBlock Studios
._______________________________________________.
Bigblock Studios
http://www.bigblockstudios.ca Web site design & development.
27-1300 King Street East. Box 167 Oshawa, Ontario L1H8J4 Canada.
phone/fax: 905-426-5525
-
- 24,544 Posts
Are you previewing from the Manager? That will mess things up.
Are you running it as a snippet in MODX? The permission tests are bypassed in CLI mode.
Are you sure the user who is logged-in in the front end doesn't have those permissions?
If it's the anonymous user, $modx->user->get('username') should return (anonymous).
TBH, I would be tempted to just put the users who can see the stuff in a user group called "ViewPrivate" and put this at the top of the snippet:
if (!$modx->user->isMember('ViewPrivate')) {
return '';
}
-
- 620 Posts
Hi Bob;
I'm running it from an external script that is loading modx as an API connector ~ I'm using the REST client in a Chrome window [that I made sure I had logged out of the manager before
] & making any modifications to the user/groups in a firefox window. Keeping modx honest like that
not running in command line mode, I'm 100% sure the user does not have permissions for the resource that is being loaded in the first line of the function.
you can take a peek at the attached if you want - it's pretty simple at the moment [and pretty 'wire-framey']
*** Not just websites, we also create signage, banners, print, trade show displays and more! ***
Sean Kimball CLP, CLS.
Technical Director / Sr. Developer | BigBlock Studios
._______________________________________________.
Bigblock Studios
http://www.bigblockstudios.ca Web site design & development.
27-1300 King Street East. Box 167 Oshawa, Ontario L1H8J4 Canada.
phone/fax: 905-426-5525
-
- 620 Posts
the attachment thing seems broken.... I'll pm it.
ahhh, does not like .rar files ...
*** Not just websites, we also create signage, banners, print, trade show displays and more! ***
Sean Kimball CLP, CLS.
Technical Director / Sr. Developer | BigBlock Studios
._______________________________________________.
Bigblock Studios
http://www.bigblockstudios.ca Web site design & development.
27-1300 King Street East. Box 167 Oshawa, Ontario L1H8J4 Canada.
phone/fax: 905-426-5525