From 5f9cfa16935ead3ac911844bc400aba790a3ab1f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Christoph=20L=C3=A4ubrich?= Date: Wed, 2 Feb 2022 10:00:56 +0100 Subject: [PATCH] MNG-7407 Introduce a ModelVersionProcessor component to make CI Friends Versions pluggable --- .../building/DefaultModelBuilderFactory.java | 12 +++- .../AbstractStringBasedModelInterpolator.java | 32 +++------ .../DefaultModelVersionProcessor.java | 69 +++++++++++++++++++ .../interpolation/ModelVersionProcessor.java | 47 +++++++++++++ .../validation/DefaultModelValidator.java | 21 +++--- .../StringSearchModelInterpolatorTest.java | 5 +- .../validation/DefaultModelValidatorTest.java | 4 +- 7 files changed, 156 insertions(+), 34 deletions(-) create mode 100644 maven-model-builder/src/main/java/org/apache/maven/model/interpolation/DefaultModelVersionProcessor.java create mode 100644 maven-model-builder/src/main/java/org/apache/maven/model/interpolation/ModelVersionProcessor.java diff --git a/maven-model-builder/src/main/java/org/apache/maven/model/building/DefaultModelBuilderFactory.java b/maven-model-builder/src/main/java/org/apache/maven/model/building/DefaultModelBuilderFactory.java index 730c5a29fee7..3e1f03128285 100644 --- a/maven-model-builder/src/main/java/org/apache/maven/model/building/DefaultModelBuilderFactory.java +++ b/maven-model-builder/src/main/java/org/apache/maven/model/building/DefaultModelBuilderFactory.java @@ -24,7 +24,9 @@ import org.apache.maven.model.composition.DependencyManagementImporter; import org.apache.maven.model.inheritance.DefaultInheritanceAssembler; import org.apache.maven.model.inheritance.InheritanceAssembler; +import org.apache.maven.model.interpolation.DefaultModelVersionProcessor; import org.apache.maven.model.interpolation.ModelInterpolator; +import org.apache.maven.model.interpolation.ModelVersionProcessor; import org.apache.maven.model.interpolation.StringVisitorModelInterpolator; import org.apache.maven.model.io.DefaultModelReader; import org.apache.maven.model.io.ModelReader; @@ -133,12 +135,18 @@ protected ModelInterpolator newModelInterpolator() { UrlNormalizer normalizer = newUrlNormalizer(); PathTranslator pathTranslator = newPathTranslator(); - return new StringVisitorModelInterpolator().setPathTranslator( pathTranslator ).setUrlNormalizer( normalizer ); + return new StringVisitorModelInterpolator().setPathTranslator( pathTranslator ).setUrlNormalizer( normalizer ) + .setVersionPropertiesProcessor( newModelVersionPropertiesProcessor() ); + } + + protected ModelVersionProcessor newModelVersionPropertiesProcessor() + { + return new DefaultModelVersionProcessor(); } protected ModelValidator newModelValidator() { - return new DefaultModelValidator(); + return new DefaultModelValidator().setModelVersionPropertiesProcessor( newModelVersionPropertiesProcessor() ); } protected ModelNormalizer newModelNormalizer() diff --git a/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/AbstractStringBasedModelInterpolator.java b/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/AbstractStringBasedModelInterpolator.java index 388671d78de2..4e535cd6455e 100644 --- a/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/AbstractStringBasedModelInterpolator.java +++ b/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/AbstractStringBasedModelInterpolator.java @@ -52,12 +52,6 @@ public abstract class AbstractStringBasedModelInterpolator implements ModelInterpolator { - public static final String SHA1_PROPERTY = "sha1"; - - public static final String CHANGELIST_PROPERTY = "changelist"; - - public static final String REVISION_PROPERTY = "revision"; - private static final List PROJECT_PREFIXES = Arrays.asList( "pom.", "project." ); private static final Collection TRANSLATED_PATH_EXPRESSIONS; @@ -88,9 +82,8 @@ public abstract class AbstractStringBasedModelInterpolator @Inject private UrlNormalizer urlNormalizer; - public AbstractStringBasedModelInterpolator() - { - } + @Inject + private ModelVersionProcessor versionProcessor; public AbstractStringBasedModelInterpolator setPathTranslator( PathTranslator pathTranslator ) { @@ -104,6 +97,12 @@ public AbstractStringBasedModelInterpolator setUrlNormalizer( UrlNormalizer urlN return this; } + public AbstractStringBasedModelInterpolator setVersionPropertiesProcessor( ModelVersionProcessor processor ) + { + this.versionProcessor = processor; + return this; + } + protected List createValueSources( final Model model, final File projectDir, final ModelBuildingRequest config, final ModelProblemCollector problems ) @@ -162,19 +161,8 @@ public Object getValue( String expression ) valueSources.add( new MapBasedValueSource( config.getUserProperties() ) ); // Overwrite existing values in model properties. Otherwise it's not possible - // to define the version via command line: mvn -Drevision=6.5.7 ... - if ( config.getSystemProperties().containsKey( REVISION_PROPERTY ) ) - { - modelProperties.put( REVISION_PROPERTY, config.getSystemProperties().get( REVISION_PROPERTY ) ); - } - if ( config.getSystemProperties().containsKey( CHANGELIST_PROPERTY ) ) - { - modelProperties.put( CHANGELIST_PROPERTY, config.getSystemProperties().get( CHANGELIST_PROPERTY ) ); - } - if ( config.getSystemProperties().containsKey( SHA1_PROPERTY ) ) - { - modelProperties.put( SHA1_PROPERTY, config.getSystemProperties().get( SHA1_PROPERTY ) ); - } + // to define them via command line e.g.: mvn -Drevision=6.5.7 ... + versionProcessor.overwriteModelProperties( modelProperties, config ); valueSources.add( new MapBasedValueSource( modelProperties ) ); valueSources.add( new MapBasedValueSource( config.getSystemProperties() ) ); diff --git a/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/DefaultModelVersionProcessor.java b/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/DefaultModelVersionProcessor.java new file mode 100644 index 000000000000..21b495813aad --- /dev/null +++ b/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/DefaultModelVersionProcessor.java @@ -0,0 +1,69 @@ +package org.apache.maven.model.interpolation; + +/* + * 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.Properties; + +import javax.inject.Named; +import javax.inject.Singleton; + +import org.apache.maven.model.building.ModelBuildingRequest; + +/** + * Maven default implementation of the {@link ModelVersionProcessor} to support + * CI Friendly Versions + */ +@Named +@Singleton +public class DefaultModelVersionProcessor + implements ModelVersionProcessor +{ + + private static final String SHA1_PROPERTY = "sha1"; + + private static final String CHANGELIST_PROPERTY = "changelist"; + + private static final String REVISION_PROPERTY = "revision"; + + @Override + public boolean isValidProperty( String property ) + { + return REVISION_PROPERTY.equals( property ) || CHANGELIST_PROPERTY.equals( property ) + || SHA1_PROPERTY.equals( property ); + } + + @Override + public void overwriteModelProperties( Properties modelProperties, ModelBuildingRequest request ) + { + if ( request.getUserProperties().containsKey( REVISION_PROPERTY ) ) + { + modelProperties.put( REVISION_PROPERTY, request.getUserProperties().get( REVISION_PROPERTY ) ); + } + if ( request.getUserProperties().containsKey( CHANGELIST_PROPERTY ) ) + { + modelProperties.put( CHANGELIST_PROPERTY, request.getUserProperties().get( CHANGELIST_PROPERTY ) ); + } + if ( request.getUserProperties().containsKey( SHA1_PROPERTY ) ) + { + modelProperties.put( SHA1_PROPERTY, request.getUserProperties().get( SHA1_PROPERTY ) ); + } + + } +} diff --git a/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/ModelVersionProcessor.java b/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/ModelVersionProcessor.java new file mode 100644 index 000000000000..35ce15ea0de6 --- /dev/null +++ b/maven-model-builder/src/main/java/org/apache/maven/model/interpolation/ModelVersionProcessor.java @@ -0,0 +1,47 @@ +package org.apache.maven.model.interpolation; + +/* + * 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.Properties; + +import org.apache.maven.model.building.ModelBuildingRequest; + +/** + * Allows a fixed set of properties that are valid inside a version and that could be overwritten for example on the + * commandline + */ +public interface ModelVersionProcessor +{ + + /** + * @param property the property to check + * @return true if this is a valid property for this processor + */ + boolean isValidProperty( String property ); + + /** + * This method is responsible for examining the request and possibly overwrite of the valid properties in the model + * + * @param modelProperties + * @param request + */ + void overwriteModelProperties( Properties modelProperties, ModelBuildingRequest request ); + +} diff --git a/maven-model-builder/src/main/java/org/apache/maven/model/validation/DefaultModelValidator.java b/maven-model-builder/src/main/java/org/apache/maven/model/validation/DefaultModelValidator.java index ad7e3c7e5a9f..153bb250baf1 100644 --- a/maven-model-builder/src/main/java/org/apache/maven/model/validation/DefaultModelValidator.java +++ b/maven-model-builder/src/main/java/org/apache/maven/model/validation/DefaultModelValidator.java @@ -44,7 +44,7 @@ import org.apache.maven.model.building.ModelProblem.Version; import org.apache.maven.model.building.ModelProblemCollector; import org.apache.maven.model.building.ModelProblemCollectorRequest; -import org.apache.maven.model.interpolation.AbstractStringBasedModelInterpolator; +import org.apache.maven.model.interpolation.ModelVersionProcessor; import org.codehaus.plexus.util.StringUtils; import java.io.File; @@ -58,6 +58,7 @@ import java.util.regex.Matcher; import java.util.regex.Pattern; +import javax.inject.Inject; import javax.inject.Named; import javax.inject.Singleton; @@ -72,11 +73,6 @@ public class DefaultModelValidator private static final Pattern CI_FRIENDLY_EXPRESSION = Pattern.compile( "\\$\\{(.+?)\\}" ); - private static final List CI_FRIENDLY_POSSIBLE_PROPERTY_NAMES = - Arrays.asList( AbstractStringBasedModelInterpolator.REVISION_PROPERTY, - AbstractStringBasedModelInterpolator.CHANGELIST_PROPERTY, - AbstractStringBasedModelInterpolator.SHA1_PROPERTY ); - private static final String ILLEGAL_FS_CHARS = "\\/:\"<>|?*"; private static final String ILLEGAL_VERSION_CHARS = ILLEGAL_FS_CHARS; @@ -87,6 +83,15 @@ public class DefaultModelValidator private final Set validIds = new HashSet<>(); + @Inject + private ModelVersionProcessor versionProcessor; + + public DefaultModelValidator setModelVersionPropertiesProcessor( ModelVersionProcessor versionProcessor ) + { + this.versionProcessor = versionProcessor; + return this; + } + @Override public void validateRawModel( Model m, ModelBuildingRequest request, ModelProblemCollector problems ) { @@ -940,11 +945,11 @@ private boolean validateVersionNoExpression( String fieldName, ModelProblemColle Matcher m = CI_FRIENDLY_EXPRESSION.matcher( string.trim() ); while ( m.find() ) { - if ( !CI_FRIENDLY_POSSIBLE_PROPERTY_NAMES.contains( m.group( 1 ) ) ) + String property = m.group( 1 ); + if ( !versionProcessor.isValidProperty( property ) ) { addViolation( problems, severity, version, fieldName, null, "contains an expression but should be a constant.", tracker ); - return false; } } diff --git a/maven-model-builder/src/test/java/org/apache/maven/model/interpolation/StringSearchModelInterpolatorTest.java b/maven-model-builder/src/test/java/org/apache/maven/model/interpolation/StringSearchModelInterpolatorTest.java index df10511cee2b..c95e37271e29 100644 --- a/maven-model-builder/src/test/java/org/apache/maven/model/interpolation/StringSearchModelInterpolatorTest.java +++ b/maven-model-builder/src/test/java/org/apache/maven/model/interpolation/StringSearchModelInterpolatorTest.java @@ -54,7 +54,8 @@ protected void setUp() throws Exception { super.setUp(); - interpolator = new StringSearchModelInterpolator(); + interpolator = + new StringSearchModelInterpolator().setVersionPropertiesProcessor( new DefaultModelVersionProcessor() ); } @@ -580,6 +581,7 @@ public void testFinalFieldsExcludedFromInterpolation() SimpleProblemCollector problems = new SimpleProblemCollector(); StringSearchModelInterpolator interpolator = new StringSearchModelInterpolator(); + interpolator.setVersionPropertiesProcessor( new DefaultModelVersionProcessor() ); interpolator.interpolateObject( new ClassWithFinalField(), new Model(), null, request, problems ); assertProblemFree( problems ); @@ -605,6 +607,7 @@ public void testLocationTrackerShouldBeExcludedFromInterpolation() SimpleProblemCollector problems = new SimpleProblemCollector(); StringSearchModelInterpolator interpolator = new StringSearchModelInterpolator(); + interpolator.setVersionPropertiesProcessor( new DefaultModelVersionProcessor() ); interpolator.interpolateObject( model, model, null, request, problems ); assertProblemFree( problems ); diff --git a/maven-model-builder/src/test/java/org/apache/maven/model/validation/DefaultModelValidatorTest.java b/maven-model-builder/src/test/java/org/apache/maven/model/validation/DefaultModelValidatorTest.java index 3e07c57754a8..656b15bf914c 100644 --- a/maven-model-builder/src/test/java/org/apache/maven/model/validation/DefaultModelValidatorTest.java +++ b/maven-model-builder/src/test/java/org/apache/maven/model/validation/DefaultModelValidatorTest.java @@ -26,6 +26,7 @@ import org.apache.maven.model.building.DefaultModelBuildingRequest; import org.apache.maven.model.building.ModelBuildingRequest; import org.apache.maven.model.building.SimpleProblemCollector; +import org.apache.maven.model.interpolation.DefaultModelVersionProcessor; import org.apache.maven.model.io.xpp3.MavenXpp3Reader; import junit.framework.TestCase; @@ -95,7 +96,8 @@ protected void setUp() { super.setUp(); - validator = new DefaultModelValidator(); + validator = + new DefaultModelValidator().setModelVersionPropertiesProcessor( new DefaultModelVersionProcessor() ); } @Override