From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from gate001.proxmox.com (gate001.proxmox.com [45.144.208.40]) by lore.proxmox.com (Postfix) with ESMTPS id 050A41FF12C for ; Wed, 05 Aug 2026 16:11:56 +0200 (CEST) Received: from gate001.proxmox.com (localhost.localdomain [127.0.0.1]) by gate001.proxmox.com (Proxmox) with ESMTP id D8B0A21A2B; Wed, 05 Aug 2026 16:11:29 +0200 (CEST) From: Thomas Ellmenreich To: pve-devel@lists.proxmox.com Subject: [PATCH common v4 2/3] pem parser: add testsuite for check_pem and split_pem Date: Wed, 5 Aug 2026 16:11:13 +0200 Message-ID: <20260805141114.190477-4-t.ellmenreich@proxmox.com> X-Mailer: git-send-email 2.47.3 In-Reply-To: <20260805141114.190477-1-t.ellmenreich@proxmox.com> References: <20260805141114.190477-1-t.ellmenreich@proxmox.com> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Bm-Milter-Handled: 55990f41-d878-4baa-be0a-ee34c49e34d2 X-Bm-Transport-Timestamp: 1785939069447 X-SPAM-LEVEL: Spam detection results: 0 AWL 0.068 Adjusted score from AWL reputation of From: address DMARC_MISSING 0.1 Missing DMARC policy KAM_DMARC_STATUS 0.01 Test Rule for DKIM or SPF Failure with Strict Alignment (newer systems) RCVD_IN_DNSWL_LOW -0.7 Sender listed at https://www.dnswl.org/, low trust SPF_HELO_NONE 0.001 SPF: HELO does not publish an SPF Record SPF_PASS -0.001 SPF: sender matches SPF record Message-ID-Hash: DJMDXC5RIQAFFIPLRH4HGV4DJSH2LSP5 X-Message-ID-Hash: DJMDXC5RIQAFFIPLRH4HGV4DJSH2LSP5 X-MailFrom: t.ellmenreich@proxmox.com X-Mailman-Rule-Misses: dmarc-mitigation; no-senders; approved; loop; banned-address; emergency; member-moderation; nonmember-moderation; administrivia; implicit-dest; max-recipients; max-size; news-moderation; no-subject; digests; suspicious-header CC: Thomas Ellmenreich X-Mailman-Version: 3.3.10 Precedence: list List-Id: Proxmox VE development discussion List-Help: List-Owner: List-Post: List-Subscribe: List-Unsubscribe: having made considerable changes to both check_pem and split_pem in the previous commit, this commit introduces tests for both methods. Signed-off-by: Thomas Ellmenreich --- test/Makefile | 2 + test/check_pem_test.pl | 365 +++++++++++++++++++++++++++++++++++++++++ test/split_pem_test.pl | 279 +++++++++++++++++++++++++++++++ 3 files changed, 646 insertions(+) create mode 100755 test/check_pem_test.pl create mode 100755 test/split_pem_test.pl diff --git a/test/Makefile b/test/Makefile index 961a0da..e5a5f42 100644 --- a/test/Makefile +++ b/test/Makefile @@ -15,6 +15,8 @@ TESTS = lock_file.test \ section_config_property_isolation_test.test \ file-test.test \ cmd-test.test \ + check_pem_test.test \ + split_pem_test.test \ all: diff --git a/test/check_pem_test.pl b/test/check_pem_test.pl new file mode 100755 index 0000000..b9f11a0 --- /dev/null +++ b/test/check_pem_test.pl @@ -0,0 +1,365 @@ +#!/usr/bin/perl +# Tests the PVE::Certificate::check_pem function for +# correctness and coverage of edgecases. +use strict; +use warnings; + +use lib '../src'; + +use Test::More; + +use PVE::Certificate; + +# Arrange +my $setup = [ + { + expected_success => 1, + name => "full pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----- +MIIBsjCCAVugAwIBAgIJAO2g8Z0dXk9tMAoGCCqGSM49BAMCMEUxCzAJBgNVBAYT +AlVTMQswCQYDVQQIDAJDQTEQMA4GA1UEBwwHQmVya2VsZXkxEDAOBgNVBAoMB1Rl +c3QgQ0EwHhcNMjAwMTAxMDAwMDAwWhcNMzAwMTAxMDAwMDAwWjBFMQswCQYDVQQG +EwJVUzELMAkGA1UECAwCQ0ExEDAOBgNVBAcMB0JlcmtlbGV5MRAwDgYDVQQKDAdU +ZXN0IENBMFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEv5Q8q1p7qZ2gqkQ0Qn5x +0n9yqv8n8n7n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8aNT +MFEwHQYDVR0OBBYEFOu2Y0bq8v3z7qkq1m1Qwqkq1m1QMB8GA1UdIwQYMBaAFOu2 +Y0bq8v3z7qkq1m1Qwqkq1m1QMA8GA1UdEwEB/wQFMAMBAf8wCgYIKoZIzj0EAwID +SAAwRQIhANfakefakefakefakefakefakefakefakefake +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "other label pem", + label => "SOME LABEL", + pem => <<'EOF', +-----BEGIN SOME LABEL----- +MIIBsjCCAVugAwIBAgIJAO2g8Z0dXk9tMAoGCCqGSM49BAMCMEUxCzAJBgNVBAYT +AlVTMQswCQYDVQQIDAJDQTEQMA4GA1UEBwwHQmVya2VsZXkxEDAOBgNVBAoMB1Rl +c3QgQ0EwHhcNMjAwMTAxMDAwMDAwWhcNMzAwMTAxMDAwMDAwWjBFMQswCQYDVQQG +EwJVUzELMAkGA1UECAwCQ0ExEDAOBgNVBAcMB0JlcmtlbGV5MRAwDgYDVQQKDAdU +ZXN0IENBMFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEv5Q8q1p7qZ2gqkQ0Qn5x +0n9yqv8n8n7n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8aNT +MFEwHQYDVR0OBBYEFOu2Y0bq8v3z7qkq1m1Qwqkq1m1QMB8GA1UdIwQYMBaAFOu2 +Y0bq8v3z7qkq1m1Qwqkq1m1QMA8GA1UdEwEB/wQFMAMBAf8wCgYIKoZIzj0EAwID +SAAwRQIhANfakefakefakefakefakefakefakefakefake +-----END SOME LABEL----- +EOF + }, + { + expected_success => 1, + name => "simple pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----- +test +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "spaced out pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----- + +test + +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "only newline pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----- +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "many newlines pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----- + + + +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 0, + name => "no content pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----------END CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "preceding content pem", + pem => <<'EOF', +some extended content +-----BEGIN CERTIFICATE----- +test +-----END CERTIFICATE----- +EOF + + expected_result => <<'EOF', +-----BEGIN CERTIFICATE----- +test +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 0, + name => "following content pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----- +test +-----END CERTIFICATE----- +some extended content +EOF + }, + { + expected_success => 0, + name => "empty pem", + pem => <<'EOF', + +EOF + }, + { + expected_success => 0, + name => "upsidedown pem", + pem => <<'EOF', +-----END CERTIFICATE----- +test +-----BEGIN CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "multi pem", + multiple => 1, + pem => <<'EOF', +-----BEGIN CERTIFICATE----- +12JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +-----BEGIN CERTIFICATE----- +22JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +-----BEGIN CERTIFICATE----- +32JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +-----BEGIN CERTIFICATE----- +42JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 0, + name => "multiple as single pem", + pem => <<'EOF', +Subject: CN=some.test.content +Issuer: CN=Org Issuing CA 3 +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +Subject: CN=Org Issuing CA 3 +Issuer: CN=Org Root CA +-----BEGIN CERTIFICATE----- +2WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "big pem different label", + multiple => 1, + label => "LABEL", + pem => <<'EOF', +Subject: CN=some.test.content +Issuer: CN=Org Issuing CA 3 +-----BEGIN LABEL----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END LABEL----- +Subject: CN=Org Issuing CA 3 +Issuer: CN=Org Root CA +-----BEGIN LABEL----- +2WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END LABEL----- +Subject: CN=Org Root CA +Issuer: CN=Org Root CA +-----BEGIN LABEL----- +3WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END LABEL----- +EOF + + expected_result => <<'EOF', +-----BEGIN LABEL----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END LABEL----- +-----BEGIN LABEL----- +2WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END LABEL----- +-----BEGIN LABEL----- +3WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END LABEL----- +EOF + }, + { + expected_success => 1, + name => "other real pem", + pem => <<'EOF', +Subject: CN=Some subject with 2 Points,O=A Organization,L=Some Lation,C=TT +Issuer: CN=The Orgs Name RootCA 2015,O=The Orgs name Institutions Cert. Authority,L=Location,C=TT +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + expected_result => <<'EOF', +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 0, + name => "invalid single pem", + pem => <<'EOF', +Subject: CN=Some subject with 2 Points,O=A Organization,L=Some Lation,C=TT +Issuer: CN=The Orgs Name RootCA 2015,O=The Orgs name Institutions Cert. Authority,L=Location,C=TT +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdthese !?''*:;$%&/ are not allowedWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 0, + name => "invalid multi pem", + multiple => 1, + pem => <<'EOF', +Subject: CN=Some subject with 2 Points,O=A Organization,L=Some Lation,C=TT +Issuer: CN=The Orgs Name RootCA 2015,O=The Orgs name Institutions Cert. Authority,L=Location,C=TT +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdthese !?''*:;$%&/ are not allowedWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +Subject: CN=Some subject with 2 Points,O=A Organization,L=Some Lation,C=TT +Issuer: CN=The Orgs Name RootCA 2015,O=The Orgs name Institutions Cert. Authority,L=Location,C=TT +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- + +EOF + }, + { + expected_success => 1, + name => "single as multiple pem", + multiple => 1, + pem => <<'EOF', +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdtheseZ2RmaXVwYWJ2aXV1YXdlYmxmamlraWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "single as multiple pem", + multiple => 1, + pem => <<'EOF', +Subject: CN=Some subject with 2 Points,O=A Organization,L=Some Lation,C=TT +Issuer: CN=The Orgs Name RootCA 2015,O=The Orgs name Institutions Cert. Authority,L=Location,C=TT +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdtheseZ2RmaXVwYWJ2aXV1YXdlYmxmamlraWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + expected_result => <<'EOF', +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdtheseZ2RmaXVwYWJ2aXV1YXdlYmxmamlraWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + }, +]; + +for my $data ($setup->@*) { + subtest $data->{name} => sub { + # Act + my $check_result = PVE::Certificate::check_pem( + $data->{pem}, + noerr => 1, + multiple => $data->{multiple}, + label => $data->{label}, + ); + + # Assert + if ($data->{expected_success}) { + ok($check_result, "is successful"); + + my $expected_result = + $data->{expected_result} + ? $data->{expected_result} + : $data->{pem}; + is( + $check_result, $expected_result, "has correct result content", + ); + } else { + is($check_result, undef, "has correctly returned undef"); + eval { + PVE::Certificate::check_pem( + $data->{pem}, + multiple => $data->{multiple}, + label => $data->{label}, + ); + }; + ok($@, "has correctly thrown an error"); + } + } +} + +done_testing(); diff --git a/test/split_pem_test.pl b/test/split_pem_test.pl new file mode 100755 index 0000000..4239e5c --- /dev/null +++ b/test/split_pem_test.pl @@ -0,0 +1,279 @@ +#!/usr/bin/perl +# Tests the PVE::Certificate::split_pem function for +# correctness and coverage of edgecases. +use strict; +use warnings; + +use lib '../src'; + +use Test::More; + +use PVE::Certificate; + +# Arrange +my $setup = [ + { + expected_success => 1, + name => "single pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----- +MIIBsjCCAVugAwIBAgIJAO2g8Z0dXk9tMAoGCCqGSM49BAMCMEUxCzAJBgNVBAYT +AlVTMQswCQYDVQQIDAJDQTEQMA4GA1UEBwwHQmVya2VsZXkxEDAOBgNVBAoMB1Rl +c3QgQ0EwHhcNMjAwMTAxMDAwMDAwWhcNMzAwMTAxMDAwMDAwWjBFMQswCQYDVQQG +EwJVUzELMAkGA1UECAwCQ0ExEDAOBgNVBAcMB0JlcmtlbGV5MRAwDgYDVQQKDAdU +ZXN0IENBMFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEv5Q8q1p7qZ2gqkQ0Qn5x +0n9yqv8n8n7n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8n8aNT +MFEwHQYDVR0OBBYEFOu2Y0bq8v3z7qkq1m1Qwqkq1m1QMB8GA1UdIwQYMBaAFOu2 +Y0bq8v3z7qkq1m1Qwqkq1m1QMA8GA1UdEwEB/wQFMAMBAf8wCgYIKoZIzj0EAwID +SAAwRQIhANfakefakefakefakefakefakefakefakefake +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "no extra text pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----- +12JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +-----BEGIN CERTIFICATE----- +22JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +-----BEGIN CERTIFICATE----- +32JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +-----BEGIN CERTIFICATE----- +42JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + expected_result => [ + <<'EOF', +-----BEGIN CERTIFICATE----- +12JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + <<'EOF', +-----BEGIN CERTIFICATE----- +22JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + <<'EOF', +-----BEGIN CERTIFICATE----- +32JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + <<'EOF', +-----BEGIN CERTIFICATE----- +42JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + ], + }, + { + expected_success => 1, + name => "leading and interleaved text pem", + pem => <<'EOF', +Subject: CN=some.test.content +Issuer: CN=Org Issuing CA 3 +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +Subject: CN=Org Issuing CA 3 +Issuer: CN=Org Root CA +-----BEGIN CERTIFICATE----- +2WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +Subject: CN=Org Root CA +Issuer: CN=Org Root CA +-----BEGIN CERTIFICATE----- +3WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + expected_result => [ + <<'EOF', +Subject: CN=some.test.content +Issuer: CN=Org Issuing CA 3 +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + <<'EOF', +Subject: CN=Org Issuing CA 3 +Issuer: CN=Org Root CA +-----BEGIN CERTIFICATE----- +2WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + <<'EOF', +Subject: CN=Org Root CA +Issuer: CN=Org Root CA +-----BEGIN CERTIFICATE----- +3WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + ], + }, + { + expected_success => 1, + name => "massive glob pem", + pem => <<'EOF', +Subject: CN=some.test.content +Issuer: CN=Org Issuing CA 3 +-----BEGIN CERTIFICATE----- +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +Subject: CN=Org Issuing CA 3 +Issuer: CN=Org Root CA +-----BEGIN CERTIFICATE----- +2WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +Subject: CN=Org Root CA +Issuer: CN=Org Root CA +-----BEGIN CERTIFICATE----- +3WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + }, + { + expected_success => 1, + name => "no beginning pem", + pem => <<'EOF', +Subject: CN=some.test.content +Issuer: CN=Org Issuing CA 3 +2WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +Subject: CN=Org Root CA +Issuer: CN=Org Root CA +3WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + expected_result => [ + <<'EOF', +Subject: CN=some.test.content +Issuer: CN=Org Issuing CA 3 +2WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + <<'EOF', +Subject: CN=Org Root CA +Issuer: CN=Org Root CA +3WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + ], + + }, + { + expected_success => 0, + name => "not a pem pem", + pem => <<'EOF', +Subject: CN=some.test.content +Issuer: CN=Org Issuing CA 3 +1WtzZGhmbGtqYXNoZ2RmaXVwYWJ2aXV1YXdlYmxmamlraGFzZGtmYWlzdXBkdW5i +dmFpdXdlYmdmw7ZrYWpkc2JoZmdpYXNkbmJpZnVhYmdzaWprZmdyYXNkaHJmaW9h +dXNkbmF1c2JmZ3ZramFzZGJma2phc2RibmZpanVhIHNkb3ZuYmF3b3VlYmZnb2F3 +c2JlZ2tseTxzZWl2IGF3ZWlidm4= +Subject: CN=Org Issuing CA 3 +Issuer: CN=Org Root CA +EOF + }, + { + expected_success => 1, + name => "following text pem", + pem => <<'EOF', +-----BEGIN CERTIFICATE----- +32JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +-----BEGIN CERTIFICATE----- +42JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +some more text that we would like to remove +EOF + + expected_result => [ + <<'EOF', +-----BEGIN CERTIFICATE----- +32JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + + <<'EOF', +-----BEGIN CERTIFICATE----- +42JlZ2tseTxzZWl2IGF3ZWlidm4= +-----END CERTIFICATE----- +EOF + ], + }, +]; + +for my $data ($setup->@*) { + subtest $data->{name} => sub { + # Act + my @split_result = PVE::Certificate::split_pem( + $data->{pem}, label => $data->{label}, + ); + + # Assert + if ($data->{expected_success}) { + ok(@split_result, "is successful"); + my $expected_result = + $data->{expected_result} + ? $data->{expected_result} + : [$data->{pem}]; + + is_deeply( + \@split_result, \@$expected_result, "has correct split output", + ); + } else { + is_deeply(\@split_result, [], "has correctly returned empty"); + } + } +} + +done_testing(); -- 2.47.3