mirror of
https://github.com/spring-projects/spring-boot.git
synced 2026-09-17 12:09:16 +00:00
Merge branch '3.5.x' into 4.0.x
Closes gh-50131
This commit is contained in:
+16
-7
@@ -489,8 +489,8 @@ class ExtractCommand extends Command {
|
||||
public @Nullable File resolve(String originalName, String newName) throws IOException {
|
||||
String layer = this.layers.getLayer(originalName);
|
||||
if (shouldExtractLayer(layer)) {
|
||||
File directory = getLayerDirectory(layer);
|
||||
return assertFileIsContainedInDirectory(directory, new File(directory, newName), newName);
|
||||
File layerDirectory = getLayerDirectory(layer);
|
||||
return assertFileIsContainedInDirectory(layerDirectory, new File(layerDirectory, newName), newName);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
@@ -499,21 +499,30 @@ class ExtractCommand extends Command {
|
||||
public @Nullable File resolveApplication() throws IOException {
|
||||
String layer = this.layers.getApplicationLayerName();
|
||||
if (shouldExtractLayer(layer)) {
|
||||
File directory = getLayerDirectory(layer);
|
||||
return assertFileIsContainedInDirectory(directory, new File(directory, this.applicationFilename),
|
||||
this.applicationFilename);
|
||||
File layerDirectory = getLayerDirectory(layer);
|
||||
return assertFileIsContainedInDirectory(layerDirectory,
|
||||
new File(layerDirectory, this.applicationFilename), this.applicationFilename);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private File getLayerDirectory(String layer) {
|
||||
return new File(this.directory, layer);
|
||||
private File getLayerDirectory(String layer) throws IOException {
|
||||
return assertLayerDirectoryLocation(new File(this.directory, layer), layer);
|
||||
}
|
||||
|
||||
private boolean shouldExtractLayer(String layer) {
|
||||
return this.layersToExtract.isEmpty() || this.layersToExtract.contains(layer);
|
||||
}
|
||||
|
||||
private File assertLayerDirectoryLocation(File layerDirectory, String layerName) throws IOException {
|
||||
String canonicalOutputPath = this.directory.getCanonicalPath() + File.separator;
|
||||
String canonicalLayerPath = layerDirectory.getCanonicalPath();
|
||||
Assert.state(canonicalLayerPath.startsWith(canonicalOutputPath),
|
||||
() -> "Layer '%s' would be written to '%s'. This is outside the output location of '%s'. Verify the contents of your archive."
|
||||
.formatted(layerName, canonicalLayerPath, canonicalOutputPath));
|
||||
return layerDirectory;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+28
@@ -174,6 +174,34 @@ class ExtractLayersCommandTests {
|
||||
.withMessageContaining("Entry 'e/../../e.jar' would be written");
|
||||
}
|
||||
|
||||
@Test
|
||||
void runWithLayerNameThatWouldWriteEntriesOutsideDestinationFails() throws Exception {
|
||||
this.command = new ExtractLayersCommand(this.context, new Layers() {
|
||||
|
||||
@Override
|
||||
public Iterator<String> iterator() {
|
||||
return Arrays.asList("a", "b", "c").iterator();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getLayer(String entryName) {
|
||||
return "../../outside-layer";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getApplicationLayerName() {
|
||||
return "application";
|
||||
}
|
||||
|
||||
});
|
||||
this.jarFile = createJarFile("test.jar");
|
||||
given(this.context.getArchiveFile()).willReturn(this.jarFile);
|
||||
given(this.context.getWorkingDir()).willReturn(this.extract);
|
||||
assertThatIllegalStateException()
|
||||
.isThrownBy(() -> this.command.run(System.out, Collections.emptyMap(), Collections.emptyList()))
|
||||
.withMessageContaining("Layer '../../outside-layer' would be written to");
|
||||
}
|
||||
|
||||
private File createJarFile(String name) throws Exception {
|
||||
return createJarFile(name, (out) -> {
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user