为什么ldap_errno()在此处提供连接?

问题描述 投票:0回答:1

我在lumen项目(Laravel 6.2)中有一个过程,其中通过LDAP识别用户。代码看起来像这样:

<?php

namespace App\Http\Helpers;

// Currently unused
// use App\User;
// use Firebase\JWT\JWT;
use Illuminate\Support\Facades\Log;

class LDAP
{
  private $connection, $password;
  protected $domain, $username, $ldap_address, $ldap_port;

  /**
   * Constructs the ldap connector with data used for the connection and
   * bind process.
   */
  function __construct()
  {
    $this->domain = env("LDAP_DOMAIN");
    $this->username = env("LDAP_USERNAME");
    $this->password = env("LDAP_PASSWORD");
    $this->ldap_address = env("LDAP_ADDRESS");
    $this->ldap_port = env("LDAP_PORT");
  }

  /**
   * Establishes a connection to the ldap server and saves it in
   * @var Resource $connection.
   *
   * @return true
   * On success
   * @return false
   * On failure
   */
  private function connect()
  {
    $this->connection = ldap_connect($this->ldap_address, $this->ldap_port);

    if($this->connection)
    {
      Log::info("Connection established");

      ldap_set_option($this->connection, LDAP_OPT_PROTOCOL_VERSION, 3);
      ldap_set_option($this->connection, LDAP_OPT_REFERRALS, 0);

      $bind = ldap_bind($this->connection, $this->domain . "\\" . $this->username, $this->password);

      if($bind)
      {
        Log::info("Bind valid");
        return true;
      }
      else
      {
        Log::info("Bind failed");
        return false;
      }
    }
    else
    {
      Log::info("Connection failed");
      return false;
    }
  }

  private function disconnect()
  {
    ldap_unbind($this->connection);
  }

  /**
   * Searches for a specific person in the LDAP-Directory and returns important
   * data from this person which will be used later in the application.
   *
   * @param String $person
   * The person to search for
   * @return Array $result
   * The persons data
   */
  public function getUser($username, $password)
  {
    try
    {
      $is_connected = $this->connect();

      if(!$is_connected)
      {
        $this->disconnect();
        return false;
      }

      $dn = "OU=Benutzer,OU=sdfsfd,DC=sfdsfsf,DC=de";

      $fields = "(|(samaccountname=*$username*))";

      $search = ldap_search($this->connection, $dn, $fields);
      $result = ldap_get_entries($this->connection, $search);

      if($result)
      {
        $bind = ldap_bind($this->connection, $this->domain . "\\" . $username, $password);
        if($bind && strlen($password) > 0)
        {
          return mb_convert_encoding($result, 'UTF-8');
        }
        else
        {
          return "Invalid credentials!";
        }
      }
      else
      {
        return "User does not exist!";
      }
    }
    catch(\Exception $e)
    {
      $errno = ldap_errno($this->connection);

      if ($errno) {
        $ret =  array("ldap_error" => $errno, "message" => ldap_err2str($errno));
      }else{
        $ret =  array("exception_code" => $e->getCode(), "message" => $e->getMessage());
      }

      return $ret;

    }
    finally
    {
      $this->disconnect();
    }
  }
}

[现在,在处理ldap_bind()中的错误时,我们遇到了一些问题。流明无法评估ldap函数抛出的错误代码,因此我们必须捕获它们并通过ldap_errno功能手动对其进行评估。

[让我感到困惑的是$this->connection被传递给ldap_errno()函数。为什么不是$bind?毕竟,它的绑定失败了,而不是连接。 AFAIK ldap_connect()甚至没有建立连接,而是验证凭据是否合理。

但是,它起作用^^但是为什么呢? ldap_errno发生了什么,将连接传递给它,而不是绑定?

php ldap lumen
1个回答
1
投票

因为ldap_connect返回了标识“连接”的内部句柄。然后,ldap_errnoldap_error返回有关该“连接”上最后一个错误的信息。

因此,当您在ldap_bind之后调用它们(根据结果返回truefalse时,您需要发生此连接,而不是绑定的结果。

请注意,“连接”并不一定意味着已经建立与服务器的连接。

© www.soinside.com 2019 - 2024. All rights reserved.