Answers.Body: <h1>Events</h1>
  
  <p>The <a href="https://github.com/civicrm/civicrm-core/blob/master/Civi/API/Kernel.php" rel="nofollow noreferrer">API kernel</a> broadcasts an <a href="https://github.com/civicrm/civicrm-core/blob/master/Civi/API/Event/AuthorizeEvent.php#L28" rel="nofollow noreferrer">authorise event</a>.</p>
  
  <h2>Core permission check listener</h2>
  
  <p>The <a href="https://github.com/civicrm/civicrm-core/blob/master/Civi/API/Subscriber/PermissionCheck.php#L56" rel="nofollow noreferrer">main API permission check subscriber</a> will respond to the event by:</p>
  
  <pre><code>$apiRequest = $event-&gt;getApiRequest();   
  if ($apiRequest['version'] &lt; 4) { /* blah */ }
  elseif ($apiRequest['version'] == 4) {      
    if (!$apiRequest-&gt;getCheckPermissions()) {
      $event-&gt;authorize();                    
      $event-&gt;stopPropagation();              
    }                                         
  }                                           
  </code></pre>
  
  <h2>Adding your own listener</h2>
  
  <p>If the core logic doesn't meet your needs, it is possible to get the <a href="http://api.symfony.com/3.2/Symfony/Component/EventDispatcher/EventDispatcher.html" rel="nofollow noreferrer">symfony event dispatcher service</a> and add either a listener (for single events) or a subscriber (for multiple events).</p>
  
  <p>For example, to add a subscriber:</p>
  
  <pre><code>$subscriber = new MySubscriberClass();            
  \Civi::service('dispatcher')-&gt;addSubscriber($subscriber);
  </code></pre>
  
  <p>When your listener/subscriber is called, then call the <code>$event-&gt;getApiRequest()</code> to find out the parameters you are being asked to authorise. If the event should be authorised then call <code>$event-&gt;authorize()</code>.</p>
  
  <h1>SQL clauses</h1>
  
  <p>For actions based on <code>get()</code>,
  the <a href="https://github.com/civicrm/civicrm-core/blob/master/Civi/API/SelectQuery.php" rel="nofollow noreferrer">selectQuery->getAclClause() method</a> will call <code>$baoName::getSelectWhereClause($tableAlias)</code> to add a where clause.</p>
  
  <p>It doesn't seem possible currently to apply differing ACL logic depending on the action with this method. </p>
  
Answers.ContentLicense: CC BY-SA 3.0
Answers.CreationDate: 2017-03-12T00:14:24.093Z
Answers.Text: Excellent, thanks for documenting this. One caveat, the api4 is currently unstable and by the time it's released this information may be out-of-date.
Answers.UserDisplayName: Coleman
Answers.ContentLicense: CC BY-SA 4.0
Answers.CreationDate: 2023-01-04T11:54:04.410Z
Answers.Text: @Coleman it's 5 years later, but I think this answer is still ok, right?
Answers.UserDisplayName: artfulrobot
Answers.ContentLicense: CC BY-SA 4.0
Answers.CreationDate: 2023-01-04T23:34:02.500Z
Answers.Text: @artfulrobot Yes there's also a `permissions()` function you can put in the api4 entity file, to control gatekeeper permissions. Otherwise the BAO generally handles permissions.
Answers.UserDisplayName: Coleman
Answers.ContentLicense: CC BY-SA 4.0
Answers.CreationDate: 2023-01-05T14:13:51.703Z
Answers.Text: @Coleman thanks for update. I guess the event method is useful primarily when wanting to alter core API permissions.
Answers.UserDisplayName: artfulrobot
Answers.ContentLicense: CC BY-SA 3.0
Answers.CreationDate: 2017-03-11T10:46:07.307Z
Answers.LastActivityDate: 2017-03-23T22:50:08.053Z
Answers.LastEditDate: 2017-03-23T22:50:08.053Z
Answers.UserDisplayName: ErichBSchulz
Body: <p>How do I control permissions for <a href="https://github.com/civicrm/api4" rel="nofollow noreferrer">API4</a> calls?</p>
  
Tags: <api><acl>
Title: How to control API4 permissions for CRUD operations?
ThreadText: # How to control API4 permissions for CRUD operations?
  
  (Asked by: username_0 on 2017-03-11)
  
  How do I control permissions for [API4](https://github.com/civicrm/api4) calls?
  
  **Tags:** api, acl
  
  
  ---
  
  ## 1 answers
  
  ### Answer by username_0 on 2017-03-11. Score: 5
  
  Events
  The API kernel broadcasts an authorise event.
  Core permission check listener
  The main API permission check subscriber will respond to the event by:
  $apiRequest = $event->getApiRequest();   
  if ($apiRequest['version'] < 4) { /* blah */ }
  elseif ($apiRequest['version'] == 4) {      
    if (!$apiRequest->getCheckPermissions()) {
      $event->authorize();                    
      $event->stopPropagation();              
    }                                         
  }                                           
  
  Adding your own listener
  If the core logic doesn't meet your needs, it is possible to get the symfony event dispatcher service and add either a listener (for single events) or a subscriber (for multiple events).
  For example, to add a subscriber:
  $subscriber = new MySubscriberClass();            
  \Civi::service('dispatcher')->addSubscriber($subscriber);
  
  When your listener/subscriber is called, then call the $event->getApiRequest() to find out the parameters you are being asked to authorise. If the event should be authorised then call $event->authorize().
  SQL clauses
  For actions based on get(),
  the selectQuery->getAclClause() method will call $baoName::getSelectWhereClause($tableAlias) to add a where clause.
  It doesn't seem possible currently to apply differing ACL logic depending on the action with this method.
  
  > **Comments:**
  > **username_1**: Excellent, thanks for documenting this. One caveat, the api4 is currently unstable and by the time it's released this information may be out-of-date.  
  > **username_2**: @username_1 it's 5 years later, but I think this answer is still ok, right?  
  > **username_1**: @username_2 Yes there's also a `permissions()` function you can put in the api4 entity file, to control gatekeeper permissions. Otherwise the BAO generally handles permissions.  
  > **username_2**: @username_1 thanks for update. I guess the event method is useful primarily when wanting to alter core API permissions.  
  
  ---
  
  