PHP Conference Japan 2024

ldap_explode_dn

(PHP 4, PHP 5, PHP 7, PHP 8)

ldap_explode_dn将 DN 分割成其组成部分

描述

ldap_explode_dn(字符串 $dn, 整数 $with_attrib): 数组|false

分割由 ldap_get_dn() 返回的 DN,并将其分解成其组成部分。每个部分称为相对可分辨名称或 RDN。

参数

dn

LDAP 实体的可分辨名称。

with_attrib

用于请求是否仅返回值或其属性以及 RDN。要获取具有属性的 RDN(即 attribute=value 格式),请将 with_attrib 设置为 0,要仅获取值,请将其设置为 1。

返回值

返回所有 DN 组件的数组,或者在失败时返回 false。数组中的第一个元素具有 count 键,表示返回的值的数量,接下来的元素是按数字索引的 DN 组件。

添加注释

用户贡献的注释 6 个注释

eero at eero dot info
7 年前
我正在将与 LDAP 相关的代码转换为 PHP7,PHP7 不再支持 preg_replace 的 /e 修饰符,但您应该改用 preg_replace_callback。这可能有助于处理相同问题的人。

<?php

$value
= 'Universität';

# < PHP7 兼容代码
echo preg_replace("/\\\([0-9A-Fa-f]{2})/e", "''.chr(hexdec('\\1')).''", $value);

# >= PHP7 兼容代码
echo preg_replace_callback('/\\\([0-9A-Fa-f]{2})/', function ($matches) { return chr(hexdec($matches[1])); }, $value);
gabriel at hrz dot uni-marburg dot de
21 年前
注意 UTF8 编码的 DN。自 openLDAP >=2.1.2 起
ldap_explode_dn 将不可打印字符(在 ASCII 意义上,UTF8
编码)转换为 \<hexcode>。

示例

$dn="ou=Universität ,c=DE";
var_dump(ldap_explode_dn($dn,0));

//返回

array(3) {
["count"]=>
int(2)
[0]=>
string(19) "ou=Universit\C3\A4t"
[1]=>
string(4) "c=DE"
}

不幸的是,PHP 不支持 ldap 函数 ldap_str2dn 和
ldap_dn2str,但可以通过 preg_replace 实现解决方法来
恢复 ldap_explode_dn 的旧行为

// 解决方法
function myldap_explode_dn($dn,$with_attribute){

$result=ldap_explode_dn ($dn, $with_attrib);
//将十六进制代码再次转换为 ascii
foreach($result as $key=>$value){
$result[$key]=preg_replace("/\\\([0-9A-Fa-f]{2})/e", "''.chr(hexdec('\\1')).''", $value);
}
return($result);

}
//
//然后遵循示例

$dn="ou=Universität ,c=DE";
var_dump(myldap_explode_dn($dn,0));

//返回

array(3) {
["count"]=>
int(2)
[0]=>
string(15) "ou=Universität"
[1]=>
string(4) "c=DE"
}
hello+php at NOSPAM dot renoirboulanger dot com
12 年前
我偶然发现了这个页面,并喜欢这些评论。

由于 LDAP 字符串有时可能很长并且具有许多属性,因此我需要能够对所有内容进行排序。

在我的情况下,我需要获取子域名部分和其他参数。

以下是我构建方法的方式。
<?php
/**
* 解析并将 DN 字符串格式化为数组
*
* 读取 LDAP DN 并返回一个数组键
* 列出所有类似的属性。
*
* 还处理字符转义和取消转义
*
* 示例:
* CN=username,OU=UNITNAME,OU=Region,OU=Country,DC=subdomain,DC=domain,DC=com
*
* 通常会返回:
* Array (
* [count] => 9
* [0] => CN=username
* [1] => OU=UNITNAME
* [2] => OU=Region
* [5] => OU=Country
* [6] => DC=subdomain
* [7] => DC=domain
* [8] => DC=com
* )
*
* 相反,返回一个易于管理的数组:
* array (
* [CN] => array( username )
* [OU] => array( UNITNAME, Region, Country )
* [DC] => array ( subdomain, domain, com )
* )
*
*
* @author gabriel at hrz dot uni-marburg dot de 05-Aug-2003 02:27 (部分字符替换)
* @author Renoir Boulanger
*
* @param string $dn DN
* @return array
*/
function parseLdapDn($dn)
{
$parsr=ldap_explode_dn($dn, 0);
//$parsr[] = 'EE=Sôme Krazï string';
//$parsr[] = 'AndBogusOne';
$out = array();
foreach(
$parsr as $key=>$value){
if(
FALSE !== strstr($value, '=')){
list(
$prefix,$data) = explode("=",$value);
$data=preg_replace("/\\\\\\([0-9A-Fa-f]{2})/e", "''.chr(hexdec('\\\\1')).''", $data);
if(isset(
$current_prefix) && $prefix == $current_prefix){
$out[$prefix][] = $data;
} else {
$current_prefix = $prefix;
$out[$prefix][] = $data;
}
}
}
return
$out;
}
?>
emepese
7 年前
可能不是最好的方法,但对于那些正在寻找一种获取 DN 的 CN(不包括“cn=”部分)的方法的人来说,这是一个带有正则表达式模式的函数



<?php
function getCNofDN($dn) {
$return=preg_match('/[^cn=]([^,]*)/i',$dn,$dn);
return(
$dn[0]);
}

echo
getCNofDN("cn=emepese,cn=someLevel,dc=someCompany");

// 输出 "emepese"

?>
DavidSmith at byu dot net
21 年前
[ 编辑注:段错误已修复,在 PHP 4.3.4 或 PHP 5.0.0 发布时将不再出现。但是,仍然需要转义特殊字符,如下所述。 ]

如果您的 DN 包含 < 或 > 字符,则必须使用反斜杠对其进行转义,否则 ldap_explode_dn() 将会报错“参数数量错误”甚至出现段错误。

例如,以下调用将导致“参数数量错误”或段错误

ldap_explode_dn( "cn=<bob>,dc=example,dc=com", 0 );
ldap_explode_dn( 'cn=<bob>,dc=example,dc=com', 0 );

但以下调用将成功

ldap_explode_dn( "cn=\<bob\>,dc=example,dc=com", 0 );

另请注意,< 和 > 使用十六进制代码进行转义,如上所述。此函数是一个很好的包装器,可以正确格式化所有 DN,并且可以安全地使用 < 和 > 字符以及 UTF-8 字符进行调用

function my_explode_dn( $dn, $with_attributes=0 )
{
$dn = addcslashes( $dn, "<>" );
$result = ldap_explode_dn( $dn, $with_attributes );
//将十六进制代码再次转换为 ascii
foreach( $result as $key => $value )
$result[$key] = preg_replace("/\\\([0-9A-Fa-f]{2})/e", "''.chr(hexdec('\\1')).''", $value);
return $result;
}

我正在使用 php 4.3.1。祝你好运!
bs at muekno dot de
23 年前
复制比打字要好得多!!!!
只需修改常量。
最好的祝愿(并感谢此有帮助的网站),
Bernd Schwaegerl
Mueller-Knoche GmbH, Systemhaus fuer EDV-Loesungen

# 示例

$HOST = "您的主机名";
$USER_DN = "您的ldap用户dn";
$PWD = "Ldap用户密码";
$BASE_DN = "o=您的组织";
$SEARCH_OBJECT="sn=您要搜索的人员对象的sn";

$ldap_handle=ldap_connect($HOST);
$bind_result=ldap_bind($ldap_handle,$USER_DN,$PWD);

$search_result=ldap_search($ldap_handle,$BASE_DN,$SEARCH_OBJECT);
$result=ldap_get_entries($ldap_handle,$search_result);
$result_array=ldap_get_entries($ldap_handle,$result);
$whole_dn=$result_array[0]["dn"];

$dn_parts=ldap_explode_dn($whole_dn,0);
To Top