? multivalue.patch
Index: ldapdata.module
===================================================================
RCS file: /cvs/drupal-contrib/contributions/modules/ldap_integration/ldapdata.module,v
retrieving revision 1.30
diff -u -p -r1.30 ldapdata.module
--- ldapdata.module	25 Aug 2009 14:17:59 -0000	1.30
+++ ldapdata.module	10 Sep 2009 22:25:42 -0000
@@ -218,9 +218,15 @@ function _ldapdata_user_load(&$account, 
     $drupal_fields = array();
     foreach (_ldapdata_reverse_mappings($account->ldap_config) as $drupal_field => $ldap_attr) {
       $value = isset($entry[strtolower($ldap_attr)]) ? $entry[strtolower($ldap_attr)][0] : '';
-
+      if ($entry[strtolower($ldap_attr)]['count'] > 1) {
+        array_shift($entry[strtolower($ldap_attr)]);
+        $value = $entry[strtolower($ldap_attr)];
+      }
+      
       // Is it a profile field?
       if (is_numeric($drupal_field)) {
+        if(is_array($value))
+          $value = implode(', ', $value);
         if ($profile_field = isset($profile_fields[$drupal_field]) ? $profile_fields[$drupal_field] : NULL) {
           if ($row = db_fetch_array(db_query("SELECT value FROM {profile_values} WHERE fid = '%d' AND uid = '%d'", $drupal_field, $account->uid))) {
             if ($row['value'] != $value)
@@ -296,6 +302,11 @@ function _ldapdata_user_submit(&$edit, &
     }
     if (!($_ldapdata_ldap->writeAttributes($user->ldap_dn, $writeout))) {
       drupal_set_message(t('The data was not written to LDAP.'), 'error');
+    } else {
+      foreach ($edit as $field => $val) {
+        if (is_array($val))
+          $edit[$field] = implode(', ', $val);
+      }
     }
   }
   $_ldapdata_ldap->disconnect();
@@ -424,15 +435,44 @@ function _ldapdata_user_update_profile(&
   if (_ldapdata_ldap_info($user, 'mapping_type') != LDAPDATA_MAP_ATTRIBUTES)
     return array();
 
+  global $_ldapdata_ldap;
+
   $ldap_drupal_reverse_mappings = _ldapdata_reverse_mappings($user->ldap_config);
 
   // Retrieve profile fields list.
   $profile_fields = _ldapdata_retrieve_profile_fields();
 
+  // Determine which profile fields are multi-valued
+  $placeholders = implode(',', array_fill(0, count($profile_fields), "'%s'"));
+  $result = db_query("SELECT name, options from {profile_fields} WHERE name IN ($placeholders) AND type = 'selection' AND  options != ''", $profile_fields);
+  $managed_fields = array();
+  while ($row = db_fetch_object($result)) {
+    $cleaned = array_map(
+      create_function('$f', 'return trim($f);'),
+      preg_split('/\n/',$row->options)
+    );
+    $managed_fields[$row->name] = $cleaned;
+  }
+  
   // Compare against $edit list.
   $writeout = array();
+
   foreach ($profile_fields as $key => $field) {
-    if (isset($edit[$field]) && isset($ldap_drupal_reverse_mappings[$key])) {
+    // Get user's current lists, so we don't clobber items we shouldn't touch
+    // We will only manage those items that aren't in the profile options
+    $unmanaged_fields[$field] = explode(', ', $user->{$field});
+    for ($i=0; $i < sizeof($managed_fields[$field]); $i++) {
+      if (in_array($managed_fields[$field][$i], $unmanaged_fields[$field])) {
+        $unmanaged_fields[$field] = array_diff($unmanaged_fields[$field], array($managed_fields[$field][$i]));
+      }
+    }
+    if ($edit[$field] && !empty($edit[$field]) && isset($ldap_drupal_reverse_mappings[$key]) && $managed_fields[$field]) {
+      // Update multivalue fields that we're managing
+      $writeout[$ldap_drupal_reverse_mappings[$key]] = array_unique(array_merge(explode(', ', $edit[$field]), $unmanaged_fields[$field]));
+    } elseif (gettype($edit[$field]) == 'string' && isset($ldap_drupal_reverse_mappings[$key]) && $managed_fields[$field]) {
+      // All drupal profile fields have been removed - apply non-managed fields
+      $writeout[$ldap_drupal_reverse_mappings[$key]] = array_unique(array_values($unmanaged_fields[$field]));
+    } elseif (!empty($edit[$field]) && isset($ldap_drupal_reverse_mappings[$key])){
       $writeout[$ldap_drupal_reverse_mappings[$key]] = $edit[$field];
     }
   }
