001 /**
002 * Copyright 2010-2013 The Kuali Foundation
003 *
004 * Licensed under the Educational Community License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 * http://www.opensource.org/licenses/ecl2.php
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016 package org.kuali.common.util;
017
018 import java.util.ArrayList;
019 import java.util.Arrays;
020 import java.util.List;
021 import java.util.Properties;
022
023 import org.apache.commons.lang3.StringUtils;
024 import org.kuali.common.util.property.Constants;
025 import org.kuali.common.util.property.GlobalPropertiesMode;
026 import org.kuali.common.util.property.ProjectProperties;
027 import org.kuali.common.util.property.PropertiesContext;
028 import org.kuali.common.util.property.processor.ProjectProcessor;
029 import org.kuali.common.util.property.processor.PropertyProcessor;
030 import org.kuali.common.util.property.processor.VersionProcessor;
031 import org.kuali.common.util.service.PropertySourceContext;
032 import org.kuali.common.util.service.SpringContext;
033 import org.kuali.common.util.service.SpringService;
034 import org.kuali.common.util.spring.SpringUtils;
035 import org.slf4j.Logger;
036 import org.slf4j.LoggerFactory;
037 import org.springframework.core.env.Environment;
038 import org.springframework.core.env.PropertySource;
039
040 public class MavenUtils {
041
042 private static final Logger logger = LoggerFactory.getLogger(MavenUtils.class);
043
044 public static final String POM = "pom";
045 public static final String INCLUDE = "properties.maven.include";
046 public static final String EXCLUDE = "properties.maven.exclude";
047 public static final String PROJECT_VERSION_KEY = "project.version";
048
049 public static SpringContext getMavenizedSpringContext(SpringService service, Properties mavenProperties, Class<?> propertySourceConfig) {
050 // This PropertySource object is backed by a set of properties that has been
051 // 1 - fully resolved
052 // 2 - contains all properties needed by Spring
053 // 3 - contains system/environment properties where system/env properties override loaded properties
054 PropertySource<?> source = getPropertySource(service, mavenProperties, propertySourceConfig);
055
056 // Setup a property source context such that our single property source is the only one registered with Spring
057 // This will make it so our PropertySource is the ONLY thing to resolve placeholders
058 PropertySourceContext psc = new PropertySourceContext(source, true);
059
060 // Setup a Spring context
061 SpringContext context = new SpringContext();
062
063 // Supply Spring with our PropertySource
064 context.setPropertySourceContext(psc);
065
066 // Return a Spring context configured with a single property source
067 return context;
068 }
069
070 protected static PropertySource<?> getPropertySource(SpringService service, Properties mavenProperties, Class<?> annotatedClass) {
071 return getPropertySource(service, annotatedClass, Constants.DEFAULT_MAVEN_PROPERTIES_BEAN_NAME, mavenProperties);
072 }
073
074 protected static PropertySource<?> getPropertySource(SpringService service, Class<?> annotatedClass, String mavenPropertiesBeanName, Properties mavenProperties) {
075 List<PropertySource<?>> sources = SpringUtils.getPropertySources(service, annotatedClass, mavenPropertiesBeanName, mavenProperties);
076 if (sources.size() > 1) {
077 throw new IllegalStateException("More than one PropertySource was registered in the context");
078 } else {
079 return sources.get(0);
080 }
081 }
082
083 /**
084 * Add organization, group, and path properties and tokenize the version number adding properties for each token along with a boolean property indicating if this is a SNAPSHOT
085 * build
086 */
087 public static void augmentProjectProperties(Properties mavenProperties) {
088 // Setup some processors
089 List<PropertyProcessor> processors = new ArrayList<PropertyProcessor>();
090
091 // Add some organization, group, and path properties
092 processors.add(new ProjectProcessor());
093
094 // Tokenize the version number and add properties for each token (major/minor/incremental)
095 // Also add a boolean property indicating if this is a SNAPSHOT build
096 processors.add(new VersionProcessor(Arrays.asList(PROJECT_VERSION_KEY), true));
097
098 // Process default Maven properties and add in our custom properties
099 PropertyUtils.process(mavenProperties, processors);
100
101 // Make sure system/environment properties still always win
102 PropertyUtils.overrideWithGlobalValues(mavenProperties, GlobalPropertiesMode.BOTH);
103 }
104
105 public static void trim(Environment env, Properties mavenProperties) {
106 List<String> excludes = getList(env, mavenProperties, EXCLUDE);
107 List<String> includes = getList(env, mavenProperties, INCLUDE);
108 PropertyUtils.trim(mavenProperties, includes, excludes);
109 }
110
111 public static ProjectProperties getMavenProjectProperties(Environment env, Properties mavenProperties) {
112 Project project = ProjectUtils.getProject(mavenProperties);
113
114 trim(env, mavenProperties);
115
116 PropertiesContext pc = new PropertiesContext();
117 pc.setProperties(mavenProperties);
118
119 ProjectProperties pp = new ProjectProperties();
120 pp.setProject(project);
121 pp.setPropertiesContext(pc);
122 return pp;
123 }
124
125 protected static List<String> getList(Environment env, Properties properties, String key) {
126 String csv1 = env.getProperty(key);
127 String csv2 = properties.getProperty(key);
128 List<String> list = new ArrayList<String>();
129 list.addAll(CollectionUtils.getTrimmedListFromCSV(csv1));
130 list.addAll(CollectionUtils.getTrimmedListFromCSV(csv2));
131 return list;
132 }
133
134 /**
135 * Always return false if <code>forceMojoExecution</code> is true, otherwise return true only if <code>skip</code> is true or <code>packaging</code> is pom.
136 */
137 public static final boolean skip(boolean forceMojoExecution, boolean skip, String packaging) {
138 if (forceMojoExecution) {
139 logger.info("Forced mojo execution");
140 return false;
141 }
142 if (skip) {
143 logger.info("Skipping mojo execution");
144 return true;
145 }
146 if (StringUtils.equalsIgnoreCase(packaging, POM)) {
147 logger.info("Skipping mojo execution for project with packaging type '{}'", POM);
148 return true;
149 } else {
150 return false;
151 }
152 }
153
154 }