CVS edit link for kassissieh

I have built a module that complements http://drupal.org/project/ldap_integration. Named LDAPsync, it automatically creates Drupal users based on live queries of the LDAP database(s) specified in LDAP Integration. This feature is important for many network administrators, who want their site to reflect current user membership on their network, even if users have not yet logged in. The module can sync users on cron or manually. It also can block Drupal users that are LDAP authentified but do not exist in LDAP.

The module depends on LDAP Integration for some settings and functions. The issue queue at http://drupal.org/node/396574 demonstrates the level of support for this module. A few other drupal.org users have tested and submitted patches to the module. See the #73 in this issue queue for the latest module code.

The maintainer of LDAP Integration, http://drupal.org/user/18741 (miglius), has requested that this module be its own separate project rather than add it to LDAP Integration.

Comments

kassissieh’s picture

StatusFileSize
new5.43 KB
kassissieh’s picture

Status: Postponed (maintainer needs more info) » Active

I think the status should be active (not postponed), as I have uploaded module code for review. Let me know if I'm mistaken! Thanks.

avpaderno’s picture

Status: Active » Needs review
Issue tags: +Module review
avpaderno’s picture

Status: Needs review » Needs work
  1. /**
     * Implementation of hook_install().
     */
    function ldapsync_install() {
      $ret = array();
    
      variable_set('ldapsync_time_interval', 999999);
      variable_set('ldapsync_last_sync_time', 0);
      variable_set('ldapsync_filter', '');
      variable_set('ldapsync_missing_users_action', '');
    
      return $ret;
    }
    

    There is no need to set Drupal variables to their default values; default values are passed to variable_get(), which will return the default values if the variable has not been set before.

  2.   require_once(drupal_get_path('module', 'ldapauth') .'/includes/LDAPInterface.inc');
    

    If you are going to include the file unconditionally, then you should merge the files.

  3.     $result = db_query("SELECT uid, name, data FROM {users} WHERE status=1");
        while ($row = db_fetch_array($result)) {
          if (!in_array($row['name'], array_keys($ldap_users))) {
            $data = unserialize($row['data']);
            if ($data['ldap_authentified']) {
              // block user if appropriate module setting is set
              if (variable_get('ldapsync_missing_users_action','warn') == 'block') {
                $result2 = db_query("UPDATE {users} SET status=0 WHERE uid=%d", $row['uid']);  // do we need to add another check to the WHERE clause just in case? User_load should provide us only one result, right?
                watchdog('ldapsync', 'Disabled LDAP-authentified user '. $row['name'] .' because the corresponding LDAP account does not exist or is disabled.');
              }
              $count_orphaned_users++;
    

    I am not sure the code is handling users in a secure way. I think that users who are blocked should also be logged out too.

  4.   $summary = 'Completed LDAP sync. New users: '. $count_new_users .'. LDAP-authentified users that do not have an enabled LDAP account: '. $count_orphaned_users .'.';
    

    The code should use placeholders, not concatenate strings that are translated.

  5.       watchdog('ldapsync', 'ldapsync basedn '.$base_dn.'.');
    

    The same is true here.

  6.     '#options' => array('warn'=>'warn', 'block'=>'block'),
    

    Strings used in the user interface should be translated.

  7.   $op = $form_state['clicked_button']['#value'];
      $values = $form_state['values'];
      switch ($op) {
        case t('Sync now'):
    

    Submission code should not depend on $op. It is possible to have a submission functions that is specific for a single button. That would eliminate the need to know the operation being executed.

kassissieh’s picture

Status: Needs work » Needs review
StatusFileSize
new5.31 KB

Thank you kiamlaluno for your review.

1. Done.
2. The file to include is part of ldapauth, not part of my module. As the maintainer of that module may make changes, I'd like to include that file rather than duplicate his code in this module. Okay?
3. I haven't found a Drupal 6 function to kill the session for a user other than the one logged in. So I'm not sure how to meet your request. The necessary function does exist in D7.
4. Done.
5. Done.
6. Done.
7. Done.

Please see new version attached.

avpaderno’s picture

To log out a user, you can look at what the function user_logout() does.

function user_logout() {
  global $user;

  watchdog('user', 'Session closed for %name.', array('%name' => $user->name));

  // Destroy the current session:
  session_destroy();
  // Only variables can be passed by reference workaround.
  $null = NULL;
  user_module_invoke('logout', $null, $user);

  // Load the anonymous user
  $user = drupal_anonymous_user();

  drupal_goto();
}
kassissieh’s picture

session_destroy() works for the currently logged in user, but I don't see how it would work for one or more other users. I could call user_module_invoke() for other actively logged in users, but do any core modules have a logout hook that destroys that user's session? I haven't found it so far.

Suuch’s picture

You could load each user you need to logout as $account and use user_module_invoke('logout', $null, $account) to log them out.

e.g.

avpaderno’s picture

Status: Needs review » Fixed
if (!$ldapresult) continue;

An IF-statement should always be written as

if (!$ldapresult) {
  continue;
}

I apologize on the delay on approving this application.

Status: Fixed » Closed (fixed)

Automatically closed -- issue fixed for 2 weeks with no activity.

kassissieh’s picture

Thank you for the approval. The task discussion thread recently regained momentum, so the approval is well-timed.