如何使用 xml 配置文件、JAVA、Spring 安全性对 LDAP 用户进行身份验证

Posted

技术标签:

【中文标题】如何使用 xml 配置文件、JAVA、Spring 安全性对 LDAP 用户进行身份验证【英文标题】:How to authenticate user with LDAP using xml config file ,JAVA, Spring security 【发布时间】:2017-01-08 15:28:26 【问题描述】:

我的程序“使用 LDAP 验证用户”(在附录中列出)在使用 JNDI 时运行良好。

根据要求,我必须使用 xml 格式的 spring-security 和配置文件(包含 ldap 信息)(不允许使用 idlf 文件)。

我正在寻找 JAVA 中的代码 sn-p(我使用的是 1.8 和 spring),它将使用此 Ldap.xml 文件来提取所有相关信息,以便 java 对用户进行身份验证。需要使用spring-security。

我可以得到任何帮助吗?

LDAP.xml 看起来像:

    <?xml version='1.0'?>


      <!-- The  Security Module.  This module will authenticate against AD
           and determine authorization against the SECURITY_OWNER schema
      -->

      <application-policy name="something-targeting">
        <authentication>
           <login-module code="com.et.security.ETLoginModule" flag="required" >        
              <module-option name="java.naming.provider.url">ldap://pcocpwdom01.corp.something.com:389</module-option>
              <module-option name="bindDN">CN=SVCLdapQry,OU=ServiceAccounts_Admins,OU=Data Services,DC=corp,DC=something,DC=com</module-option>
              <module-option name="bindCredential">+byZB0ocHUQL0MDhd2mN3dSjskf2S7ff2hiCcCDThSE=</module-option>
              <module-option name="baseCtxDN">DC=corp,DC=something,DC=com</module-option>
              <module-option name="baseFilter">(samaccountname=0)</module-option>
              <module-option name="allowEmptyPasswords">false</module-option>

           </login-module>
        </authentication>
      </application-policy>

寻找类似的东西:

@Autowired
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception 
    auth
        .ldapAuthentication()
            .userDnPatterns("uid=0,ou=people")
            .groupSearchBase("ou=groups")
            .contextSource().ldif("classpath:LDAP.xml");

感谢任何帮助。如果需要更多信息,请告诉我。

我尝试了以下示例:

http://krams915.blogspot.com/2011/01/spring-security-mvc-using-ldap.html

https://spring.io/guides/gs/authenticating-ldap/

它们中的任何一个都无法工作。

附录 A:

    package com.something.online.ice.ui.authentication;

    import java.util.Hashtable;
    import java.util.Properties;

    import javax.annotation.Resource;
    import javax.naming.Context;
    import javax.naming.NamingEnumeration;
    import javax.naming.NamingException;
    import javax.naming.directory.Attributes;
    import javax.naming.directory.DirContext;
    import javax.naming.directory.InitialDirContext;
    import javax.naming.directory.SearchControls;
    import javax.naming.directory.SearchResult;
    import javax.naming.ldap.InitialLdapContext;
    import javax.naming.ldap.LdapContext;


    /**
     * 

     * This is a solution that can be used to authenticate a user with something else than the DN, for example with a uid or sAMAccountName.

        The steps to do are:

        -Connect to the LDAP server
        -Authenticate with a service user of whom we know the DN and credentials
        -Search for the user you want to authenticate, search him with some attribute (for example sAMAccountName)
        -Get the DN of the user we found
        -Open another connection to the LDAP server with the found DN and the password
        -If the user is found and authentication works, you are fine

     *
     */

    public class LdapAuthManagerJNDI 
    
        public static void main(String[] args)
        
            LdapAuthManagerJNDI mgr = new LdapAuthManagerJNDI();
            System.out.println(mgr.authenticateUsr("svc_oapusr", "pswd"));

        

        public boolean authenticateUsr(String usrName, String pswd)
        


            Hashtable<String, String> serviceEnv = new Hashtable<String, String>();
            boolean authenticationresullt = false;


            serviceEnv.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
            serviceEnv.put(Context.PROVIDER_URL, "ldap://pcocpwdom01.corp.something.com:389");

            serviceEnv.put(Context.SECURITY_AUTHENTICATION, "simple");
            serviceEnv.put(Context.SECURITY_PRINCIPAL, "CN=SVCLdapQry,OU=ServiceAccounts_Admins,OU=Data Services,DC=corp,DC=something,DC=com"); 
            serviceEnv.put(Context.SECURITY_CREDENTIALS, "ADR0cks!~");

            // Create the initial context

            DirContext serviceCtx;
            try 
            
                serviceCtx = new InitialDirContext(serviceEnv);
             
            catch (NamingException e) 
            
                // TODO Auto-generated catch block
                e.printStackTrace();
                return false;
            

            boolean serviceConnectionResult = serviceCtx != null;

            if(serviceConnectionResult)
            
                System.out.println("LDAP basic authorization is successful");
            

            // user to authenticate
            String identifyingAttribute = "samaccountname";
            String ldapUrl = "ldap://pcocpwdom01.corp.something.com:389";
            String base = "DC=corp,DC=something,DC=com";

            // we don't need all attributes, just let it get the identifying one
            String[] attributeFilter =  identifyingAttribute ;
            SearchControls sc = new SearchControls();
            sc.setReturningAttributes(attributeFilter);
            sc.setSearchScope(SearchControls.SUBTREE_SCOPE);

         // use a search filter to find only the user we want to authenticate
            String searchFilter = "(" + identifyingAttribute + "=" + usrName + ")";

            NamingEnumeration<SearchResult> results = null;

            try 
            
                results = serviceCtx.search(base, searchFilter, sc);
             
            catch (NamingException e1) 
            
                // TODO Auto-generated catch block
                e1.printStackTrace();
            

            DirContext usrCtx = null;
            try 
                if (results.hasMore()) 
                    // get the users DN (distinguishedName) from the result
                    SearchResult result = results.next();
                    String distinguishedName = result.getNameInNamespace();

                    // attempt another authentication, now with the user
                    Properties authEnv = new Properties();
                    authEnv.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
                    authEnv.put(Context.PROVIDER_URL, ldapUrl);
                    authEnv.put(Context.SECURITY_PRINCIPAL, distinguishedName);
                    authEnv.put(Context.SECURITY_CREDENTIALS, pswd);
                    usrCtx = new InitialDirContext(authEnv);

                    System.out.println("Authentication successful");
                    authenticationresullt =  true;
                
             catch (NamingException e1) 
                // TODO Auto-generated catch block
                e1.printStackTrace();
            


          //close the service context
            if(usrCtx != null)
                try 
                
                    usrCtx.close();
                 
                catch (NamingException e) 
                
                    e.printStackTrace();
                    return false;
                


            //close the service context
            if(serviceCtx != null)
                try 
                
                    serviceCtx.close();
                 
                catch (NamingException e) 
                
                    e.printStackTrace();
                    return false;
                

            return authenticationresullt;


        




    

【问题讨论】:

【参考方案1】:

我关注了:

https://www.intertech.com/Blog/spring-security-active-directory-ldap-example/ https://www.mkyong.com/spring-security/spring-security-form-login-example/

实现“Spring Security Active Directory LDAP 示例 Spring Security Active Directory LDAP"。

【讨论】:

以上是关于如何使用 xml 配置文件、JAVA、Spring 安全性对 LDAP 用户进行身份验证的主要内容,如果未能解决你的问题,请参考以下文章

Spring 3.2 - 如何将 XML 中配置的 FlatFileItemWriter 注入 java 类中的参数化属性

如何从系统变量设置 Spring 配置文件?

如何在不使用带有java配置的spring的orm.xml中注册实体监听器?

Spring中如何混用XML与Java装配方式

【Spring源码配置文件解析】2. xml注入配置信息 & @Value

[刘阳Java]_Spring AOP基于XML配置介绍_第9讲