I can haz API ?

Published
2011-05-13 00:12
Written by

Hi,

Some improvements on permissions and the API are landing on 3.4.2 and 4.0.2.

On the previous versions, the permissions where not enforced (on php and smarty) and checked on the same permission "access civicrm" for the rest and ajax no matter the operation and entity.

 

As API v3 is exposing more and more entities, it became necessary to control better what could be accessed. We re-used the permissions has defined on drupal for the menues, but instead of applying them to a path (in order to access civicrm/admin/event  the user need the priviledge "access CiviEvent"), we applied them to the entities and action (in order to create an event using the api, the user need the priviledge "access CiviEvent").

 

We realised there isn't a perfect match between these two logics "protect what pages and form you can access" vs. "protect what type of content and action", but mostly worked out ok.

 

This permission check is applied to all the remote calls (ajax and api), but isn't by default for the code hosted on your server (smarty and php)

 

ajax and REST calls

Now if you have a remote server calling an api (eg. create event), it will not only check that you can have "access civicrm", but based on the action, if you have the specific permission (eg. "access CiviEvent").

 

If after the upgrade your ajax or REST doesn't work, please verify that the user has the necessary permissions and grant the right ones.

 

php and smarty calls

For php and smarty, we ignore by default the permissions. In most of the case, you are using php to fetch informations, eg the list of the staff to display it to visitors that don't have access to civicrm, so it makes sense that your custom code can access as much as needed, no matter the connected user.

 

This has been the behaviour of the api since the beginning, but now you can reverse this and enforce the permission check by adding 'check_permissions' => true.

So

$contacts = civicrm_api("Contact","get", array ('version' =>'3', 'group' => 42, 'check_permissions' => true));

Will only returns the contacts if the user visiting the page generated by that code has access to civicrm. If you want to display the contacts no matter what are the permissions:

$contacts = civicrm_api("Contact","get", array ('version' =>'3', 'group' => 42));

that is equivalent to:

$contacts = civicrm_api("Contact","get", array ('version' =>'3', 'group' => 42, 'check_permissions' => false));

 

Is this a security issue to not check the permission by default? When you write the code, you should know if you want the permission checked or not. And if you think someone could run bad code on your server, having the "check_permission" false by default is the least of your problem ;). Trying to enforce that at the code level was proven annoying without bringing any extra security.

 

What about 3.4.1 & 4.0.1

Err, on that one we unfortunately enforced the permissions even on the php code. Some users did hit that problem. Either wait for the next release (comming next week), or apply this patch.

 

How to change the ACL and custom API?

A new hook hook_civicrm_alterAPIPermissions allows you either to add new entities (custom API) and define what permissions are needed to access them (via ajax), or to change the default permissions.

 

It obviously means that you might end up letting anonymous users access more information than necessary, use responsibly.

 

Future of permissioning in CiviCRM?

As said, we have two different logic of permissions now in civicrm, one based on the menu/url, the other on the content type and action. We would like to see if this can be made more coherent, and you are welcome to join the discussion that will start soon.

 

And the mandatory picture as a conclusion

 

lame lolcat

lamecat.jpg48.94 KB
Filed under

Comments

Anonymous (not verified)
2011-05-13 - 05:09

Thanks for deciding to revert this!  It totally messed up part of our site after I upgraded to 3.4.1.  Luckily Eileen clued me in.

I have also made some minor changes to the Membership Get function output - this is due to the output not being per standard & it still being so early in the v3 release that I thought I could get away with changing it

http://forum.civicrm.org/index.php/topic,19957.0.html