【问题标题】:Connect/Bind to Active Directory (Windows) using LDAP in Symfony 3 without using a dn string在 Symfony 3 中使用 LDAP 连接/绑定到 Active Directory (Windows),而不使用 dn 字符串
【发布时间】:2017-09-08 21:25:55
【问题描述】:

我正在尝试使用 Active Directory 对我公司的 Symfony3 应用程序用户进行身份验证。我当前的配置如下(这也通过在线 LDAP 测试服务器成功测试,因此我可以确认 Symfony 配置是正确的)。

//services.yml

Symfony\Component\Ldap\Ldap:
        arguments: ['@Symfony\Component\Ldap\Adapter\ExtLdap\Adapter']
    Symfony\Component\Ldap\Adapter\ExtLdap\Adapter:
        arguments:
            -   host: host.dom1.dom2.net
                port: 389
                encryption: none
                options:
                    protocol_version: 3
                    referrals: false
//security.yml

my_ldap:
      ldap:
         service: Symfony\Component\Ldap\Ldap
         base_dn: dc=dom1,dc=dom2,dc=net
         search_dn: "cn=myUsername,dc=dom1,dc=dom2,dc=net"
         search_password: myPassword
         default_roles: ROLE_ADMIN
         uid_key: sAMAccountName

....
firewalls:
      form_login_ldap:
         provider: my_ldap
         service: Symfony\Component\Ldap\Ldap
         dn_string: 'sAMAccountName={username},dc=dom1,dc=dom2,dc=net'
         login_path: login
         check_path: login
         default_target_path: /index

当我尝试登录时,我会因为“凭据无效”而被拒绝,但我确信我的凭据输入正确。我希望这里的主要问题是“search_dn”和“search_password”是我自己的,我在我们的 AD 中没有管理员权限。看来(根据 Symfony 文档)这些凭据需要是 AD 管理员用户的凭据。我正在等待来自我的系统管理员的此信息,但它必须上链,因此可能需要一段时间。我也尝试用 null 替换它们,这会引发不同的错误。

我的问题出现在这一点上,因为我实际上能够通过以下代码单独使用 PHP 建立成功的连接并与我们的 AD 绑定:

//ldapconnect.php

$ldap = ldap_connect("host.dom1.dom2.net");

if (ldap_bind($ldap, "myUsername@dom1.dom2.net", "myPassword")) {
    echo "login successful";
 } else {
    echo "Incorrect Login";
}

基本上,我正在寻找是否可以以某种方式将上述独立的 PHP ldap 绑定代码复制到我的 Symfony 项目中(似乎 Symfony 中所需的 dn 字符串导致了问题)。我对此很陌生,所以我不太明白为什么独立的 PHP 代码允许 LDAP 绑定,而使用 dn 字符串却不允许(除了我们的 AD 可能在使用 dn 字符串时阻止请求)。

提前感谢您的帮助。

编辑:已更新为只读管理员搜索 dn 信息:

//security.yml

my_ldap:
      ldap:
         service: Symfony\Component\Ldap\Ldap
         base_dn: 'CN=Users,dc=dom1,dc=dom2,dc=net'
         search_dn: "cn=ReadOnlyAdmin,OU=ou1,OU=ou2,dc=dom1,dc=dom2,dc=net"
         search_password: adminPass
         default_roles: ROLE_USER
         uid_key: sAMAccountName
....
firewalls:
      http_basic_ldap:
         provider: my_ldap
         service: Symfony\Component\Ldap\Ldap
         dn_string: 'DOMAIN\{username}'

看来我现在至少能够绑定到 ldap 服务器,但是我仍然收到无效凭据并出现“未找到用户”错误:

//dev.log

[2017-09-11 13:10:15] request.INFO: Matched route "app_default_admin". {"route":"app_default_admin","route_parameters":{"_controller":"AppBundle\\Controller\\DefaultController::adminAction","_route":"app_default_admin"},"request_uri":"http://localhost:8000/index","method":"GET"} []
[2017-09-11 13:10:15] security.INFO: Basic authentication Authorization header found for user. {"username":"myUsername"} []
[2017-09-11 13:10:15] security.INFO: Basic authentication failed for user. {"username":"myUsername","exception":"[object] (Symfony\\Component\\Security\\Core\\Exception\\BadCredentialsException(code: 0): Bad credentials. at C:\\pathtoSymfonyProject\\vendor\\symfony\\symfony\\src\\Symfony\\Component\\Security\\Core\\Authentication\\Provider\\UserAuthenticationProvider.php:73, Symfony\\Component\\Security\\Core\\Exception\\UsernameNotFoundException(code: 0): User \"myUsername\" not found. at C:\\pathtoSymfonyProject\\vendor\\symfony\\symfony\\src\\Symfony\\Component\\Security\\Core\\User\\LdapUserProvider.php:82)"} []

我还在对第三行末尾的“用户\“我的用户名\”未找到”错误提出质疑,它是在广告中搜索用户名“我的用户名\”并添加反斜杠吗?这可能只是错误代码的格式,因为它在第二行和第三行开头看起来是正确的。

编辑 2

我终于连接成功了,正确的配置如下:

//security.yml

my_ldap:
      ldap:
         service: Symfony\Component\Ldap\Ldap
         base_dn: 'dc=dom1,dc=dom2,dc=net'
         search_dn: "cn=ReadOnlyAdmin,OU=ou1,OU=ou2,dc=dom1,dc=dom2,dc=net"
         search_password: 'adminPass'
         default_roles: ROLE_USER
         uid_key: sAMAccountName
....
firewalls:
      http_basic_ldap:
         provider: my_ldap
         service: Symfony\Component\Ldap\Ldap
         dn_string: 'MYDOMAIN\{username}'

从我之前的编辑中,我所要做的就是从 base_dn 中删除“CN=Users”,因为用户帐户实际上并不位于那里,删除它并只留下域组件就可以搜索我们的整个 AD用户。另一个重要的注意事项是 dn_string 必须配置为 'MYDOMAIN\{username}' 或身份验证将不会通过(根据 Alvin Bunk 的回复)。正如 Alvin 在下面链接的文章中指出的那样,很遗憾,Symfony LDAP 文档中没有提到该部分。

【问题讨论】:

    标签: php symfony active-directory ldap symfony3.x


    【解决方案1】:

    看看我最近的文章:

    https://alvinbunk.wordpress.com/2017/09/07/symfony-ldap-component-ad-authentication/

    我怀疑您只需要像这样更改您的dn_string

    dn_string: 'DOMAIN\{username}'
    

    请阅读我的文章。也可以试试:

    default_roles: ROLE_USER
    

    您也可以按照我的文章尝试使用http_basic_ldap 并查看开发日志。这可能很简单——不要放弃!

    【讨论】:

    • 您好,Alvin,感谢您的快速回复。我已经更新了我的配置以反映您的建议以及您文章中发布的内容。从那以后,我还收到了我们 AD 的只读管理员帐户。我更新了我的帖子以显示新配置以及错误日志消息。看来我现在可以绑定到 ldap 服务器了,但是我仍然收到“错误凭据”/“未找到用户”错误(编辑中也显示错误日志)。
    • “DOMAIN”是正确的 Windows 域吗?我对此表示怀疑?我举了一个例子......错误消息只显示了myUsername周围的引号,这是正确的。您是否使用 LDAP 浏览器在 baseDN CN=Users,dc=dom1,dc=dom2,dc=net 下搜索了 myUsername。用户myUsername 也需要存在于那里。我想你几乎已经成功了!
    • 您也可以尝试Active Directory Explorer 并尝试使用您的只读管理员帐户,然后展开CN=Configuration,DC=dom1,DC=dom2,DC=net 并在其下展开CN=Partitions。您应该有一个 Windows 域可以在该域下使用。它将有一个nETBIOSName 值。
    • 抱歉,我应该澄清一下我在上次编辑时使用的是正确的公司域,而不是字面意义上的“域”。我已经得到了连接工作!正如你所指出的,我对 base_dn 有一个小错误,只需要删除“CN=Users”,因为用户实际上并不位于那里,然后它就可以搜索整个 AD。我会接受您的第一个回复作为答案,因为如果不将 dn_string 设置为“DOMAIN\{username}”,则连接绝对无法正常工作。再次感谢 Alvin,你就是那个人。
    • 嗨@TomShelby 我一直在尝试在 Symfony 下设置 LDAP 身份验证系统。我试图准确地遵循您已经做过的事情以及对您有用的事情。但我仍然遇到连接问题。你能在下面看到我的代码吗?
    猜你喜欢
    • 1970-01-01
    • 2019-04-11
    • 1970-01-01
    • 2019-08-21
    • 1970-01-01
    • 2014-01-06
    • 2013-01-26
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多