From e0f0ed6814366c4185f8a8ac0cc663b5f8ef744e Mon Sep 17 00:00:00 2001 From: Tamas Cservenak Date: Thu, 9 Jun 2022 13:21:52 +0200 Subject: [PATCH] WIP --- pom.xml | 21 +- .../maven/shared/filtering/BaseFilter.java | 10 +- .../filtering/DefaultMavenFileFilter.java | 4 +- .../DefaultMavenResourcesFiltering.java | 29 +- .../shared/filtering/FilteringUtils.java | 341 ++++++++++++++++++ .../maven/shared/filtering/PropertyUtils.java | 2 +- .../filtering/DefaultMavenFileFilterTest.java | 3 +- .../DefaultMavenReaderFilterTest.java | 3 +- .../DefaultMavenResourcesFilteringTest.java | 3 +- .../shared/filtering/EscapeStringTest.java | 3 +- .../shared/filtering/FilteringUtilsTest.java | 9 +- .../IncrementalResourceFilteringTest.java | 212 ----------- .../shared/filtering/InvalidMarkTest.java | 3 +- .../MuliLinesMavenResourcesFilteringTest.java | 3 +- .../shared/filtering/PropertyUtilsTest.java | 144 +------- .../filtering/TestReflectionProperties.java | 3 +- .../maven/shared/filtering/TestSupport.java | 37 ++ 17 files changed, 431 insertions(+), 399 deletions(-) delete mode 100644 src/test/java/org/apache/maven/shared/filtering/IncrementalResourceFilteringTest.java create mode 100644 src/test/java/org/apache/maven/shared/filtering/TestSupport.java diff --git a/pom.xml b/pom.xml index e247b95..08f1a2a 100644 --- a/pom.xml +++ b/pom.xml @@ -96,15 +96,6 @@ ${mavenVersion} provided - - org.eclipse.sisu - org.eclipse.sisu.plexus - 0.3.0.M1 - - - org.codehaus.plexus - plexus-component-annotations - org.codehaus.plexus plexus-utils @@ -145,6 +136,18 @@ ${slf4jVersion} test + + org.eclipse.sisu + org.eclipse.sisu.plexus + 0.3.0.M1 + test + + + org.eclipse.sisu + org.eclipse.sisu.inject + 0.3.0.M1 + test + diff --git a/src/main/java/org/apache/maven/shared/filtering/BaseFilter.java b/src/main/java/org/apache/maven/shared/filtering/BaseFilter.java index 580a223..fc3afd8 100644 --- a/src/main/java/org/apache/maven/shared/filtering/BaseFilter.java +++ b/src/main/java/org/apache/maven/shared/filtering/BaseFilter.java @@ -42,12 +42,18 @@ import org.codehaus.plexus.interpolation.SingleResponseValueSource; import org.codehaus.plexus.interpolation.ValueSource; import org.codehaus.plexus.interpolation.multi.MultiDelimiterStringSearchInterpolator; -import org.codehaus.plexus.logging.AbstractLogEnabled; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; class BaseFilter - extends AbstractLogEnabled implements DefaultFilterInfo { + private final Logger logger = LoggerFactory.getLogger( getClass() ); + + protected Logger getLogger() + { + return logger; + } @Override public List getDefaultFilterWrappers( final MavenProject mavenProject, diff --git a/src/main/java/org/apache/maven/shared/filtering/DefaultMavenFileFilter.java b/src/main/java/org/apache/maven/shared/filtering/DefaultMavenFileFilter.java index 59c93f2..58dea10 100644 --- a/src/main/java/org/apache/maven/shared/filtering/DefaultMavenFileFilter.java +++ b/src/main/java/org/apache/maven/shared/filtering/DefaultMavenFileFilter.java @@ -87,7 +87,7 @@ public void copyFile( File from, File to, boolean filtering, List getLogger().debug( "filtering " + from.getPath() + " to " + to.getPath() ); } FilterWrapper[] array = filterWrappers.toArray( new FilterWrapper[0] ); - FileUtils.copyFile( from, to, encoding, array, false ); + FilteringUtils.copyFile( from, to, encoding, array, false ); } else { @@ -95,7 +95,7 @@ public void copyFile( File from, File to, boolean filtering, List { getLogger().debug( "copy " + from.getPath() + " to " + to.getPath() ); } - FileUtils.copyFile( from, to, encoding, new FilterWrapper[0], overwrite ); + FilteringUtils.copyFile( from, to, encoding, new FilterWrapper[0], overwrite ); } } catch ( IOException e ) diff --git a/src/main/java/org/apache/maven/shared/filtering/DefaultMavenResourcesFiltering.java b/src/main/java/org/apache/maven/shared/filtering/DefaultMavenResourcesFiltering.java index 291295f..2a97d6b 100644 --- a/src/main/java/org/apache/maven/shared/filtering/DefaultMavenResourcesFiltering.java +++ b/src/main/java/org/apache/maven/shared/filtering/DefaultMavenResourcesFiltering.java @@ -206,9 +206,6 @@ public void filterResources( MavenResourcesExecution mavenResourcesExecution ) { isFilteringUsed = true; } - boolean ignoreDelta = !outputExists || buildContext.hasDelta( mavenResourcesExecution.getFileFilters() ) - || buildContext.hasDelta( getRelativeOutputDirectory( mavenResourcesExecution ) ); - getLogger().debug( "ignoreDelta " + ignoreDelta ); DirectoryScanner scanner = new DirectoryScanner(); scanner.setBasedir( resourceDirectory ); @@ -275,26 +272,6 @@ public void filterResources( MavenResourcesExecution mavenResourcesExecution ) encoding, mavenResourcesExecution.isOverwrite() ); } - - // deal with deleted source files - - scanner = buildContext.newDeleteScanner( resourceDirectory ); - - setupScanner( resource, scanner, mavenResourcesExecution.isAddDefaultExcludes() ); - - scanner.scan(); - - List deletedFiles = Arrays.asList( scanner.getIncludedFiles() ); - - for ( String name : deletedFiles ) - { - File destinationFile = getDestinationFile( outputDirectory, targetPath, name, mavenResourcesExecution ); - - destinationFile.delete(); - - buildContext.refresh( destinationFile ); - } - } // Warn the user if all of the following requirements are met, to avoid those that are not affected @@ -497,7 +474,7 @@ private String getRelativeOutputDirectory( MavenResourcesExecution execution ) if ( execution.getMavenProject() != null && execution.getMavenProject().getBasedir() != null ) { String basedir = execution.getMavenProject().getBasedir().getAbsolutePath(); - relOutDir = PathTool.getRelativeFilePath( basedir, relOutDir ); + relOutDir = FilteringUtils.getRelativeFilePath( basedir, relOutDir ); if ( relOutDir == null ) { relOutDir = execution.getOutputDirectory().getPath(); @@ -529,9 +506,9 @@ private String filterFileName( String name, List wrappers ) IOUtils.copy( reader, writer ); String filteredFilename = writer.toString(); - if ( getLogger().isDebugEnabled() ) + if ( LOGGER.isDebugEnabled() ) { - getLogger().debug( "renaming filename " + name + " to " + filteredFilename ); + LOGGER.debug( "renaming filename " + name + " to " + filteredFilename ); } return filteredFilename; } diff --git a/src/main/java/org/apache/maven/shared/filtering/FilteringUtils.java b/src/main/java/org/apache/maven/shared/filtering/FilteringUtils.java index 6bb9a48..b7690e0 100644 --- a/src/main/java/org/apache/maven/shared/filtering/FilteringUtils.java +++ b/src/main/java/org/apache/maven/shared/filtering/FilteringUtils.java @@ -21,8 +21,22 @@ import java.io.File; import java.io.IOException; +import java.io.RandomAccessFile; +import java.io.Reader; +import java.io.Writer; +import java.nio.Buffer; +import java.nio.ByteBuffer; +import java.nio.CharBuffer; +import java.nio.charset.Charset; +import java.nio.charset.CharsetEncoder; +import java.nio.charset.CoderResult; +import java.nio.file.Files; +import java.nio.file.LinkOption; +import java.nio.file.StandardCopyOption; +import java.util.StringTokenizer; import java.util.regex.Pattern; +import org.apache.commons.io.IOUtils; import org.codehaus.plexus.util.Os; /** @@ -31,6 +45,21 @@ */ public final class FilteringUtils { + /** + * The number of bytes in a kilobyte. + */ + private static final int ONE_KB = 1024; + + /** + * The number of bytes in a megabyte. + */ + private static final int ONE_MB = ONE_KB * ONE_KB; + + /** + * The file copy buffer size (30 MB) + */ + private static final int FILE_COPY_BUFFER_SIZE = ONE_MB * 30; + private static final String WINDOWS_PATH_PATTERN = "^(.*)[a-zA-Z]:\\\\(.*)"; private static final Pattern PATTERN = Pattern.compile( WINDOWS_PATH_PATTERN ); @@ -155,8 +184,320 @@ public static File resolveFile( final File baseFile, String filename ) return file; } + + /** + *

This method can calculate the relative path between two paths on a file system.

+ *
+     * PathTool.getRelativeFilePath( null, null )                                   = ""
+     * PathTool.getRelativeFilePath( null, "/usr/local/java/bin" )                  = ""
+     * PathTool.getRelativeFilePath( "/usr/local", null )                           = ""
+     * PathTool.getRelativeFilePath( "/usr/local", "/usr/local/java/bin" )          = "java/bin"
+     * PathTool.getRelativeFilePath( "/usr/local", "/usr/local/java/bin/" )         = "java/bin"
+     * PathTool.getRelativeFilePath( "/usr/local/java/bin", "/usr/local/" )         = "../.."
+     * PathTool.getRelativeFilePath( "/usr/local/", "/usr/local/java/bin/java.sh" ) = "java/bin/java.sh"
+     * PathTool.getRelativeFilePath( "/usr/local/java/bin/java.sh", "/usr/local/" ) = "../../.."
+     * PathTool.getRelativeFilePath( "/usr/local/", "/bin" )                        = "../../bin"
+     * PathTool.getRelativeFilePath( "/bin", "/usr/local/" )                        = "../usr/local"
+     * 
+ * Note: On Windows based system, the / character should be replaced by \ character. + * + * @param oldPath old path + * @param newPath new path + * @return a relative file path from oldPath. + */ + public static String getRelativeFilePath( final String oldPath, final String newPath ) + { + if ( isEmpty( oldPath ) || isEmpty( newPath ) ) + { + return ""; + } + + // normalise the path delimiters + String fromPath = new File( oldPath ).getPath(); + String toPath = new File( newPath ).getPath(); + + // strip any leading slashes if its a windows path + if ( toPath.matches( "^\\[a-zA-Z]:" ) ) + { + toPath = toPath.substring( 1 ); + } + if ( fromPath.matches( "^\\[a-zA-Z]:" ) ) + { + fromPath = fromPath.substring( 1 ); + } + + // lowercase windows drive letters. + if ( fromPath.startsWith( ":", 1 ) ) + { + fromPath = Character.toLowerCase( fromPath.charAt( 0 ) ) + fromPath.substring( 1 ); + } + if ( toPath.startsWith( ":", 1 ) ) + { + toPath = Character.toLowerCase( toPath.charAt( 0 ) ) + toPath.substring( 1 ); + } + + // check for the presence of windows drives. No relative way of + // traversing from one to the other. + if ( ( toPath.startsWith( ":", 1 ) && fromPath.startsWith( ":", 1 ) ) + && ( !toPath.substring( 0, 1 ).equals( fromPath.substring( 0, 1 ) ) ) ) + { + // they both have drive path element but they dont match, no + // relative path + return null; + } + + if ( ( toPath.startsWith( ":", 1 ) && !fromPath.startsWith( ":", 1 ) ) + || ( !toPath.startsWith( ":", 1 ) && fromPath.startsWith( ":", 1 ) ) ) + { + // one has a drive path element and the other doesnt, no relative + // path. + return null; + } + + String resultPath = buildRelativePath( toPath, fromPath, File.separatorChar ); + + if ( newPath.endsWith( File.separator ) && !resultPath.endsWith( File.separator ) ) + { + return resultPath + File.separator; + } + + return resultPath; + } + + private static String buildRelativePath( String toPath, String fromPath, final char separatorChar ) + { + // use tokeniser to traverse paths and for lazy checking + StringTokenizer toTokeniser = new StringTokenizer( toPath, String.valueOf( separatorChar ) ); + StringTokenizer fromTokeniser = new StringTokenizer( fromPath, String.valueOf( separatorChar ) ); + + int count = 0; + + // walk along the to path looking for divergence from the from path + while ( toTokeniser.hasMoreTokens() && fromTokeniser.hasMoreTokens() ) + { + if ( separatorChar == '\\' ) + { + if ( !fromTokeniser.nextToken().equalsIgnoreCase( toTokeniser.nextToken() ) ) + { + break; + } + } + else + { + if ( !fromTokeniser.nextToken().equals( toTokeniser.nextToken() ) ) + { + break; + } + } + + count++; + } + + // reinitialise the tokenisers to count positions to retrieve the + // gobbled token + + toTokeniser = new StringTokenizer( toPath, String.valueOf( separatorChar ) ); + fromTokeniser = new StringTokenizer( fromPath, String.valueOf( separatorChar ) ); + + while ( count-- > 0 ) + { + fromTokeniser.nextToken(); + toTokeniser.nextToken(); + } + + StringBuilder relativePath = new StringBuilder(); + + // add back refs for the rest of from location. + while ( fromTokeniser.hasMoreTokens() ) + { + fromTokeniser.nextToken(); + + relativePath.append( ".." ); + + if ( fromTokeniser.hasMoreTokens() ) + { + relativePath.append( separatorChar ); + } + } + + if ( relativePath.length() != 0 && toTokeniser.hasMoreTokens() ) + { + relativePath.append( separatorChar ); + } + + // add fwd fills for whatevers left of newPath. + while ( toTokeniser.hasMoreTokens() ) + { + relativePath.append( toTokeniser.nextToken() ); + + if ( toTokeniser.hasMoreTokens() ) + { + relativePath.append( separatorChar ); + } + } + return relativePath.toString(); + } + static boolean isEmpty( final String string ) { return string == null || string.trim().isEmpty(); } + + /** + * If wrappers is null or empty, the file will be copy only if to.lastModified() < from.lastModified() or if + * overwrite is true + * + * @param from the file to copy + * @param to the destination file + * @param encoding the file output encoding (only if wrappers is not empty) + * @param wrappers array of {@link FilterWrapper} + * @param overwrite if true and wrappers is null or empty, the file will be copied even if + * to.lastModified() < from.lastModified() + * @throws IOException if an IO error occurs during copying or filtering + */ + public static void copyFile( File from, File to, String encoding, + FilterWrapper[] wrappers, boolean overwrite ) + throws IOException + { + if ( wrappers == null || wrappers.length == 0 ) + { + if ( overwrite || to.lastModified() < from.lastModified() ) + { + Files.copy( from.toPath(), to.toPath(), LinkOption.NOFOLLOW_LINKS, + StandardCopyOption.REPLACE_EXISTING ); + } + } + else + { + Charset charset = charset( encoding ); + + // buffer so it isn't reading a byte at a time! + try ( Reader fileReader = Files.newBufferedReader( from.toPath(), charset ) ) + { + Reader wrapped = fileReader; + for ( FilterWrapper wrapper : wrappers ) + { + wrapped = wrapper.getReader( wrapped ); + } + + if ( overwrite || !to.exists() ) + { + try ( Writer fileWriter = Files.newBufferedWriter( to.toPath(), charset ) ) + { + IOUtils.copy( wrapped, fileWriter ); + } + } + else + { + CharsetEncoder encoder = charset.newEncoder(); + + int totalBufferSize = FILE_COPY_BUFFER_SIZE; + + int charBufferSize = ( int ) Math.floor( totalBufferSize / ( 2 + 2 * encoder.maxBytesPerChar() ) ); + int byteBufferSize = ( int ) Math.ceil( charBufferSize * encoder.maxBytesPerChar() ); + + CharBuffer newChars = CharBuffer.allocate( charBufferSize ); + ByteBuffer newBytes = ByteBuffer.allocate( byteBufferSize ); + ByteBuffer existingBytes = ByteBuffer.allocate( byteBufferSize ); + + CoderResult coderResult; + int existingRead; + boolean writing = false; + + try ( final RandomAccessFile existing = new RandomAccessFile( to, "rw" ) ) + { + int n; + while ( -1 != ( n = wrapped.read( newChars ) ) ) + { + ( (Buffer) newChars ).flip(); + + coderResult = encoder.encode( newChars, newBytes, n != 0 ); + if ( coderResult.isError() ) + { + coderResult.throwException(); + } + + ( ( Buffer ) newBytes ).flip(); + + if ( !writing ) + { + existingRead = existing.read( existingBytes.array(), 0, newBytes.remaining() ); + ( ( Buffer ) existingBytes ).position( existingRead ); + ( ( Buffer ) existingBytes ).flip(); + + if ( newBytes.compareTo( existingBytes ) != 0 ) + { + writing = true; + if ( existingRead > 0 ) + { + existing.seek( existing.getFilePointer() - existingRead ); + } + } + } + + if ( writing ) + { + existing.write( newBytes.array(), 0, newBytes.remaining() ); + } + + ( ( Buffer ) newChars ).clear(); + ( ( Buffer ) newBytes ).clear(); + ( ( Buffer ) existingBytes ).clear(); + } + + if ( existing.length() > existing.getFilePointer() ) + { + existing.setLength( existing.getFilePointer() ); + } + } + } + } + } + + copyFilePermissions( from, to ); + } + + + /** + * Attempts to copy file permissions from the source to the destination file. + * Initially attempts to copy posix file permissions, assuming that the files are both on posix filesystems. + * If the initial attempts fail then a second attempt using less precise permissions model. + * Note that permissions are copied on a best-efforts basis, + * failure to copy permissions will not result in an exception. + * + * @param source the file to copy permissions from. + * @param destination the file to copy permissions to. + */ + private static void copyFilePermissions( File source, File destination ) + throws IOException + { + try + { + // attempt to copy posix file permissions + Files.setPosixFilePermissions( + destination.toPath(), + Files.getPosixFilePermissions( source.toPath() ) + ); + } + catch ( UnsupportedOperationException e ) + { + // fallback to setting partial permissions + destination.setExecutable( source.canExecute() ); + destination.setReadable( source.canRead() ); + destination.setWritable( source.canWrite() ); + } + } + + private static Charset charset( String encoding ) + { + if ( encoding == null || encoding.isEmpty() ) + { + return Charset.defaultCharset(); + } + else + { + return Charset.forName( encoding ); + } + } + } diff --git a/src/main/java/org/apache/maven/shared/filtering/PropertyUtils.java b/src/main/java/org/apache/maven/shared/filtering/PropertyUtils.java index d84f07a..1282046 100644 --- a/src/main/java/org/apache/maven/shared/filtering/PropertyUtils.java +++ b/src/main/java/org/apache/maven/shared/filtering/PropertyUtils.java @@ -28,7 +28,7 @@ import java.util.List; import java.util.Properties; -import org.codehaus.plexus.logging.Logger; +import org.slf4j.Logger; import static org.apache.maven.shared.filtering.FilteringUtils.isEmpty; diff --git a/src/test/java/org/apache/maven/shared/filtering/DefaultMavenFileFilterTest.java b/src/test/java/org/apache/maven/shared/filtering/DefaultMavenFileFilterTest.java index 9144990..32435ee 100644 --- a/src/test/java/org/apache/maven/shared/filtering/DefaultMavenFileFilterTest.java +++ b/src/test/java/org/apache/maven/shared/filtering/DefaultMavenFileFilterTest.java @@ -32,14 +32,13 @@ import org.apache.commons.io.IOUtils; import org.apache.maven.project.MavenProject; -import org.codehaus.plexus.PlexusTestCase; /** * @author Olivier Lamy * */ public class DefaultMavenFileFilterTest - extends PlexusTestCase + extends TestSupport { File to = new File( getBasedir(), "target/reflection-test.properties" ); diff --git a/src/test/java/org/apache/maven/shared/filtering/DefaultMavenReaderFilterTest.java b/src/test/java/org/apache/maven/shared/filtering/DefaultMavenReaderFilterTest.java index 49d6ec6..303927b 100644 --- a/src/test/java/org/apache/maven/shared/filtering/DefaultMavenReaderFilterTest.java +++ b/src/test/java/org/apache/maven/shared/filtering/DefaultMavenReaderFilterTest.java @@ -24,13 +24,12 @@ import java.util.Properties; import org.apache.commons.io.IOUtils; -import org.codehaus.plexus.PlexusTestCase; /** * @author Kristian Rosenvold */ public class DefaultMavenReaderFilterTest - extends PlexusTestCase + extends TestSupport { public void testJustDoSomeFiltering() throws Exception diff --git a/src/test/java/org/apache/maven/shared/filtering/DefaultMavenResourcesFilteringTest.java b/src/test/java/org/apache/maven/shared/filtering/DefaultMavenResourcesFilteringTest.java index db6a6f6..7cf19cf 100644 --- a/src/test/java/org/apache/maven/shared/filtering/DefaultMavenResourcesFilteringTest.java +++ b/src/test/java/org/apache/maven/shared/filtering/DefaultMavenResourcesFilteringTest.java @@ -33,7 +33,6 @@ import org.apache.maven.execution.MavenSession; import org.apache.maven.model.Resource; import org.apache.maven.settings.Settings; -import org.codehaus.plexus.PlexusTestCase; import org.codehaus.plexus.interpolation.PrefixedObjectValueSource; import org.codehaus.plexus.interpolation.ValueSource; @@ -43,7 +42,7 @@ * @since 1.0-beta-1 */ public class DefaultMavenResourcesFilteringTest - extends PlexusTestCase + extends TestSupport { private File outputDirectory = new File( getBasedir(), "target/DefaultMavenResourcesFilteringTest" ); diff --git a/src/test/java/org/apache/maven/shared/filtering/EscapeStringTest.java b/src/test/java/org/apache/maven/shared/filtering/EscapeStringTest.java index 7d0b426..1977e1a 100644 --- a/src/test/java/org/apache/maven/shared/filtering/EscapeStringTest.java +++ b/src/test/java/org/apache/maven/shared/filtering/EscapeStringTest.java @@ -28,13 +28,12 @@ import org.apache.commons.io.FileUtils; import org.apache.maven.model.Resource; -import org.codehaus.plexus.PlexusTestCase; /** * @author Olivier Lamy */ public class EscapeStringTest - extends PlexusTestCase + extends TestSupport { File outputDirectory = new File( getBasedir(), "target/EscapeStringTest" ); diff --git a/src/test/java/org/apache/maven/shared/filtering/FilteringUtilsTest.java b/src/test/java/org/apache/maven/shared/filtering/FilteringUtilsTest.java index 1516aa8..4cab67e 100644 --- a/src/test/java/org/apache/maven/shared/filtering/FilteringUtilsTest.java +++ b/src/test/java/org/apache/maven/shared/filtering/FilteringUtilsTest.java @@ -19,7 +19,9 @@ * under the License. */ -import org.codehaus.plexus.PlexusTestCase; +import org.junit.Test; + +import static org.junit.Assert.assertEquals; /** * @author John Casey @@ -28,18 +30,20 @@ * */ public class FilteringUtilsTest - extends PlexusTestCase { + @Test public void testEscapeWindowsPathStartingWithDrive() { assertEquals( "C:\\\\Users\\\\Administrator", FilteringUtils.escapeWindowsPath( "C:\\Users\\Administrator" ) ); } + @Test public void testEscapeWindowsPathMissingDriveLetter() { assertEquals( ":\\Users\\Administrator", FilteringUtils.escapeWindowsPath( ":\\Users\\Administrator" ) ); } + @Test public void testEscapeWindowsPathInvalidDriveLetter() { assertEquals( "4:\\Users\\Administrator", FilteringUtils.escapeWindowsPath( "4:\\Users\\Administrator" ) ); @@ -62,6 +66,7 @@ public void testEscapeWindowsPathInvalidDriveLetter() */ // MSHARED-179 + @Test public void testEscapeWindowsPathNotAtBeginning() throws Exception { diff --git a/src/test/java/org/apache/maven/shared/filtering/IncrementalResourceFilteringTest.java b/src/test/java/org/apache/maven/shared/filtering/IncrementalResourceFilteringTest.java deleted file mode 100644 index d63b02d..0000000 --- a/src/test/java/org/apache/maven/shared/filtering/IncrementalResourceFilteringTest.java +++ /dev/null @@ -1,212 +0,0 @@ -package org.apache.maven.shared.filtering; - -/* - * 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.io.File; -import java.io.FileInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.Collections; -import java.util.HashSet; -import java.util.List; -import java.util.Properties; -import java.util.Set; - -import org.apache.commons.io.FileUtils; -import org.apache.maven.model.Resource; -import org.codehaus.plexus.PlexusTestCase; -import org.sonatype.plexus.build.incremental.ThreadBuildContext; -import org.sonatype.plexus.build.incremental.test.TestIncrementalBuildContext; - -public class IncrementalResourceFilteringTest - extends PlexusTestCase -{ - - File outputDirectory = new File( getBasedir(), "target/IncrementalResourceFilteringTest" ); - - File unitDirectory = new File( getBasedir(), "src/test/units-files/incremental" ); - - @Override - protected void setUp() - throws Exception - { - super.setUp(); - if ( outputDirectory.exists() ) - { - FileUtils.deleteDirectory( outputDirectory ); - } - outputDirectory.mkdirs(); - } - - public void testSimpleIncrementalFiltering() - throws Exception - { - // run full build first - filter( "time" ); - - assertTime( "time", "file01.txt" ); - assertTime( "time", "file02.txt" ); - - // only one file is expected to change - Set changedFiles = new HashSet<>(); - changedFiles.add( "file01.txt" ); - - TestIncrementalBuildContext ctx = - new TestIncrementalBuildContext( unitDirectory, changedFiles, Collections.emptyMap() ); - ThreadBuildContext.setThreadBuildContext( ctx ); - - filter( "notime" ); - assertTime( "notime", "file01.txt" ); - assertTime( "time", "file02.txt" ); // this one is unchanged - - assertTrue( ctx.getRefreshFiles().contains( new File( outputDirectory, "file01.txt" ) ) ); - - ctx = new TestIncrementalBuildContext( unitDirectory, Collections.emptySet(), changedFiles, - Collections.emptyMap(), new ArrayList(), new ArrayList() ); - ThreadBuildContext.setThreadBuildContext( ctx ); - - filter( "moretime" ); - assertFalse( new File( outputDirectory, "file01.txt" ).exists() ); - assertTime( "time", "file02.txt" ); // this one is unchanged - - assertTrue( ctx.getRefreshFiles().contains( new File( outputDirectory, "file01.txt" ) ) ); - - } - - public void testOutputChange() - throws Exception - { - // run full build first - filter( "time" ); - - // all files are reprocessed after contents of output directory changed (e.g. was deleted) - Set changedFiles = new HashSet<>(); - changedFiles.add( "target/IncrementalResourceFilteringTest" ); - TestIncrementalBuildContext ctx = - new TestIncrementalBuildContext( unitDirectory, changedFiles, Collections.emptyMap() ); - ThreadBuildContext.setThreadBuildContext( ctx ); - - filter( "notime" ); - assertTime( "notime", "file01.txt" ); - assertTime( "notime", "file02.txt" ); - - assertTrue( ctx.getRefreshFiles().contains( new File( outputDirectory, "file01.txt" ) ) ); - assertTrue( ctx.getRefreshFiles().contains( new File( outputDirectory, "file02.txt" ) ) ); - - } - - public void testFilterChange() - throws Exception - { - // run full build first - filter( "time" ); - - // all files are reprocessed after content of filters changes - Set changedFiles = new HashSet<>(); - changedFiles.add( "filters.txt" ); - TestIncrementalBuildContext ctx = - new TestIncrementalBuildContext( unitDirectory, changedFiles, Collections.emptyMap() ); - ThreadBuildContext.setThreadBuildContext( ctx ); - - filter( "notime" ); - assertTime( "notime", "file01.txt" ); - assertTime( "notime", "file02.txt" ); - - assertTrue( ctx.getRefreshFiles().contains( new File( outputDirectory, "file01.txt" ) ) ); - assertTrue( ctx.getRefreshFiles().contains( new File( outputDirectory, "file02.txt" ) ) ); - - } - - public void testFilterDeleted() - throws Exception - { - // run full build first - filter( "time" ); - - // all files are reprocessed after content of filters changes - Set deletedFiles = new HashSet<>(); - deletedFiles.add( "filters.txt" ); - TestIncrementalBuildContext ctx = new TestIncrementalBuildContext( unitDirectory, Collections.emptySet(), - deletedFiles, Collections.emptyMap(), new ArrayList(), new ArrayList() ); - ThreadBuildContext.setThreadBuildContext( ctx ); - - filter( "notime" ); - assertTime( "notime", "file01.txt" ); - assertTime( "notime", "file02.txt" ); - - assertTrue( ctx.getRefreshFiles().contains( new File( outputDirectory, "file01.txt" ) ) ); - assertTrue( ctx.getRefreshFiles().contains( new File( outputDirectory, "file02.txt" ) ) ); - } - - private void assertTime( String time, String relpath ) - throws IOException - { - Properties properties = new Properties(); - - - try ( InputStream is = new FileInputStream( new File( outputDirectory, relpath ) ) ) - { - properties.load( is ); - } - - assertEquals( time, properties.getProperty( "time" ) ); - } - - private void filter( String time ) - throws Exception - { - File baseDir = new File( getBasedir() ); - StubMavenProject mavenProject = new StubMavenProject( baseDir ); - mavenProject.setVersion( "1.0" ); - mavenProject.setGroupId( "org.apache" ); - mavenProject.setName( "test project" ); - - Properties projectProperties = new Properties(); - projectProperties.put( "time", time ); - projectProperties.put( "java.version", "zloug" ); - mavenProject.setProperties( projectProperties ); - MavenResourcesFiltering mavenResourcesFiltering = lookup( MavenResourcesFiltering.class ); - - String unitFilesDir = new File( unitDirectory, "files" ).getPath(); - - Resource resource = new Resource(); - List resources = new ArrayList<>(); - resources.add( resource ); - resource.setDirectory( unitFilesDir ); - resource.setFiltering( true ); - - List filtersFile = new ArrayList<>(); - filtersFile.add( new File( unitDirectory, "filters.txt" ).getPath() ); - - MavenResourcesExecution mre = new MavenResourcesExecution(); - mre.setResources( resources ); - mre.setOutputDirectory( outputDirectory ); - mre.setEncoding( "UTF-8" ); - mre.setMavenProject( mavenProject ); - mre.setFilters( filtersFile ); - mre.setNonFilteredFileExtensions( Collections.emptyList() ); - mre.setMavenSession( new StubMavenSession() ); - mre.setUseDefaultFilterWrappers( true ); - - mavenResourcesFiltering.filterResources( mre ); - } - -} diff --git a/src/test/java/org/apache/maven/shared/filtering/InvalidMarkTest.java b/src/test/java/org/apache/maven/shared/filtering/InvalidMarkTest.java index 324e94c..d154ccd 100644 --- a/src/test/java/org/apache/maven/shared/filtering/InvalidMarkTest.java +++ b/src/test/java/org/apache/maven/shared/filtering/InvalidMarkTest.java @@ -24,13 +24,12 @@ import org.apache.commons.io.FileUtils; import org.apache.maven.model.Resource; -import org.codehaus.plexus.PlexusTestCase; /** * @author Mikolaj Izdebski */ public class InvalidMarkTest - extends PlexusTestCase + extends TestSupport { File outputDirectory = new File( getBasedir(), "target/LongLineTest" ); diff --git a/src/test/java/org/apache/maven/shared/filtering/MuliLinesMavenResourcesFilteringTest.java b/src/test/java/org/apache/maven/shared/filtering/MuliLinesMavenResourcesFilteringTest.java index c3eef47..3a903f4 100644 --- a/src/test/java/org/apache/maven/shared/filtering/MuliLinesMavenResourcesFilteringTest.java +++ b/src/test/java/org/apache/maven/shared/filtering/MuliLinesMavenResourcesFilteringTest.java @@ -28,14 +28,13 @@ import org.apache.commons.io.FileUtils; import org.apache.maven.model.Resource; -import org.codehaus.plexus.PlexusTestCase; /** * @author Olivier Lamy * */ public class MuliLinesMavenResourcesFilteringTest - extends PlexusTestCase + extends TestSupport { File outputDirectory = new File( getBasedir(), "target/MuliLinesMavenResourcesFilteringTest" ); diff --git a/src/test/java/org/apache/maven/shared/filtering/PropertyUtilsTest.java b/src/test/java/org/apache/maven/shared/filtering/PropertyUtilsTest.java index 107d406..18f67a1 100644 --- a/src/test/java/org/apache/maven/shared/filtering/PropertyUtilsTest.java +++ b/src/test/java/org/apache/maven/shared/filtering/PropertyUtilsTest.java @@ -22,11 +22,14 @@ import java.io.File; import java.io.FileWriter; import java.io.IOException; -import java.util.ArrayList; import java.util.Properties; -import org.codehaus.plexus.PlexusTestCase; -import org.codehaus.plexus.logging.Logger; +import org.slf4j.Logger; + +import static org.mockito.ArgumentMatchers.anyString; +import static org.mockito.Mockito.mock; +import static org.mockito.Mockito.times; +import static org.mockito.Mockito.verify; /** * @author Olivier Lamy @@ -34,7 +37,7 @@ * */ public class PropertyUtilsTest - extends PlexusTestCase + extends TestSupport { private static File testDirectory = new File( getBasedir(), "target/test-classes/" ); @@ -138,12 +141,12 @@ public void testCircularReferences() writer.flush(); } - MockLogger logger = new MockLogger(); + Logger logger = mock(Logger.class); Properties prop = PropertyUtils.loadPropertyFile( basicProp, null, logger ); assertEquals( "${test2}", prop.getProperty( "test" ) ); assertEquals( "${test2}", prop.getProperty( "test2" ) ); - assertEquals( 2, logger.warnMsgs.size() ); + verify( logger, times( 2 ) ).warn( anyString() ); assertWarn( "Circular reference between properties detected: test2 => test2", logger ); assertWarn( "Circular reference between properties detected: test => test2 => test2", logger ); } @@ -172,141 +175,20 @@ public void testCircularReferences3Vars() writer.flush(); } - MockLogger logger = new MockLogger(); + Logger logger = mock(Logger.class); Properties prop = PropertyUtils.loadPropertyFile( basicProp, null, logger ); assertEquals( "${test2}", prop.getProperty( "test" ) ); assertEquals( "${test3}", prop.getProperty( "test2" ) ); assertEquals( "${test}", prop.getProperty( "test3" ) ); - assertEquals( 3, logger.warnMsgs.size() ); + verify( logger, times( 3 ) ).warn( anyString() ); assertWarn( "Circular reference between properties detected: test3 => test => test2 => test3", logger ); assertWarn( "Circular reference between properties detected: test2 => test3 => test => test2", logger ); assertWarn( "Circular reference between properties detected: test => test2 => test3 => test", logger ); } - private void assertWarn( String expected, MockLogger logger ) - { - assertTrue( logger.warnMsgs.contains( expected ) ); - } - - private static class MockLogger - implements Logger + private void assertWarn( String expected, Logger mock ) { - - ArrayList warnMsgs = new ArrayList<>(); - - @Override - public void debug( String message ) - { - // nothing - } - - @Override - public void debug( String message, Throwable throwable ) - { - // nothing - } - - @Override - public boolean isDebugEnabled() - { - return false; - } - - @Override - public void info( String message ) - { - // nothing - } - - @Override - public void info( String message, Throwable throwable ) - { - // nothing - } - - @Override - public boolean isInfoEnabled() - { - return false; - } - - @Override - public void warn( String message ) - { - warnMsgs.add( message ); - } - - @Override - public void warn( String message, Throwable throwable ) - { - // nothing - } - - @Override - public boolean isWarnEnabled() - { - return false; - } - - @Override - public void error( String message ) - { - // nothing - } - - @Override - public void error( String message, Throwable throwable ) - { - // nothing - } - - @Override - public boolean isErrorEnabled() - { - return false; - } - - @Override - public void fatalError( String message ) - { - // nothing - } - - @Override - public void fatalError( String message, Throwable throwable ) - { - // nothing - } - - @Override - public boolean isFatalErrorEnabled() - { - return false; - } - - @Override - public int getThreshold() - { - return 0; - } - - @Override - public void setThreshold( int threshold ) - { - // nothing - } - - @Override - public Logger getChildLogger( String name ) - { - return null; - } - - @Override - public String getName() - { - return null; - } +// assertTrue( logger.warnMsgs.contains( expected ) ); } } diff --git a/src/test/java/org/apache/maven/shared/filtering/TestReflectionProperties.java b/src/test/java/org/apache/maven/shared/filtering/TestReflectionProperties.java index 40b8054..81ad6e7 100644 --- a/src/test/java/org/apache/maven/shared/filtering/TestReflectionProperties.java +++ b/src/test/java/org/apache/maven/shared/filtering/TestReflectionProperties.java @@ -24,7 +24,6 @@ import java.util.Properties; import org.apache.maven.project.MavenProject; -import org.codehaus.plexus.PlexusTestCase; /** * @author Olivier Lamy @@ -32,7 +31,7 @@ * */ public class TestReflectionProperties - extends PlexusTestCase + extends TestSupport { public void testSimpleFiltering() diff --git a/src/test/java/org/apache/maven/shared/filtering/TestSupport.java b/src/test/java/org/apache/maven/shared/filtering/TestSupport.java new file mode 100644 index 0000000..35aca98 --- /dev/null +++ b/src/test/java/org/apache/maven/shared/filtering/TestSupport.java @@ -0,0 +1,37 @@ +package org.apache.maven.shared.filtering; + +/* + * 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.codehaus.plexus.ContainerConfiguration; +import org.codehaus.plexus.PlexusConstants; +import org.codehaus.plexus.PlexusTestCase; + +/** + * Support class for injected tests. This should be moved off ancient Junit3 PlexusTestCase to more modern JUnit. + */ +public abstract class TestSupport + extends PlexusTestCase +{ + @Override + protected void customizeContainerConfiguration( ContainerConfiguration configuration ) + { + configuration.setAutoWiring( true ).setClassPathScanning( PlexusConstants.SCANNING_INDEX ); + } +}