This is an automated email from the ASF dual-hosted git repository. twolf pushed a commit to branch dev_3.0 in repository https://gitbox.apache.org/repos/asf/mina-sshd.git
commit 0afa5fb2bd96a834ebce814057753bdf57d8859c Author: Thomas Wolf <[email protected]> AuthorDate: Sat Mar 28 23:15:55 2026 +0100 [releng] Bump testcontainers to 2.0.4 Upgrade from 1.21.3 to 2.0.4. --- pom.xml | 2 +- sshd-scp/pom.xml | 2 +- sshd-sftp/pom.xml | 4 +- .../sshd/sftp/client/SftpPerformanceTest.java | 247 --------------------- .../sshd/sftp/client/fs/SftpFileSystemTest.java | 22 +- sshd-test/pom.xml | 4 +- 6 files changed, 9 insertions(+), 272 deletions(-) diff --git a/pom.xml b/pom.xml index d491a25ff..1d5f02fd7 100644 --- a/pom.xml +++ b/pom.xml @@ -108,7 +108,7 @@ <jgit.version>5.13.5.202508271544-r</jgit.version> <!-- mockito 5.0 requires Java 11. --> <mockito.version>4.11.0</mockito.version> - <testcontainers.version>1.21.3</testcontainers.version> + <testcontainers.version>2.0.4</testcontainers.version> <grpc.version>1.78.0</grpc.version> <!-- Used only in tests --> <maven.archiver.version>3.6.5</maven.archiver.version> diff --git a/sshd-scp/pom.xml b/sshd-scp/pom.xml index aa34e2c38..02944357a 100644 --- a/sshd-scp/pom.xml +++ b/sshd-scp/pom.xml @@ -82,7 +82,7 @@ </dependency> <dependency> <groupId>org.testcontainers</groupId> - <artifactId>junit-jupiter</artifactId> + <artifactId>testcontainers-junit-jupiter</artifactId> <scope>test</scope> </dependency> </dependencies> diff --git a/sshd-sftp/pom.xml b/sshd-sftp/pom.xml index 994bef6e7..cccdc0005 100644 --- a/sshd-sftp/pom.xml +++ b/sshd-sftp/pom.xml @@ -77,12 +77,12 @@ </dependency> <dependency> <groupId>org.testcontainers</groupId> - <artifactId>junit-jupiter</artifactId> + <artifactId>testcontainers-junit-jupiter</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.testcontainers</groupId> - <artifactId>toxiproxy</artifactId> + <artifactId>testcontainers-toxiproxy</artifactId> <scope>test</scope> </dependency> </dependencies> diff --git a/sshd-sftp/src/test/java/org/apache/sshd/sftp/client/SftpPerformanceTest.java b/sshd-sftp/src/test/java/org/apache/sshd/sftp/client/SftpPerformanceTest.java deleted file mode 100644 index 51eb5f341..000000000 --- a/sshd-sftp/src/test/java/org/apache/sshd/sftp/client/SftpPerformanceTest.java +++ /dev/null @@ -1,247 +0,0 @@ -/* - * 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. - */ -package org.apache.sshd.sftp.client; - -import java.io.BufferedInputStream; -import java.io.BufferedOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; -import java.nio.file.Files; -import java.nio.file.Path; -import java.nio.file.Paths; -import java.nio.file.StandardOpenOption; -import java.time.Duration; -import java.util.Arrays; - -import eu.rekawek.toxiproxy.model.ToxicDirection; -import eu.rekawek.toxiproxy.model.toxic.Latency; -import org.apache.sshd.client.SshClient; -import org.apache.sshd.client.config.hosts.HostConfigEntryResolver; -import org.apache.sshd.client.keyverifier.AcceptAllServerKeyVerifier; -import org.apache.sshd.client.session.ClientSession; -import org.apache.sshd.common.keyprovider.KeyIdentityProvider; -import org.apache.sshd.sftp.client.SftpClient.OpenMode; -import org.apache.sshd.sftp.client.fs.SftpFileSystem; -import org.apache.sshd.util.test.CoreTestSupportUtils; -import org.junit.Rule; -import org.junit.jupiter.api.Disabled; -import org.junit.jupiter.api.Test; -import org.testcontainers.containers.GenericContainer; -import org.testcontainers.containers.Network; -import org.testcontainers.containers.ToxiproxyContainer; -import org.testcontainers.containers.ToxiproxyContainer.ContainerProxy; - -@Disabled("Special class used for development only - not really a test just useful to run as such") -public class SftpPerformanceTest { - public static final Duration SFTP_CONNECT_TIMEOUT = CoreTestSupportUtils.getTimeout("sftp.connect", Duration.ofSeconds(30)); - public static final Duration SFTP_AUTH_TIMEOUT = CoreTestSupportUtils.getTimeout("sftp.auth", Duration.ofSeconds(15)); - - public static final String USERNAME = "foo"; - public static final String PASSWORD = "pass"; - - // Create a common docker network so that containers can communicate - @Rule - public Network network = Network.newNetwork(); - - // the target container - this could be anything - @Rule - public GenericContainer<?> sftp = new GenericContainer<>("atmoz/sftp") - .withEnv("SFTP_USERS", USERNAME + ":" + PASSWORD) - .withNetwork(network) - .withFileSystemBind("target", "/home/foo") - .withExposedPorts(22); - - // Toxiproxy container, which will be used as a TCP proxy - @Rule - public ToxiproxyContainer toxiproxy = new ToxiproxyContainer() - .withNetwork(network); - - public SftpPerformanceTest() { - super(); - } - - @Test - void uploadLatency() throws IOException { - final ContainerProxy proxy = toxiproxy.getProxy(sftp, 22); - for (int latency : Arrays.asList(0, 1, 5, 10, 50, 100, 500)) { - Latency toxic = proxy.toxics().latency("latency", ToxicDirection.DOWNSTREAM, latency); - for (int megabytes : Arrays.asList(1, 5, 10, 50, 100)) { - try (SshClient client = createSshClient()) { - long orgTime; - long newTime; - try (ClientSession session = createClientSession(client, proxy)) { - orgTime = uploadPrevious(session, megabytes); - } - try (ClientSession session = createClientSession(client, proxy)) { - newTime = uploadOptimized(session, megabytes); - } - System.out.println(String.format("%3d MB / %3d ms latency: %7d down to %5d ms, gain = %d%%", - megabytes, latency, orgTime, newTime, - (int) (100 * (orgTime - newTime) / orgTime))); - } - } - toxic.remove(); - } - } - - @Test - void downloadLatency() throws IOException { - final ContainerProxy proxy = toxiproxy.getProxy(sftp, 22); - for (int latency : Arrays.asList(0, 1, 5, 10, 50, 100, 500)) { - Latency toxic = proxy.toxics().latency("latency", ToxicDirection.DOWNSTREAM, latency); - for (int megabytes : Arrays.asList(1, 5, 10, 50, 100)) { - try (SshClient client = createSshClient()) { - long orgTime; - long newTime; - try (ClientSession session = createClientSession(client, proxy)) { - newTime = downloadOptimized(session, megabytes); - } - try (ClientSession session = createClientSession(client, proxy)) { - orgTime = downloadPrevious(session, megabytes); - } - System.out.println(String.format("%3d MB / %3d ms latency: %7d down to %5d ms, gain = %d%%", - megabytes, latency, orgTime, newTime, - (int) (100 * (orgTime - newTime) / orgTime))); - } - } - toxic.remove(); - } - } - - public ClientSession createClientSession(SshClient client, ContainerProxy proxy) throws IOException { - final String ipAddressViaToxiproxy = proxy.getContainerIpAddress(); - final int portViaToxiproxy = proxy.getProxyPort(); - - ClientSession session = client.connect(USERNAME, ipAddressViaToxiproxy, portViaToxiproxy) - .verify(SFTP_CONNECT_TIMEOUT) - .getClientSession(); - session.addPasswordIdentity(PASSWORD); - session.auth().verify(SFTP_AUTH_TIMEOUT); - return session; - } - - public SshClient createSshClient() { - SshClient client = SshClient.setUpDefaultClient(); - client.setServerKeyVerifier(AcceptAllServerKeyVerifier.INSTANCE); - client.setHostConfigEntryResolver(HostConfigEntryResolver.EMPTY); - client.setKeyIdentityProvider(KeyIdentityProvider.EMPTY_KEYS_PROVIDER); - client.start(); - return client; - } - - public long uploadPrevious(ClientSession session, int mb) throws IOException { - long t0 = System.currentTimeMillis(); - try (SftpClient client = SftpClientFactory.instance().createSftpClient(session)) { - try (OutputStream os = new BufferedOutputStream( - new SftpOutputStreamWithChannel( - client, 32768, "out.txt", - Arrays.asList(OpenMode.Write, - OpenMode.Create, - OpenMode.Truncate)), - 32768)) { - byte[] bytes = "123456789abcdef\n".getBytes(); - for (int i = 0; i < 1024 * 1024 * mb / bytes.length; i++) { - os.write(bytes); - } - } - } - long t1 = System.currentTimeMillis(); - return t1 - t0; - } - - public long uploadOptimized(ClientSession session, int mb) throws IOException { - long t0 = System.currentTimeMillis(); - try (SftpFileSystem fs = SftpClientFactory.instance().createSftpFileSystem(session)) { - Path p = fs.getPath("out.txt"); - try (OutputStream os = new BufferedOutputStream( - Files.newOutputStream(p, StandardOpenOption.CREATE, - StandardOpenOption.TRUNCATE_EXISTING), - 32768)) { - byte[] bytes = "123456789abcdef\n".getBytes(); - for (int i = 0; i < 1024 * 1024 * mb / bytes.length; i++) { - os.write(bytes); - } - } - } - long t1 = System.currentTimeMillis(); - return t1 - t0; - } - - public long downloadPrevious(ClientSession session, int mb) throws IOException { - Path f = Paths.get("target/out.txt"); - byte[] bytes = "123456789abcdef\n".getBytes(); - try (BufferedOutputStream bos = new BufferedOutputStream( - Files.newOutputStream(f, StandardOpenOption.CREATE, - StandardOpenOption.TRUNCATE_EXISTING, - StandardOpenOption.WRITE))) { - for (int i = 0; i < 1024 * 1024 * mb / bytes.length; i++) { - bos.write(bytes); - } - } - long t0 = System.currentTimeMillis(); - try (SftpClient client = SftpClientFactory.instance().createSftpClient(session)) { - try (InputStream os = new BufferedInputStream( - new SftpInputStreamWithChannel( - client, 32768, "out.txt", - Arrays.asList(OpenMode.Read)), - 32768)) { - byte[] data = new byte[8192]; - for (int i = 0; i < 1024 * 1024 * mb / data.length; i++) { - int l = os.read(data); - if (l < 0) { - break; - } - } - } - } - long t1 = System.currentTimeMillis(); - return t1 - t0; - } - - public long downloadOptimized(ClientSession session, int mb) throws IOException { - Path f = Paths.get("target/out.txt"); - byte[] bytes = "123456789abcdef\n".getBytes(); - try (BufferedOutputStream bos = new BufferedOutputStream( - Files.newOutputStream(f, StandardOpenOption.CREATE, - StandardOpenOption.TRUNCATE_EXISTING, - StandardOpenOption.WRITE))) { - for (int i = 0; i < 1024 * 1024 * mb / bytes.length; i++) { - bos.write(bytes); - } - } - long t0 = System.currentTimeMillis(); - try (SftpFileSystem fs = SftpClientFactory.instance().createSftpFileSystem(session)) { - Path p = fs.getPath("out.txt"); - try (InputStream os = new BufferedInputStream( - Files.newInputStream(p, StandardOpenOption.READ), 32768)) { - byte[] data = new byte[8192]; - for (int i = 0; i < 1024 * 1024 * mb / data.length; i++) { - int l = os.read(data); - if (l < 0) { - break; - } - } - } - } - long t1 = System.currentTimeMillis(); - return t1 - t0; - } - -} diff --git a/sshd-sftp/src/test/java/org/apache/sshd/sftp/client/fs/SftpFileSystemTest.java b/sshd-sftp/src/test/java/org/apache/sshd/sftp/client/fs/SftpFileSystemTest.java index 931541d59..49430eabb 100644 --- a/sshd-sftp/src/test/java/org/apache/sshd/sftp/client/fs/SftpFileSystemTest.java +++ b/sshd-sftp/src/test/java/org/apache/sshd/sftp/client/fs/SftpFileSystemTest.java @@ -88,8 +88,6 @@ import org.apache.sshd.sftp.server.SftpSubsystemEnvironment; import org.apache.sshd.sftp.server.SftpSubsystemFactory; import org.apache.sshd.util.test.CommonTestSupportUtils; import org.apache.sshd.util.test.CoreTestSupportUtils; -import org.hamcrest.BaseMatcher; -import org.hamcrest.Description; import org.junit.jupiter.api.Assumptions; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.MethodOrderer.MethodName; @@ -100,8 +98,6 @@ import org.junit.jupiter.params.provider.CsvSource; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import static org.hamcrest.MatcherAssert.assertThat; - /** * @author <a href="mailto:[email protected]">Apache MINA SSHD Project</a> */ @@ -398,21 +394,9 @@ class SftpFileSystemTest extends AbstractSftpFilesSystemSupport { assertTrue(readDirCount.get() > 0, "Upstream server not called"); // The current implementation stats 3 times: once to detect whether the directory exists, is a directory, // and is readable; once again for the "." entry, and the parent directory once for "..". - assertThat( - "Files.getAttributes() should have been called at most a few times for the directory itself", - statCount.get(), new BaseMatcher<Integer>() { - - @Override - public boolean matches(Object item) { - return item instanceof Integer && ((Integer) item).intValue() < 4; - } - - @Override - public void describeTo(Description description) { - description.appendText("smaller than 4"); - } - }); - + assertTrue(statCount.get() < 4, + "Files.getAttributes() should have been called at most a few times for the directory itself; expected less than 4 calls but got " + + statCount.get()); // Repeat this a few times to get slightly more reliable timings final int maxRepeats = 10; long directTime = 0; diff --git a/sshd-test/pom.xml b/sshd-test/pom.xml index e05cf9812..0fe0b7297 100644 --- a/sshd-test/pom.xml +++ b/sshd-test/pom.xml @@ -1,4 +1,4 @@ -<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="https://maven.apache.org/POM/4.0.0 https://maven.apache.org/maven-v4_0_0.xsd"> +<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/maven-v4_0_0.xsd"> <!-- Licensed to the Apache Software Foundation (ASF) under one or more @@ -91,7 +91,7 @@ </dependency> <dependency> <groupId>org.testcontainers</groupId> - <artifactId>junit-jupiter</artifactId> + <artifactId>testcontainers-junit-jupiter</artifactId> <scope>test</scope> </dependency> <dependency>
