Skip to content

Commit

Permalink
Fix flow for groups & tags
Browse files Browse the repository at this point in the history
The new way is
- create the tags & groups at the form layer & only the ids
go to the parser - which adds them

This patch should be a nullop in terms of the efficiency of these
  • Loading branch information
eileenmcnaughton committed Jun 3, 2022
1 parent 4d9f4d6 commit 578e4db
Show file tree
Hide file tree
Showing 7 changed files with 187 additions and 238 deletions.
135 changes: 82 additions & 53 deletions CRM/Contact/Import/Form/Preview.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@
* @copyright CiviCRM LLC https://civicrm.org/licensing
*/

use Civi\Api4\Group;
use Civi\Api4\Tag;

/**
* This class previews the uploaded file and returns summary statistics.
*/
Expand All @@ -36,15 +39,6 @@ class CRM_Contact_Import_Form_Preview extends CRM_Import_Form_Preview {
public function preProcess() {
parent::preProcess();
$this->_disableUSPS = $this->getSubmittedValue('disableUSPS');

$groups = CRM_Core_PseudoConstant::nestedGroup();
$this->set('groups', $groups);

$tag = CRM_Core_PseudoConstant::get('CRM_Core_DAO_EntityTag', 'tag_id', array('onlyActive' => FALSE));
if ($tag) {
$this->set('tag', $tag);
}

$this->setStatusUrl();
}

Expand All @@ -63,24 +57,25 @@ public function buildQuickForm() {
);
}

$groups = $this->get('groups');
$groups = CRM_Core_PseudoConstant::nestedGroup();;

if (!empty($groups)) {
$this->addElement('select', 'groups', ts('Add imported records to existing group(s)'), $groups, array(
$this->addElement('select', 'groups', ts('Add imported records to existing group(s)'), $groups, [
'multiple' => "multiple",
'class' => 'crm-select2',
));
]);
}

//display new tag
$this->addElement('text', 'newTagName', ts('Tag'), CRM_Core_DAO::getAttribute('CRM_Core_DAO_Tag', 'name'));
$this->addElement('text', 'newTagDesc', ts('Description'), CRM_Core_DAO::getAttribute('CRM_Core_DAO_Tag', 'description'));

$tag = $this->get('tag');
$tag = CRM_Core_PseudoConstant::get('CRM_Core_DAO_EntityTag', 'tag_id', ['onlyActive' => FALSE]);
if (!empty($tag)) {
foreach ($tag as $tagID => $tagName) {
$this->addElement('checkbox', "tag[$tagID]", NULL, $tagName);
}
$this->addElement('select', 'tag', ts(' Tag imported records'), $tag, [
'multiple' => 'multiple',
'class' => 'crm-select2',
]);
}

$this->addFormRule(array('CRM_Contact_Import_Form_Preview', 'formRule'), $this);
Expand Down Expand Up @@ -142,37 +137,71 @@ public static function formRule($fields, $files, $self) {
/**
* Process the mapped fields and map it into the uploaded file.
*
* @throws \API_Exception
* @throws \API_Exception|\CRM_Core_Exception
*/
public function postProcess() {

$importJobParams = array(
'doGeocodeAddress' => $this->getSubmittedValue('doGeocodeAddress'),
'invalidRowCount' => $this->getRowCount(CRM_Import_Parser::ERROR),
'onDuplicate' => $this->getSubmittedValue('onDuplicate'),
'dedupe' => $this->getSubmittedValue('dedupe_rule_id'),
'newGroupName' => $this->controller->exportValue($this->_name, 'newGroupName'),
'newGroupDesc' => $this->controller->exportValue($this->_name, 'newGroupDesc'),
'newGroupType' => $this->controller->exportValue($this->_name, 'newGroupType'),
'groups' => $this->controller->exportValue($this->_name, 'groups'),
'allGroups' => $this->get('groups'),
'newTagName' => $this->controller->exportValue($this->_name, 'newTagName'),
'newTagDesc' => $this->controller->exportValue($this->_name, 'newTagDesc'),
'tag' => $this->controller->exportValue($this->_name, 'tag'),
'allTags' => $this->get('tag'),
'mapper' => $this->controller->exportValue('MapField', 'mapper'),
'mapFields' => $this->getAvailableFields(),
'contactType' => $this->getContactType(),
'contactSubType' => $this->getSubmittedValue('contactSubType'),
'primaryKeyName' => '_id',
'statusFieldName' => '_status',
'statusID' => $this->get('statusID'),
'totalRowCount' => $this->getRowCount([]),
'userJobID' => $this->getUserJobID(),
);
public function postProcess(): void {
$groupsToAddTo = (array) $this->getSubmittedValue('groups');
$summaryInfo = ['groups' => [], 'tags' => []];
foreach ($groupsToAddTo as $groupID) {
// This is a convenience for now - really url & name should be determined at
// presentation stage - ie the summary screen. The only info we are really
// preserving is which groups were created vs already existed.
$summaryInfo['groups'][$groupID] = [
'url' => CRM_Utils_System::url('civicrm/group/search', 'reset=1&force=1&context=smog&gid=' . $groupID),
'name' => Group::get(FALSE)->addWhere('id', '=', $groupID)->addSelect('name')->execute()->first()['name'],
'new' => FALSE,
'added' => 0,
'notAdded' => 0,
];
}

$importJob = new CRM_Contact_Import_ImportJob();
$importJob->setJobParams($importJobParams);
if ($this->getSubmittedValue('newGroupName')) {
/* Create a new group */
$groupsToAddTo[] = $groupID = Group::create(FALSE)->setValues([
'title' => $this->getSubmittedValue('newGroupName'),
'description' => $this->getSubmittedValue('newGroupDesc'),
'group_type' => $this->getSubmittedValue('newGroupType') ?? [],
'is_active' => TRUE,
])->execute()->first()['id'];
$summaryInfo['groups'][$groupID] = [
'url' => CRM_Utils_System::url('civicrm/group/search', 'reset=1&force=1&context=smog&gid=' . $groupID),
'name' => $this->getSubmittedValue('newGroupName'),
'new' => TRUE,
'added' => 0,
'notAdded' => 0,
];
}
$tagsToAdd = (array) $this->getSubmittedValue('tag');
foreach ($tagsToAdd as $tagID) {
// This is a convenience for now - really url & name should be determined at
// presentation stage - ie the summary screen. The only info we are really
// preserving is which tags were created vs already existed.
$summaryInfo['tags'][$tagID] = [
'url' => CRM_Utils_System::url('civicrm/contact/search', 'reset=1&force=1&context=smog&id=' . $tagID),
'name' => Tag::get(FALSE)->addWhere('id', '=', $tagID)->addSelect('name')->execute()->first()['name'],
'new' => TRUE,
'added' => 0,
'notAdded' => 0,
];
}
if ($this->getSubmittedValue('newTagName')) {
$tagsToAdd[] = $tagID = Tag::create(FALSE)->setValues([
'name' => $this->getSubmittedValue('newTagName'),
'description' => $this->getSubmittedValue('newTagDesc'),
'is_selectable' => TRUE,
'used_for' => 'civicrm_contact',
])->execute()->first()['id'];
$summaryInfo['tags'][$tagID] = [
'url' => CRM_Utils_System::url('civicrm/contact/search', 'reset=1&force=1&context=smog&id=' . $tagID),
'name' => $this->getSubmittedValue('newTagName'),
'new' => FALSE,
'added' => 0,
'notAdded' => 0,
];
}
// Store the actions to take on each row & the data to present at the end to the userJob.
$this->updateUserJobMetadata('post_actions', ['group' => $groupsToAddTo, 'tag' => $tagsToAdd]);
$this->updateUserJobMetadata('summary_info', $summaryInfo);

// If ACL applies to the current user, update cache before running the import.
if (!CRM_Core_Permission::check('view all contacts')) {
Expand All @@ -184,16 +213,20 @@ public function postProcess() {
CRM_Utils_Address_USPS::disable($this->_disableUSPS);

// run the import
$importJob->runImport($this);

$this->_parser = $this->getParser();
$this->_parser->run(
[],
CRM_Import_Parser::MODE_IMPORT,
$this->get('statusID')
);

// Clear all caches, forcing any searches to recheck the ACLs or group membership as the import
// may have changed it.
CRM_Contact_BAO_Contact_Utils::clearContactCaches(TRUE);

// add all the necessary variables to the form
$importJob->setFormVariables($this);

// check if there is any error occurred
// @todo - it's really unclear that this error code should still exist...
$errorStack = CRM_Core_Error::singleton();
$errors = $errorStack->getErrors();
$errorMessage = [];
Expand All @@ -214,10 +247,6 @@ public function postProcess() {

$this->set('errorFile', $errorFile);
}

//hack to clean db
//if job complete drop table.
$importJob->isComplete();
}

/**
Expand Down
7 changes: 4 additions & 3 deletions CRM/Contact/Import/Form/Summary.php
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,8 @@ class CRM_Contact_Import_Form_Summary extends CRM_Import_Form_Summary {
* @throws \CRM_Core_Exception
*/
public function preProcess() {
// set the error message path to display
// @todo - totally unclear that this errorFile could ever be set / render.
// Probably it can go.
$this->assign('errorFile', $this->get('errorFile'));
$onDuplicate = $this->getSubmittedValue('onDuplicate');
$this->assign('dupeError', FALSE);
Expand All @@ -44,8 +45,8 @@ public function preProcess() {
$this->assign('dupeError', TRUE);
}

$this->assign('groupAdditions', $this->get('groupAdditions'));
$this->assign('tagAdditions', $this->get('tagAdditions'));
$this->assign('groupAdditions', $this->getUserJob()['metadata']['summary_info']['groups']);
$this->assign('tagAdditions', $this->getUserJob()['metadata']['summary_info']['tags']);
$this->assign('totalRowCount', $this->getRowCount());
$this->assign('validRowCount', $this->getRowCount(CRM_Import_Parser::VALID) + $this->getRowCount(CRM_Import_Parser::UNPARSED_ADDRESS_WARNING));
$this->assign('invalidRowCount', $this->getRowCount(CRM_Import_Parser::ERROR));
Expand Down
156 changes: 0 additions & 156 deletions CRM/Contact/Import/ImportJob.php
Original file line number Diff line number Diff line change
Expand Up @@ -23,14 +23,10 @@ class CRM_Contact_Import_ImportJob {
protected $_onDuplicate;
protected $_dedupe;
protected $_newGroupName;
protected $_newGroupDesc;
protected $_newGroupType;
protected $_groups;
protected $_allGroups;
protected $_newTagName;
protected $_newTagDesc;
protected $_tag;
protected $_allTags;

protected $_mapper;
protected $_mapperKeys = [];
Expand Down Expand Up @@ -72,44 +68,6 @@ public function runImport(&$form, $timeout = 55) {
$this->_mapperKeys[$key] = $mapper[$key][0] ?? NULL;
}

$this->_parser = new CRM_Contact_Import_Parser_Contact(
$this->_mapperKeys
);
$this->_parser->setUserJobID($this->_userJobID);
$this->_parser->run(
[],
CRM_Import_Parser::MODE_IMPORT,
$this->_statusID
);

$contactIds = $this->_parser->getImportedContacts();

//get the related contactIds. CRM-2926
$relatedContactIds = $this->_parser->getRelatedImportedContacts();
if ($relatedContactIds) {
$contactIds = array_merge($contactIds, $relatedContactIds);
}

if ($this->_newGroupName || count($this->_groups)) {
$groupAdditions = $this->_addImportedContactsToNewGroup($contactIds,
$this->_newGroupName,
$this->_newGroupDesc,
$this->_newGroupType
);
if ($form) {
$form->set('groupAdditions', $groupAdditions);
}
}

if ($this->_newTagName || !empty($this->_tag)) {
$tagAdditions = $this->_tagImportedContactsWithNewTag($contactIds,
$this->_newTagName,
$this->_newTagDesc
);
if ($form) {
$form->set('tagAdditions', $tagAdditions);
}
}
}

/**
Expand All @@ -119,118 +77,4 @@ public function setFormVariables($form) {
$this->_parser->set($form, CRM_Import_Parser::MODE_IMPORT);
}

/**
* Add imported contacts.
*
* @param array $contactIds
* @param string $newGroupName
* @param string $newGroupDesc
* @param string $newGroupType
*
* @return array|bool
*/
private function _addImportedContactsToNewGroup(
$contactIds,
$newGroupName, $newGroupDesc, $newGroupType
) {

$newGroupId = NULL;

if ($newGroupName) {
/* Create a new group */
$newGroupType = $newGroupType ?? [];
$gParams = array(
'title' => $newGroupName,
'description' => $newGroupDesc,
'group_type' => $newGroupType,
'is_active' => TRUE,
);
$group = CRM_Contact_BAO_Group::create($gParams);
$this->_groups[] = $newGroupId = $group->id;
}

if (is_array($this->_groups)) {
$groupAdditions = [];
foreach ($this->_groups as $groupId) {
$addCount = CRM_Contact_BAO_GroupContact::addContactsToGroup($contactIds, $groupId);
$totalCount = $addCount[1];
if ($groupId == $newGroupId) {
$name = $newGroupName;
$new = TRUE;
}
else {
$name = $this->_allGroups[$groupId];
$new = FALSE;
}
$groupAdditions[] = array(
'url' => CRM_Utils_System::url('civicrm/group/search',
'reset=1&force=1&context=smog&gid=' . $groupId
),
'name' => $name,
'added' => $totalCount,
'notAdded' => $addCount[2],
'new' => $new,
);
}
return $groupAdditions;
}
return FALSE;
}

/**
* @param $contactIds
* @param string $newTagName
* @param $newTagDesc
*
* @return array|bool
* @throws \CRM_Core_Exception
*/
private function _tagImportedContactsWithNewTag(
$contactIds,
$newTagName, $newTagDesc
) {

$newTagId = NULL;
if ($newTagName) {
/* Create a new Tag */

$tagParams = array(
'name' => $newTagName,
'description' => $newTagDesc,
'is_selectable' => TRUE,
'used_for' => 'civicrm_contact',
);
$addedTag = CRM_Core_BAO_Tag::add($tagParams);
$this->_tag[$addedTag->id] = 1;
}
//add Tag to Import

if (is_array($this->_tag)) {
$tagAdditions = [];
foreach ($this->_tag as $tagId => $val) {
$addTagCount = CRM_Core_BAO_EntityTag::addEntitiesToTag($contactIds, $tagId, 'civicrm_contact', FALSE);
$totalTagCount = $addTagCount[1];
if (isset($addedTag) && $tagId == $addedTag->id) {
$tagName = $newTagName;
$new = TRUE;
}
else {
$tagName = $this->_allTags[$tagId];
$new = FALSE;
}
$tagAdditions[] = array(
'url' => CRM_Utils_System::url('civicrm/contact/search',
'reset=1&force=1&context=smog&id=' . $tagId
),
'name' => $tagName,
'added' => $totalTagCount,
'notAdded' => $addTagCount[2],
'new' => $new,
);
}
return $tagAdditions;
}
return FALSE;
}

}
Loading

0 comments on commit 578e4db

Please sign in to comment.