]> source.dussan.org Git - archiva.git/blob
a4b27de15f51e270aef08da35a608561b55d8c3a
[archiva.git] /
1 package org.apache.archiva.web.startup;
2
3 /*
4  * Licensed to the Apache Software Foundation (ASF) under one
5  * or more contributor license agreements.  See the NOTICE file
6  * distributed with this work for additional information
7  * regarding copyright ownership.  The ASF licenses this file
8  * to you under the Apache License, Version 2.0 (the
9  * "License"); you may not use this file except in compliance
10  * with the License.  You may obtain a copy of the License at
11  *
12  *  http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing,
15  * software distributed under the License is distributed on an
16  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17  * KIND, either express or implied.  See the License for the
18  * specific language governing permissions and limitations
19  * under the License.
20  */
21
22 import org.apache.archiva.common.ArchivaException;
23 import org.apache.archiva.configuration.ArchivaConfiguration;
24 import org.apache.archiva.configuration.ConfigurationNames;
25 import org.apache.archiva.configuration.ManagedRepositoryConfiguration;
26 import org.apache.archiva.redback.rbac.RBACManager;
27 import org.apache.archiva.redback.role.RoleManagerException;
28 import org.apache.archiva.redback.system.check.EnvironmentCheck;
29 import org.apache.archiva.security.common.ArchivaRoleConstants;
30 import org.apache.commons.collections.CollectionUtils;
31 import org.apache.commons.lang.StringUtils;
32 import org.apache.archiva.redback.rbac.RbacManagerException;
33 import org.apache.archiva.redback.rbac.UserAssignment;
34 import org.apache.archiva.redback.role.RoleManager;
35 import org.apache.archiva.redback.users.UserManager;
36 import org.apache.archiva.redback.components.registry.RegistryListener;
37 import org.slf4j.Logger;
38 import org.slf4j.LoggerFactory;
39 import org.springframework.context.ApplicationContext;
40 import org.springframework.stereotype.Service;
41
42 import javax.annotation.PostConstruct;
43 import javax.inject.Inject;
44 import javax.inject.Named;
45 import java.util.ArrayList;
46 import java.util.HashMap;
47 import java.util.List;
48 import java.util.Map;
49 import java.util.Map.Entry;
50
51 /**
52  * ConfigurationSynchronization
53  *
54  *
55  */
56 @Service
57 public class SecuritySynchronization
58     implements RegistryListener
59 {
60     private Logger log = LoggerFactory.getLogger( SecuritySynchronization.class );
61
62     @Inject
63     private RoleManager roleManager;
64
65     @Inject
66     @Named( value = "rBACManager#cached" )
67     private RBACManager rbacManager;
68
69     private Map<String, EnvironmentCheck> checkers;
70
71     @Inject
72     private ArchivaConfiguration archivaConfiguration;
73
74     @Inject
75     private ApplicationContext applicationContext;
76
77     @PostConstruct
78     public void initialize()
79     {
80         checkers = getBeansOfType( EnvironmentCheck.class );
81     }
82
83     protected <T> Map<String, T> getBeansOfType( Class<T> clazz )
84     {
85         //TODO do some caching here !!!
86         // olamy : with plexus we get only roleHint
87         // as per convention we named spring bean role#hint remove role# if exists
88         Map<String, T> springBeans = applicationContext.getBeansOfType( clazz );
89
90         Map<String, T> beans = new HashMap<String, T>( springBeans.size() );
91
92         for ( Entry<String, T> entry : springBeans.entrySet() )
93         {
94             String key = StringUtils.substringAfterLast( entry.getKey(), "#" );
95             beans.put( key, entry.getValue() );
96         }
97         return beans;
98     }
99
100     public void afterConfigurationChange( org.apache.archiva.redback.components.registry.Registry registry, String propertyName, Object propertyValue )
101     {
102         if ( ConfigurationNames.isManagedRepositories( propertyName ) && propertyName.endsWith( ".id" ) )
103         {
104             if ( propertyValue != null )
105             {
106                 syncRepoConfiguration( (String) propertyValue );
107             }
108         }
109     }
110
111     public void beforeConfigurationChange( org.apache.archiva.redback.components.registry.Registry registry, String propertyName, Object propertyValue )
112     {
113         /* do nothing */
114     }
115
116     private void synchConfiguration( List<ManagedRepositoryConfiguration> repos )
117     {
118         // NOTE: Remote Repositories do not have roles or security placed around them.
119
120         for ( ManagedRepositoryConfiguration repoConfig : repos )
121         {
122             syncRepoConfiguration( repoConfig.getId() );
123         }
124     }
125
126     private void syncRepoConfiguration( String id )
127     {
128         // manage roles for repositories
129         try
130         {
131             if ( !roleManager.templatedRoleExists( ArchivaRoleConstants.TEMPLATE_REPOSITORY_OBSERVER, id ) )
132             {
133                 roleManager.createTemplatedRole( ArchivaRoleConstants.TEMPLATE_REPOSITORY_OBSERVER, id );
134             }
135             else
136             {
137                 roleManager.verifyTemplatedRole( ArchivaRoleConstants.TEMPLATE_REPOSITORY_OBSERVER, id );
138             }
139
140             if ( !roleManager.templatedRoleExists( ArchivaRoleConstants.TEMPLATE_REPOSITORY_MANAGER, id ) )
141             {
142                 roleManager.createTemplatedRole( ArchivaRoleConstants.TEMPLATE_REPOSITORY_MANAGER, id );
143             }
144             else
145             {
146                 roleManager.verifyTemplatedRole( ArchivaRoleConstants.TEMPLATE_REPOSITORY_MANAGER, id );
147             }
148         }
149         catch ( RoleManagerException e )
150         {
151             // Log error.
152             log.error( "Unable to create roles for configured repositories: " + e.getMessage(), e );
153         }
154     }
155
156     public void startup()
157         throws ArchivaException
158     {
159         executeEnvironmentChecks();
160
161         synchConfiguration( archivaConfiguration.getConfiguration().getManagedRepositories() );
162         archivaConfiguration.addChangeListener( this );
163
164         if ( archivaConfiguration.isDefaulted() )
165         {
166             assignRepositoryObserverToGuestUser( archivaConfiguration.getConfiguration().getManagedRepositories() );
167         }
168     }
169
170     private void executeEnvironmentChecks()
171         throws ArchivaException
172     {
173         if ( ( checkers == null ) || CollectionUtils.isEmpty( checkers.values() ) )
174         {
175             throw new ArchivaException(
176                 "Unable to initialize the Redback Security Environment, " + "no Environment Check components found." );
177         }
178
179         List<String> violations = new ArrayList<String>();
180
181         for ( Entry<String, EnvironmentCheck> entry : checkers.entrySet() )
182         {
183             EnvironmentCheck check = entry.getValue();
184             List<String> v = new ArrayList<String>();
185             check.validateEnvironment( v );
186             log.info( "Environment Check: " + entry.getKey() + " -> " + v.size() + " violation(s)" );
187             for ( String s : v )
188             {
189                 violations.add( "[" + entry.getKey() + "] " + s );
190             }
191         }
192
193         if ( CollectionUtils.isNotEmpty( violations ) )
194         {
195             StringBuilder msg = new StringBuilder();
196             msg.append( "EnvironmentCheck Failure.\n" );
197             msg.append( "======================================================================\n" );
198             msg.append( " ENVIRONMENT FAILURE !! \n" );
199             msg.append( "\n" );
200
201             for ( String violation : violations )
202             {
203                 msg.append( violation ).append( "\n" );
204             }
205
206             msg.append( "\n" );
207             msg.append( "======================================================================" );
208             log.error( msg.toString() );
209
210             throw new ArchivaException( "Unable to initialize Redback Security Environment, [" + violations.size()
211                                             + "] violation(s) encountered, See log for details." );
212         }
213     }
214
215     private void assignRepositoryObserverToGuestUser( List<ManagedRepositoryConfiguration> repos )
216     {
217         for ( ManagedRepositoryConfiguration repoConfig : repos )
218         {
219             String repoId = repoConfig.getId();
220
221             String principal = UserManager.GUEST_USERNAME;
222
223             try
224             {
225                 UserAssignment ua;
226
227                 if ( rbacManager.userAssignmentExists( principal ) )
228                 {
229                     ua = rbacManager.getUserAssignment( principal );
230                 }
231                 else
232                 {
233                     ua = rbacManager.createUserAssignment( principal );
234                 }
235
236                 ua.addRoleName( ArchivaRoleConstants.toRepositoryObserverRoleName( repoId ) );
237                 rbacManager.saveUserAssignment( ua );
238             }
239             catch ( RbacManagerException e )
240             {
241                 log.warn( "Unable to add role [" + ArchivaRoleConstants.toRepositoryObserverRoleName( repoId ) + "] to "
242                               + principal + " user.", e );
243             }
244         }
245     }
246 }