From d3f1fc6502cec6c484f9d85f18107438e1816f6a Mon Sep 17 00:00:00 2001 From: "pavol.misudik" Date: Tue, 9 Jun 2026 12:11:54 +0200 Subject: [PATCH 1/2] Fix "Empty input" when loading SSL_CERT_FILE/SSL_CERT_DIR cert bundles. --- api/src/main/java/io/minio/Http.java | 4 +- .../minio/HttpExternalCertificatesTest.java | 85 +++++++++++++++++++ 2 files changed, 87 insertions(+), 2 deletions(-) create mode 100644 api/src/test/java/io/minio/HttpExternalCertificatesTest.java diff --git a/api/src/main/java/io/minio/Http.java b/api/src/main/java/io/minio/Http.java index a61226839..fd8872073 100644 --- a/api/src/main/java/io/minio/Http.java +++ b/api/src/main/java/io/minio/Http.java @@ -37,6 +37,7 @@ import java.security.KeyStoreException; import java.security.NoSuchAlgorithmException; import java.security.SecureRandom; +import java.security.cert.Certificate; import java.security.cert.CertificateException; import java.security.cert.CertificateFactory; import java.security.cert.X509Certificate; @@ -451,8 +452,7 @@ private static int setCertificateEntry( throws CertificateException, IOException, KeyStoreException { try (InputStream in = Files.newInputStream(file)) { int index = 0; - while (in.available() > 0) { - X509Certificate cert = (X509Certificate) cf.generateCertificate(in); + for (Certificate cert : cf.generateCertificates(in)) { ks.setCertificateEntry(namePrefix + (index++), cert); } return index; diff --git a/api/src/test/java/io/minio/HttpExternalCertificatesTest.java b/api/src/test/java/io/minio/HttpExternalCertificatesTest.java new file mode 100644 index 000000000..db2862fa5 --- /dev/null +++ b/api/src/test/java/io/minio/HttpExternalCertificatesTest.java @@ -0,0 +1,85 @@ +/* + * MinIO Java SDK for Amazon S3 Compatible Cloud Storage, + * (C) 2026 MinIO, Inc. + * + * Licensed 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 io.minio; + +import java.io.File; +import java.nio.charset.StandardCharsets; +import java.nio.file.Files; +import java.util.Arrays; +import java.util.Collection; +import okhttp3.OkHttpClient; +import org.junit.Assert; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.junit.runners.Parameterized; +import org.junit.runners.Parameterized.Parameter; +import org.junit.runners.Parameterized.Parameters; + +@RunWith(Parameterized.class) +public class HttpExternalCertificatesTest { + private static final String CERT = + "-----BEGIN CERTIFICATE-----\n" + + "MIIC8TCCAdmgAwIBAgIIVQI5/aydlf4wDQYJKoZIhvcNAQEMBQAwJzElMCMGA1UE\n" + + "AxMcbWluaW8tamF2YS10ZXN0LWUwZWVmYWQwYjRiZTAeFw0yNjA2MDkwOTI4MDNa\n" + + "Fw0zNjA2MDYwOTI4MDNaMCcxJTAjBgNVBAMTHG1pbmlvLWphdmEtdGVzdC1lMGVl\n" + + "ZmFkMGI0YmUwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQC2wswKet+8\n" + + "P0KEPycjP0cUeWtVuzwReMG4iMJxU80xg6rHzHW33tx89HEyhqBM0tAhnOlv8uyN\n" + + "dIlLQRKMNj2U82PW1DNfDqvahCqI1P5HEcqmHXYMXUIIuHQ42Vaq5Jw6LfUT5Xp3\n" + + "OskJuXsrqhJ/lI2tjO2IA6Ihq2qWH8HMK13usrRU8ercMi3v3l+NmE2v9cAYNjDn\n" + + "y+wE4TGIjxBnOcR7fSF6zcMydiu371FD53o3any47BGcjQrf11KuToMWCI6xRyox\n" + + "oRFif2heDNtPlm+sN7fLoz8RozLLN0GCT1+g3RfLDnbMOD/Zpl4JSSW+ZW43wrhH\n" + + "Kt+M32Wg1mvjAgMBAAGjITAfMB0GA1UdDgQWBBQc31QOSV+G44gzEaP0Nzki7+3j\n" + + "zDANBgkqhkiG9w0BAQwFAAOCAQEAbS1xk1KS7yflxFHcD0kdwaUi3y+zsD7JEqPo\n" + + "YtZsJB3YZF+7mCLcvpQpeOj/YjjS4Nfm+BTiBEm4iQ10XYJqq7Ld8+b37Lu0lUwq\n" + + "BEM05XdGqIy2ZElYLB4uwai/foAPqpASbtqfuF3k/r7Iv+vuLAcNDIZ95gpIbgyS\n" + + "1VezowSP4jSTlIISFhUlTJwD4sSA4FpdBs2JytjdQ+5bRbQPKC2lTRNUjDzIHWN0\n" + + "FcA+xu6MMlXe1EtVYSPPRoHnc/qBE0yEiyBglgqETxd1XUGuCZfCNSAICMafHtua\n" + + "DppeWJHfHv2CXNFva0iicwzYJ5kqoeJF8GAU3+QD0TMx59IfwA==\n" + + "-----END CERTIFICATE-----\n"; + + @Parameters(name = "{0}") + public static Collection bundles() { + return Arrays.asList( + new Object[][] { + {"single trailing newline", CERT}, + {"no trailing newline", CERT.trim()}, + {"trailing blank line", CERT + "\n"}, + {"trailing whitespace", CERT + " \n"}, + }); + } + + @Parameter() + public String name; + + @Parameter(1) + public String bundle; + + @Test + public void loadsExternalCertificateBundle() throws Exception { + String path = writeBundle(bundle); + OkHttpClient client = Http.enableExternalCertificates(new OkHttpClient(), path, null); + Assert.assertNotNull(client); + } + + private static String writeBundle(String content) throws Exception { + File file = File.createTempFile("minio-ca-bundle", ".pem"); + file.deleteOnExit(); + Files.write(file.toPath(), content.getBytes(StandardCharsets.UTF_8)); + return file.getAbsolutePath(); + } +} From 12571169a74d3d6605f572436c8bf8d58d3cc512 Mon Sep 17 00:00:00 2001 From: "pavol.misudik" Date: Sat, 13 Jun 2026 13:02:49 +0200 Subject: [PATCH 2/2] spotless --- api/src/test/java/io/minio/HttpExternalCertificatesTest.java | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/api/src/test/java/io/minio/HttpExternalCertificatesTest.java b/api/src/test/java/io/minio/HttpExternalCertificatesTest.java index db2862fa5..32f711bd4 100644 --- a/api/src/test/java/io/minio/HttpExternalCertificatesTest.java +++ b/api/src/test/java/io/minio/HttpExternalCertificatesTest.java @@ -63,8 +63,7 @@ public static Collection bundles() { }); } - @Parameter() - public String name; + @Parameter() public String name; @Parameter(1) public String bundle;