From 3fe3418556aac1beaf79e5786532972c3fb6ed29 Mon Sep 17 00:00:00 2001 From: Coleman Watts Date: Sun, 25 Aug 2019 19:44:55 -0400 Subject: [PATCH] Add api for afform prefill --- .../core/CRM/Afform/Page/AfformBase.php | 2 +- ext/afform/core/Civi/Afform/Utils.php | 65 ++++++++++++++++ .../Api4/Action/Afform/AbstractProcessor.php | 57 ++++++++++++++ .../core/Civi/Api4/Action/Afform/Prefill.php | 75 +++++++++++++++++++ ext/afform/core/Civi/Api4/Afform.php | 16 ++++ ext/afform/core/ang/af/ModelList.js | 19 +++-- ext/afform/core/ang/af/ModelProp.js | 6 +- 7 files changed, 229 insertions(+), 11 deletions(-) create mode 100644 ext/afform/core/Civi/Afform/Utils.php create mode 100644 ext/afform/core/Civi/Api4/Action/Afform/AbstractProcessor.php create mode 100644 ext/afform/core/Civi/Api4/Action/Afform/Prefill.php diff --git a/ext/afform/core/CRM/Afform/Page/AfformBase.php b/ext/afform/core/CRM/Afform/Page/AfformBase.php index 91bec9509c..3d389528b6 100644 --- a/ext/afform/core/CRM/Afform/Page/AfformBase.php +++ b/ext/afform/core/CRM/Afform/Page/AfformBase.php @@ -18,7 +18,7 @@ class CRM_Afform_Page_AfformBase extends CRM_Core_Page { ]); $loader->load(); - $afform = civicrm_api4('Afform', 'get', ['where' => [['name', '=', $pageArgs['afform']]], 'select' => ['title']]); + $afform = civicrm_api4('Afform', 'get', ['checkPermissions' => FALSE, 'where' => [['name', '=', $pageArgs['afform']]], 'select' => ['title']]); if (!empty($afform[0]['title'])) { CRM_Utils_System::setTitle(strip_tags($afform[0]['title'])); diff --git a/ext/afform/core/Civi/Afform/Utils.php b/ext/afform/core/Civi/Afform/Utils.php new file mode 100644 index 0000000000..4a89307d21 --- /dev/null +++ b/ext/afform/core/Civi/Afform/Utils.php @@ -0,0 +1,65 @@ +_afform = (array) civicrm_api4('Afform', 'get', ['checkPermissions' => FALSE, 'where' => [['name', '=', $this->name]]], 0); + $this->_afformEntities = Utils::getEntities($this->_afform['layout']); + $this->validateArgs(); + $result->exchangeArray($this->processForm()); + } + + /** + * Strip out arguments that are not allowed on this form + */ + protected function validateArgs() { + $rawArgs = $this->args; + $this->args = []; + foreach ($rawArgs as $arg => $val) { + if (!empty($this->_afformEntities[$arg]['af-url-autofill'])) { + $this->args[$arg] = $val; + } + } + } + + /** + * @return array + */ + abstract protected function processForm(); + +} diff --git a/ext/afform/core/Civi/Api4/Action/Afform/Prefill.php b/ext/afform/core/Civi/Api4/Action/Afform/Prefill.php new file mode 100644 index 0000000000..64ff21822f --- /dev/null +++ b/ext/afform/core/Civi/Api4/Action/Afform/Prefill.php @@ -0,0 +1,75 @@ +_afformEntities as $entityName => $entity) { + // Load entities from args + if (!empty($this->args[$entityName])) { + $this->loadEntity($entity, $this->args[$entityName]); + } + // Load entities from autofill settings + elseif (!empty($entity['af-autofill'])) { + $this->autofillEntity($entity, $entity['af-autofill']); + } + } + $data = []; + foreach ($this->_data as $name => $values) { + $data[] = ['name' => $name, 'values' => $values]; + } + return $data; + } + + /** + * Fetch all fields needed to display a given entity on this form + * + * @param $entity + * @param $id + * @throws \API_Exception + */ + private function loadEntity($entity, $id) { + $checkPermissions = TRUE; + if ($entity['af-type'] == 'Contact' && !empty($this->args[$entity['af-name'] . '-cs'])) { + $checkSum = civicrm_api4('Contact', 'validateChecksum', [ + 'checksum' => $this->args[$entity['af-name'] . '-cs'], + 'contactId' => $id, + ]); + $checkPermissions = empty($checkSum[0]['valid']); + } + $result = civicrm_api4($entity['af-type'], 'get', [ + 'where' => [['id', '=', $id]], + 'select' => array_column($entity['fields'], 'field-name'), + 'checkPermissions' => $checkPermissions, + ]); + if ($result->first()) { + $this->_data[$entity['af-name']] = $result->first(); + } + } + + /** + * Fetch an entity based on its autofill settings + * + * @param $entity + * @param $mode + */ + private function autoFillEntity($entity, $mode) { + $id = NULL; + if ($entity['af-type'] == 'Contact') { + if ($mode == 'user') { + $id = \CRM_Core_Session::getLoggedInContactID(); + } + } + if ($id) { + $this->loadEntity($entity, $id); + } + } + +} diff --git a/ext/afform/core/Civi/Api4/Afform.php b/ext/afform/core/Civi/Api4/Afform.php index ecfffa0e80..75b2095d87 100644 --- a/ext/afform/core/Civi/Api4/Afform.php +++ b/ext/afform/core/Civi/Api4/Afform.php @@ -56,6 +56,20 @@ class Afform extends AbstractEntity { return new \Civi\Api4\Action\Afform\Update('Afform', __FUNCTION__, 'name'); } + /** + * @return \Civi\Api4\Action\Afform\Prefill + */ + public static function prefill() { + return new \Civi\Api4\Action\Afform\Prefill('Afform', __FUNCTION__); + } + + /** + * @return \Civi\Api4\Action\Afform\Submit + */ + public static function submit() { + return new \Civi\Api4\Action\Afform\Submit('Afform', __FUNCTION__); + } + public static function getFields() { return new BasicGetFieldsAction('Afform', __FUNCTION__, function() { return [ @@ -92,6 +106,8 @@ class Afform extends AbstractEntity { return [ "meta" => ["access CiviCRM"], "default" => ["administer CiviCRM"], + 'prefill' => [], + 'submit' => [], ]; } diff --git a/ext/afform/core/ang/af/ModelList.js b/ext/afform/core/ang/af/ModelList.js index 7e28e0e608..b4465a4515 100644 --- a/ext/afform/core/ang/af/ModelList.js +++ b/ext/afform/core/ang/af/ModelList.js @@ -30,6 +30,7 @@ this.getEntity = function getEntity(name) { return schema[name]; }; + // Returns field values for a given entity this.getData = function getData(name) { return data[name]; }; @@ -37,17 +38,19 @@ return schema[name]; }; this.loadData = function() { - var apiCalls = {}; + var toLoad = 0; _.each(schema, function(entity, entityName) { - if ($routeParams[entityName]) { - var id = $routeParams[entityName]; - apiCalls[entityName] = [entity.type, 'get', {select: entity.fields, where: [['id', '=', id]]}, 0]; + if ($routeParams[entityName] || entity.autofill) { + toLoad++; } }); - if (!_.isEmpty(apiCalls)) { - crmApi4(apiCalls).then(function(resp) { - data = resp; - }); + if (toLoad) { + crmApi4('Afform', 'prefill', {name: CRM.afform.open, args: $routeParams}) + .then(function(result) { + _.each(result, function(item) { + data[item.name] = item.values; + }); + }); } }; diff --git a/ext/afform/core/ang/af/ModelProp.js b/ext/afform/core/ang/af/ModelProp.js index 399c6a60bf..ce597661ed 100644 --- a/ext/afform/core/ang/af/ModelProp.js +++ b/ext/afform/core/ang/af/ModelProp.js @@ -8,7 +8,8 @@ scope: { afType: '@', afName: '@', - afLabel: '@' + afLabel: '@', + afAutofill: '@' }, link: function($scope, $el, $attr, afModelListCtrl) { var ts = $scope.ts = CRM.ts('afform'); @@ -17,7 +18,8 @@ type: $scope.afType, name: $scope.afName, label: $scope.afLabel, - fields: [], + autofill: $scope.afAutofill, + fields: [] }); // $scope.$watch('afModelProp', function(newValue){$scope.myOptions = newValue;}); } -- 2.25.1