]> source.dussan.org Git - archiva.git/blob
097136d5af21f4d089edd40fff20d86b6e64dd83
[archiva.git] /
1 package org.apache.archiva.redback.rbac.ldap;
2 /*
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  * http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  */
20
21 import org.apache.archiva.redback.common.ldap.MappingException;
22 import org.apache.archiva.redback.common.ldap.connection.LdapConnection;
23 import org.apache.archiva.redback.common.ldap.connection.LdapConnectionFactory;
24 import org.apache.archiva.redback.common.ldap.connection.LdapException;
25 import org.apache.archiva.redback.configuration.UserConfiguration;
26 import org.apache.archiva.redback.configuration.UserConfigurationKeys;
27 import org.apache.commons.lang.StringUtils;
28 import org.slf4j.Logger;
29 import org.slf4j.LoggerFactory;
30 import org.springframework.stereotype.Service;
31
32 import javax.annotation.PostConstruct;
33 import javax.inject.Inject;
34 import javax.inject.Named;
35 import javax.naming.NamingEnumeration;
36 import javax.naming.NamingException;
37 import javax.naming.directory.Attribute;
38 import javax.naming.directory.DirContext;
39 import javax.naming.directory.SearchControls;
40 import javax.naming.directory.SearchResult;
41 import java.util.ArrayList;
42 import java.util.Collections;
43 import java.util.List;
44 import java.util.Map;
45
46 /**
47  * @author Olivier Lamy
48  * @since 2.1
49  */
50 @Service( "ldapRoleMapper#default" )
51 public class DefaultLdapRoleMapper
52     implements LdapRoleMapper
53 {
54
55     private Logger log = LoggerFactory.getLogger( getClass() );
56
57     @Inject
58     private LdapConnectionFactory ldapConnectionFactory;
59
60     @Inject
61     @Named( value = "userConfiguration#default" )
62     private UserConfiguration userConf;
63
64     //---------------------------
65     // fields
66     //---------------------------
67
68     private String ldapGroupClass = "groupOfUniqueNames";
69
70     private String groupsDn;
71
72     private String baseDn;
73
74     @PostConstruct
75     public void initialize()
76     {
77         this.ldapGroupClass = userConf.getString( UserConfigurationKeys.LDAP_GROUPS_CLASS, this.ldapGroupClass );
78
79         this.groupsDn = userConf.getString( UserConfigurationKeys.LDAP_GROUPS_BASEDN, this.groupsDn );
80
81         this.baseDn = userConf.getString( UserConfigurationKeys.LDAP_BASEDN, this.baseDn );
82     }
83
84     public String getLdapGroup( String role )
85     {
86         return userConf.getString( UserConfigurationKeys.LDAP_GROUPS_ROLE_START_KEY + role );
87     }
88
89     public List<String> getAllGroups()
90         throws MappingException
91     {
92         // TODO caching
93         LdapConnection ldapConnection = null;
94
95         NamingEnumeration<SearchResult> namingEnumeration = null;
96         try
97         {
98             ldapConnection = ldapConnectionFactory.getConnection();
99
100             DirContext context = ldapConnection.getDirContext();
101
102             SearchControls searchControls = new SearchControls();
103
104             searchControls.setDerefLinkFlag( true );
105             searchControls.setSearchScope( SearchControls.SUBTREE_SCOPE );
106
107             String filter = "objectClass=" + getLdapGroupClass();
108
109             namingEnumeration = context.search( getGroupsDn(), filter, searchControls );
110
111             List<String> allGroups = new ArrayList<String>();
112
113             while ( namingEnumeration.hasMore() )
114             {
115                 SearchResult searchResult = namingEnumeration.next();
116
117                 String groupName = searchResult.getName();
118                 // cn=blabla we only want bla bla
119                 groupName = StringUtils.substringAfter( groupName, "=" );
120
121                 log.debug( "found groupName: '{}", groupName );
122
123                 allGroups.add( groupName );
124
125             }
126
127             return allGroups;
128         }
129         catch ( LdapException e )
130         {
131             throw new MappingException( e.getMessage(), e );
132         }
133         catch ( NamingException e )
134         {
135             throw new MappingException( e.getMessage(), e );
136         }
137
138         finally
139         {
140             if ( ldapConnection != null )
141             {
142                 ldapConnection.close();
143             }
144             if ( namingEnumeration != null )
145             {
146                 try
147                 {
148                     namingEnumeration.close();
149                 }
150                 catch ( NamingException e )
151                 {
152                     log.warn( "failed to close search results", e );
153                 }
154             }
155         }
156     }
157
158     public List<String> getGroupsMember( String group )
159         throws MappingException
160     {
161         // TODO caching
162         LdapConnection ldapConnection = null;
163
164         NamingEnumeration<SearchResult> namingEnumeration = null;
165         try
166         {
167             ldapConnection = ldapConnectionFactory.getConnection();
168
169             DirContext context = ldapConnection.getDirContext();
170
171             SearchControls searchControls = new SearchControls();
172
173             searchControls.setDerefLinkFlag( true );
174             searchControls.setSearchScope( SearchControls.SUBTREE_SCOPE );
175
176             String filter = "objectClass=" + getLdapGroupClass();
177
178             namingEnumeration = context.search( "cn=" + group + "," + getGroupsDn(), filter, searchControls );
179
180             List<String> allMembers = new ArrayList<String>();
181
182             while ( namingEnumeration.hasMore() )
183             {
184                 SearchResult searchResult = namingEnumeration.next();
185
186                 Attribute uniqueMemberAttr = searchResult.getAttributes().get( "uniquemember" );
187
188                 if ( uniqueMemberAttr != null )
189                 {
190                     NamingEnumeration<String> allMembersEnum = (NamingEnumeration<String>) uniqueMemberAttr.getAll();
191                     while ( allMembersEnum.hasMore() )
192                     {
193                         String userName = allMembersEnum.next();
194                         // uid=blabla we only want bla bla
195                         userName = StringUtils.substringAfter( userName, "=" );
196                         userName = StringUtils.substringBefore( userName, "," );
197                         log.debug( "found userName for group {}: '{}", group, userName );
198
199                         allMembers.add( userName );
200                     }
201                     close( allMembersEnum );
202                 }
203
204
205             }
206
207             return allMembers;
208         }
209         catch ( LdapException e )
210         {
211             throw new MappingException( e.getMessage(), e );
212         }
213         catch ( NamingException e )
214         {
215             throw new MappingException( e.getMessage(), e );
216         }
217
218         finally
219         {
220             if ( ldapConnection != null )
221             {
222                 ldapConnection.close();
223             }
224             close( namingEnumeration );
225         }
226     }
227
228     public List<String> getGroups( String username )
229         throws MappingException
230     {
231         // TODO caching and a filter with uid
232
233         List<String> allGroups = getAllGroups();
234         List<String> userGroups = new ArrayList<String>();
235         for ( String group : allGroups )
236         {
237             List<String> users = getGroupsMember( group );
238             if ( users.contains( username ) )
239             {
240                 userGroups.add( group );
241             }
242         }
243         return userGroups;
244         /*
245         List<String> userGroups = new ArrayList<String>();
246
247         LdapConnection ldapConnection = null;
248
249         NamingEnumeration<SearchResult> namingEnumeration = null;
250         try
251         {
252             ldapConnection = ldapConnectionFactory.getConnection();
253
254             DirContext context = ldapConnection.getDirContext();
255
256             SearchControls searchControls = new SearchControls();
257
258             searchControls.setDerefLinkFlag( true );
259             searchControls.setSearchScope( SearchControls.SUBTREE_SCOPE );
260
261             //String filter =
262             //    "(&(objectClass=" + getLdapGroupClass() + ") (uniquemember=uid" + username + "," + this.getGroupsDn()
263             //        + "))";
264
265             String filter =
266                 new StringBuilder().append( "(&" ).append( "(objectClass=" + getLdapGroupClass() + ")" ).append(
267                     "(uniquemember=" ).append( "uid=" + username + "," + this.getBaseDn() ).append( ")" ).append(
268                     ")" ).toString();
269
270             namingEnumeration = context.search( getGroupsDn(), filter, searchControls );
271
272             List<String> allMembers = new ArrayList<String>();
273
274             while ( namingEnumeration.hasMore() )
275             {
276                 SearchResult searchResult = namingEnumeration.next();
277
278                 Attribute uniqueMemberAttr = searchResult.getAttributes().get( "uniquemember" );
279
280                 if ( uniqueMemberAttr != null )
281                 {
282                     NamingEnumeration<String> allMembersEnum = (NamingEnumeration<String>) uniqueMemberAttr.getAll();
283                     while ( allMembersEnum.hasMore() )
284                     {
285                         String userName = allMembersEnum.next();
286                         // uid=blabla we only want bla bla
287                         userName = StringUtils.substringAfter( userName, "=" );
288                         userName = StringUtils.substringBefore( userName, "," );
289                         //log.debug( "found group for username {}: '{}", group, userName );
290
291                         allMembers.add( userName );
292                     }
293                     close( allMembersEnum );
294                 }
295
296
297             }
298
299             return userGroups;
300         }
301         catch ( LdapException e )
302         {
303             throw new MappingException( e.getMessage(), e );
304         }
305         catch ( NamingException e )
306         {
307             throw new MappingException( e.getMessage(), e );
308         }
309
310         finally
311         {
312             if ( ldapConnection != null )
313             {
314                 ldapConnection.close();
315             }
316             close( namingEnumeration );
317         }
318         */
319     }
320
321     private void close( NamingEnumeration namingEnumeration )
322     {
323         if ( namingEnumeration != null )
324         {
325             try
326             {
327                 namingEnumeration.close();
328             }
329             catch ( NamingException e )
330             {
331                 log.warn( "fail to close namingEnumeration: {}", e.getMessage() );
332             }
333         }
334     }
335
336     public String getGroupsDn()
337     {
338         return this.groupsDn;
339     }
340
341     public String getLdapGroupClass()
342     {
343         return this.ldapGroupClass;
344     }
345
346     public void addLdapMapping( String role, String ldapGroup )
347     {
348         log.warn( "addLdapMapping not implemented" );
349     }
350
351     public void removeLdapMapping( String role )
352     {
353         log.warn( "removeLdapMapping not implemented" );
354     }
355
356     public Map<String, String> getLdapGroupMappings()
357     {
358         log.warn( "getLdapGroupMappings not implemented" );
359         return Collections.emptyMap();
360     }
361
362     //---------------------------------
363     // setters for unit tests
364     //---------------------------------
365
366
367     public void setGroupsDn( String groupsDn )
368     {
369         this.groupsDn = groupsDn;
370     }
371
372     public void setLdapGroupClass( String ldapGroupClass )
373     {
374         this.ldapGroupClass = ldapGroupClass;
375     }
376
377     public void setUserConf( UserConfiguration userConf )
378     {
379         this.userConf = userConf;
380     }
381
382     public void setLdapConnectionFactory( LdapConnectionFactory ldapConnectionFactory )
383     {
384         this.ldapConnectionFactory = ldapConnectionFactory;
385     }
386
387     public String getBaseDn()
388     {
389         return baseDn;
390     }
391
392     public void setBaseDn( String baseDn )
393     {
394         this.baseDn = baseDn;
395     }
396 }