From: Olivier Lamy Date: Fri, 9 Dec 2011 00:29:35 +0000 (+0000) Subject: make archiva-webapp-js/ started with tomcat:run X-Git-Tag: archiva-1.4-M2~47 X-Git-Url: https://source.dussan.org/?a=commitdiff_plain;h=b7c003acb6b2c2a930443c511cb087d2776b4891;p=archiva.git make archiva-webapp-js/ started with tomcat:run git-svn-id: https://svn.apache.org/repos/asf/archiva/trunk@1212197 13f79535-47bb-0310-9956-ffa450edef68 --- diff --git a/.gitignore b/.gitignore index 12aa07fa0..3f91650c9 100644 --- a/.gitignore +++ b/.gitignore @@ -12,6 +12,9 @@ archiva-modules/archiva-web/archiva-webapp/src/main/webapp/WEB-INF/classes/ archiva-modules/archiva-web/archiva-webapp/src/main/webapp/WEB-INF/jsp/redback/ archiva-modules/archiva-web/archiva-webapp/src/main/webapp/WEB-INF/lib/ archiva-modules/archiva-web/archiva-webapp-test/cargo-installs/ + +archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/WEB-INF/classes/ + *.ipr *.iws .DS_Store diff --git a/archiva-modules/archiva-web/archiva-webapp-js/pom.xml b/archiva-modules/archiva-web/archiva-webapp-js/pom.xml index 01efe76fc..7a0e557d5 100644 --- a/archiva-modules/archiva-web/archiva-webapp-js/pom.xml +++ b/archiva-modules/archiva-web/archiva-webapp-js/pom.xml @@ -14,11 +14,12 @@ ~ See the License for the specific language governing permissions and ~ limitations under the License. --> - + 4.0.0 org.apache.archiva - archiva-modules + archiva-web 1.4-M2-SNAPSHOT archiva-webapp-js @@ -27,4 +28,572 @@ Archiva Web :: Javascript Application + + ${basedir}/src/test/tomcat/tomcat-context.xml + + + + + org.apache.archiva + generic-metadata-support + + + org.apache.archiva + npanday-support + + + org.apache.archiva + repository-statistics + + + org.apache.archiva + problem-reports + + + org.apache.archiva + audit + + + org.apache.archiva + archiva-scheduler-repository + + + org.apache.archiva + archiva-indexer + + + + org.apache.archiva + archiva-repository-admin-api + + + + + org.apache.archiva + archiva-repository-admin-default + + + + org.apache.archiva + metadata-repository-api + + + org.apache.archiva + metadata-store-jcr + runtime + + + org.apache.jackrabbit + jackrabbit-core + + + commons-logging + commons-logging + + + + + + org.apache.velocity + velocity + + + org.apache.velocity + velocity-tools + 1.3 + runtime + + + commons-logging + commons-logging + + + velocity + velocity-dep + + + velocity + velocity + + + struts + struts + + + + + org.apache.archiva + + maven2-repository + + + + org.codehaus.plexus + plexus-slf4j-logging + runtime + + + org.codehaus.plexus + plexus-component-api + + + + + org.codehaus.plexus + plexus-utils + + + org.apache.maven.indexer + indexer-core + + + org.codehaus.plexus + plexus-container-default + + + classworlds + classworlds + + + commons-logging + commons-logging + + + velocity + velocity-dep + + + org.apache.maven + maven-plugin-registry + + + org.apache.maven + maven-settings + + + com.google.code.atinject + atinject + + + + + org.apache.archiva + archiva-proxy + + + org.apache.archiva + archiva-repository-layer + + + org.apache.archiva + archiva-xml-tools + + + xerces + xercesImpl + + + + + org.apache.archiva + archiva-security + + + org.apache.archiva + archiva-core-consumers + + + org.apache.archiva + archiva-configuration + + + + org.apache.archiva + archiva-metadata-consumer + runtime + + + org.apache.archiva + archiva-lucene-consumers + + + org.apache.archiva + stage-repository-merge + + + org.apache.archiva + archiva-signature-consumers + + + org.apache.archiva + archiva-applet + + provided + + + org.apache.archiva + archiva-rss + + + org.apache.archiva + archiva-xmlrpc-api + + + org.apache.archiva + archiva-xmlrpc-services + + + org.apache.archiva + archiva-xmlrpc-security + + + + org.codehaus.redback + redback-xmlrpc-services + runtime + + + org.codehaus.redback + redback-xmlrpc-security + runtime + + + + + org.apache.archiva + archiva-rest-services + + + org.eclipse.jetty + jetty-server + + + org.eclipse.jetty + jetty-continuation + + + org.eclipse.jetty + jetty-http + + + org.eclipse.jetty + jetty-io + + + org.eclipse.jetty + jetty-util + + + org.eclipse.jetty + jetty-security + + + commons-logging + commons-logging + + + org.apache.geronimo.specs + geronimo-servlet_3.0_spec + + + org.apache.geronimo.specs + geronimo-javamail_1.4_spec + + + org.apache.geronimo.specs + geronimo-servlet_2.5_spec + + + + + org.apache.archiva + archiva-rest-api + + + org.eclipse.jetty + jetty-server + + + org.eclipse.jetty + jetty-continuation + + + org.eclipse.jetty + jetty-http + + + org.eclipse.jetty + jetty-io + + + org.eclipse.jetty + jetty-util + + + org.eclipse.jetty + jetty-security + + + commons-logging + commons-logging + + + org.apache.geronimo.specs + geronimo-servlet_3.0_spec + + + org.apache.geronimo.specs + geronimo-javamail_1.4_spec + + + org.apache.geronimo.specs + geronimo-servlet_2.5_spec + + + + + javax.servlet + servlet-api + provided + + + + org.apache.archiva + archiva-webdav + + + + jpox + jpox + + + javax.transaction + jta + + + + + jpox + jpox-ehcache + + + commons-logging + commons-logging + + + ehcache + ehcache + + + + + + org.codehaus.redback + redback-rest-services + + + org.codehaus.redback + redback-common-integrations + + + stax + stax-api + + + + + org.codehaus.redback + redback-integrations-security + + + org.slf4j + slf4j-log4j12 + runtime + + + org.slf4j + jcl-over-slf4j + runtime + + + org.apache.cxf + cxf-bundle-jaxrs + + + org.eclipse.jetty + jetty-server + + + org.apache.geronimo.specs + geronimo-servlet_2.5_spec + + + org.apache.geronimo.specs + geronimo-javamail_1.4_spec + + + + + org.springframework + spring-core + + + org.springframework + spring-web + + + javax.servlet + servlet-api + provided + + + + + + + + src/main/resources + + + src/main/filtered-resources + true + + + + + + + org.codehaus.mojo + tomcat-maven-plugin + + 9091 + /archiva + ${tomcatContextXml} + + ${project.build.directory}/appserver-base + ${project.build.directory}/appserver-base + ${project.build.directory}/appserver-home + ${project.build.directory}/appserver-base/logs + ${basedir}/target/auto-admin-creation.properties + ${project.build.directory} + + + + + org.apache.derby + derby + ${derbyVersion} + + + javax.mail + mail + ${javaxMailVersion} + + + + + + + + + + dev + + + + maven-antrun-plugin + + + override-log4j-with-console-output + process-resources + + run + + + + + + + + + + + + + + + + tdev + + + + org.apache.tomcat.maven + tomcat6-maven-plugin + + 9090 + / + ${tomcatContextXml} + + ${project.build.directory}/appserver-base + ${project.build.directory}/appserver-base + ${project.build.directory}/appserver-home + ${project.build.directory}/appserver-base/logs + ${basedir}/target/auto-admin-creation.properties + + ${project.build.directory} + + + + + org.apache.derby + derby + ${derbyVersion} + + + javax.mail + mail + 1.4 + + + + + org.apache.tomcat.maven + tomcat7-maven-plugin + 2.0-SNAPSHOT + + 9090 + / + ${tomcatContextXml} + + ${project.build.directory}/appserver-base + ${project.build.directory}/appserver-base + ${project.build.directory}/appserver-home + ${project.build.directory}/appserver-base/logs + ${basedir}/target/auto-admin-creation.properties + + ${project.build.directory} + + + + + org.apache.derby + derby + ${derbyVersion} + + + javax.mail + mail + 1.4 + + + + + + + + diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/filtered-resources/application.properties b/archiva-modules/archiva-web/archiva-webapp-js/src/main/filtered-resources/application.properties new file mode 100644 index 000000000..12806aa73 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/filtered-resources/application.properties @@ -0,0 +1,22 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. +# +user.agent=Apache Archiva/${project.version} +archiva.version=${project.version} +archiva.buildNumber=${buildNumber} +archiva.timestamp=${timestamp} diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/spring/RepositoryListenerFactoryBean.java b/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/spring/RepositoryListenerFactoryBean.java new file mode 100644 index 000000000..582290284 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/spring/RepositoryListenerFactoryBean.java @@ -0,0 +1,64 @@ +package org.apache.archiva.web.spring; + +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import org.apache.archiva.repository.events.RepositoryListener; +import org.springframework.beans.BeansException; +import org.springframework.beans.factory.FactoryBean; +import org.springframework.context.ApplicationContext; +import org.springframework.context.ApplicationContextAware; + +import java.util.List; + +/** + * @todo though we will eventually remove this altogether, an interim cleanup would be to genericise this + * and replace the calls in RepositoryContentConsumers with calls to the same thing + */ +public class RepositoryListenerFactoryBean + implements FactoryBean, ApplicationContextAware +{ + + private ApplicationContext applicationContext; + + public void setApplicationContext( ApplicationContext applicationContext ) + throws BeansException + { + this.applicationContext = applicationContext; + } + + public Object getObject() + throws Exception + { + return applicationContext.getBeansOfType( RepositoryListener.class ).values(); + } + + @SuppressWarnings("unchecked") + public Class getObjectType() + { + return List.class; + } + + public boolean isSingleton() + { + return true; + } + + +} diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/startup/ArchivaStartup.java b/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/startup/ArchivaStartup.java new file mode 100644 index 000000000..46aca0bb7 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/startup/ArchivaStartup.java @@ -0,0 +1,208 @@ +package org.apache.archiva.web.startup; + +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import org.apache.archiva.common.ArchivaException; +import org.apache.archiva.common.plexusbridge.PlexusSisuBridge; +import org.apache.archiva.common.plexusbridge.PlexusSisuBridgeException; +import org.apache.archiva.scheduler.repository.RepositoryArchivaTaskScheduler; +import org.apache.maven.index.NexusIndexer; +import org.apache.maven.index.context.IndexingContext; +import org.codehaus.plexus.taskqueue.Task; +import org.codehaus.plexus.taskqueue.execution.ThreadedTaskQueueExecutor; +import org.codehaus.redback.components.scheduler.DefaultScheduler; +import org.quartz.SchedulerException; +import org.springframework.web.context.WebApplicationContext; +import org.springframework.web.context.support.WebApplicationContextUtils; + +import javax.servlet.ServletContextEvent; +import javax.servlet.ServletContextListener; +import java.lang.reflect.Field; +import java.util.Properties; +import java.util.concurrent.ExecutorService; + +/** + * ArchivaStartup - the startup of all archiva features in a deterministic order. + * + * @version $Id$ + */ +public class ArchivaStartup + implements ServletContextListener +{ + private ThreadedTaskQueueExecutor tqeDbScanning; + + private ThreadedTaskQueueExecutor tqeRepoScanning; + + private ThreadedTaskQueueExecutor tqeIndexing; + + private RepositoryArchivaTaskScheduler repositoryTaskScheduler; + + private PlexusSisuBridge plexusSisuBridge; + + private NexusIndexer nexusIndexer; + + public void contextInitialized( ServletContextEvent contextEvent ) + { + WebApplicationContext wac = + WebApplicationContextUtils.getRequiredWebApplicationContext( contextEvent.getServletContext() ); + + SecuritySynchronization securitySync = wac.getBean( SecuritySynchronization.class ); + + repositoryTaskScheduler = + wac.getBean( "archivaTaskScheduler#repository", RepositoryArchivaTaskScheduler.class ); + + Properties archivaRuntimeProperties = wac.getBean( "archivaRuntimeProperties", Properties.class ); + + tqeRepoScanning = wac.getBean( "taskQueueExecutor#repository-scanning", ThreadedTaskQueueExecutor.class ); + + tqeIndexing = wac.getBean( "taskQueueExecutor#indexing", ThreadedTaskQueueExecutor.class ); + + plexusSisuBridge = wac.getBean( PlexusSisuBridge.class ); + + try + { + nexusIndexer = plexusSisuBridge.lookup( NexusIndexer.class ); + } + catch ( PlexusSisuBridgeException e ) + { + throw new RuntimeException( "Unable to get NexusIndexer: " + e.getMessage(), e ); + } + try + { + securitySync.startup(); + repositoryTaskScheduler.startup(); + Banner.display( (String) archivaRuntimeProperties.get( "archiva.version" ) ); + } + catch ( ArchivaException e ) + { + throw new RuntimeException( "Unable to properly startup archiva: " + e.getMessage(), e ); + } + } + + public void contextDestroyed( ServletContextEvent contextEvent ) + { + WebApplicationContext applicationContext = + WebApplicationContextUtils.getRequiredWebApplicationContext( contextEvent.getServletContext() ); + + // TODO check this stop + + /* + if ( applicationContext != null && applicationContext instanceof ClassPathXmlApplicationContext ) + { + ( (ClassPathXmlApplicationContext) applicationContext ).close(); + } */ + + if ( applicationContext != null ) //&& applicationContext instanceof PlexusWebApplicationContext ) + { + // stop task queue executors + stopTaskQueueExecutor( tqeDbScanning ); + stopTaskQueueExecutor( tqeRepoScanning ); + stopTaskQueueExecutor( tqeIndexing ); + + // stop the DefaultArchivaTaskScheduler and its scheduler + if ( repositoryTaskScheduler != null ) + { + try + { + repositoryTaskScheduler.stop(); + } + catch ( SchedulerException e ) + { + e.printStackTrace(); + } + + try + { + // shutdown the scheduler, otherwise Quartz scheduler and Threads still exists + Field schedulerField = repositoryTaskScheduler.getClass().getDeclaredField( "scheduler" ); + schedulerField.setAccessible( true ); + + DefaultScheduler scheduler = (DefaultScheduler) schedulerField.get( repositoryTaskScheduler ); + scheduler.stop(); + } + catch ( Exception e ) + { + e.printStackTrace(); + } + } + + // close the application context + //applicationContext.close(); + // TODO fix close call + //applicationContext. + } + + // closing correctly indexer to close correctly lock and file + for ( IndexingContext indexingContext : nexusIndexer.getIndexingContexts().values() ) + { + try + { + indexingContext.close( false ); + } + catch ( Exception e ) + { + contextEvent.getServletContext().log( "skip error closing indexingContext " + e.getMessage() ); + } + } + + } + + private void stopTaskQueueExecutor( ThreadedTaskQueueExecutor taskQueueExecutor ) + { + if ( taskQueueExecutor != null ) + { + Task currentTask = taskQueueExecutor.getCurrentTask(); + if ( currentTask != null ) + { + taskQueueExecutor.cancelTask( currentTask ); + } + + try + { + taskQueueExecutor.stop(); + ExecutorService service = getExecutorServiceForTTQE( taskQueueExecutor ); + if ( service != null ) + { + service.shutdown(); + } + } + catch ( Exception e ) + { + e.printStackTrace(); + } + } + } + + private ExecutorService getExecutorServiceForTTQE( ThreadedTaskQueueExecutor ttqe ) + { + ExecutorService service = null; + try + { + Field executorServiceField = ttqe.getClass().getDeclaredField( "executorService" ); + executorServiceField.setAccessible( true ); + service = (ExecutorService) executorServiceField.get( ttqe ); + } + catch ( Exception e ) + { + e.printStackTrace(); + } + return service; + } +} diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/startup/Banner.java b/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/startup/Banner.java new file mode 100644 index 000000000..e9272c808 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/startup/Banner.java @@ -0,0 +1,229 @@ +package org.apache.archiva.web.startup; + +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +import org.apache.commons.lang.StringUtils; +import org.slf4j.LoggerFactory; + +/** + * Banner + * + * @version $Id$ + */ +public class Banner +{ + private static final String eol = System.getProperty("line.separator"); + + public static String encode( String raw ) + { + // Canonicalize line ends to make them easier to process + raw = raw.replace("\r\n", "\n").replace("\r", "\n"); + + StringBuilder encoded = new StringBuilder(); + int rawlen = raw.length(); + + for ( int i = 0; i < rawlen; i++ ) + { + char c = raw.charAt( i ); + if ( c == '\\' ) + { + encoded.append( "$." ); + } + else if ( c == '$' ) + { + encoded.append( "$$" ); + } + else if ( c == '\n' ) + { + encoded.append( "$n" ); + } + else if ( Character.isDigit( c ) ) + { + encoded.append( c ); + } + else if ( Character.isLetter( c ) ) + { + encoded.append( rot13( c ) ); + } + else if ( i < raw.length() - 1 ) + { + char nc; + boolean done = false; + int count = 0; + for ( int n = i; !done; n++ ) + { + if ( n >= rawlen ) + { + break; + } + + nc = raw.charAt( n ); + + if ( nc != c ) + { + done = true; + } + else + { + count++; + } + } + if ( count < 3 ) + { + encoded.append( c ); + } + else + { + encoded.append( "$" ).append( String.valueOf( count ) ).append( c ); + i += count - 1; + } + } + else + { + encoded.append( c ); + } + } + + return encoded.toString(); + } + + public static String decode( String encoded ) + { + StringBuilder decoded = new StringBuilder(); + int enlen = encoded.length(); + for ( int i = 0; i < enlen; i++ ) + { + char c = encoded.charAt( i ); + if ( c == '$' ) + { + char nc = encoded.charAt( i + 1 ); + if ( nc == '$' ) + { + decoded.append( '$' ); + i++; + } + else if ( nc == '.' ) + { + decoded.append( '\\' ); + i++; + } + else if ( nc == 'n' ) + { + decoded.append( eol ); + i++; + } + else if ( Character.isDigit( nc ) ) + { + int count = 0; + int nn = i + 1; + while ( Character.isDigit( nc ) ) + { + count = ( count * 10 ); + count += ( nc - '0' ); + nc = encoded.charAt( ++nn ); + } + for ( int d = 0; d < count; d++ ) + { + decoded.append( nc ); + } + i = nn; + } + } + else if ( Character.isLetter( c ) ) + { + decoded.append( rot13( c ) ); + } + else + { + decoded.append( c ); + } + } + + return decoded.toString(); + } + + private static char rot13( char c ) + { + if ( ( c >= 'a' ) && ( c <= 'z' ) ) + { + char dc = c += 13; + if ( dc > 'z' ) + { + dc -= 26; + } + return dc; + } + else if ( ( c >= 'A' ) && ( c <= 'Z' ) ) + { + char dc = c += 13; + if ( dc > 'Z' ) + { + dc -= 26; + } + return dc; + } + else + { + return c; + } + } + + public static String injectVersion( String text, String version ) + { + Pattern pat = Pattern.compile( "#{2,}" ); + Matcher mat = pat.matcher( text ); + StringBuilder ret = new StringBuilder(); + int off = 0; + + while ( mat.find( off ) ) + { + ret.append( text.substring( off, mat.start() ) ); + String repl = mat.group(); + ret.append( StringUtils.center( version, repl.length() ) ); + off = mat.end(); + } + + ret.append( text.substring( off ) ); + + return ret.toString(); + } + + public static String getBanner( String version ) + { + String encodedBanner = "$26 $34_$n$15 /$._$7 /$34 $.$n$14 /`/@),$4 | Ba" + + " orunys bs nyy bs gur nycnpnf |$n$14 | (~' __| gbvyvat njnl ba " + + "gur Ncnpur Nepuvin |$n$6 _,--.$3_/ |$4 $.$5 cebwrpg grnz, V jbhyq y" + + "vxr gb$3 |$n$4 ,' ,$5 ($3 |$5 $.$5 jrypbzr lbh gb Nepuvin$6 |$" + + "n$4 | ($6 $. /$6 | $32# |$n$5 $. )$._/ ,_/$7 |$36 |$n$5 / /$3 " + + "( |/$9 | uggc://nepuvin.ncnpur.bet/ |$n$4 ( |$4 ( |$10 | hf" + + "ref@nepuvin.ncnpur.bet$7 |$n$5 $.|$5 $.|$11 $.$34_/$n$n"; + + return injectVersion( decode( encodedBanner ), version ); + } + + public static void display( String version ) + { + String banner = getBanner( version ); + LoggerFactory.getLogger( Banner.class ).info( StringUtils.repeat( "_", 25 ) + eol + banner ); + } +} diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/startup/SecuritySynchronization.java b/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/startup/SecuritySynchronization.java new file mode 100644 index 000000000..a49ea5a2a --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/java/org/apache/archiva/web/startup/SecuritySynchronization.java @@ -0,0 +1,245 @@ +package org.apache.archiva.web.startup; + +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import org.apache.archiva.security.common.ArchivaRoleConstants; +import org.apache.commons.collections.CollectionUtils; +import org.apache.commons.lang.StringUtils; +import org.apache.archiva.common.ArchivaException; +import org.apache.archiva.configuration.ArchivaConfiguration; +import org.apache.archiva.configuration.ConfigurationNames; +import org.apache.archiva.configuration.ManagedRepositoryConfiguration; +import org.codehaus.plexus.redback.rbac.RBACManager; +import org.codehaus.plexus.redback.rbac.RbacManagerException; +import org.codehaus.plexus.redback.rbac.UserAssignment; +import org.codehaus.plexus.redback.role.RoleManager; +import org.codehaus.plexus.redback.role.RoleManagerException; +import org.codehaus.plexus.redback.system.check.EnvironmentCheck; +import org.codehaus.plexus.redback.users.UserManager; +import org.codehaus.plexus.registry.Registry; +import org.codehaus.plexus.registry.RegistryListener; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.context.ApplicationContext; +import org.springframework.stereotype.Service; + +import javax.annotation.PostConstruct; +import javax.inject.Inject; +import javax.inject.Named; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; + +/** + * ConfigurationSynchronization + * + * @version $Id$ + */ +@Service +public class SecuritySynchronization + implements RegistryListener +{ + private Logger log = LoggerFactory.getLogger( SecuritySynchronization.class ); + + @Inject + private RoleManager roleManager; + + @Inject + @Named( value = "rBACManager#cached" ) + private RBACManager rbacManager; + + private Map checkers; + + @Inject + private ArchivaConfiguration archivaConfiguration; + + @Inject + private ApplicationContext applicationContext; + + @PostConstruct + public void initialize() + { + checkers = getBeansOfType( EnvironmentCheck.class ); + } + + protected Map getBeansOfType( Class clazz ) + { + //TODO do some caching here !!! + // olamy : with plexus we get only roleHint + // as per convention we named spring bean role#hint remove role# if exists + Map springBeans = applicationContext.getBeansOfType( clazz ); + + Map beans = new HashMap( springBeans.size() ); + + for ( Entry entry : springBeans.entrySet() ) + { + String key = StringUtils.substringAfterLast( entry.getKey(), "#" ); + beans.put( key, entry.getValue() ); + } + return beans; + } + + public void afterConfigurationChange( Registry registry, String propertyName, Object propertyValue ) + { + if ( ConfigurationNames.isManagedRepositories( propertyName ) ) + { + synchConfiguration( archivaConfiguration.getConfiguration().getManagedRepositories() ); + } + } + + public void beforeConfigurationChange( Registry registry, String propertyName, Object propertyValue ) + { + /* do nothing */ + } + + private void synchConfiguration( List repos ) + { + // NOTE: Remote Repositories do not have roles or security placed around them. + + for ( ManagedRepositoryConfiguration repoConfig : repos ) + { + // manage roles for repositories + try + { + if ( !roleManager.templatedRoleExists( ArchivaRoleConstants.TEMPLATE_REPOSITORY_OBSERVER, + repoConfig.getId() ) ) + { + roleManager.createTemplatedRole( ArchivaRoleConstants.TEMPLATE_REPOSITORY_OBSERVER, + repoConfig.getId() ); + } + else + { + roleManager.verifyTemplatedRole( ArchivaRoleConstants.TEMPLATE_REPOSITORY_OBSERVER, + repoConfig.getId() ); + } + + if ( !roleManager.templatedRoleExists( ArchivaRoleConstants.TEMPLATE_REPOSITORY_MANAGER, + repoConfig.getId() ) ) + { + roleManager.createTemplatedRole( ArchivaRoleConstants.TEMPLATE_REPOSITORY_MANAGER, + repoConfig.getId() ); + } + else + { + roleManager.verifyTemplatedRole( ArchivaRoleConstants.TEMPLATE_REPOSITORY_MANAGER, + repoConfig.getId() ); + } + } + catch ( RoleManagerException e ) + { + // Log error. + log.error( "Unable to create roles for configured repositories: " + e.getMessage(), e ); + } + } + } + + public void startup() + throws ArchivaException + { + executeEnvironmentChecks(); + + synchConfiguration( archivaConfiguration.getConfiguration().getManagedRepositories() ); + archivaConfiguration.addChangeListener( this ); + + if ( archivaConfiguration.isDefaulted() ) + { + assignRepositoryObserverToGuestUser( archivaConfiguration.getConfiguration().getManagedRepositories() ); + } + } + + private void executeEnvironmentChecks() + throws ArchivaException + { + if ( ( checkers == null ) || CollectionUtils.isEmpty( checkers.values() ) ) + { + throw new ArchivaException( + "Unable to initialize the Redback Security Environment, " + "no Environment Check components found." ); + } + + List violations = new ArrayList(); + + for ( Entry entry : checkers.entrySet() ) + { + EnvironmentCheck check = entry.getValue(); + List v = new ArrayList(); + check.validateEnvironment( v ); + log.info( "Environment Check: " + entry.getKey() + " -> " + v.size() + " violation(s)" ); + for ( String s : v ) + { + violations.add( "[" + entry.getKey() + "] " + s ); + } + } + + if ( CollectionUtils.isNotEmpty( violations ) ) + { + StringBuilder msg = new StringBuilder(); + msg.append( "EnvironmentCheck Failure.\n" ); + msg.append( "======================================================================\n" ); + msg.append( " ENVIRONMENT FAILURE !! \n" ); + msg.append( "\n" ); + + for ( String violation : violations ) + { + msg.append( violation ).append( "\n" ); + } + + msg.append( "\n" ); + msg.append( "======================================================================" ); + log.error( msg.toString() ); + + throw new ArchivaException( "Unable to initialize Redback Security Environment, [" + violations.size() + + "] violation(s) encountered, See log for details." ); + } + } + + private void assignRepositoryObserverToGuestUser( List repos ) + { + for ( ManagedRepositoryConfiguration repoConfig : repos ) + { + String repoId = repoConfig.getId(); + + String principal = UserManager.GUEST_USERNAME; + + try + { + UserAssignment ua; + + if ( rbacManager.userAssignmentExists( principal ) ) + { + ua = rbacManager.getUserAssignment( principal ); + } + else + { + ua = rbacManager.createUserAssignment( principal ); + } + + ua.addRoleName( ArchivaRoleConstants.toRepositoryObserverRoleName( repoId ) ); + rbacManager.saveUserAssignment( ua ); + } + catch ( RbacManagerException e ) + { + log.warn( "Unable to add role [" + ArchivaRoleConstants.toRepositoryObserverRoleName( repoId ) + "] to " + + principal + " user.", e ); + } + } + } +} diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/resources/META-INF/spring-context.xml b/archiva-modules/archiva-web/archiva-webapp-js/src/main/resources/META-INF/spring-context.xml new file mode 100755 index 000000000..fb14d761a --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/resources/META-INF/spring-context.xml @@ -0,0 +1,48 @@ + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/resources/org/apache/archiva/security.properties b/archiva-modules/archiva-web/archiva-webapp-js/src/main/resources/org/apache/archiva/security.properties new file mode 100644 index 000000000..2074ef020 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/resources/org/apache/archiva/security.properties @@ -0,0 +1,27 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. +# + +# -------------------------------------------------------------------- +# Email Settings + +# The subject line for the email message. +email.validation.subject=Welcome to Archiva + +# Feedback page +email.feedback.path=http://archiva.apache.org/mail-lists.html diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/resources/org/apache/archiva/security_en.properties b/archiva-modules/archiva-web/archiva-webapp-js/src/main/resources/org/apache/archiva/security_en.properties new file mode 100644 index 000000000..661b0cba7 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/resources/org/apache/archiva/security_en.properties @@ -0,0 +1,20 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. +# + + diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/WEB-INF/applicationContext.xml b/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/WEB-INF/applicationContext.xml new file mode 100644 index 000000000..3c04c0140 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/WEB-INF/applicationContext.xml @@ -0,0 +1,419 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + ]]> + + + + + + + + + + + true + false + false + false + None + READ_COMMITTED + READ_COMMITTED + JDK_DEFAULT_TIMEZONE + + 255 + + + + + true + ehcacheclassbased + defaultJpox + /ehcache.xml + + + + + + + + + scheduler1 + org.quartz.simpl.SimpleThreadPool + 2 + 4 + org.quartz.simpl.RAMJobStore + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/WEB-INF/web.xml b/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/WEB-INF/web.xml index 9f88c1f96..c607265e8 100644 --- a/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/WEB-INF/web.xml +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/WEB-INF/web.xml @@ -1,7 +1,180 @@ - + + + + + + + + Apache Archiva + + + contextConfigLocation + + classpath*:META-INF/spring-context.xml, + /WEB-INF/applicationContext.xml + + + + + encodingFilter + org.springframework.web.filter.CharacterEncodingFilter + + encoding + UTF-8 + + + forceEncoding + true + + + + + encodingFilter + /* + + + + + org.springframework.web.context.ContextLoaderListener + + + + + + org.apache.archiva.web.startup.ArchivaStartup + + + + + net.sf.ehcache.constructs.web.ShutdownListener + + + + + org.apache.archiva.webdav.util.TemporaryGroupIndexSessionCleaner + + + + RepositoryServlet + + org.apache.archiva.webdav.RepositoryServlet + + + 1 + + + + XmlRpcServlet + + com.atlassian.xmlrpc.spring.BinderSpringXmlRpcServlet + + + serviceListBeanName + xmlrpcServicesList + + + authHandlerBeanName + xmlRpcAuthenticator + + + enabledForExtensions + true + + 2 + + + + RedbackXmlRpcServlet + com.atlassian.xmlrpc.spring.BinderSpringXmlRpcServlet + + serviceListBeanName + redbackXmlrpcServicesList + + + authHandlerBeanName + redbackXmlRpcAuthenticator + + + enabledForExtensions + true + + + + + RssFeedServlet + + org.apache.archiva.web.rss.RssFeedServlet + + + + + RssFeedServlet + /feeds/* + + + + RepositoryServlet + /repository/* + + + + XmlRpcServlet + /xmlrpc + + + + RedbackXmlRpcServlet + /redback-xmlrpc + + + + jdbc/users + javax.sql.DataSource + Container + Shareable + + + mail/Session + javax.mail.Session + Container + Shareable + + + + + CXFServlet + org.apache.cxf.transport.servlet.CXFServlet + 1 + + + + CXFServlet + /restServices/* + + + + index.html + + + + + 30 + - - Archetype Created Web Application diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/index.html b/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/index.html new file mode 100644 index 000000000..ba9f35830 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/index.html @@ -0,0 +1,67 @@ + + + + + + + + + + + + + + + +
+ +
+ + +
+
+ +
+
+
+ + + + +
+ + + + + + + + diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/index.jsp b/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/index.jsp deleted file mode 100644 index c38169bb9..000000000 --- a/archiva-modules/archiva-web/archiva-webapp-js/src/main/webapp/index.jsp +++ /dev/null @@ -1,5 +0,0 @@ - - -

Hello World!

- - diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/test/tomcat/auto-admin-creation.properties b/archiva-modules/archiva-web/archiva-webapp-js/src/test/tomcat/auto-admin-creation.properties new file mode 100644 index 000000000..7c8c5815b --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/test/tomcat/auto-admin-creation.properties @@ -0,0 +1,22 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. +# + +redback.admin.fullname=Archiva Admin +redback.admin.email=admin@toto.com +redback.admin.password=admin123 \ No newline at end of file diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/test/tomcat/log4j.xml b/archiva-modules/archiva-web/archiva-webapp-js/src/test/tomcat/log4j.xml new file mode 100644 index 000000000..934409da7 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/test/tomcat/log4j.xml @@ -0,0 +1,80 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/archiva-modules/archiva-web/archiva-webapp-js/src/test/tomcat/tomcat-context-archiva.xml b/archiva-modules/archiva-web/archiva-webapp-js/src/test/tomcat/tomcat-context-archiva.xml new file mode 100644 index 000000000..fda8f8221 --- /dev/null +++ b/archiva-modules/archiva-web/archiva-webapp-js/src/test/tomcat/tomcat-context-archiva.xml @@ -0,0 +1,31 @@ + + + + + + + diff --git a/pom.xml b/pom.xml index b031079ac..b8be55173 100644 --- a/pom.xml +++ b/pom.xml @@ -921,6 +921,17 @@ + + org.codehaus.redback + redback-integrations-security + ${redback.version} + + + commons-logging + commons-logging + + + org.apache.velocity velocity