PHP LDAP 访问 Windows AD(Active Directory)

倘若接收移动目录(Active DirectoryState of Qatar代替在数据库表中创设账号,
你能够行使原本Windows互连网中的账号.LDAP, 轻量级目录采访左券(Lightweight
Directory Access Protocol卡塔尔国, 是用来访谈微软的移动目录等目录服务器(DS,
Directory Server卡塔尔国的公约.
PHP暗中同意帮助LDAP.上面是行使LDAP实行顾客身份验证的PHP程序.
在微软的活动目录中, 客商的独一标志是samaccountname, 某个DS是uid. 方法是:

这一周做LDAP做得头都大了。现在好不轻易有一点头绪了,记录一下,以备后用。

  1. 用有权力的账号的dn(形如
    cn=user_name,ou=web,dc=ideawu,dc=comState of Qatar连接LDAP Server. 2.
    依据登陆客商的名字查询其dn. 3. 用该dn连接LDAP Server.
    若是老是上便是登陆成功. 注意!
    微软的移位目录服务器能够使用空账号连接成功(设置难题? 暗许?
    特例?State of Qatar!$userid = $_POST[”userid”];$user_password =
    $_POST[”password”];if($userid $user_password){// config//
    $ldap_server = ideawu.com;// $ldap_admin = user_name;//
    $ldap_password = xxx;// $base_cn = ou=web,dc=ideawu,dc=com;$conn =
    ldap_connect($ldap_server);if(!$conn){die(brConnection LDAP server
    error);}$bind = ldap_bind($conn, $ldap_admin,
    $ldap_password);if(!$bind){die(brBind LDAP server error);}$filter =
    ”samaccountname=” . $userid;$attributes = array(”mail”);$result =
    ldap_search($conn, $base_dn, $filter, $attributes);$info =
    ldap_get_entries($conn, $result);if(!$result){die(brSearch
    failed);}if($info[count] != 0){$user_dn =
    $info[0][dn];unset($bind2);$bind2 = @ldap_bind($conn, $user_dn,
    $user_password);if($bind2){// Login done. Set
    session}}ldap_close($conn);}

 

LDAP是什么?
LDAP是轻量级目录访谈合同,日语全称是Lightweight Directory Access
Protocol,平常都简单的称呼为LDAP.
貌似用来创设聚集的身份验证系统能够减弱管理资金,巩固安全性,幸免数据复制的标题,并抓好数据的一致性。

ActiveDirectory是什么?
Active
Directory存款和储蓄了关于网络对象的音信,何况让管理员和客商能够轻巧地搜寻和利用那些音信。Active
Directory使用了一种布局化的数据存款和储蓄方式,并以此作为根底对目录新闻实行合乎逻辑的道岔协会。
①功底互联网服务:包含DNS、WINS、DHCP、证书服务等。

 

②服务器及顾客端Computer管理:管理服务器及顾客端Computer账户,全部服务器及顾客端Computer参加域管理并施行组计谋。

 

③客户服务:管理客户域账户、客户音信、集团通信录(与电子邮件系统集成)、客商组处理、客户居民身份表明、客户授权管理等,按省实行组管理攻略。

 

④财富管理:管理打字与印刷机、文件分享服务等互联网能源。

 

⑤桌面配置:系统助理馆员能够聚集的布署种种桌面配置计谋,如:分界面作用的约束、应用程序实行特征限定、互连网连接约束、安全体署范围等。

 

s⑥应用系统扶植:支持财务、人事、电子邮件、集团新闻门户、办公自动化、补丁管理、防病毒系统等各类应用种类。


概念皆以搜出来的,不是相通的虚幻。那也是自个儿花了近四日时间才弄懂一些的案由所在。
自己的掌握是足以把mirectory的ActiveDirectory当做二个LDAP服务器,提供LDAP验证服务。当然其余平台或公司也许有温馨的ldap服务器。如sun,ibm,等的。

自身的需假诺在EOS开辟平台(基于EclipseJAVA工作流)上经过内嵌的开源ABFrame(权限管理种类)达成LDAP验证,
紧接着完成SSO。

找到了LDAP的配备文件后经过查找资料不论怎么着也通可是验证,还跟了很深的代码,JNDI的资料也查了大多,无果。

 

无奈,微软温馨家东西,就试着用.net写了个程序,未有怎么阻力,相当的轻松就经过了登入验证。代码如下:

图片 1图片 2ldap C#

using
System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.DirectoryServices;
using System.Configuration;
using System.Text.RegularExpressions;

namespace ldapcs
{
class Program
{
staticvoid
Main(string[] args)
{
string path =”LDAP://192.168.137.210:389/ou=pet,dc=abc,dc=com
“;
string username =”uname”;
string pwd =”upwd”;
string domain =”abc.com”;

LdapAuthentication ldap =new
LdapAuthentication(path);
Console.WriteLine( ldap.IsAuthenticated(domain, username, pwd));
Console.WriteLine(ldap.GetGroups());
}

publicclass
LdapAuthentication
{
privatestring
_path;
privatestring
_filterAttribute;

public LdapAuthentication(string
path)
{
_path = path;
}

publicbool
IsAuthenticated(string domain, string
username, string pwd)
{
string domainAndUsername = domain
+@””+
username;
DirectoryEntry entry =new
DirectoryEntry(_path, username, pwd);

try
{
//Bind to the native AdsObject to force
authentication.
object obj =
entry.NativeObject;

DirectorySearcher search =new
DirectorySearcher(entry);

search.Filter =”(SAMAccountName=”+ username
+”)”;
search.PropertiesToLoad.Add(“cn”);
SearchResult result = search.FindOne();

if (null==
result)
{
returnfalse;
}

//Update the new path to the user in the
directory.
_path =
result.Path;
_filterAttribute = (string)result.Properties[“cn”][0];
}
catch (Exception ex)
{
thrownew
Exception(“Error authenticating user. “+
ex.Message);
}

returntrue;
}

publicstring
GetGroups()
{
DirectorySearcher search =new
DirectorySearcher(_path);
search.Filter =”(cn=”+
_filterAttribute +”)”;
//search.SearchRoot = “PET”;
StringBuilder groupNames
=new
StringBuilder();

try
{
SearchResult result = search.FindOne();
int propertyCount =
result.Properties[“memberOf”].Count;
string dn;
int equalsIndex, commaIndex;

for (int
propertyCounter =0;
propertyCounter < propertyCount; propertyCounter++)
{
dn = (string)result.Properties[“memberOf”][propertyCounter];
equalsIndex = dn.IndexOf(“=”,
1);
commaIndex = dn.IndexOf(“,”,
1);
if (-1==
equalsIndex)
{
returnnull;
}
groupNames.Append(dn.Substring((equalsIndex +1),
(commaIndex – equalsIndex) -1));
groupNames.Append(“|”);
}
}
catch (Exception ex)
{
thrownew
Exception(“Error obtaining group names. “+
ex.Message);
}
return groupNames.ToString();
}
}

///<summary>
/// 验证AD顾客是或不是登陆成功
///</summary>
///<param
name=”domain”></param>
///<param
name=”userName”></param>
///<param
name=”password”></param>
///<returns></returns>
publicstaticbool
TryAuthenticate(string domain, string
userName, string password)
{
bool isLogin =false;
try
{
DirectoryEntry entry =new
DirectoryEntry(string.Format(“LDAP://{0}”, domain),
userName, password);
entry.RefreshCache();
isLogin =true;
}
catch
{
isLogin =false;
}
return isLogin;
}
}
}

 

再回头去用abframe的事物,照旧尚未结果。于是再找叁个java验证的事例,照旧得以经过验证

图片 3图片 4代码

/**
*
* @author icuit
*/
import java.util.Hashtable;
import java.util.Enumeration;
import javax.naming.Context;
import javax.naming.NamingException;
import javax.naming.directory.DirContext;
import javax.naming.directory.InitialDirContext;
import javax.naming.directory.SearchControls ;
import javax.naming.NamingEnumeration;
import javax.naming.directory.SearchResult;

publicclass
LDAPtest {

publicstaticvoid
main(String[] args) {
LDAPtest ldap=new
LDAPtest();
ldap.init();
}
publicvoid
init(){
DirContext ctx =null;
Hashtable env =new
Hashtable();
env.put(Context.INITIAL_CONTEXT_FACTORY, “com.sun.jndi.ldap.LdapCtxFactory”);
env.put(Context.PROVIDER_URL, “ldap://192.168.137.210:389/”);//连接LDAP的URL和端口

//env.put(Context.SECURITY_AUTHENTICATION,
“simple”卡塔尔国;//以simple模式发送
env.put(Context.SECURITY_PRINCIPAL,
“cn=uname,ou=PET,DC=abc,DC=com”);//用户名
env.put(Context.SECURITY_CREDENTIALS,
“upwd”);//密码
String baseDN=”ou=PET,DC=abc,DC=com”;//查询区域
String filter=”(&(objectClass=person卡塔尔State of Qatar”;//条件查询

try{
ctx =new
InitialDirContext(env);//连接LDAP服务器
System.out.println(“Success”);
SearchControls constraints =new
SearchControls(State of Qatar;//履行查询操作
constraints.setSearchScope(SearchControls.SUBTREE_SCOPE);
NamingEnumeration en=ctx.search(baseDN, filter, constraints);
if(en==null){
System.out.println(“There have no value”);
}else{
while(en.hasMoreElements()){

Object obj=en.nextElement();
if(obj instanceof
SearchResult){
SearchResult sr=(SearchResult) obj;
String cn=sr.getName();

System.out.println(“cccccc: “+cn);
}
}
}

}catch(javax.naming.AuthenticationException e){
System.out.println(e.getMessage());
}catch(Exception e){
System.out.println(“erro:”+e);
}
}
}

于是乎又去跟abframe的代码,人己一视新检讨文件,并查了部分有关LDAP验证参数的资料。终于能够证实,计算如下:

ldap验证有几个比较关键的参数:
ldap_base_provider_url, 
ldap服务器的地址及端口,如:

ldap_security_principal,  
用来查询验证ldap服务的客商

cn=uname,ou=pet,dc=abc,dc=com,大概有相当大希望是cn=uadmin,cn=users,dc=abc,dc=com
那边是最最重大的地点,笔者也是在此方面开销了最多的时光,
假设服务器的域名是 abc.com 那么将在有 dc=abc,dc=com,其余情形就那样类推
cn是指的客户名,不过此地有二种情状,一种是cn=uname,ou=pet,另一种是cn=uadmin,cn=users
小编的推测是假若在windows Active
Directory的内建分组users下的顾客则用第三种
如假若在windows Active Directory的自行建造分组,如组名称为PET,则用第一种

dap_security_credentials,
用来查询验证ldap服务的密码,与ldap_security_principal配对 如 f34dgd

这里要求珍视说澳优(Nutrilon卡塔尔(قطر‎下,ldap_security_principal与ldap_security_principal所内定的客商和密码并非
最后要证实的顾客,而是贰个用来查询所要验证的顾客是还是不是留存的客商。

ldap_base_dn,           
 ldap服务的认证基址,因为ldap是借助目录,也就有等级次序关系,如ou=PET,dc=intasect,dc=local
那边是索要表明的客户目录,至于参数的分解同ldap_security_principal

ldap_auth_search_filter
询问求证用户的查找条件,日常是(objectClass=person卡塔尔,是哪些意思笔者也没细去研讨

ldap_auth_method
身份验证形式, bind 或 password-compare
bind 基于绑定客商身份检查,笔者那边运用的首先种,只怕是因为windows
AD是这一种,另一种不或者透过
password-compare 基于加密算法,选拔密码比较艺术

ldap_auth_password_encryption_algorithm
密码加密方法 MD5,SHA等。
本身用的是MD5

以上参数错贰个可能就通然则验证,所以参数的科学是注重。

此处留下一些参照的质地
1,LDAP验证经常见到的错误代码

javax.naming.AuthenticationException: [LDAP: error code 49 – 80090308:
LdapErr: DSID-0C090334, comment: AcceptSecurityContext error, data 52e,
vece
意思是客商名或密码错误

javax.naming.NamingException: [LDAP: error code 1 – 00000000: LdapErr:
DSID-0C090AE2, comment: In order to perform this operation a successful
bind must be completed on the connection., data 0, vece
粗粗是询问的目录无效,应该是ou设置错误

 

2,仿效网址

 

3,windows active directory在win贰零零零上的设置格局
其实安装AD的进度也正是把此机器进级为域调控器的经过,有好几要升迁的是在晋级域在此之前必定要备份自行建造账户音信
不然当降级为日常计算机时享有自行建造账户新闻将遗失。切记。

 

4,在ActiveDirectory新建组,新建客户,配置域名

希望有其余朋友境遇同样题目时少走弯路。

发表评论

电子邮件地址不会被公开。 必填项已用*标注