From 0709bce35cc5043b6d2b1ddf81583a1d3c0d6f05 Mon Sep 17 00:00:00 2001 From: Paul Schaub Date: Tue, 31 Jan 2023 18:20:27 +0100 Subject: [PATCH] Allow for extension of test suite from 3rd party SOP implementations --- .woodpecker/.build.yml | 2 +- external-sop/build.gradle | 16 +- .../sop/{ => testsuite}/external/.gitignore | 0 .../{ => testsuite}/external/config.json.ci | 0 .../external/config.json.example | 0 ...ternalDetachedSignVerifyRoundTripTest.java | 263 ------------------ .../external/ExternalSOPInstanceFactory.java} | 32 +-- .../operation/ExternalArmorDearmorTest.java | 11 + .../ExternalDecryptWithSessionKeyTest.java | 11 + ...xternalDetachedSignDetachedVerifyTest.java | 10 + .../operation/ExternalEncryptDecryptTest.java | 11 + .../operation/ExternalExtractCertTest.java | 11 + .../operation/ExternalGenerateKeyTest.java | 11 + ...ineSignInlineDetachDetachedVerifyTest.java | 12 + .../ExternalInlineSignInlineVerifyTest.java | 11 + .../operation/ExternalVersionTest.java | 11 + sop-java/build.gradle | 4 +- .../java/sop/testing/package-info.java | 8 - .../sop/{testing => testsuite}/JUtils.java | 2 +- .../sop/testsuite/SOPInstanceFactory.java | 30 ++ .../sop/{testing => testsuite}/TestData.java | 2 +- .../testsuite/operation/AbstractSOPTest.java | 51 ++++ .../testsuite/operation/ArmorDearmorTest.java | 101 ++++--- .../operation/DecryptWithSessionKeyTest.java | 27 +- .../DetachedSignDetachedVerifyTest.java | 250 +++++++++++++++++ .../operation/EncryptDecryptTest.java | 106 ++++--- .../testsuite/operation/ExtractCertTest.java | 54 ++-- .../testsuite/operation/GenerateKeyTest.java | 54 ++-- ...ineSignInlineDetachDetachedVerifyTest.java | 39 +-- .../operation/InlineSignInlineVerifyTest.java | 98 ++++--- .../sop/testsuite/operation/VersionTest.java | 24 +- .../sop/testsuite/operation/package-info.java | 8 + .../java/sop/testsuite/package-info.java | 8 + 33 files changed, 731 insertions(+), 547 deletions(-) rename external-sop/src/main/resources/sop/{ => testsuite}/external/.gitignore (100%) rename external-sop/src/main/resources/sop/{ => testsuite}/external/config.json.ci (100%) rename external-sop/src/main/resources/sop/{ => testsuite}/external/config.json.example (100%) delete mode 100644 external-sop/src/test/java/sop/external/ExternalDetachedSignVerifyRoundTripTest.java rename external-sop/src/test/java/sop/{external/AbstractExternalSOPTest.java => testsuite/external/ExternalSOPInstanceFactory.java} (65%) create mode 100644 external-sop/src/test/java/sop/testsuite/external/operation/ExternalArmorDearmorTest.java create mode 100644 external-sop/src/test/java/sop/testsuite/external/operation/ExternalDecryptWithSessionKeyTest.java create mode 100644 external-sop/src/test/java/sop/testsuite/external/operation/ExternalDetachedSignDetachedVerifyTest.java create mode 100644 external-sop/src/test/java/sop/testsuite/external/operation/ExternalEncryptDecryptTest.java create mode 100644 external-sop/src/test/java/sop/testsuite/external/operation/ExternalExtractCertTest.java create mode 100644 external-sop/src/test/java/sop/testsuite/external/operation/ExternalGenerateKeyTest.java create mode 100644 external-sop/src/test/java/sop/testsuite/external/operation/ExternalInlineSignInlineDetachDetachedVerifyTest.java create mode 100644 external-sop/src/test/java/sop/testsuite/external/operation/ExternalInlineSignInlineVerifyTest.java create mode 100644 external-sop/src/test/java/sop/testsuite/external/operation/ExternalVersionTest.java delete mode 100644 sop-java/src/testFixtures/java/sop/testing/package-info.java rename sop-java/src/testFixtures/java/sop/{testing => testsuite}/JUtils.java (99%) create mode 100644 sop-java/src/testFixtures/java/sop/testsuite/SOPInstanceFactory.java rename sop-java/src/testFixtures/java/sop/{testing => testsuite}/TestData.java (99%) create mode 100644 sop-java/src/testFixtures/java/sop/testsuite/operation/AbstractSOPTest.java rename external-sop/src/test/java/sop/external/ExternalArmorDearmorRoundTripTest.java => sop-java/src/testFixtures/java/sop/testsuite/operation/ArmorDearmorTest.java (62%) rename external-sop/src/test/java/sop/external/ExternalDecryptWithSessionKeyTest.java => sop-java/src/testFixtures/java/sop/testsuite/operation/DecryptWithSessionKeyTest.java (70%) create mode 100644 sop-java/src/testFixtures/java/sop/testsuite/operation/DetachedSignDetachedVerifyTest.java rename external-sop/src/test/java/sop/external/ExternalEncryptDecryptRoundTripTest.java => sop-java/src/testFixtures/java/sop/testsuite/operation/EncryptDecryptTest.java (72%) rename external-sop/src/test/java/sop/external/ExternalExtractCertTest.java => sop-java/src/testFixtures/java/sop/testsuite/operation/ExtractCertTest.java (59%) rename external-sop/src/test/java/sop/external/ExternalGenerateKeyTest.java => sop-java/src/testFixtures/java/sop/testsuite/operation/GenerateKeyTest.java (53%) rename external-sop/src/test/java/sop/external/ExternalInlineSignDetachVerifyRoundTripTest.java => sop-java/src/testFixtures/java/sop/testsuite/operation/InlineSignInlineDetachDetachedVerifyTest.java (68%) rename external-sop/src/test/java/sop/external/ExternalInlineSignVerifyTest.java => sop-java/src/testFixtures/java/sop/testsuite/operation/InlineSignInlineVerifyTest.java (62%) rename external-sop/src/test/java/sop/external/ExternalVersionTest.java => sop-java/src/testFixtures/java/sop/testsuite/operation/VersionTest.java (65%) create mode 100644 sop-java/src/testFixtures/java/sop/testsuite/operation/package-info.java create mode 100644 sop-java/src/testFixtures/java/sop/testsuite/package-info.java diff --git a/.woodpecker/.build.yml b/.woodpecker/.build.yml index e235f7f..d72d19e 100644 --- a/.woodpecker/.build.yml +++ b/.woodpecker/.build.yml @@ -7,7 +7,7 @@ pipeline: # Checkout code - git checkout $CI_COMMIT_BRANCH # Prepare CI - - cp external-sop/src/main/resources/sop/external/config.json.ci external-sop/src/main/resources/sop/external/config.json + - cp external-sop/src/main/resources/sop/testsuite/external/config.json.ci external-sop/src/main/resources/sop/testsuite/external/config.json # Code works - gradle test # Code is clean diff --git a/external-sop/build.gradle b/external-sop/build.gradle index bd45c71..acd55f6 100644 --- a/external-sop/build.gradle +++ b/external-sop/build.gradle @@ -16,21 +16,27 @@ dependencies { testImplementation "org.junit.jupiter:junit-jupiter-api:$junitVersion" testImplementation "org.junit.jupiter:junit-jupiter-params:$junitVersion" testRuntimeOnly "org.junit.jupiter:junit-jupiter-engine:$junitVersion" - // Read json config file - testImplementation "com.google.code.gson:gson:2.10.1" api project(":sop-java") - testImplementation(testFixtures(project(":sop-java"))) - api "org.slf4j:slf4j-api:$slf4jVersion" testImplementation "ch.qos.logback:logback-classic:$logbackVersion" // @Nonnull, @Nullable... implementation "com.google.code.findbugs:jsr305:$jsrVersion" + + // The ExternalTestSubjectFactory reads json config file to find configured SOP binaries... + testImplementation "com.google.code.gson:gson:2.10.1" + // ...and extends TestSubjectFactory + testImplementation(testFixtures(project(":sop-java"))) } test { + // Inject configured external SOP instances using our custom TestSubjectFactory + environment("test.implementation", "sop.testsuite.external.ExternalSOPInstanceFactory") + useJUnitPlatform() + // since we test external backends, we ignore test failures in this module ignoreFailures = true -} \ No newline at end of file +} + diff --git a/external-sop/src/main/resources/sop/external/.gitignore b/external-sop/src/main/resources/sop/testsuite/external/.gitignore similarity index 100% rename from external-sop/src/main/resources/sop/external/.gitignore rename to external-sop/src/main/resources/sop/testsuite/external/.gitignore diff --git a/external-sop/src/main/resources/sop/external/config.json.ci b/external-sop/src/main/resources/sop/testsuite/external/config.json.ci similarity index 100% rename from external-sop/src/main/resources/sop/external/config.json.ci rename to external-sop/src/main/resources/sop/testsuite/external/config.json.ci diff --git a/external-sop/src/main/resources/sop/external/config.json.example b/external-sop/src/main/resources/sop/testsuite/external/config.json.example similarity index 100% rename from external-sop/src/main/resources/sop/external/config.json.example rename to external-sop/src/main/resources/sop/testsuite/external/config.json.example diff --git a/external-sop/src/test/java/sop/external/ExternalDetachedSignVerifyRoundTripTest.java b/external-sop/src/test/java/sop/external/ExternalDetachedSignVerifyRoundTripTest.java deleted file mode 100644 index e08d7a9..0000000 --- a/external-sop/src/test/java/sop/external/ExternalDetachedSignVerifyRoundTripTest.java +++ /dev/null @@ -1,263 +0,0 @@ -// SPDX-FileCopyrightText: 2023 Paul Schaub -// -// SPDX-License-Identifier: Apache-2.0 - -package sop.external; - -import org.junit.jupiter.api.condition.EnabledIf; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.MethodSource; -import sop.SOP; -import sop.Verification; -import sop.enums.SignAs; -import sop.exception.SOPGPException; - -import java.io.IOException; -import java.nio.charset.StandardCharsets; -import java.util.Date; -import java.util.List; - -import static org.junit.jupiter.api.Assertions.assertFalse; -import static org.junit.jupiter.api.Assertions.assertThrows; -import static sop.testing.JUtils.assertArrayStartsWith; -import static sop.testing.JUtils.assertSignedBy; -import static sop.testing.TestData.ALICE_CERT; -import static sop.testing.TestData.ALICE_DETACHED_SIGNED_MESSAGE; -import static sop.testing.TestData.ALICE_DETACHED_SIGNED_MESSAGE_DATE; -import static sop.testing.TestData.ALICE_KEY; -import static sop.testing.TestData.ALICE_PRIMARY_FINGERPRINT; -import static sop.testing.TestData.ALICE_SIGNING_FINGERPRINT; -import static sop.testing.TestData.BEGIN_PGP_SIGNATURE; -import static sop.testing.TestData.BOB_CERT; -import static sop.testing.TestData.BOB_KEY; -import static sop.testing.TestData.BOB_PRIMARY_FINGERPRINT; -import static sop.testing.TestData.BOB_SIGNING_FINGERPRINT; -import static sop.testing.TestData.CAROL_CERT; -import static sop.testing.TestData.CAROL_KEY; -import static sop.testing.TestData.CAROL_PRIMARY_FINGERPRINT; -import static sop.testing.TestData.CAROL_SIGNING_FINGERPRINT; -import static sop.testing.TestData.PASSWORD; -import static sop.testing.TestData.PASSWORD_PROTECTED_CERT; -import static sop.testing.TestData.PASSWORD_PROTECTED_KEY; -import static sop.testing.TestData.PLAINTEXT; - -@EnabledIf("sop.external.AbstractExternalSOPTest#hasBackends") -public class ExternalDetachedSignVerifyRoundTripTest extends AbstractExternalSOPTest { - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void signVerifyWithAliceKey(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - - byte[] signature = sop.detachedSign() - .key(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) - .data(message) - .toByteArrayAndResult() - .getBytes(); - - List verificationList = sop.detachedVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) - .signatures(signature) - .data(message); - - assertFalse(verificationList.isEmpty()); - assertSignedBy(verificationList, ALICE_SIGNING_FINGERPRINT, ALICE_PRIMARY_FINGERPRINT); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void signVerifyTextModeWithAliceKey(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - - byte[] signature = sop.detachedSign() - .key(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) - .mode(SignAs.Text) - .data(message) - .toByteArrayAndResult() - .getBytes(); - - List verificationList = sop.detachedVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) - .signatures(signature) - .data(message); - - assertFalse(verificationList.isEmpty()); - assertSignedBy(verificationList, ALICE_SIGNING_FINGERPRINT, ALICE_PRIMARY_FINGERPRINT); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void verifyKnownMessageWithAliceCert(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - byte[] signature = ALICE_DETACHED_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8); - - List verificationList = sop.detachedVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) - .signatures(signature) - .data(message); - - assertFalse(verificationList.isEmpty()); - assertSignedBy(verificationList, ALICE_SIGNING_FINGERPRINT, ALICE_PRIMARY_FINGERPRINT, ALICE_DETACHED_SIGNED_MESSAGE_DATE); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void signVerifyWithBobKey(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - - byte[] signature = sop.detachedSign() - .key(BOB_KEY.getBytes(StandardCharsets.UTF_8)) - .data(message) - .toByteArrayAndResult() - .getBytes(); - - List verificationList = sop.detachedVerify() - .cert(BOB_CERT.getBytes(StandardCharsets.UTF_8)) - .signatures(signature) - .data(message); - - assertFalse(verificationList.isEmpty()); - assertSignedBy(verificationList, BOB_SIGNING_FINGERPRINT, BOB_PRIMARY_FINGERPRINT); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void signVerifyWithCarolKey(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - - byte[] signature = sop.detachedSign() - .key(CAROL_KEY.getBytes(StandardCharsets.UTF_8)) - .data(message) - .toByteArrayAndResult() - .getBytes(); - - List verificationList = sop.detachedVerify() - .cert(CAROL_CERT.getBytes(StandardCharsets.UTF_8)) - .signatures(signature) - .data(message); - - assertFalse(verificationList.isEmpty()); - assertSignedBy(verificationList, CAROL_SIGNING_FINGERPRINT, CAROL_PRIMARY_FINGERPRINT); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void signVerifyWithEncryptedKey(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - - byte[] signature = sop.detachedSign() - .key(PASSWORD_PROTECTED_KEY.getBytes(StandardCharsets.UTF_8)) - .withKeyPassword(PASSWORD) - .data(message) - .toByteArrayAndResult() - .getBytes(); - - assertArrayStartsWith(signature, BEGIN_PGP_SIGNATURE); - - List verificationList = sop.detachedVerify() - .cert(PASSWORD_PROTECTED_CERT.getBytes(StandardCharsets.UTF_8)) - .signatures(signature) - .data(message); - - assertFalse(verificationList.isEmpty()); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void signArmorVerifyWithBobKey(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - - byte[] signature = sop.detachedSign() - .key(BOB_KEY.getBytes(StandardCharsets.UTF_8)) - .noArmor() - .data(message) - .toByteArrayAndResult() - .getBytes(); - - byte[] armored = sop.armor() - .data(signature) - .getBytes(); - - List verificationList = sop.detachedVerify() - .cert(BOB_CERT.getBytes(StandardCharsets.UTF_8)) - .signatures(armored) - .data(message); - - assertFalse(verificationList.isEmpty()); - assertSignedBy(verificationList, BOB_SIGNING_FINGERPRINT, BOB_PRIMARY_FINGERPRINT); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void verifyNotAfterThrowsNoSignature(SOP sop) { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - byte[] signature = ALICE_DETACHED_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8); - Date beforeSignature = new Date(ALICE_DETACHED_SIGNED_MESSAGE_DATE.getTime() - 1000); // 1 sec before sig - - assertThrows(SOPGPException.NoSignature.class, () -> sop.detachedVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) - .notAfter(beforeSignature) - .signatures(signature) - .data(message)); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void verifyNotBeforeThrowsNoSignature(SOP sop) { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - byte[] signature = ALICE_DETACHED_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8); - Date afterSignature = new Date(ALICE_DETACHED_SIGNED_MESSAGE_DATE.getTime() + 1000); // 1 sec after sig - - assertThrows(SOPGPException.NoSignature.class, () -> sop.detachedVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) - .notBefore(afterSignature) - .signatures(signature) - .data(message)); - } - - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void signVerifyWithEncryptedKeyWithoutPassphraseFails(SOP sop) { - assertThrows(SOPGPException.KeyIsProtected.class, () -> - sop.detachedSign() - .key(PASSWORD_PROTECTED_KEY.getBytes(StandardCharsets.UTF_8)) - .data(PLAINTEXT.getBytes(StandardCharsets.UTF_8)) - .toByteArrayAndResult() - .getBytes()); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void signWithProtectedKeyAndMultiplePassphrasesTest(SOP sop) - throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - - byte[] signature = sop.sign() - .key(PASSWORD_PROTECTED_KEY.getBytes(StandardCharsets.UTF_8)) - .withKeyPassword("wrong") - .withKeyPassword(PASSWORD) // correct - .withKeyPassword("wrong2") - .data(message) - .toByteArrayAndResult() - .getBytes(); - - assertFalse(sop.verify() - .cert(PASSWORD_PROTECTED_CERT.getBytes(StandardCharsets.UTF_8)) - .signatures(signature) - .data(message) - .isEmpty()); - } - - @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") - public void verifyMissingCertCausesMissingArg(SOP sop) { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); - - assertThrows(SOPGPException.MissingArg.class, () -> - sop.verify() - .signatures(ALICE_DETACHED_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8)) - .data(message)); - } - -} diff --git a/external-sop/src/test/java/sop/external/AbstractExternalSOPTest.java b/external-sop/src/test/java/sop/testsuite/external/ExternalSOPInstanceFactory.java similarity index 65% rename from external-sop/src/test/java/sop/external/AbstractExternalSOPTest.java rename to external-sop/src/test/java/sop/testsuite/external/ExternalSOPInstanceFactory.java index 824990f..aa051ff 100644 --- a/external-sop/src/test/java/sop/external/AbstractExternalSOPTest.java +++ b/external-sop/src/test/java/sop/testsuite/external/ExternalSOPInstanceFactory.java @@ -2,26 +2,26 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.external; +package sop.testsuite.external; import com.google.gson.Gson; -import org.junit.jupiter.api.Named; -import org.junit.jupiter.params.provider.Arguments; import sop.SOP; +import sop.external.ExternalSOP; +import sop.testsuite.SOPInstanceFactory; import java.io.File; import java.io.InputStream; import java.io.InputStreamReader; -import java.util.ArrayList; +import java.util.HashMap; import java.util.List; +import java.util.Map; import java.util.Properties; -import java.util.stream.Stream; -public abstract class AbstractExternalSOPTest { +public class ExternalSOPInstanceFactory extends SOPInstanceFactory { - private static final List backends = new ArrayList<>(); - - static { + @Override + public Map provideSOPInstances() { + Map backends = new HashMap<>(); TestSuite suite = readConfiguration(); if (suite != null && !suite.backends.isEmpty()) { for (TestSubject subject : suite.backends) { @@ -37,30 +37,24 @@ public abstract class AbstractExternalSOPTest { } SOP sop = new ExternalSOP(subject.sop, env); - backends.add(Arguments.of(Named.of(subject.name, sop))); + backends.put(subject.name, sop); } } + return backends; } - public static Stream provideBackends() { - return backends.stream(); - } public static TestSuite readConfiguration() { Gson gson = new Gson(); - InputStream inputStream = AbstractExternalSOPTest.class.getResourceAsStream("config.json"); + InputStream inputStream = ExternalSOPInstanceFactory.class.getResourceAsStream("config.json"); if (inputStream == null) { return null; } InputStreamReader reader = new InputStreamReader(inputStream); - TestSuite suite = gson.fromJson(reader, TestSuite.class); - return suite; + return gson.fromJson(reader, TestSuite.class); } - public static boolean hasBackends() { - return !backends.isEmpty(); - } // JSON DTOs diff --git a/external-sop/src/test/java/sop/testsuite/external/operation/ExternalArmorDearmorTest.java b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalArmorDearmorTest.java new file mode 100644 index 0000000..f3ee7be --- /dev/null +++ b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalArmorDearmorTest.java @@ -0,0 +1,11 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.external.operation; + +import sop.testsuite.operation.ArmorDearmorTest; + +public class ExternalArmorDearmorTest extends ArmorDearmorTest { + +} diff --git a/external-sop/src/test/java/sop/testsuite/external/operation/ExternalDecryptWithSessionKeyTest.java b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalDecryptWithSessionKeyTest.java new file mode 100644 index 0000000..4f9364d --- /dev/null +++ b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalDecryptWithSessionKeyTest.java @@ -0,0 +1,11 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.external.operation; + +import sop.testsuite.operation.DecryptWithSessionKeyTest; + +public class ExternalDecryptWithSessionKeyTest extends DecryptWithSessionKeyTest { + +} diff --git a/external-sop/src/test/java/sop/testsuite/external/operation/ExternalDetachedSignDetachedVerifyTest.java b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalDetachedSignDetachedVerifyTest.java new file mode 100644 index 0000000..b831295 --- /dev/null +++ b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalDetachedSignDetachedVerifyTest.java @@ -0,0 +1,10 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.external.operation; + +import sop.testsuite.operation.DetachedSignDetachedVerifyTest; + +public class ExternalDetachedSignDetachedVerifyTest extends DetachedSignDetachedVerifyTest { +} diff --git a/external-sop/src/test/java/sop/testsuite/external/operation/ExternalEncryptDecryptTest.java b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalEncryptDecryptTest.java new file mode 100644 index 0000000..3584c95 --- /dev/null +++ b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalEncryptDecryptTest.java @@ -0,0 +1,11 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.external.operation; + +import sop.testsuite.operation.EncryptDecryptTest; + +public class ExternalEncryptDecryptTest extends EncryptDecryptTest { + +} diff --git a/external-sop/src/test/java/sop/testsuite/external/operation/ExternalExtractCertTest.java b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalExtractCertTest.java new file mode 100644 index 0000000..47cd8e1 --- /dev/null +++ b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalExtractCertTest.java @@ -0,0 +1,11 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.external.operation; + +import sop.testsuite.operation.ExtractCertTest; + +public class ExternalExtractCertTest extends ExtractCertTest { + +} diff --git a/external-sop/src/test/java/sop/testsuite/external/operation/ExternalGenerateKeyTest.java b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalGenerateKeyTest.java new file mode 100644 index 0000000..6352736 --- /dev/null +++ b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalGenerateKeyTest.java @@ -0,0 +1,11 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.external.operation; + +import sop.testsuite.operation.GenerateKeyTest; + +public class ExternalGenerateKeyTest extends GenerateKeyTest { + +} diff --git a/external-sop/src/test/java/sop/testsuite/external/operation/ExternalInlineSignInlineDetachDetachedVerifyTest.java b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalInlineSignInlineDetachDetachedVerifyTest.java new file mode 100644 index 0000000..48633f3 --- /dev/null +++ b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalInlineSignInlineDetachDetachedVerifyTest.java @@ -0,0 +1,12 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.external.operation; + +import sop.testsuite.operation.InlineSignInlineDetachDetachedVerifyTest; + +public class ExternalInlineSignInlineDetachDetachedVerifyTest + extends InlineSignInlineDetachDetachedVerifyTest { + +} diff --git a/external-sop/src/test/java/sop/testsuite/external/operation/ExternalInlineSignInlineVerifyTest.java b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalInlineSignInlineVerifyTest.java new file mode 100644 index 0000000..705b05f --- /dev/null +++ b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalInlineSignInlineVerifyTest.java @@ -0,0 +1,11 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.external.operation; + +import sop.testsuite.operation.InlineSignInlineVerifyTest; + +public class ExternalInlineSignInlineVerifyTest extends InlineSignInlineVerifyTest { + +} diff --git a/external-sop/src/test/java/sop/testsuite/external/operation/ExternalVersionTest.java b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalVersionTest.java new file mode 100644 index 0000000..4c0e3a3 --- /dev/null +++ b/external-sop/src/test/java/sop/testsuite/external/operation/ExternalVersionTest.java @@ -0,0 +1,11 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.external.operation; + +import sop.testsuite.operation.VersionTest; + +public class ExternalVersionTest extends VersionTest { + +} diff --git a/sop-java/build.gradle b/sop-java/build.gradle index 0211189..c958610 100644 --- a/sop-java/build.gradle +++ b/sop-java/build.gradle @@ -15,10 +15,12 @@ repositories { dependencies { testImplementation "org.junit.jupiter:junit-jupiter-api:$junitVersion" + testImplementation "org.junit.jupiter:junit-jupiter-params:$junitVersion" testRuntimeOnly "org.junit.jupiter:junit-jupiter-engine:$junitVersion" testFixturesImplementation "org.junit.jupiter:junit-jupiter-api:$junitVersion" + testFixturesImplementation "org.junit.jupiter:junit-jupiter-params:$junitVersion" } test { useJUnitPlatform() -} \ No newline at end of file +} diff --git a/sop-java/src/testFixtures/java/sop/testing/package-info.java b/sop-java/src/testFixtures/java/sop/testing/package-info.java deleted file mode 100644 index 1d4527a..0000000 --- a/sop-java/src/testFixtures/java/sop/testing/package-info.java +++ /dev/null @@ -1,8 +0,0 @@ -// SPDX-FileCopyrightText: 2021 Paul Schaub -// -// SPDX-License-Identifier: Apache-2.0 - -/** - * Stateless OpenPGP Interface for Java. - */ -package sop.testing; diff --git a/sop-java/src/testFixtures/java/sop/testing/JUtils.java b/sop-java/src/testFixtures/java/sop/testsuite/JUtils.java similarity index 99% rename from sop-java/src/testFixtures/java/sop/testing/JUtils.java rename to sop-java/src/testFixtures/java/sop/testsuite/JUtils.java index 99f5a5f..c30d86b 100644 --- a/sop-java/src/testFixtures/java/sop/testing/JUtils.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/JUtils.java @@ -2,7 +2,7 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.testing; +package sop.testsuite; import sop.Verification; import sop.util.UTCUtil; diff --git a/sop-java/src/testFixtures/java/sop/testsuite/SOPInstanceFactory.java b/sop-java/src/testFixtures/java/sop/testsuite/SOPInstanceFactory.java new file mode 100644 index 0000000..106c494 --- /dev/null +++ b/sop-java/src/testFixtures/java/sop/testsuite/SOPInstanceFactory.java @@ -0,0 +1,30 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite; + +import sop.SOP; + +import java.util.Map; + +/** + * Factory class to instantiate SOP implementations for testing. + * Overwrite this class and the {@link #provideSOPInstances()} method to return the SOP instances you want + * to test. + * Then, add the following line to your
build.gradle
files
dependencies
section: + *
{@code
+ *     testImplementation(testFixtures("org.pgpainless:sop-java:"))
+ * }
+ * To inject the factory class into the test suite, add the following line to your modules
test
task: + *
{@code
+ *     environment("test.implementation", "org.example.YourTestSubjectFactory")
+ * }
+ * Next, in your
test
sources, extend all test classes from the
testFixtures
+ *
sop.operation
package. + * Take a look at the
external-sop
module for an example. + */ +public abstract class SOPInstanceFactory { + + public abstract Map provideSOPInstances(); +} diff --git a/sop-java/src/testFixtures/java/sop/testing/TestData.java b/sop-java/src/testFixtures/java/sop/testsuite/TestData.java similarity index 99% rename from sop-java/src/testFixtures/java/sop/testing/TestData.java rename to sop-java/src/testFixtures/java/sop/testsuite/TestData.java index f573eef..e1d35c2 100644 --- a/sop-java/src/testFixtures/java/sop/testing/TestData.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/TestData.java @@ -2,7 +2,7 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.testing; +package sop.testsuite; import sop.util.UTCUtil; diff --git a/sop-java/src/testFixtures/java/sop/testsuite/operation/AbstractSOPTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/AbstractSOPTest.java new file mode 100644 index 0000000..fa9cbbf --- /dev/null +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/AbstractSOPTest.java @@ -0,0 +1,51 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.operation; + +import org.junit.jupiter.api.Named; +import org.junit.jupiter.params.provider.Arguments; +import sop.SOP; +import sop.testsuite.SOPInstanceFactory; + +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import java.util.stream.Stream; + +public abstract class AbstractSOPTest { + + private static final List backends = new ArrayList<>(); + + static { + // populate instances list via configured test subject factory + String factoryName = System.getenv("test.implementation"); + if (factoryName != null) { + try { + Class testSubjectFactoryClass = Class.forName(factoryName); + SOPInstanceFactory factory = (SOPInstanceFactory) testSubjectFactoryClass.newInstance(); + Map testSubjects = factory.provideSOPInstances(); + + for (String key : testSubjects.keySet()) { + backends.add(Arguments.of(Named.of(key, testSubjects.get(key)))); + } + } catch (ClassNotFoundException e) { + throw new RuntimeException(e); + } catch (InstantiationException e) { + throw new RuntimeException(e); + } catch (IllegalAccessException e) { + throw new RuntimeException(e); + } + } + } + + public static Stream provideBackends() { + return backends.stream(); + } + + public static boolean hasBackends() { + return !backends.isEmpty(); + } + +} diff --git a/external-sop/src/test/java/sop/external/ExternalArmorDearmorRoundTripTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/ArmorDearmorTest.java similarity index 62% rename from external-sop/src/test/java/sop/external/ExternalArmorDearmorRoundTripTest.java rename to sop-java/src/testFixtures/java/sop/testsuite/operation/ArmorDearmorTest.java index f1d29e6..ce3427a 100644 --- a/external-sop/src/test/java/sop/external/ExternalArmorDearmorRoundTripTest.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/ArmorDearmorTest.java @@ -2,37 +2,32 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.external; +package sop.testsuite.operation; +import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.condition.EnabledIf; import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; import org.junit.jupiter.params.provider.MethodSource; import sop.SOP; -import sop.testing.TestData; +import sop.testsuite.JUtils; +import sop.testsuite.TestData; import java.io.IOException; import java.nio.charset.StandardCharsets; +import java.util.stream.Stream; import static org.junit.jupiter.api.Assertions.assertArrayEquals; -import static org.junit.jupiter.api.Assertions.assertFalse; -import static sop.testing.JUtils.arrayStartsWith; -import static sop.testing.JUtils.assertArrayEndsWithIgnoreNewlines; -import static sop.testing.JUtils.assertArrayStartsWith; -import static sop.testing.JUtils.assertAsciiArmorEquals; -import static sop.testing.TestData.BEGIN_PGP_MESSAGE; -import static sop.testing.TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK; -import static sop.testing.TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK; -import static sop.testing.TestData.BEGIN_PGP_SIGNATURE; -import static sop.testing.TestData.END_PGP_MESSAGE; -import static sop.testing.TestData.END_PGP_PRIVATE_KEY_BLOCK; -import static sop.testing.TestData.END_PGP_PUBLIC_KEY_BLOCK; -import static sop.testing.TestData.END_PGP_SIGNATURE; -@EnabledIf("sop.external.AbstractExternalSOPTest#hasBackends") -public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { +@EnabledIf("sop.operation.AbstractSOPTest#hasBackends") +public class ArmorDearmorTest { + + static Stream provideInstances() { + return AbstractSOPTest.provideBackends(); + } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void dearmorArmorAliceKey(SOP sop) throws IOException { byte[] aliceKey = TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8); @@ -40,20 +35,20 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { .data(aliceKey) .getBytes(); - assertFalse(arrayStartsWith(dearmored, BEGIN_PGP_PRIVATE_KEY_BLOCK)); + Assertions.assertFalse(JUtils.arrayStartsWith(dearmored, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK)); byte[] armored = sop.armor() .data(dearmored) .getBytes(); - assertArrayStartsWith(armored, BEGIN_PGP_PRIVATE_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(armored, END_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayStartsWith(armored, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(armored, TestData.END_PGP_PRIVATE_KEY_BLOCK); // assertAsciiArmorEquals(aliceKey, armored); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void dearmorArmorAliceCert(SOP sop) throws IOException { byte[] aliceCert = TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8); @@ -61,20 +56,20 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { .data(aliceCert) .getBytes(); - assertFalse(arrayStartsWith(dearmored, BEGIN_PGP_PUBLIC_KEY_BLOCK)); + Assertions.assertFalse(JUtils.arrayStartsWith(dearmored, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK)); byte[] armored = sop.armor() .data(dearmored) .getBytes(); - assertArrayStartsWith(armored, BEGIN_PGP_PUBLIC_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(armored, END_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayStartsWith(armored, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(armored, TestData.END_PGP_PUBLIC_KEY_BLOCK); // assertAsciiArmorEquals(aliceCert, armored); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void dearmorArmorBobKey(SOP sop) throws IOException { byte[] bobKey = TestData.BOB_KEY.getBytes(StandardCharsets.UTF_8); @@ -82,20 +77,20 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { .data(bobKey) .getBytes(); - assertFalse(arrayStartsWith(dearmored, BEGIN_PGP_PRIVATE_KEY_BLOCK)); + Assertions.assertFalse(JUtils.arrayStartsWith(dearmored, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK)); byte[] armored = sop.armor() .data(dearmored) .getBytes(); - assertArrayStartsWith(armored, BEGIN_PGP_PRIVATE_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(armored, END_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayStartsWith(armored, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(armored, TestData.END_PGP_PRIVATE_KEY_BLOCK); // assertAsciiArmorEquals(bobKey, armored); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void dearmorArmorBobCert(SOP sop) throws IOException { byte[] bobCert = TestData.BOB_CERT.getBytes(StandardCharsets.UTF_8); @@ -103,20 +98,20 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { .data(bobCert) .getBytes(); - assertFalse(arrayStartsWith(dearmored, BEGIN_PGP_PUBLIC_KEY_BLOCK)); + Assertions.assertFalse(JUtils.arrayStartsWith(dearmored, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK)); byte[] armored = sop.armor() .data(dearmored) .getBytes(); - assertArrayStartsWith(armored, BEGIN_PGP_PUBLIC_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(armored, END_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayStartsWith(armored, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(armored, TestData.END_PGP_PUBLIC_KEY_BLOCK); // assertAsciiArmorEquals(bobCert, armored); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void dearmorArmorCarolKey(SOP sop) throws IOException { byte[] carolKey = TestData.CAROL_KEY.getBytes(StandardCharsets.UTF_8); @@ -124,20 +119,20 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { .data(carolKey) .getBytes(); - assertFalse(arrayStartsWith(dearmored, BEGIN_PGP_PRIVATE_KEY_BLOCK)); + Assertions.assertFalse(JUtils.arrayStartsWith(dearmored, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK)); byte[] armored = sop.armor() .data(dearmored) .getBytes(); - assertArrayStartsWith(armored, BEGIN_PGP_PRIVATE_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(armored, END_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayStartsWith(armored, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(armored, TestData.END_PGP_PRIVATE_KEY_BLOCK); // assertAsciiArmorEquals(carolKey, armored); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void dearmorArmorCarolCert(SOP sop) throws IOException { byte[] carolCert = TestData.CAROL_CERT.getBytes(StandardCharsets.UTF_8); @@ -145,20 +140,20 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { .data(carolCert) .getBytes(); - assertFalse(arrayStartsWith(dearmored, BEGIN_PGP_PUBLIC_KEY_BLOCK)); + Assertions.assertFalse(JUtils.arrayStartsWith(dearmored, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK)); byte[] armored = sop.armor() .data(dearmored) .getBytes(); - assertArrayStartsWith(armored, BEGIN_PGP_PUBLIC_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(armored, END_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayStartsWith(armored, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(armored, TestData.END_PGP_PUBLIC_KEY_BLOCK); // assertAsciiArmorEquals(carolCert, armored); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void dearmorArmorMessage(SOP sop) throws IOException { byte[] message = ("-----BEGIN PGP MESSAGE-----\n" + "\n" + @@ -172,20 +167,20 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { .data(message) .getBytes(); - assertFalse(arrayStartsWith(dearmored, BEGIN_PGP_MESSAGE)); + Assertions.assertFalse(JUtils.arrayStartsWith(dearmored, TestData.BEGIN_PGP_MESSAGE)); byte[] armored = sop.armor() .data(dearmored) .getBytes(); - assertArrayStartsWith(armored, BEGIN_PGP_MESSAGE); - assertArrayEndsWithIgnoreNewlines(armored, END_PGP_MESSAGE); + JUtils.assertArrayStartsWith(armored, TestData.BEGIN_PGP_MESSAGE); + JUtils.assertArrayEndsWithIgnoreNewlines(armored, TestData.END_PGP_MESSAGE); // assertAsciiArmorEquals(message, armored); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void dearmorArmorSignature(SOP sop) throws IOException { byte[] signature = ("-----BEGIN PGP SIGNATURE-----\n" + "\n" + @@ -200,20 +195,20 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { .data(signature) .getBytes(); - assertFalse(arrayStartsWith(dearmored, BEGIN_PGP_SIGNATURE)); + Assertions.assertFalse(JUtils.arrayStartsWith(dearmored, TestData.BEGIN_PGP_SIGNATURE)); byte[] armored = sop.armor() .data(dearmored) .getBytes(); - assertArrayStartsWith(armored, BEGIN_PGP_SIGNATURE); - assertArrayEndsWithIgnoreNewlines(armored, END_PGP_SIGNATURE); + JUtils.assertArrayStartsWith(armored, TestData.BEGIN_PGP_SIGNATURE); + JUtils.assertArrayEndsWithIgnoreNewlines(armored, TestData.END_PGP_SIGNATURE); - assertAsciiArmorEquals(signature, armored); + JUtils.assertAsciiArmorEquals(signature, armored); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void testDearmoringTwiceIsIdempotent(SOP sop) throws IOException { byte[] dearmored = sop.dearmor() .data(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) @@ -227,7 +222,7 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void testArmoringTwiceIsIdempotent(SOP sop) throws IOException { byte[] armored = ("-----BEGIN PGP SIGNATURE-----\n" + "\n" + @@ -242,7 +237,7 @@ public class ExternalArmorDearmorRoundTripTest extends AbstractExternalSOPTest { .data(armored) .getBytes(); - assertAsciiArmorEquals(armored, armoredAgain); + JUtils.assertAsciiArmorEquals(armored, armoredAgain); } } diff --git a/external-sop/src/test/java/sop/external/ExternalDecryptWithSessionKeyTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/DecryptWithSessionKeyTest.java similarity index 70% rename from external-sop/src/test/java/sop/external/ExternalDecryptWithSessionKeyTest.java rename to sop-java/src/testFixtures/java/sop/testsuite/operation/DecryptWithSessionKeyTest.java index b75ec04..2321770 100644 --- a/external-sop/src/test/java/sop/external/ExternalDecryptWithSessionKeyTest.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/DecryptWithSessionKeyTest.java @@ -2,26 +2,27 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.external; +package sop.testsuite.operation; +import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.condition.EnabledIf; import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; import org.junit.jupiter.params.provider.MethodSource; import sop.ByteArrayAndResult; import sop.DecryptionResult; import sop.SOP; import sop.SessionKey; +import sop.testsuite.TestData; import java.io.IOException; import java.nio.charset.StandardCharsets; +import java.util.stream.Stream; -import static org.junit.jupiter.api.Assertions.assertArrayEquals; import static org.junit.jupiter.api.Assertions.assertEquals; -import static sop.testing.TestData.ALICE_KEY; -import static sop.testing.TestData.PLAINTEXT; -@EnabledIf("sop.external.AbstractExternalSOPTest#hasBackends") -public class ExternalDecryptWithSessionKeyTest extends AbstractExternalSOPTest { +@EnabledIf("sop.operation.AbstractSOPTest#hasBackends") +public class DecryptWithSessionKeyTest extends AbstractSOPTest { private static final String CIPHERTEXT = "-----BEGIN PGP MESSAGE-----\n" + "\n" + @@ -33,21 +34,25 @@ public class ExternalDecryptWithSessionKeyTest extends AbstractExternalSOPTest { "-----END PGP MESSAGE-----\n"; private static final String SESSION_KEY = "9:ED682800F5FEA829A82E8B7DDF8CE9CF4BF9BB45024B017764462EE53101C36A"; + static Stream provideInstances() { + return provideBackends(); + } + @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void testDecryptAndExtractSessionKey(SOP sop) throws IOException { ByteArrayAndResult bytesAndResult = sop.decrypt() - .withKey(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .withKey(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .ciphertext(CIPHERTEXT.getBytes(StandardCharsets.UTF_8)) .toByteArrayAndResult(); assertEquals(SESSION_KEY, bytesAndResult.getResult().getSessionKey().get().toString()); - assertArrayEquals(PLAINTEXT.getBytes(StandardCharsets.UTF_8), bytesAndResult.getBytes()); + Assertions.assertArrayEquals(TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8), bytesAndResult.getBytes()); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void testDecryptWithSessionKey(SOP sop) throws IOException { byte[] decrypted = sop.decrypt() .withSessionKey(SessionKey.fromString(SESSION_KEY)) @@ -55,6 +60,6 @@ public class ExternalDecryptWithSessionKeyTest extends AbstractExternalSOPTest { .toByteArrayAndResult() .getBytes(); - assertArrayEquals(PLAINTEXT.getBytes(StandardCharsets.UTF_8), decrypted); + Assertions.assertArrayEquals(TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8), decrypted); } } diff --git a/sop-java/src/testFixtures/java/sop/testsuite/operation/DetachedSignDetachedVerifyTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/DetachedSignDetachedVerifyTest.java new file mode 100644 index 0000000..a822f89 --- /dev/null +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/DetachedSignDetachedVerifyTest.java @@ -0,0 +1,250 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +package sop.testsuite.operation; + +import org.junit.jupiter.api.condition.EnabledIf; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; +import org.junit.jupiter.params.provider.MethodSource; +import sop.SOP; +import sop.Verification; +import sop.enums.SignAs; +import sop.exception.SOPGPException; +import sop.testsuite.JUtils; +import sop.testsuite.TestData; + +import java.io.IOException; +import java.nio.charset.StandardCharsets; +import java.util.Date; +import java.util.List; +import java.util.stream.Stream; + +import static org.junit.jupiter.api.Assertions.assertFalse; +import static org.junit.jupiter.api.Assertions.assertThrows; + +@EnabledIf("sop.operation.AbstractSOPTest#hasBackends") +public class DetachedSignDetachedVerifyTest extends AbstractSOPTest { + + static Stream provideInstances() { + return provideBackends(); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void signVerifyWithAliceKey(SOP sop) throws IOException { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + + byte[] signature = sop.detachedSign() + .key(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .data(message) + .toByteArrayAndResult() + .getBytes(); + + List verificationList = sop.detachedVerify() + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .signatures(signature) + .data(message); + + assertFalse(verificationList.isEmpty()); + JUtils.assertSignedBy(verificationList, TestData.ALICE_SIGNING_FINGERPRINT, TestData.ALICE_PRIMARY_FINGERPRINT); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void signVerifyTextModeWithAliceKey(SOP sop) throws IOException { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + + byte[] signature = sop.detachedSign() + .key(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .mode(SignAs.Text) + .data(message) + .toByteArrayAndResult() + .getBytes(); + + List verificationList = sop.detachedVerify() + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .signatures(signature) + .data(message); + + assertFalse(verificationList.isEmpty()); + JUtils.assertSignedBy(verificationList, TestData.ALICE_SIGNING_FINGERPRINT, TestData.ALICE_PRIMARY_FINGERPRINT); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void verifyKnownMessageWithAliceCert(SOP sop) throws IOException { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] signature = TestData.ALICE_DETACHED_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8); + + List verificationList = sop.detachedVerify() + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .signatures(signature) + .data(message); + + assertFalse(verificationList.isEmpty()); + JUtils.assertSignedBy(verificationList, TestData.ALICE_SIGNING_FINGERPRINT, TestData.ALICE_PRIMARY_FINGERPRINT, TestData.ALICE_DETACHED_SIGNED_MESSAGE_DATE); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void signVerifyWithBobKey(SOP sop) throws IOException { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + + byte[] signature = sop.detachedSign() + .key(TestData.BOB_KEY.getBytes(StandardCharsets.UTF_8)) + .data(message) + .toByteArrayAndResult() + .getBytes(); + + List verificationList = sop.detachedVerify() + .cert(TestData.BOB_CERT.getBytes(StandardCharsets.UTF_8)) + .signatures(signature) + .data(message); + + assertFalse(verificationList.isEmpty()); + JUtils.assertSignedBy(verificationList, TestData.BOB_SIGNING_FINGERPRINT, TestData.BOB_PRIMARY_FINGERPRINT); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void signVerifyWithCarolKey(SOP sop) throws IOException { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + + byte[] signature = sop.detachedSign() + .key(TestData.CAROL_KEY.getBytes(StandardCharsets.UTF_8)) + .data(message) + .toByteArrayAndResult() + .getBytes(); + + List verificationList = sop.detachedVerify() + .cert(TestData.CAROL_CERT.getBytes(StandardCharsets.UTF_8)) + .signatures(signature) + .data(message); + + assertFalse(verificationList.isEmpty()); + JUtils.assertSignedBy(verificationList, TestData.CAROL_SIGNING_FINGERPRINT, TestData.CAROL_PRIMARY_FINGERPRINT); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void signVerifyWithEncryptedKey(SOP sop) throws IOException { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + + byte[] signature = sop.detachedSign() + .key(TestData.PASSWORD_PROTECTED_KEY.getBytes(StandardCharsets.UTF_8)) + .withKeyPassword(TestData.PASSWORD) + .data(message) + .toByteArrayAndResult() + .getBytes(); + + JUtils.assertArrayStartsWith(signature, TestData.BEGIN_PGP_SIGNATURE); + + List verificationList = sop.detachedVerify() + .cert(TestData.PASSWORD_PROTECTED_CERT.getBytes(StandardCharsets.UTF_8)) + .signatures(signature) + .data(message); + + assertFalse(verificationList.isEmpty()); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void signArmorVerifyWithBobKey(SOP sop) throws IOException { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + + byte[] signature = sop.detachedSign() + .key(TestData.BOB_KEY.getBytes(StandardCharsets.UTF_8)) + .noArmor() + .data(message) + .toByteArrayAndResult() + .getBytes(); + + byte[] armored = sop.armor() + .data(signature) + .getBytes(); + + List verificationList = sop.detachedVerify() + .cert(TestData.BOB_CERT.getBytes(StandardCharsets.UTF_8)) + .signatures(armored) + .data(message); + + assertFalse(verificationList.isEmpty()); + JUtils.assertSignedBy(verificationList, TestData.BOB_SIGNING_FINGERPRINT, TestData.BOB_PRIMARY_FINGERPRINT); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void verifyNotAfterThrowsNoSignature(SOP sop) { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] signature = TestData.ALICE_DETACHED_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8); + Date beforeSignature = new Date(TestData.ALICE_DETACHED_SIGNED_MESSAGE_DATE.getTime() - 1000); // 1 sec before sig + + assertThrows(SOPGPException.NoSignature.class, () -> sop.detachedVerify() + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .notAfter(beforeSignature) + .signatures(signature) + .data(message)); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void verifyNotBeforeThrowsNoSignature(SOP sop) { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] signature = TestData.ALICE_DETACHED_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8); + Date afterSignature = new Date(TestData.ALICE_DETACHED_SIGNED_MESSAGE_DATE.getTime() + 1000); // 1 sec after sig + + assertThrows(SOPGPException.NoSignature.class, () -> sop.detachedVerify() + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .notBefore(afterSignature) + .signatures(signature) + .data(message)); + } + + + @ParameterizedTest + @MethodSource("provideInstances") + public void signVerifyWithEncryptedKeyWithoutPassphraseFails(SOP sop) { + assertThrows(SOPGPException.KeyIsProtected.class, () -> + sop.detachedSign() + .key(TestData.PASSWORD_PROTECTED_KEY.getBytes(StandardCharsets.UTF_8)) + .data(TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8)) + .toByteArrayAndResult() + .getBytes()); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void signWithProtectedKeyAndMultiplePassphrasesTest(SOP sop) + throws IOException { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + + byte[] signature = sop.sign() + .key(TestData.PASSWORD_PROTECTED_KEY.getBytes(StandardCharsets.UTF_8)) + .withKeyPassword("wrong") + .withKeyPassword(TestData.PASSWORD) // correct + .withKeyPassword("wrong2") + .data(message) + .toByteArrayAndResult() + .getBytes(); + + assertFalse(sop.verify() + .cert(TestData.PASSWORD_PROTECTED_CERT.getBytes(StandardCharsets.UTF_8)) + .signatures(signature) + .data(message) + .isEmpty()); + } + + @ParameterizedTest + @MethodSource("provideInstances") + public void verifyMissingCertCausesMissingArg(SOP sop) { + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); + + assertThrows(SOPGPException.MissingArg.class, () -> + sop.verify() + .signatures(TestData.ALICE_DETACHED_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8)) + .data(message)); + } + +} diff --git a/external-sop/src/test/java/sop/external/ExternalEncryptDecryptRoundTripTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/EncryptDecryptTest.java similarity index 72% rename from external-sop/src/test/java/sop/external/ExternalEncryptDecryptRoundTripTest.java rename to sop-java/src/testFixtures/java/sop/testsuite/operation/EncryptDecryptTest.java index fa5f2a8..255bc19 100644 --- a/external-sop/src/test/java/sop/external/ExternalEncryptDecryptRoundTripTest.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/EncryptDecryptTest.java @@ -2,10 +2,11 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.external; +package sop.testsuite.operation; import org.junit.jupiter.api.condition.EnabledIf; import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; import org.junit.jupiter.params.provider.MethodSource; import sop.ByteArrayAndResult; import sop.DecryptionResult; @@ -13,36 +14,33 @@ import sop.SOP; import sop.Verification; import sop.enums.EncryptAs; import sop.exception.SOPGPException; +import sop.testsuite.JUtils; +import sop.testsuite.TestData; import sop.util.UTCUtil; import java.io.IOException; import java.nio.charset.StandardCharsets; import java.util.Date; import java.util.List; +import java.util.stream.Stream; import static org.junit.jupiter.api.Assertions.assertArrayEquals; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertFalse; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertThrows; -import static sop.testing.JUtils.assertSignedBy; -import static sop.testing.TestData.ALICE_CERT; -import static sop.testing.TestData.ALICE_KEY; -import static sop.testing.TestData.ALICE_PRIMARY_FINGERPRINT; -import static sop.testing.TestData.ALICE_SIGNING_FINGERPRINT; -import static sop.testing.TestData.BOB_CERT; -import static sop.testing.TestData.BOB_KEY; -import static sop.testing.TestData.CAROL_CERT; -import static sop.testing.TestData.CAROL_KEY; -import static sop.testing.TestData.PLAINTEXT; -@EnabledIf("sop.external.AbstractExternalSOPTest#hasBackends") -public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest { +@EnabledIf("sop.operation.AbstractSOPTest#hasBackends") +public class EncryptDecryptTest extends AbstractSOPTest { + + static Stream provideInstances() { + return provideBackends(); + } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void encryptDecryptRoundTripPasswordTest(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] ciphertext = sop.encrypt() .withPassword("sw0rdf1sh") .plaintext(message) @@ -58,16 +56,16 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void encryptDecryptRoundTripAliceTest(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] ciphertext = sop.encrypt() - .withCert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .withCert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .plaintext(message) .getBytes(); ByteArrayAndResult bytesAndResult = sop.decrypt() - .withKey(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .withKey(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .ciphertext(ciphertext) .toByteArrayAndResult(); @@ -79,16 +77,16 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void encryptDecryptRoundTripBobTest(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] ciphertext = sop.encrypt() - .withCert(BOB_CERT.getBytes(StandardCharsets.UTF_8)) + .withCert(TestData.BOB_CERT.getBytes(StandardCharsets.UTF_8)) .plaintext(message) .getBytes(); byte[] plaintext = sop.decrypt() - .withKey(BOB_KEY.getBytes(StandardCharsets.UTF_8)) + .withKey(TestData.BOB_KEY.getBytes(StandardCharsets.UTF_8)) .ciphertext(ciphertext) .toByteArrayAndResult() .getBytes(); @@ -97,16 +95,16 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void encryptDecryptRoundTripCarolTest(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] ciphertext = sop.encrypt() - .withCert(CAROL_CERT.getBytes(StandardCharsets.UTF_8)) + .withCert(TestData.CAROL_CERT.getBytes(StandardCharsets.UTF_8)) .plaintext(message) .getBytes(); byte[] plaintext = sop.decrypt() - .withKey(CAROL_KEY.getBytes(StandardCharsets.UTF_8)) + .withKey(TestData.CAROL_KEY.getBytes(StandardCharsets.UTF_8)) .ciphertext(ciphertext) .toByteArrayAndResult() .getBytes(); @@ -115,11 +113,11 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void encryptNoArmorThenArmorThenDecryptRoundTrip(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] ciphertext = sop.encrypt() - .withCert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .withCert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .noArmor() .plaintext(message) .getBytes(); @@ -129,7 +127,7 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest .getBytes(); ByteArrayAndResult bytesAndResult = sop.decrypt() - .withKey(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .withKey(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .ciphertext(armored) .toByteArrayAndResult(); @@ -138,18 +136,18 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void encryptSignDecryptVerifyRoundTripAliceTest(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] ciphertext = sop.encrypt() - .withCert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) - .signWith(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .withCert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .signWith(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .plaintext(message) .getBytes(); ByteArrayAndResult bytesAndResult = sop.decrypt() - .withKey(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) - .verifyWithCert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .withKey(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .verifyWithCert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .ciphertext(ciphertext) .toByteArrayAndResult(); @@ -160,23 +158,23 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest assertNotNull(result.getSessionKey().get()); List verificationList = result.getVerifications(); assertEquals(1, verificationList.size()); - assertSignedBy(verificationList, ALICE_SIGNING_FINGERPRINT, ALICE_PRIMARY_FINGERPRINT); + JUtils.assertSignedBy(verificationList, TestData.ALICE_SIGNING_FINGERPRINT, TestData.ALICE_PRIMARY_FINGERPRINT); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void encryptSignAsTextDecryptVerifyRoundTripAliceTest(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] ciphertext = sop.encrypt() - .withCert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) - .signWith(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .withCert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .signWith(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .mode(EncryptAs.Text) .plaintext(message) .getBytes(); ByteArrayAndResult bytesAndResult = sop.decrypt() - .withKey(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) - .verifyWithCert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .withKey(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .verifyWithCert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .ciphertext(ciphertext) .toByteArrayAndResult(); @@ -187,11 +185,11 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest assertNotNull(result.getSessionKey().get()); List verificationList = result.getVerifications(); assertEquals(1, verificationList.size()); - assertSignedBy(verificationList, ALICE_SIGNING_FINGERPRINT, ALICE_PRIMARY_FINGERPRINT); + JUtils.assertSignedBy(verificationList, TestData.ALICE_SIGNING_FINGERPRINT, TestData.ALICE_PRIMARY_FINGERPRINT); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void encryptSignDecryptVerifyRoundTripWithFreshEncryptedKeyTest(SOP sop) throws IOException { byte[] keyPassword = "sw0rdf1sh".getBytes(StandardCharsets.UTF_8); byte[] key = sop.generateKey() @@ -223,7 +221,7 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void decryptVerifyNotAfterTest(SOP sop) { byte[] message = ("-----BEGIN PGP MESSAGE-----\n" + "\n" + @@ -243,8 +241,8 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest assertThrows(SOPGPException.NoSignature.class, () -> { ByteArrayAndResult bytesAndResult = sop.decrypt() - .withKey(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) - .verifyWithCert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .withKey(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .verifyWithCert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .verifyNotAfter(beforeSignature) .ciphertext(message) .toByteArrayAndResult(); @@ -256,7 +254,7 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void decryptVerifyNotBeforeTest(SOP sop) { byte[] message = ("-----BEGIN PGP MESSAGE-----\n" + "\n" + @@ -276,8 +274,8 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest assertThrows(SOPGPException.NoSignature.class, () -> { ByteArrayAndResult bytesAndResult = sop.decrypt() - .withKey(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) - .verifyWithCert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .withKey(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .verifyWithCert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .verifyNotBefore(afterSignature) .ciphertext(message) .toByteArrayAndResult(); @@ -289,9 +287,9 @@ public class ExternalEncryptDecryptRoundTripTest extends AbstractExternalSOPTest } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void missingArgsTest(SOP sop) { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); assertThrows(SOPGPException.MissingArg.class, () -> sop.encrypt() .plaintext(message) diff --git a/external-sop/src/test/java/sop/external/ExternalExtractCertTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/ExtractCertTest.java similarity index 59% rename from external-sop/src/test/java/sop/external/ExternalExtractCertTest.java rename to sop-java/src/testFixtures/java/sop/testsuite/operation/ExtractCertTest.java index 53d7e6d..a0b421a 100644 --- a/external-sop/src/test/java/sop/external/ExternalExtractCertTest.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/ExtractCertTest.java @@ -2,31 +2,31 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.external; +package sop.testsuite.operation; +import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.condition.EnabledIf; import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; import org.junit.jupiter.params.provider.MethodSource; import sop.SOP; -import sop.testing.TestData; +import sop.testsuite.JUtils; +import sop.testsuite.TestData; import java.io.IOException; import java.io.InputStream; import java.nio.charset.StandardCharsets; +import java.util.stream.Stream; -import static org.junit.jupiter.api.Assertions.assertFalse; -import static sop.testing.JUtils.arrayStartsWith; -import static sop.testing.JUtils.assertArrayEndsWithIgnoreNewlines; -import static sop.testing.JUtils.assertArrayStartsWith; -import static sop.testing.JUtils.assertAsciiArmorEquals; -import static sop.testing.TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK; -import static sop.testing.TestData.END_PGP_PUBLIC_KEY_BLOCK; +@EnabledIf("sop.operation.AbstractSOPTest#hasBackends") +public class ExtractCertTest extends AbstractSOPTest { -@EnabledIf("sop.external.AbstractExternalSOPTest#hasBackends") -public class ExternalExtractCertTest extends AbstractExternalSOPTest { + static Stream provideInstances() { + return provideBackends(); + } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void extractArmoredCertFromArmoredKeyTest(SOP sop) throws IOException { InputStream keyIn = sop.generateKey() .userId("Alice ") @@ -34,39 +34,39 @@ public class ExternalExtractCertTest extends AbstractExternalSOPTest { .getInputStream(); byte[] cert = sop.extractCert().key(keyIn).getBytes(); - assertArrayStartsWith(cert, BEGIN_PGP_PUBLIC_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(cert, END_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayStartsWith(cert, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(cert, TestData.END_PGP_PUBLIC_KEY_BLOCK); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void extractAliceCertFromAliceKeyTest(SOP sop) throws IOException { byte[] armoredCert = sop.extractCert() .key(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .getBytes(); - assertAsciiArmorEquals(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8), armoredCert); + JUtils.assertAsciiArmorEquals(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8), armoredCert); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void extractBobsCertFromBobsKeyTest(SOP sop) throws IOException { byte[] armoredCert = sop.extractCert() .key(TestData.BOB_KEY.getBytes(StandardCharsets.UTF_8)) .getBytes(); - assertAsciiArmorEquals(TestData.BOB_CERT.getBytes(StandardCharsets.UTF_8), armoredCert); + JUtils.assertAsciiArmorEquals(TestData.BOB_CERT.getBytes(StandardCharsets.UTF_8), armoredCert); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void extractCarolsCertFromCarolsKeyTest(SOP sop) throws IOException { byte[] armoredCert = sop.extractCert() .key(TestData.CAROL_KEY.getBytes(StandardCharsets.UTF_8)) .getBytes(); - assertAsciiArmorEquals(TestData.CAROL_CERT.getBytes(StandardCharsets.UTF_8), armoredCert); + JUtils.assertAsciiArmorEquals(TestData.CAROL_CERT.getBytes(StandardCharsets.UTF_8), armoredCert); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void extractUnarmoredCertFromArmoredKeyTest(SOP sop) throws IOException { InputStream keyIn = sop.generateKey() .userId("Alice ") @@ -78,11 +78,11 @@ public class ExternalExtractCertTest extends AbstractExternalSOPTest { .key(keyIn) .getBytes(); - assertFalse(arrayStartsWith(cert, BEGIN_PGP_PUBLIC_KEY_BLOCK)); + Assertions.assertFalse(JUtils.arrayStartsWith(cert, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK)); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void extractArmoredCertFromUnarmoredKeyTest(SOP sop) throws IOException { InputStream keyIn = sop.generateKey() .userId("Alice ") @@ -94,12 +94,12 @@ public class ExternalExtractCertTest extends AbstractExternalSOPTest { .key(keyIn) .getBytes(); - assertArrayStartsWith(cert, BEGIN_PGP_PUBLIC_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(cert, END_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayStartsWith(cert, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(cert, TestData.END_PGP_PUBLIC_KEY_BLOCK); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void extractUnarmoredCertFromUnarmoredKeyTest(SOP sop) throws IOException { InputStream keyIn = sop.generateKey() .noArmor() @@ -112,6 +112,6 @@ public class ExternalExtractCertTest extends AbstractExternalSOPTest { .key(keyIn) .getBytes(); - assertFalse(arrayStartsWith(cert, BEGIN_PGP_PUBLIC_KEY_BLOCK)); + Assertions.assertFalse(JUtils.arrayStartsWith(cert, TestData.BEGIN_PGP_PUBLIC_KEY_BLOCK)); } } diff --git a/external-sop/src/test/java/sop/external/ExternalGenerateKeyTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/GenerateKeyTest.java similarity index 53% rename from external-sop/src/test/java/sop/external/ExternalGenerateKeyTest.java rename to sop-java/src/testFixtures/java/sop/testsuite/operation/GenerateKeyTest.java index 606efab..748817b 100644 --- a/external-sop/src/test/java/sop/external/ExternalGenerateKeyTest.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/GenerateKeyTest.java @@ -2,39 +2,41 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.external; +package sop.testsuite.operation; +import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.condition.EnabledIf; import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; import org.junit.jupiter.params.provider.MethodSource; import sop.SOP; -import sop.testing.JUtils; +import sop.testsuite.JUtils; +import sop.testsuite.TestData; import java.io.IOException; +import java.util.stream.Stream; -import static org.junit.jupiter.api.Assertions.assertFalse; -import static sop.testing.JUtils.assertArrayEndsWithIgnoreNewlines; -import static sop.testing.JUtils.assertArrayStartsWith; -import static sop.testing.TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK; -import static sop.testing.TestData.END_PGP_PRIVATE_KEY_BLOCK; +@EnabledIf("sop.operation.AbstractSOPTest#hasBackends") +public class GenerateKeyTest extends AbstractSOPTest { -@EnabledIf("sop.external.AbstractExternalSOPTest#hasBackends") -public class ExternalGenerateKeyTest extends AbstractExternalSOPTest { + static Stream provideInstances() { + return provideBackends(); + } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void generateKeyTest(SOP sop) throws IOException { byte[] key = sop.generateKey() .userId("Alice ") .generate() .getBytes(); - assertArrayStartsWith(key, BEGIN_PGP_PRIVATE_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(key, END_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayStartsWith(key, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(key, TestData.END_PGP_PRIVATE_KEY_BLOCK); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void generateKeyNoArmor(SOP sop) throws IOException { byte[] key = sop.generateKey() .userId("Alice ") @@ -42,11 +44,11 @@ public class ExternalGenerateKeyTest extends AbstractExternalSOPTest { .generate() .getBytes(); - assertFalse(JUtils.arrayStartsWith(key, BEGIN_PGP_PRIVATE_KEY_BLOCK)); + Assertions.assertFalse(JUtils.arrayStartsWith(key, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK)); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void generateKeyWithMultipleUserIdsTest(SOP sop) throws IOException { byte[] key = sop.generateKey() .userId("Alice ") @@ -54,23 +56,23 @@ public class ExternalGenerateKeyTest extends AbstractExternalSOPTest { .generate() .getBytes(); - assertArrayStartsWith(key, BEGIN_PGP_PRIVATE_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(key, END_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayStartsWith(key, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(key, TestData.END_PGP_PRIVATE_KEY_BLOCK); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void generateKeyWithoutUserIdTest(SOP sop) throws IOException { byte[] key = sop.generateKey() .generate() .getBytes(); - assertArrayStartsWith(key, BEGIN_PGP_PRIVATE_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(key, END_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayStartsWith(key, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(key, TestData.END_PGP_PRIVATE_KEY_BLOCK); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void generateKeyWithPasswordTest(SOP sop) throws IOException { byte[] key = sop.generateKey() .userId("Alice ") @@ -78,12 +80,12 @@ public class ExternalGenerateKeyTest extends AbstractExternalSOPTest { .generate() .getBytes(); - assertArrayStartsWith(key, BEGIN_PGP_PRIVATE_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(key, END_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayStartsWith(key, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(key, TestData.END_PGP_PRIVATE_KEY_BLOCK); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void generateKeyWithMultipleUserIdsAndPassword(SOP sop) throws IOException { byte[] key = sop.generateKey() .userId("Alice ") @@ -92,7 +94,7 @@ public class ExternalGenerateKeyTest extends AbstractExternalSOPTest { .generate() .getBytes(); - assertArrayStartsWith(key, BEGIN_PGP_PRIVATE_KEY_BLOCK); - assertArrayEndsWithIgnoreNewlines(key, END_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayStartsWith(key, TestData.BEGIN_PGP_PRIVATE_KEY_BLOCK); + JUtils.assertArrayEndsWithIgnoreNewlines(key, TestData.END_PGP_PRIVATE_KEY_BLOCK); } } diff --git a/external-sop/src/test/java/sop/external/ExternalInlineSignDetachVerifyRoundTripTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/InlineSignInlineDetachDetachedVerifyTest.java similarity index 68% rename from external-sop/src/test/java/sop/external/ExternalInlineSignDetachVerifyRoundTripTest.java rename to sop-java/src/testFixtures/java/sop/testsuite/operation/InlineSignInlineDetachDetachedVerifyTest.java index 23ba7fd..6b1e250 100644 --- a/external-sop/src/test/java/sop/external/ExternalInlineSignDetachVerifyRoundTripTest.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/InlineSignInlineDetachDetachedVerifyTest.java @@ -2,39 +2,42 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.external; +package sop.testsuite.operation; +import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.condition.EnabledIf; import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; import org.junit.jupiter.params.provider.MethodSource; import sop.ByteArrayAndResult; import sop.SOP; import sop.Signatures; import sop.Verification; +import sop.testsuite.JUtils; +import sop.testsuite.TestData; import java.io.IOException; import java.nio.charset.StandardCharsets; import java.util.List; +import java.util.stream.Stream; import static org.junit.jupiter.api.Assertions.assertArrayEquals; import static org.junit.jupiter.api.Assertions.assertFalse; -import static sop.testing.JUtils.arrayStartsWith; -import static sop.testing.JUtils.assertArrayStartsWith; -import static sop.testing.TestData.ALICE_CERT; -import static sop.testing.TestData.ALICE_KEY; -import static sop.testing.TestData.BEGIN_PGP_SIGNATURE; -import static sop.testing.TestData.PLAINTEXT; -@EnabledIf("sop.external.AbstractExternalSOPTest#hasBackends") -public class ExternalInlineSignDetachVerifyRoundTripTest extends AbstractExternalSOPTest { +@EnabledIf("sop.operation.AbstractSOPTest#hasBackends") +public class InlineSignInlineDetachDetachedVerifyTest extends AbstractSOPTest { + + static Stream provideInstances() { + return provideBackends(); + } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void inlineSignThenDetachThenDetachedVerifyTest(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] inlineSigned = sop.inlineSign() - .key(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .key(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .data(message) .getBytes(); @@ -49,7 +52,7 @@ public class ExternalInlineSignDetachVerifyRoundTripTest extends AbstractExterna .getBytes(); List verifications = sop.detachedVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .signatures(signatures) .data(plaintext); @@ -57,12 +60,12 @@ public class ExternalInlineSignDetachVerifyRoundTripTest extends AbstractExterna } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void inlineSignThenDetachNoArmorThenArmorThenDetachedVerifyTest(SOP sop) throws IOException { byte[] message = "Hello, World!\n".getBytes(StandardCharsets.UTF_8); byte[] inlineSigned = sop.inlineSign() - .key(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .key(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .data(message) .getBytes(); @@ -76,15 +79,15 @@ public class ExternalInlineSignDetachVerifyRoundTripTest extends AbstractExterna byte[] signatures = bytesAndResult.getResult() .getBytes(); - assertFalse(arrayStartsWith(signatures, BEGIN_PGP_SIGNATURE)); + Assertions.assertFalse(JUtils.arrayStartsWith(signatures, TestData.BEGIN_PGP_SIGNATURE)); byte[] armored = sop.armor() .data(signatures) .getBytes(); - assertArrayStartsWith(armored, BEGIN_PGP_SIGNATURE); + JUtils.assertArrayStartsWith(armored, TestData.BEGIN_PGP_SIGNATURE); List verifications = sop.detachedVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .signatures(armored) .data(plaintext); diff --git a/external-sop/src/test/java/sop/external/ExternalInlineSignVerifyTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/InlineSignInlineVerifyTest.java similarity index 62% rename from external-sop/src/test/java/sop/external/ExternalInlineSignVerifyTest.java rename to sop-java/src/testFixtures/java/sop/testsuite/operation/InlineSignInlineVerifyTest.java index 5d1012f..96782ea 100644 --- a/external-sop/src/test/java/sop/external/ExternalInlineSignVerifyTest.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/InlineSignInlineVerifyTest.java @@ -2,123 +2,121 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.external; +package sop.testsuite.operation; +import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.condition.EnabledIf; import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; import org.junit.jupiter.params.provider.MethodSource; import sop.ByteArrayAndResult; import sop.SOP; import sop.Verification; import sop.enums.InlineSignAs; import sop.exception.SOPGPException; -import sop.testing.JUtils; -import sop.testing.TestData; +import sop.testsuite.JUtils; +import sop.testsuite.TestData; import java.io.IOException; import java.nio.charset.StandardCharsets; import java.util.Date; import java.util.List; +import java.util.stream.Stream; import static org.junit.jupiter.api.Assertions.assertArrayEquals; -import static org.junit.jupiter.api.Assertions.assertFalse; import static org.junit.jupiter.api.Assertions.assertThrows; -import static sop.testing.JUtils.assertSignedBy; -import static sop.testing.TestData.ALICE_CERT; -import static sop.testing.TestData.ALICE_KEY; -import static sop.testing.TestData.ALICE_PRIMARY_FINGERPRINT; -import static sop.testing.TestData.ALICE_SIGNING_FINGERPRINT; -import static sop.testing.TestData.BEGIN_PGP_MESSAGE; -import static sop.testing.TestData.BEGIN_PGP_SIGNED_MESSAGE; -import static sop.testing.TestData.PLAINTEXT; -@EnabledIf("sop.external.AbstractExternalSOPTest#hasBackends") -public class ExternalInlineSignVerifyTest extends AbstractExternalSOPTest { +@EnabledIf("sop.operation.AbstractSOPTest#hasBackends") +public class InlineSignInlineVerifyTest extends AbstractSOPTest { + + static Stream provideInstances() { + return provideBackends(); + } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void inlineSignVerifyAlice(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] inlineSigned = sop.inlineSign() - .key(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .key(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .data(message) .getBytes(); - JUtils.assertArrayStartsWith(inlineSigned, BEGIN_PGP_MESSAGE); + JUtils.assertArrayStartsWith(inlineSigned, TestData.BEGIN_PGP_MESSAGE); ByteArrayAndResult> bytesAndResult = sop.inlineVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .data(inlineSigned) .toByteArrayAndResult(); assertArrayEquals(message, bytesAndResult.getBytes()); List verificationList = bytesAndResult.getResult(); - assertSignedBy(verificationList, ALICE_SIGNING_FINGERPRINT, ALICE_PRIMARY_FINGERPRINT); + JUtils.assertSignedBy(verificationList, TestData.ALICE_SIGNING_FINGERPRINT, TestData.ALICE_PRIMARY_FINGERPRINT); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void inlineSignVerifyAliceNoArmor(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] inlineSigned = sop.inlineSign() - .key(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .key(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .noArmor() .data(message) .getBytes(); - assertFalse(JUtils.arrayStartsWith(inlineSigned, BEGIN_PGP_MESSAGE)); + Assertions.assertFalse(JUtils.arrayStartsWith(inlineSigned, TestData.BEGIN_PGP_MESSAGE)); ByteArrayAndResult> bytesAndResult = sop.inlineVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .data(inlineSigned) .toByteArrayAndResult(); assertArrayEquals(message, bytesAndResult.getBytes()); List verificationList = bytesAndResult.getResult(); - assertSignedBy(verificationList, ALICE_SIGNING_FINGERPRINT, ALICE_PRIMARY_FINGERPRINT); + JUtils.assertSignedBy(verificationList, TestData.ALICE_SIGNING_FINGERPRINT, TestData.ALICE_PRIMARY_FINGERPRINT); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void clearsignVerifyAlice(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] clearsigned = sop.inlineSign() - .key(ALICE_KEY.getBytes(StandardCharsets.UTF_8)) + .key(TestData.ALICE_KEY.getBytes(StandardCharsets.UTF_8)) .mode(InlineSignAs.clearsigned) .data(message) .getBytes(); - JUtils.assertArrayStartsWith(clearsigned, BEGIN_PGP_SIGNED_MESSAGE); + JUtils.assertArrayStartsWith(clearsigned, TestData.BEGIN_PGP_SIGNED_MESSAGE); ByteArrayAndResult> bytesAndResult = sop.inlineVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .data(clearsigned) .toByteArrayAndResult(); assertArrayEquals(message, bytesAndResult.getBytes()); List verificationList = bytesAndResult.getResult(); - assertSignedBy(verificationList, ALICE_SIGNING_FINGERPRINT, ALICE_PRIMARY_FINGERPRINT); + JUtils.assertSignedBy(verificationList, TestData.ALICE_SIGNING_FINGERPRINT, TestData.ALICE_PRIMARY_FINGERPRINT); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void inlineVerifyCompareSignatureDate(SOP sop) throws IOException { byte[] message = TestData.ALICE_INLINE_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8); Date signatureDate = TestData.ALICE_INLINE_SIGNED_MESSAGE_DATE; ByteArrayAndResult> bytesAndResult = sop.inlineVerify() - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .data(message) .toByteArrayAndResult(); List verificationList = bytesAndResult.getResult(); - assertSignedBy(verificationList, ALICE_SIGNING_FINGERPRINT, ALICE_PRIMARY_FINGERPRINT, signatureDate); + JUtils.assertSignedBy(verificationList, TestData.ALICE_SIGNING_FINGERPRINT, TestData.ALICE_PRIMARY_FINGERPRINT, signatureDate); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void assertNotBeforeThrowsNoSignature(SOP sop) { byte[] message = TestData.ALICE_INLINE_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8); Date signatureDate = TestData.ALICE_INLINE_SIGNED_MESSAGE_DATE; @@ -126,13 +124,13 @@ public class ExternalInlineSignVerifyTest extends AbstractExternalSOPTest { assertThrows(SOPGPException.NoSignature.class, () -> sop.inlineVerify() .notBefore(afterSignature) - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .data(message) .toByteArrayAndResult()); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void assertNotAfterThrowsNoSignature(SOP sop) { byte[] message = TestData.ALICE_INLINE_SIGNED_MESSAGE.getBytes(StandardCharsets.UTF_8); Date signatureDate = TestData.ALICE_INLINE_SIGNED_MESSAGE_DATE; @@ -140,22 +138,22 @@ public class ExternalInlineSignVerifyTest extends AbstractExternalSOPTest { assertThrows(SOPGPException.NoSignature.class, () -> sop.inlineVerify() .notAfter(beforeSignature) - .cert(ALICE_CERT.getBytes(StandardCharsets.UTF_8)) + .cert(TestData.ALICE_CERT.getBytes(StandardCharsets.UTF_8)) .data(message) .toByteArrayAndResult()); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void inlineSignVerifyBob(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] inlineSigned = sop.inlineSign() .key(TestData.BOB_KEY.getBytes(StandardCharsets.UTF_8)) .data(message) .getBytes(); - JUtils.assertArrayStartsWith(inlineSigned, BEGIN_PGP_MESSAGE); + JUtils.assertArrayStartsWith(inlineSigned, TestData.BEGIN_PGP_MESSAGE); ByteArrayAndResult> bytesAndResult = sop.inlineVerify() .cert(TestData.BOB_CERT.getBytes(StandardCharsets.UTF_8)) @@ -164,20 +162,20 @@ public class ExternalInlineSignVerifyTest extends AbstractExternalSOPTest { assertArrayEquals(message, bytesAndResult.getBytes()); List verificationList = bytesAndResult.getResult(); - assertSignedBy(verificationList, TestData.BOB_SIGNING_FINGERPRINT, TestData.BOB_PRIMARY_FINGERPRINT); + JUtils.assertSignedBy(verificationList, TestData.BOB_SIGNING_FINGERPRINT, TestData.BOB_PRIMARY_FINGERPRINT); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void inlineSignVerifyCarol(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] inlineSigned = sop.inlineSign() .key(TestData.CAROL_KEY.getBytes(StandardCharsets.UTF_8)) .data(message) .getBytes(); - JUtils.assertArrayStartsWith(inlineSigned, BEGIN_PGP_MESSAGE); + JUtils.assertArrayStartsWith(inlineSigned, TestData.BEGIN_PGP_MESSAGE); ByteArrayAndResult> bytesAndResult = sop.inlineVerify() .cert(TestData.CAROL_CERT.getBytes(StandardCharsets.UTF_8)) @@ -186,13 +184,13 @@ public class ExternalInlineSignVerifyTest extends AbstractExternalSOPTest { assertArrayEquals(message, bytesAndResult.getBytes()); List verificationList = bytesAndResult.getResult(); - assertSignedBy(verificationList, TestData.CAROL_SIGNING_FINGERPRINT, TestData.CAROL_PRIMARY_FINGERPRINT); + JUtils.assertSignedBy(verificationList, TestData.CAROL_SIGNING_FINGERPRINT, TestData.CAROL_PRIMARY_FINGERPRINT); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void inlineSignVerifyProtectedKey(SOP sop) throws IOException { - byte[] message = PLAINTEXT.getBytes(StandardCharsets.UTF_8); + byte[] message = TestData.PLAINTEXT.getBytes(StandardCharsets.UTF_8); byte[] inlineSigned = sop.inlineSign() .withKeyPassword(TestData.PASSWORD) @@ -207,7 +205,7 @@ public class ExternalInlineSignVerifyTest extends AbstractExternalSOPTest { .toByteArrayAndResult(); List verificationList = bytesAndResult.getResult(); - assertSignedBy(verificationList, TestData.PASSWORD_PROTECTED_SIGNING_FINGERPRINT, TestData.PASSWORD_PROTECTED_PRIMARY_FINGERPRINT); + JUtils.assertSignedBy(verificationList, TestData.PASSWORD_PROTECTED_SIGNING_FINGERPRINT, TestData.PASSWORD_PROTECTED_PRIMARY_FINGERPRINT); } } diff --git a/external-sop/src/test/java/sop/external/ExternalVersionTest.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/VersionTest.java similarity index 65% rename from external-sop/src/test/java/sop/external/ExternalVersionTest.java rename to sop-java/src/testFixtures/java/sop/testsuite/operation/VersionTest.java index 4b1f87c..a1f4701 100644 --- a/external-sop/src/test/java/sop/external/ExternalVersionTest.java +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/VersionTest.java @@ -2,22 +2,28 @@ // // SPDX-License-Identifier: Apache-2.0 -package sop.external; +package sop.testsuite.operation; import org.junit.jupiter.api.condition.EnabledIf; import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; import org.junit.jupiter.params.provider.MethodSource; import sop.SOP; +import java.util.stream.Stream; + import static org.junit.jupiter.api.Assertions.assertFalse; import static org.junit.jupiter.api.Assertions.assertNotNull; -import static org.junit.jupiter.api.Assertions.assertTrue; -@EnabledIf("sop.external.AbstractExternalSOPTest#hasBackends") -public class ExternalVersionTest extends AbstractExternalSOPTest { +@EnabledIf("sop.operation.AbstractSOPTest#hasBackends") +public class VersionTest extends AbstractSOPTest { + + static Stream provideInstances() { + return provideBackends(); + } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void versionNameTest(SOP sop) { String name = sop.version().getName(); assertNotNull(name); @@ -25,21 +31,21 @@ public class ExternalVersionTest extends AbstractExternalSOPTest { } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void versionVersionTest(SOP sop) { String version = sop.version().getVersion(); - assertTrue(version.matches("\\d+(\\.\\d+)*\\S*")); + assertFalse(version.isEmpty()); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void backendVersionTest(SOP sop) { String backend = sop.version().getBackendVersion(); assertFalse(backend.isEmpty()); } @ParameterizedTest - @MethodSource("sop.external.AbstractExternalSOPTest#provideBackends") + @MethodSource("provideInstances") public void extendedVersionTest(SOP sop) { String extended = sop.version().getExtendedVersion(); assertFalse(extended.isEmpty()); diff --git a/sop-java/src/testFixtures/java/sop/testsuite/operation/package-info.java b/sop-java/src/testFixtures/java/sop/testsuite/operation/package-info.java new file mode 100644 index 0000000..e3a27ee --- /dev/null +++ b/sop-java/src/testFixtures/java/sop/testsuite/operation/package-info.java @@ -0,0 +1,8 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +/** + * SOP binary test suite. + */ +package sop.testsuite.operation; diff --git a/sop-java/src/testFixtures/java/sop/testsuite/package-info.java b/sop-java/src/testFixtures/java/sop/testsuite/package-info.java new file mode 100644 index 0000000..cfb68d2 --- /dev/null +++ b/sop-java/src/testFixtures/java/sop/testsuite/package-info.java @@ -0,0 +1,8 @@ +// SPDX-FileCopyrightText: 2023 Paul Schaub +// +// SPDX-License-Identifier: Apache-2.0 + +/** + * SOP binary test suite. + */ +package sop.testsuite;