1ldap(n)                           LDAP client                          ldap(n)
2
3
4
5______________________________________________________________________________
6

NAME

8       ldap - LDAP client
9

SYNOPSIS

11       package require Tcl  8.4
12
13       package require ldap  ?1.9.2?
14
15       ::ldap::connect host ?port?
16
17       ::ldap::secure_connect host ?port? ?verify_cert? ?sni_servername?
18
19       ::ldap::disconnect handle
20
21       ::ldap::starttls  handle  ?cafile?  ?certfile?  ?keyfile? ?verify_cert?
22       ?sni_servername?
23
24       ::ldap::bind handle ?name? ?password?
25
26       ::ldap::bindSASL handle ?name? ?password?
27
28       ::ldap::unbind handle
29
30       ::ldap::search handle baseObject filterString attributes options
31
32       ::ldap::searchInit handle baseObject filterString attributes options
33
34       ::ldap::searchNext handle
35
36       ::ldap::searchEnd handle
37
38       ::ldap::modify handle dn attrValToReplace ?attrToDelete? ?attrValToAdd?
39
40       ::ldap::modifyMulti handle dn attrValToReplace ?attrValToDelete? ?attr‐
41       ValToAdd?
42
43       ::ldap::add handle dn attrValueTuples
44
45       ::ldap::addMulti handle dn attrValueTuples
46
47       ::ldap::delete handle dn
48
49       ::ldap::modifyDN handle dn newrdn ?deleteOld? ?newSuperior?
50
51       ::ldap::info ip handle
52
53       ::ldap::info bound handle
54
55       ::ldap::info bounduser handle
56
57       ::ldap::info connections
58
59       ::ldap::info tls handle
60
61       ::ldap::info saslmechanisms handle
62
63       ::ldap::info control handle
64
65       ::ldap::info extensions extensions
66
67       ::ldap::info whoami handle
68
69______________________________________________________________________________
70

DESCRIPTION

72       The ldap package provides a Tcl-only client library for the LDAPv3 pro‐
73       tocol    as    specified    in    RFC     4511     (http://www.rfc-edi
74       tor.org/rfc/rfc4511.txt).  It works by opening the standard (or secure)
75       LDAP socket on the server, and then providing a Tcl API to  access  the
76       LDAP  protocol  commands.  All server errors are returned as Tcl errors
77       (thrown) which must be caught with the Tcl catch command.
78

TLS SECURITY CONSIDERATIONS

80       This package uses the TLS package to handle the security for https urls
81       and other socket connections.
82
83       Policy  decisions like the set of protocols to support and what ciphers
84       to use are not the responsibility of TLS, nor of  this  package  itself
85       however.   Such  decisions are the responsibility of whichever applica‐
86       tion is using the package, and are likely  influenced  by  the  set  of
87       servers the application will talk to as well.
88
89       For  example,  in light of the recent POODLE attack [http://googleonli
90       nesecurity.blogspot.co.uk/2014/10/this-poodle-bites-exploiting-
91       ssl-30.html] discovered by Google many servers will disable support for
92       the SSLv3 protocol.  To handle this change the applications  using  TLS
93       must  be  patched,  and not this package, nor TLS itself.  Such a patch
94       may be as simple as generally activating tls1 support, as shown in  the
95       example below.
96
97
98                  package require tls
99                  tls::init -tls1 1 ;# forcibly activate support for the TLS1 protocol
100
101                  ... your own application code ...
102
103

COMMANDS

105       ::ldap::connect host ?port?
106              Opens  a  LDAPv3  connection to the specified host, at the given
107              port, and returns a token for the connection. This token is  the
108              handle  argument for all other commands. If no port is specified
109              it will default to 389.
110
111              The command blocks until the connection has been established, or
112              establishment definitely failed.
113
114       ::ldap::secure_connect host ?port? ?verify_cert? ?sni_servername?
115              Like  ::ldap::connect,  except  that  the  created connection is
116              secured by SSL. The port defaults to 636.  This command  depends
117              on  the  availability of the package TLS, which is a SSL binding
118              for Tcl. If TLS is not available, then this command will fail.
119
120              The command blocks until the connection has been established, or
121              establishment definitely failed.
122
123              If  verify_cert is set to 1, the default, this checks the server
124              certificate against the known hosts. If sni_servername  is  set,
125              the given hostname is used as the hostname for Server Name Indi‐
126              cation in the TLS handshake.
127
128              Use ::tls::init to setup defaults for trusted certificates.
129
130
131                  tls::init -cadir /etc/ssl/certs/ca-certificates.crt
132
133
134       TLS supports different protocol levels. In common use are the  versions
135       1.0,  1.1  and  1.2.  By default all those versions are offered. If you
136       need  to  modify  the  acceptable  protocols,  you   can   change   the
137       ::ldap::tlsProtocols list.
138
139       ::ldap::disconnect handle
140              Closes  the  ldap  connection  refered  to  by the token handle.
141              Returns the empty string as its result.
142
143       ::ldap::starttls handle  ?cafile?  ?certfile?  ?keyfile?  ?verify_cert?
144       ?sni_servername?
145              Start  TLS negotiation on the connection denoted by handle.  You
146              need to set at least the cafile argument to a file with  trusted
147              certificates,  if  verify_cert  is 1, which is the default.  The
148              sni_servername can be used to signal a different hostname during
149              the  TLS  handshake.   The announced protocols are determined in
150              the same way as ::ldap::secure_connect.  You can specify  a  TLS
151              client certificate with the certfile and keyfile options.
152
153       ::ldap::bind handle ?name? ?password?
154              This command authenticates the ldap connection refered to by the
155              token in handle, with a user name and  associated  password.  It
156              blocks until a response from the ldap server arrives. Its result
157              is the empty string.  Both name and passwd default to the  empty
158              string  if  they  are  not  specified.   By leaving out name and
159              passwd you can make an anonymous bind to the ldap  server.   You
160              can issue ::ldap::bind again to bind with different credentials.
161
162       ::ldap::bindSASL handle ?name? ?password?
163              This  command uses SASL authentication mechanisms to do a multi‐
164              stage  bind.   Its   otherwise   identical   to   the   standard
165              ::ldap::bind.   This  feature is currently experimental and sub‐
166              ject to change. See the  documentation  for  the  SASL  and  the
167              "SASL.txt" in the tcllib CVS repository for details how to setup
168              and use SASL with openldap.
169
170       ::ldap::unbind handle
171              This command asks the ldap server to release the last bind  done
172              for  the connection refered to by the token in handle.  The han‐
173              dle is invalid after the unbind, as the server closes  the  con‐
174              nection.   So  this  is effectivly just a more polite disconnect
175              operation.
176
177       ::ldap::search handle baseObject filterString attributes options
178              This command performs a LDAP search below  the  baseObject  tree
179              using  a complex LDAP search expression filterString and returns
180              the specified attributes of all matching objects (DNs).  If  the
181              list  of  attributes  was empty all attributes are returned. The
182              command blocks until it has received  all  results.   The  valid
183              options  are  identical  to the options listed for ::ldap::sear‐
184              chInit.
185
186              An example of a search expression is
187
188
189
190                  set filterString "|(cn=Linus*)(sn=Torvalds*)"
191
192
193       The return value of the command is a list of nested  dictionaries.  The
194       first  level  keys are object identifiers (DNs), second levels keys are
195       attribute names. In other words, it is in the form
196
197
198
199                  {dn1 {attr1 {val11 val12 ...} attr2 {val21...} ...}} {dn2 {a1 {v11 ...} ...}} ...
200
201
202
203       ::ldap::searchInit handle baseObject filterString attributes options
204              This command initiates a LDAP search below the  baseObject  tree
205              using a complex LDAP search expression filterString.  The search
206              gets the specified attributes of  all  matching  objects  (DNs).
207              The  command  itself  just  starts  the  search, to retrieve the
208              actual results, use ::ldap::searchNext.  A search can be  termi‐
209              nated  at any time by ::ldap::searchEnd. This informs the server
210              that no further results should be sent by  sending  and  ABANDON
211              message  and  cleans  up the internal state of the search.  Only
212              one ::ldap::search can be active at a given time, this  includes
213              the    introspection   commands   ::ldap::info   saslmechanisms,
214              ldap::info control and ldap::info  extensions,  which  invoke  a
215              search internally.  Error responses from the server due to wrong
216              arguments  or  similar  things  are  returned  with  the   first
217              ::ldap::searchNext  call  and  should be checked and dealed with
218              there.  If  the  list  of  requested  attributes  is  empty  all
219              attributes  will  be  returned.  The parameter options specifies
220              the options to be used in the search, and has the following for‐
221              mat:
222
223
224
225                  {-option1 value1 -option2 value2 ... }
226
227
228       Following options are available:
229
230              -scope base one sub
231                     Control  the  scope of the search to be one of base, one,
232                     or sub,  to  specify  a  base object,  one-level or  sub‐
233                     tree  search.   The  default is sub.
234
235              -derefaliases never search find always
236                     Control how aliases dereferencing is done.  Should be one
237                     of never, always, search,   or   find   to  specify  that
238                     aliases  are  never  dereferenced,  always  dereferenced,
239                     dereferenced when searching, or  dereferenced  only  when
240                     locating  the base object for the search.  The default is
241                     to never dereference aliases.
242
243              -sizelimit num
244                     Determines the maximum number of entries to return  in  a
245                     search.  If  specified  as  0  no  limit is enforced. The
246                     server may enforce a configuration  dependent  sizelimit,
247                     which may be lower than the one given by this option. The
248                     default is 0, no limit.
249
250              -timelimit seconds
251                     Asks the server to use a timelimit  of  seconds  for  the
252                     search. Zero means no limit. The default is 0, no limit.
253
254              -attrsonly boolean
255                     If  set  to 1 only the attribute names but not the values
256                     will be present in the search result.  The default is  to
257                     retrieve attribute names and values.
258
259              -referencevar varname
260                     If  set the search result reference LDAPURIs, if any, are
261                     returned in the given  variable.   The  caller  can  than
262                     decide  to  follow  those references and query other LDAP
263                     servers for further results.
264
265
266       ::ldap::searchNext handle
267              This command returns the next entry from a LDAP search initiated
268              by  ::ldap::searchInit.  It  returns  only after a new result is
269              received or when no further results  are  available,  but  takes
270              care to keep the event loop alive.  The returned entry is a list
271              with two elements: the first is the DN of the entry, the  second
272              is the list of attributes and values, under the format:
273
274
275
276                  dn {attr1 {val11 val12 ...} attr2 {val21...} ...}
277
278
279       The  ::ldap::searchNext command returns an empty list at the end of the
280       search.
281
282
283       ::ldap::searchEnd handle
284              This command terminates a LDAP search initiated by ::ldap::sear‐
285              chInit. It also cleans up the internal state so a new search can
286              be initiated.  If the client has not yet received  all  results,
287              the client sends an ABANDON message to inform the server that no
288              further results for the previous search should to be sent.
289
290
291       ::ldap::modify handle dn attrValToReplace ?attrToDelete? ?attrValToAdd?
292              This command modifies the object dn on the ldap  server  we  are
293              connected to via handle. It replaces attributes with new values,
294              deletes attributes, and adds new  attributes  with  new  values.
295              All  arguments  are dictionaries mapping attribute names to val‐
296              ues. The optional arguments default  to  the  empty  dictionary,
297              which means that no attributes will be deleted nor added.
298
299              dictionary attrValToReplace (in)
300                     No  attributes will be changed if this argument is empty.
301                     The dictionary contains the new attributes and their val‐
302                     ues. They replace all attributes known to the object.
303
304              dictionary attrToDelete (in)
305                     No  attributes will be deleted if this argument is empty.
306                     The dictionary values are restrictions on  the  deletion.
307                     An  attribute  listed here will be deleted if and only if
308                     its current value at the server matches the value  speci‐
309                     fied in the dictionary, or if the value in the dictionary
310                     is the empty string.
311
312              dictionary attrValToAdd (in)
313                     No attributes will be added if this  argument  is  empty.
314                     The   dictionary  values  are  the  values  for  the  new
315                     attributes.
316
317       The command blocks until all modifications have completed.  Its  result
318       is the empty string.
319
320       ::ldap::modifyMulti handle dn attrValToReplace ?attrValToDelete? ?attr‐
321       ValToAdd?
322              This command modifies the object dn on the ldap  server  we  are
323              connected to via handle. It replaces attributes with new values,
324              deletes attributes, and adds new  attributes  with  new  values.
325              All arguments are lists with the format:
326
327
328
329                  attr1 {val11 val12 ...} attr2 {val21...} ...
330
331
332       where  each  value  list may be empty for deleting all attributes.  The
333       optional arguments default to empty lists of attributes to  delete  and
334       to add.
335
336              list attrValToReplace (in)
337                     No  attributes will be changed if this argument is empty.
338                     The dictionary contains the new attributes and their val‐
339                     ues. They replace all attributes known to the object.
340
341              list attrValToDelete (in)
342                     No  attributes will be deleted if this argument is empty.
343                     If no value is specified, the whole set of values for  an
344                     attribute will be deleted.
345
346              list attrValToAdd (in)
347                     No attributes will be added if this argument is empty.
348
349       The  command  blocks until all modifications have completed. Its result
350       is the empty string.
351
352       ::ldap::add handle dn attrValueTuples
353              This command creates a new object using the  specified  dn.  The
354              attributes  of  the new object are set to the values in the list
355              attrValueTuples.  Multiple valuated attributes may be  specified
356              using  multiple  tuples.  The command blocks until the operation
357              has completed. Its result is the empty string.
358
359       ::ldap::addMulti handle dn attrValueTuples
360              This command is the preferred one to create a new  object  using
361              the  specified  dn.  The attributes of the new object are set to
362              the values in the dictionary attrValueTuples (which is keyed  by
363              the  attribute names).  Each tuple is a list containing multiple
364              values.  The command blocks until the operation  has  completed.
365              Its result is the empty string.
366
367       ::ldap::delete handle dn
368              This  command  removes  the  object specified by dn, and all its
369              attributes from the server.  The command blocks until the opera‐
370              tion has completed. Its result is the empty string.
371
372       ::ldap::modifyDN handle dn newrdn ?deleteOld? ?newSuperior?
373              This command moves or copies the object specified by dn to a new
374              location in the tree of object. This location  is  specified  by
375              newrdn,  a relative designation, or by newrdn and newSuperior, a
376              absolute designation.  The optional argument deleteOld  defaults
377              to  true,  i.e.  a move operation. If deleteOld is not set, then
378              the operation will create a copy of dn in the new location.  The
379              optional  argument newSuperior defaults an empty string, meaning
380              that the object must not be relocated in another branch  of  the
381              tree.  If this argument is given, the argument deleteOld must be
382              specified also.  The command blocks until the operation has com‐
383              pleted. Its result is the empty string.
384
385       ::ldap::info ip handle
386              This  command  returns  the IP address of the remote LDAP server
387              the handle is connected to.
388
389       ::ldap::info bound handle
390              This command returns 1 if a handle has successfully completed  a
391              ::ldap::bind.   If  no  bind  was  done  or  it  failed,  a 0 is
392              returned.
393
394       ::ldap::info bounduser handle
395              This command returns the username used in the bind operation  if
396              a handle has successfully completed a ::ldap::bind.  If no bound
397              was done or it failed, an empty string is returned.
398
399       ::ldap::info connections
400              This command returns all currently existing ldap connection han‐
401              dles.
402
403       ::ldap::info tls handle
404              This  command  returns  1  if  the  ldap  connection handle used
405              TLS/SSL for connection  via  ldap::secure_connect  or  completed
406              ldap::starttls, 0 otherwise.
407
408       ::ldap::info saslmechanisms handle
409              Return  the  supported SASL mechanisms advertised by the server.
410              Only valid in a bound state (anonymous or other).
411
412       ::ldap::info control handle
413              Return the supported controls advertised by the server as a list
414              of OIDs. Only valid in a bound state.  This is currently experi‐
415              mental and subject to change.
416
417       ::ldap::info extensions extensions
418              Returns the supported LDAP extensions  as  list  of  OIDs.  Only
419              valid in a bound state.  This is currently experimental and sub‐
420              ject to change.
421
422       ::ldap::info whoami handle
423              Returns authzId for the current connection. This implements  the
424              RFC 4532 protocol extension.
425

EXAMPLES

427       A  small  example, extracted from the test application coming with this
428       code.
429
430                  package require ldap
431
432                  # Connect, bind, add a new object, modify it in various ways
433
434                  set handle [ldap::connect localhost 9009]
435
436                  set dn "cn=Manager, o=University of Michigan, c=US"
437                  set pw secret
438
439                  ldap::bind $handle $dn $pw
440
441                  set dn "cn=Test User,ou=People,o=University of Michigan,c=US"
442
443                  ldap::add $handle $dn {
444                objectClass     OpenLDAPperson
445                cn              {Test User}
446                mail            test.user@google.com
447                uid             testuid
448                sn              User
449                telephoneNumber +31415926535
450                telephoneNumber +27182818285
451                  }
452
453                  set dn "cn=Another User,ou=People,o=University of Michigan,c=US"
454
455                  ldap::addMulti $handle $dn {
456                objectClass     {OpenLDAPperson}
457                cn              {{Anotther User}}
458                mail            {test.user@google.com}
459                uid             {testuid}
460                sn              {User}
461                telephoneNumber {+31415926535 +27182818285}
462                  }
463
464                  # Replace all attributes
465                  ldap::modify $handle $dn [list drink icetea uid JOLO]
466
467                  # Add some more
468                  ldap::modify $handle $dn {} {} [list drink water  drink orangeJuice pager "+1 313 555 7671"]
469
470                  # Delete
471                  ldap::modify $handle $dn {} [list drink water  pager ""]
472
473                  # Move
474                  ldap::modifyDN $handle $dn "cn=Tester"
475
476                  # Kill the test object, and shut the connection down.
477                  set dn "cn=Tester,ou=People,o=University of Michigan,c=US"
478                  ldap::delete $handle $dn
479
480                  ldap::unbind     $handle
481                  ldap::disconnect $handle
482
483
484       And a another example, a simple query, and processing the results.
485
486                  package require ldap
487                  set handle [ldap::connect ldap.acme.com 389]
488                  ldap::bind $handle
489                  set results [ldap::search $handle "o=acme,dc=com" "(uid=jdoe)" {}]
490                  foreach result $results {
491                foreach {object attributes} $result break
492
493                # The processing here is similar to what 'parray' does.
494                # I.e. finding the longest attribute name and then
495                # generating properly aligned output listing all attributes
496                # and their values.
497
498                set width 0
499                set sortedAttribs {}
500                foreach {type values} $attributes {
501                    if {[string length $type] > $width} {
502                   set width [string length $type]
503                    }
504                    lappend sortedAttribs [list $type $values]
505                }
506
507                puts "object='$object'"
508
509                foreach sortedAttrib  $sortedAttribs {
510                    foreach {type values} $sortedAttrib break
511                    foreach value $values {
512                   regsub -all "\[\x01-\x1f\]" $value ? value
513                   puts [format "  %-${width}s %s" $type $value]
514                    }
515                }
516                puts ""
517                  }
518                  ldap::unbind $handle
519                  ldap::disconnect $handle
520
521

BUGS, IDEAS, FEEDBACK

523       This document, and the package it describes, will  undoubtedly  contain
524       bugs  and  other  problems.  Please report such in the category ldap of
525       the  Tcllib  Trackers  [http://core.tcl.tk/tcllib/reportlist].   Please
526       also  report any ideas for enhancements you may have for either package
527       and/or documentation.
528
529       When proposing code changes, please provide unified diffs, i.e the out‐
530       put of diff -u.
531
532       Note  further  that  attachments  are  strongly  preferred over inlined
533       patches. Attachments can be made by going  to  the  Edit  form  of  the
534       ticket  immediately  after  its  creation, and then using the left-most
535       button in the secondary navigation bar.
536

KEYWORDS

538       directory access, internet, ldap, ldap client, protocol, rfc 2251,  rfc
539       4511, x.500
540

CATEGORY

542       Networking
543
545       Copyright (c) 2004 Andreas Kupries <andreas_kupries@users.sourceforge.net>
546       Copyright (c) 2004 Jochen Loewer <loewerj@web.de>
547       Copyright (c) 2006 Michael Schlenker <mic42@users.sourceforge.net>
548
549
550
551
552tcllib                               1.9.2                             ldap(n)
Impressum