RedmineLDAP » History » Version 28

Chris Clemson, 2021-01-14 11:24
Add FreeIPA 4.6.8 LDAP config

1 16 Perico Os Palotes
{{>toc}}
2 16 Perico Os Palotes
3 1 Jean-Philippe Lang
h1. LDAP Authentication
4 1 Jean-Philippe Lang
5 1 Jean-Philippe Lang
Redmine natively supports LDAP authentication using one or multiple LDAP directories.
6 1 Jean-Philippe Lang
7 1 Jean-Philippe Lang
h2. Declaring the LDAP
8 1 Jean-Philippe Lang
9 5 Eric Davis
Go to Administration and click *LDAP authentication* in the menu.
10 1 Jean-Philippe Lang
11 1 Jean-Philippe Lang
Enter the following:
12 1 Jean-Philippe Lang
13 1 Jean-Philippe Lang
* *Name*: an arbitrary name for the directory
14 1 Jean-Philippe Lang
* *Host*: the LDAP host name
15 1 Jean-Philippe Lang
* *Port*: the LDAP port (default is 389)
16 1 Jean-Philippe Lang
* *LDAPS*: check this if you want or need to use LDAPS to access the directory
17 9 T. Hauptman
* *Account*: enter a username that has read access to the LDAP , otherwise leave this field empty if your LDAP can be read anonymously (Active Directory servers generally do not allow anonymous access)
18 1 Jean-Philippe Lang
* *Password*: password for the account
19 1 Jean-Philippe Lang
* *Base DN*: the top level DN of your LDAP directory tree
20 1 Jean-Philippe Lang
* *Login attribute*: enter the name of the LDAP attribute that will be used as the Redmine username
21 1 Jean-Philippe Lang
22 2 Jean-Philippe Lang
Redmine users should now be able to authenticate using their LDAP username and password if their accounts are set to use the LDAP for authentication.
23 3 Jean-Philippe Lang
24 22 Mikhail Voronyuk
To test this, create a Redmine user with a login that matches his LDAP account (normally, Redmine will advise you by looking up the LDAP data), select the newly created LDAP in the *Authentication mode* drop-down list (this field is visible on the account screen only if a LDAP is declared) and leave his password empty. Try to log in into Redmine using the LDAP username and password.
25 1 Jean-Philippe Lang
26 1 Jean-Philippe Lang
h2. On the fly user creation
27 1 Jean-Philippe Lang
28 1 Jean-Philippe Lang
By checking *on-the-fly user creation*, any LDAP user will have his Redmine account automatically created the first time he logs into Redmine.
29 1 Jean-Philippe Lang
For that, you have to specify the LDAP attributes name (firstname, lastname, email) that will be used to create their Redmine accounts.
30 1 Jean-Philippe Lang
31 1 Jean-Philippe Lang
Here is an typical example using Active Directory:
32 1 Jean-Philippe Lang
33 1 Jean-Philippe Lang
<pre>
34 1 Jean-Philippe Lang
Name     = My Directory
35 1 Jean-Philippe Lang
Host     = host.domain.org
36 1 Jean-Philippe Lang
Port     = 389
37 1 Jean-Philippe Lang
LDAPS    = no
38 7 John Dell
Account  = MyDomain\UserName (or UserName@MyDomain depending on AD server)
39 1 Jean-Philippe Lang
Password = <password>
40 1 Jean-Philippe Lang
Base DN  = CN=users,DC=host,DC=domain,DC=org
41 9 T. Hauptman
42 9 T. Hauptman
On-the-fly user creation = yes
43 9 T. Hauptman
Attributes
44 9 T. Hauptman
  Login     = sAMAccountName
45 9 T. Hauptman
  Firstname = givenName
46 9 T. Hauptman
  Lastname  = sN
47 9 T. Hauptman
  Email     = mail
48 9 T. Hauptman
</pre>
49 9 T. Hauptman
50 9 T. Hauptman
Here is another example for Active Directory with a compartmentalized intranet:
51 9 T. Hauptman
52 9 T. Hauptman
<pre>
53 9 T. Hauptman
Name     = Just a description for the auth modes page
54 9 T. Hauptman
Host     = DepartmentName.OrganizationName.local
55 9 T. Hauptman
Port     = 389
56 9 T. Hauptman
LDAPS    = no
57 13 mouson chen
Account  = DepartmentName\UserName (or UserName@MyDomain depending on AD server or bind DN uid=Manager,cn=users,dc=MyDomain,dc=com)
58 9 T. Hauptman
Password = <password>
59 9 T. Hauptman
Base DN  = DC=DepartmentName,DC=OrganizationName,DC=local
60 1 Jean-Philippe Lang
61 1 Jean-Philippe Lang
On-the-fly user creation = yes
62 1 Jean-Philippe Lang
Attributes
63 1 Jean-Philippe Lang
  Login     = sAMAccountName
64 1 Jean-Philippe Lang
  Firstname = givenName
65 1 Jean-Philippe Lang
  Lastname  = sN
66 1 Jean-Philippe Lang
  Email     = mail
67 1 Jean-Philippe Lang
</pre>
68 1 Jean-Philippe Lang
69 1 Jean-Philippe Lang
Note that LDAP attribute names are *case sensitive*.
70 22 Mikhail Voronyuk
 
71 14 Alexander Menk
h3. Dynamic Bind Account 
72 14 Alexander Menk
73 21 Stanislav German-Evtushenko
The above setup would need a special account on the directory server which Redmine uses to pre-authenticate. It is possible to use the keyword *$login* in the account field which then would be replaced by the current login. The password can be left empty in this case, for example: <pre>Account: $login@COMPANY.DOMAIN.NAME</pre> or <pre>Account: company\$login</pre>
74 14 Alexander Menk
75 6 Chris Rose
h3. Base DN variants
76 6 Chris Rose
77 6 Chris Rose
Although it's quite possible that the Base DN above is standard for Active Directory, the Active Directory at my employer's site does not use the Users container for standard users, so those instructions sent me down a long and painful path.  I recommend also trying just "DC=host,DC=domain,DC=org" if login fail swith the settings there.
78 1 Jean-Philippe Lang
79 16 Perico Os Palotes
h2. Group based LDAP login
80 16 Perico Os Palotes
81 16 Perico Os Palotes
If you want to just allow logins to users that belongs to a particular LDAP group you should follow below instructions. They are based on OpenLDAP LDAP server and redmine 2.3.0.
82 16 Perico Os Palotes
83 16 Perico Os Palotes
1. (OpenLDAP server) Enable memberof overlay
84 16 Perico Os Palotes
85 16 Perico Os Palotes
1.1. Create a file:
86 16 Perico Os Palotes
87 16 Perico Os Palotes
>vim ~/memberof_add.ldif
88 16 Perico Os Palotes
89 16 Perico Os Palotes
With below content:
90 16 Perico Os Palotes
91 16 Perico Os Palotes
>dn: cn=module,cn=config
92 16 Perico Os Palotes
>objectClass: olcModuleList
93 16 Perico Os Palotes
>cn: module
94 16 Perico Os Palotes
>olcModulePath: /usr/lib/ldap
95 16 Perico Os Palotes
>olcModuleLoad: memberof
96 16 Perico Os Palotes
97 16 Perico Os Palotes
1.2. Create a file:
98 16 Perico Os Palotes
99 16 Perico Os Palotes
>vim ~/memberof_config.ldif
100 16 Perico Os Palotes
101 16 Perico Os Palotes
With below content:
102 16 Perico Os Palotes
103 16 Perico Os Palotes
>dn: olcOverlay=memberof,olcDatabase={1}hdb,cn=config
104 16 Perico Os Palotes
>objectClass: olcMemberOf
105 16 Perico Os Palotes
>objectClass: olcOverlayConfig
106 16 Perico Os Palotes
>objectClass: olcConfig
107 16 Perico Os Palotes
>objectClass: top
108 16 Perico Os Palotes
>olcOverlay: memberof
109 16 Perico Os Palotes
>olcMemberOfDangling: ignore
110 16 Perico Os Palotes
>olcMemberOfRefInt: TRUE
111 16 Perico Os Palotes
>olcMemberOfGroupOC: groupOfNames
112 16 Perico Os Palotes
>olcMemberOfMemberAD: member
113 16 Perico Os Palotes
>olcMemberOfMemberOfAD: memberOf
114 16 Perico Os Palotes
115 16 Perico Os Palotes
1.3. Load them. It will depend on your OpenLDAP configuration, so we will propose some possibilities:
116 16 Perico Os Palotes
117 16 Perico Os Palotes
>sudo ldapadd -c -Y EXTERNAL -H ldapi:/// -f memberof_add.ldif
118 16 Perico Os Palotes
>sudo ldapadd -c -Y EXTERNAL -H ldapi:/// -f memberof_config.ldif
119 16 Perico Os Palotes
120 16 Perico Os Palotes
Or:
121 16 Perico Os Palotes
122 16 Perico Os Palotes
>ldapadd -D cn=admin,cn=config -w "password" -H ldapi:/// -f memberof_add.ldif
123 16 Perico Os Palotes
>ldapadd -D cn=admin,cn=config -w "password" -H ldapi:/// -f memberof_config.ldif
124 16 Perico Os Palotes
125 16 Perico Os Palotes
A restart is NOT needed if you use dynamic runtime configuration engine (slapd-config).
126 16 Perico Os Palotes
127 16 Perico Os Palotes
1.4. (Optional) Test it:
128 16 Perico Os Palotes
129 16 Perico Os Palotes
>ldapsearch -D cn=admin,dc=example,dc=com -x -W -b 'dc=example,dc=com' -H 'ldap://127.0.0.1:389/' '(&(objectClass=posixAccount)(memberOf=cn=ldapredmine,ou=groups,dc=example,dc=com))'
130 16 Perico Os Palotes
131 16 Perico Os Palotes
2. (OpenLDAP server) Create the group. In this example the user is "ldap_user_1" and the group is "ldapredmine":
132 16 Perico Os Palotes
133 16 Perico Os Palotes
>dn: cn=ldapredmine,ou=groups,dc=example,dc=com
134 16 Perico Os Palotes
>cn: ldapredmine
135 16 Perico Os Palotes
>description: Staff members allowed to login to redmine ticketing system
136 16 Perico Os Palotes
>member: cn=ldap_user_1,ou=people,dc=example,dc=com
137 16 Perico Os Palotes
>objectclass: groupOfNames
138 16 Perico Os Palotes
>objectclass: top
139 16 Perico Os Palotes
140 16 Perico Os Palotes
Adjust "dn" and "cn"s to fit to your DIT structure
141 16 Perico Os Palotes
142 16 Perico Os Palotes
3. (Redmine) Edit the LDAP authentication mode. In my case "ldap_user_1" is a "posixAccount" objectclass:
143 16 Perico Os Palotes
144 16 Perico Os Palotes
>Base DN: dc=example,dc=com
145 16 Perico Os Palotes
>Filter: (&(objectClass=posixAccount)(memberOf=cn=ldapredmine,ou=groups,dc=example,dc=com))
146 6 Chris Rose
147 1 Jean-Philippe Lang
h2. Troubleshooting
148 1 Jean-Philippe Lang
149 4 Jean-Philippe Lang
If you want to use on-the-fly user creation, make sure that Redmine can fetch from your LDAP all the required information to create a valid user.
150 4 Jean-Philippe Lang
For example, on-the-fly user creation won't work if you don't have valid email adresses in your directory (you will get an 'Invalid username/password' error message when trying to log in).
151 6 Chris Rose
(This is not true with newer Redmine versions; the user creation dialog is populated with everything it can find from the LDAP server, and asks the new user to fill in the rest.)
152 4 Jean-Philippe Lang
153 4 Jean-Philippe Lang
Also, make sure you don't have any custom field marked as *required* for user accounts. These custom fields would prevent user accounts from being created on the fly.
154 6 Chris Rose
155 1 Jean-Philippe Lang
Errors in the login system are not reported with any real information in the Redmine logs, which makes troubleshooting difficult.  However, you can found most of the information you need using ??Wireshark?? between your Redmine host and the LDAP server. Note that this only works if you have permissions to read network traffic between those two hosts.
156 15 Wiebe Cazemier
157 15 Wiebe Cazemier
You can also use the tool 'ldapsearch' to test if your settings are correct. Log into the Linux machine hosting your redmine (and possibly install ldaputils) and run this:
158 15 Wiebe Cazemier
159 15 Wiebe Cazemier
    ldapsearch -x -b  "dc=example,dc=com" -H ldap://hostname/ -D "DOMAIN\USER" -w mypassword [searchterm]
160 15 Wiebe Cazemier
161 15 Wiebe Cazemier
If succesful, you will get a listing of the contents of the AD, matching your search query. Then, you will know what how to fill out the fields in the LDAP config in Redmine.
162 12 Etienne Massip
163 12 Etienne Massip
164 12 Etienne Massip
h3. ??Account?? value format
165 12 Etienne Massip
166 12 Etienne Massip
The username for the bind credentials might need to be specified as a DN(i.e. CN=user,OU=optional,DC=domain,DC=com) rather than as a UPN(user@domain.com) or as ??domain\user??, as pointed out by this comment in source:trunk/vendor/plugins/ruby-net-ldap-0.0.4/lib/net/ldap.rb:
167 11 John Lewin
<pre>
168 11 John Lewin
  # As described under #bind, most LDAP servers require that you supply a complete DN
169 1 Jean-Philippe Lang
  # as a binding-credential, along with an authenticator such as a password.
170 1 Jean-Philippe Lang
</pre>
171 22 Mikhail Voronyuk
Therefore user with MyDomain\MyUserName or MyUserName@MyDomain.com username might enter only MyUserName as a Redmine login name.
172 22 Mikhail Voronyuk
173 22 Mikhail Voronyuk
h3. Slow LDAP authentification
174 22 Mikhail Voronyuk
175 22 Mikhail Voronyuk
If LDAP authentification is slow and you have an AD cluster, try to specify in Host field one of the AD physical servers (http://www.redmine.org/boards/2/topics/3056). It may help.
176 8 Oli Kessler
177 8 Oli Kessler
h3. OpenDS 
178 8 Oli Kessler
179 8 Oli Kessler
If you are using the OpenDS server, you might have issues with the request control "Paged results" sent with the initial query searching for the user by the specified login attribute. This request control 1.2.840.113556.1.4.319 is not allowed for anonymous users by default, thus preventing redmine from finding the user in the directory even before the binding takes place.
180 8 Oli Kessler
181 8 Oli Kessler
Add a global ACI like this
182 8 Oli Kessler
<pre>
183 8 Oli Kessler
./dsconfig -h SERVER_IP -p 4444 -D cn="Directory Manager" -w PASSWORD -n set-access-control-handler-prop --trustAll 
184 8 Oli Kessler
--add global-aci:\(targetcontrol=\"1.2.840.113556.1.4.319\"\)\ \(version\ 3.0\;\ acl\ 
185 8 Oli Kessler
\"Anonymous\ control\ access\ to\ 1.2.840.113556.1.4.319\"\;\ allow\ \(read\)\ userdn=\"ldap:///anyone\"\;\)
186 8 Oli Kessler
</pre>Note: Enter the command on one line, use the escaping exactly as indicated (the \ after "acl" is meant to be "\ " for a space).
187 17 Axel Pospischil
188 17 Axel Pospischil
h2.  Solutions:
189 17 Axel Pospischil
190 17 Axel Pospischil
h3. Zentyal 3.2, Redmine 2.3.x
191 17 Axel Pospischil
192 17 Axel Pospischil
I successfully updated and (re)setup my Zentyal 3.2 on an Ubuntu 12.04 LTS server.
193 17 Axel Pospischil
194 17 Axel Pospischil
Because this really drove me nuts after an update to Zentyal 3.2 and Redmine 2.3, I like to make the story short and share this simple solution with you:
195 17 Axel Pospischil
196 17 Axel Pospischil
* https://wiki.blue-it.org/Zentyal#LDAP
197 18 Axel Pospischil
198 18 Axel Pospischil
Using zentyals readonly credentials:
199 19 Axel Pospischil
<pre>> Basedomain (Base DN):  dc=your_domain,dc=your_tld
200 19 Axel Pospischil
  Rootdomain (Root DN):  cn=zentyal,dc=your_domain,dc=your_tld
201 19 Axel Pospischil
  Password:              <admin_secret_pass>
202 19 Axel Pospischil
> Read-only root DN:     cn=zentyalro,dc=your_domain,dc=your_tld
203 19 Axel Pospischil
> Read-only password:    <ro_secret_pass>
204 19 Axel Pospischil
  Default Users DN:      ou=Users,dc=your_domain,dc=your_tld
205 19 Axel Pospischil
  Default Groups DN:     ou=Groups,dc=your_domain,dc=your_tld
206 18 Axel Pospischil
</pre> 
207 18 Axel Pospischil
208 18 Axel Pospischil
And in Redmine (use the credentials above, without <>) and be aware of the changed LDAP port 390 (read the article above):
209 18 Axel Pospischil
<pre>
210 18 Axel Pospischil
Name     = Just a description for the auth modes page
211 19 Axel Pospischil
> Host     = <IP of the host>
212 19 Axel Pospischil
> Port     = <390>
213 19 Axel Pospischil
  LDAPS    = no
214 19 Axel Pospischil
> Account  = <Read-only root DN>
215 19 Axel Pospischil
> Password = <ro_secret_pass>
216 19 Axel Pospischil
> Base DN  = <Basedomain (Base DN)>
217 18 Axel Pospischil
218 18 Axel Pospischil
On-the-fly user creation = yes
219 18 Axel Pospischil
Attributes
220 19 Axel Pospischil
>  Login     = uid
221 19 Axel Pospischil
   Firstname = givenName
222 19 Axel Pospischil
>  Lastname  = sN
223 18 Axel Pospischil
  Email     = mail
224 18 Axel Pospischil
</pre>
225 23 [ Desperados ]
226 23 [ Desperados ]
h3. Zentyal 4.x, Redmine 3.3.x
227 23 [ Desperados ]
228 23 [ Desperados ]
Use port 389 and sAMAccountName instead of uid
229 24 Dhia Eddine
230 24 Dhia Eddine
h3. Zentyal 5.0, Redmine 3.2
231 24 Dhia Eddine
232 24 Dhia Eddine
<pre>
233 25 Dhia Eddine
  Name     = Just a description for the auth modes page
234 24 Dhia Eddine
  Host     = <IP of the host>
235 24 Dhia Eddine
  Port     = <389>
236 25 Dhia Eddine
  LDAPS    = no (yes/checked is ok too with Port set to 636)
237 24 Dhia Eddine
  Account  = username@domain.tld
238 24 Dhia Eddine
  Password = <username_pass>
239 24 Dhia Eddine
  Base DN  = < Default Users DN > (cn=Users,dc=domain,dc=tld)   
240 24 Dhia Eddine
241 24 Dhia Eddine
On-the-fly user creation = yes
242 24 Dhia Eddine
Attributes
243 24 Dhia Eddine
   Login     = sAMAccountName
244 24 Dhia Eddine
   Firstname = givenName
245 24 Dhia Eddine
   Lastname  = sN
246 24 Dhia Eddine
   Email     = mail
247 24 Dhia Eddine
</pre>
248 26 frnk snck
249 26 frnk snck
h3. OpenLDAP, Redmine 3.4.2.stable
250 28 Chris Clemson
251 26 frnk snck
<pre>
252 26 frnk snck
  Name     = Some random description
253 26 frnk snck
  Host     = <IP of the host>
254 26 frnk snck
  Port     = <389>
255 26 frnk snck
  LDAPS    = no
256 26 frnk snck
  Account  = < Admins DN > (cn=admin,dc=domain,dc=tld)
257 26 frnk snck
  Password = < Admins Pass >
258 26 frnk snck
  Base DN  = < Default Users DN > (cn=People,dc=domain,dc=tld)   
259 26 frnk snck
260 26 frnk snck
On-the-fly user creation = yes
261 26 frnk snck
Attributes
262 27 frnk snck
   Login     = uid
263 26 frnk snck
   Firstname = givenName
264 26 frnk snck
   Lastname  = sn
265 26 frnk snck
   Email     = mail
266 26 frnk snck
</pre>
267 26 frnk snck
268 27 frnk snck
The admin account may be any other LDAP account with global read permission. The "domain" and "tld" part has to fit the LDAP setup, as everything else. Login attribute is used for login. The rest has to be according to LDAP setup.
269 28 Chris Clemson
270 28 Chris Clemson
h3. FreeIPA 4.6.8, Redmine 3.2.6
271 28 Chris Clemson
272 28 Chris Clemson
<pre>
273 28 Chris Clemson
  Name     = Service Description or server name etc.
274 28 Chris Clemson
  Host     = <IP/domain of the host>
275 28 Chris Clemson
  Port     = <389>
276 28 Chris Clemson
  LDAPS    = no ("yes" not tested)
277 28 Chris Clemson
  Account  = uid=<bind username>,cn=users,cn=accounts,dc=<domain>,dc=<tld>
278 28 Chris Clemson
  Password = <bind password>
279 28 Chris Clemson
  Base DN   = cn=accounts,dc=<domain>,dc=<tld>
280 28 Chris Clemson
281 28 Chris Clemson
Attributes
282 28 Chris Clemson
   Login     = uid
283 28 Chris Clemson
   Firstname = givenName
284 28 Chris Clemson
   Lastname  = sn
285 28 Chris Clemson
   Email     = mail
286 28 Chris Clemson
</pre>
287 28 Chris Clemson
288 28 Chris Clemson
The "domain" and "tld" part has to fit the LDAP setup, as everything else. uid attribute is used for login.