tapmodo / node-ldif

Nodejs LDIF (LDAP Data Interchange Format) parser based on RFC2849
9 stars 7 forks source link

Cannot read LDIF file when entry has no attributes #5

Open skissane opened 7 years ago

skissane commented 7 years ago

I ran an ldapsearch against AD, to dump all entries my account has permission to see. (I am using OpenLDAP ldapsearch client.) I get back an LDIF file which includes some entries with no attributes:

dn: CN=NTDS Quotas,DC=ad,DC=example,DC=com

dn: CN=VolumeTable,CN=FileLinks,CN=System,DC=ad,DC=example,DC=com

dn: CN=IP Security,CN=System,DC=ad,DC=example,DC=com

etc...

I am not sure why. Maybe I have permission to see the entry exists but not read it?

Now, I try to parse this LDIF file with node-ldif. And it gets a syntax error when it gets to these entries because the attributes are missing.

I realise that per RFC2849 this is invalid syntax and node-ldif is just following the RFC:

ldif-attrval-record      = dn-spec SEP 1*attrval-spec

But, given real world LDIF files seem to violate the spec in this way, it would be nice if node-ldif could be a bit more forgiving, even if just as an option...

As a workaround, I use this script to pre-process my LDIF file:

var input = require('fs').readFileSync("/dev/stdin", 'utf8');
input = input.replace(/\r\n/g, "\n");
input = input.replace(/\n /g, "");
input = input.replace(/\n#[^\n]*\n/g, "\n");
while (input.match(/\ndn:[^\n]*\n\n/))
    input = input.replace(/\ndn:[^\n]*\n\n/g, "\n");
process.stdout.write(input);

but would be nice if there was an out-of-the-box solution.

skissane commented 7 years ago

BTW, it probably doesn't matter, but just in case, this is the ldapsearch command which generates the problematic LDIF file:

ldapsearch -LLL -h ${_adServer} -x -b "${_baseDN}" -D "${_user}@${_userDomain}" -W -E pr=2147483647/noprompt

That is out of a shell script, hence the ${...} variables which the shell script defines earlier...

jasonk commented 6 years ago

FYI, for anyone else who runs into this, you can also work around it by making sure your output includes at least one attribute value. We were encountering this when parsing the output of a script that was only retrieving DNs.

# ldif.parse can't handle the output from this command:
ldapsearch <opts> '(objectclass=user)' dn

# but this one is fine:
ldapsearch <opts> '(objectclass=user)' dn cn