When I add a user to a group, I get an error message from CiviNode:

Warning: Invalid argument supplied for foreach() in /Library/WebServer/Documents/civicrm/modules/civinode/civinode_utils.inc on line 894

I'm not quite sure what this code is looking for:

function civinode_add_node_memberships($gid, $contact_list){
  //Are any nodes associated with this group?
	$lookup = civinode_get_node_memberships($gid);
	//Loop over the contact IDs and if they have associated
	//nodes, add them to this group's list.
	$sql = "INSERT INTO {civinode_node_memberships} (nid, contact_id, group_id) VALUES (%d,%d,%d)";
	foreach ($contact_list as $cid) {
		if ( !isset($lookup[$cid]) ) {
		  //See if a node exists
		  $node = civinode_util_node_factory($cid, FALSE);
		  if (isset($node->nid))
			  db_query($sql, $node->nid, $cid, $gid);
		}
	}
}

Comments

Torenware’s picture

Component: Code » Documentation
Assigned: Unassigned » Torenware

Mark,

The bug here really is one of documentation, since this API isn't used to add contacts to CRM groups; it's used to update a table used by the access system. So it's really part of the private API. I haven't marked it, so there isn't much way you'd be able to tell.

Clearly, though, there needs to be a call to this, since doing this directly in the CRM API is a big messy.

What you really want to do right now is this:

$group = civinode_get_group_by_id($gid);
$contact = crm_get_contact(array('contact_id' => $contact_id));
$contacts = array($contact);
//'API' could be whatever you want, including the name of your module
crm_add_group_contacts($group, $contacts, 'Added', 'API');

I haven't had the need yet to add this functionality to the library, but plenty of modules do exactly what you want here.

I'll start factoring some of the more obscure code, like civinode_add_node_memberships(), into .inc files, and will do a better job of labelling them as private APIs when I do.

Torenware’s picture

I'm adding an API to do this to the library:

/**
 * Wrapper to add a contact to a group.
 *
 */
function civinode_add_contact_to_group($group_id, $contact_id, $source = 'civinode'){
  if (civinode_util_cid_in_group($contact_id, $group_id))
    return TRUE; //nothing to do.
  $group = civinode_get_group_by_id($group_id);
  if (!$group or civinode_check_error($group))
    return FALSE;
  $contact = crm_get_contact(array('contact_id' => $contact_id));
  if (!$contact or civinode_check_error($contact))
    return FALSE;
  $contacts = array($contact);
  //'API' could be whatever you want, including the name of your module
  crm_add_group_contacts($group, $contacts, 'Added', 'API');
  return TRUE;
}


I want to test this before I commit it, but this should be fairly bullet proof, I think.

mfredrickson’s picture

I get a sql error now (which might not be your fault):

Warning: Unknown table 'na' in field list query: SELECT na.nid, na.gid as access_id FROM node_access WHERE na.realm = 'civinode' AND na.gid IN (2) in /Library/WebServer/Documents/civicontact/includes/database.mysql.inc on line 120
mfredrickson’s picture

Also, a point of clarification, when I say "add a contact to a group" I mean using the point-n-click CiviCRM method (click on contact, select group, click add button). I'm not doing this through an API.