diff options
-rwxr-xr-x | acme-tinier.pl | 75 |
1 files changed, 36 insertions, 39 deletions
diff --git a/acme-tinier.pl b/acme-tinier.pl index 5e877a0..c34cce3 100755 --- a/acme-tinier.pl +++ b/acme-tinier.pl @@ -70,8 +70,8 @@ sub send_signed { my $b64payload = b64 $json->encode($payload); my $b64protected = b64 $json->encode($protected); - my $out = communicate('openssl', 'dgst', '-sha256', '-sign', $account_key, - "$b64protected.$b64payload"); + my $out = communicate('openssl', 'dgst', '-sha256', '-sign', + $account_key, "$b64protected.$b64payload"); die 'cannot sign request' if $? >> 8; return get $url, $json->encode({ header => $header, protected => $b64protected, @@ -99,40 +99,20 @@ my ($code, $result, $headers) = get "$ca/terms"; }); die "cannot register: $code" if $code != 201 && $code != 409; -# Run each domain through the ACME challenge -for my $domain (@domains) { - my ($code, $result) = send_signed("$ca/acme/new-authz", { - resource => 'new-authz', - identifier => { type => 'dns', value => $domain } - }); - die "cannot request challenge: $code" if $code != 201; - - my ($challenge) = grep { $_->{type} eq 'http-01' } - @{$json->decode($result)->{challenges}}; - my $token = $challenge->{token} =~ s/[^A-Za-z0-9_-]/_/r; - my $key_auth = "$token.$thumbprint"; - my $known_path = "$acme_dir/$token"; - - # Make the challenge file and check that it can be retrieved - open(my $fh, '>', $known_path) or die "cannot write $known_path: $!"; - print $fh $key_auth; - close $fh; - -eval { - my $url = "http://$domain/.well-known/acme-challenge/$token"; - my ($code, $result) = get $url; - die "checking $url failed: $code" if $code != 200; +# Check if the file is really there, submit an HTTP challenge and wait +sub verify_http { + my ($checked_url, $key_auth, $challenge_uri) = @_; + my ($code, $result) = get $checked_url; + die "checking $checked_url failed: $code" if $code != 200; die 'challenge contents differ' if $result ne $key_auth; - # Submit the challenge and wait for the verification to finish - ($code, $result) = send_signed($challenge->{uri}, { - resource => 'challenge', - keyAuthorization => $key_auth + ($code, $result) = send_signed($challenge_uri, { + resource => 'challenge', keyAuthorization => $key_auth }); die "challenge submission failed: $code" if $code != 202; while (1) { - ($code, $result) = get $challenge->{uri}; + ($code, $result) = get $challenge_uri; die "challenge verification failed: $code" if $code >= 400; my $status = $json->decode($result); if ($status->{status} eq 'valid') { @@ -143,22 +123,39 @@ eval { die "challenge verification failed: $result"; } } -}; +} + +for my $domain (@domains) { + my ($code, $result) = send_signed("$ca/acme/new-authz", { + resource => 'new-authz', + identifier => { type => 'dns', value => $domain } + }); + die "cannot request challenge: $code" if $code != 201; + + my ($challenge) = grep { $_->{type} eq 'http-01' } + @{$json->decode($result)->{challenges}}; + my $token = $challenge->{token} =~ s/[^A-Za-z0-9_-]/_/r; + my $key_auth = "$token.$thumbprint"; + my $known_path = "$acme_dir/$token"; + + open(my $fh, '>', $known_path) or die "cannot write to $known_path: $!"; + print $fh $key_auth; + close $fh; + + eval { verify_http("http://$domain/.well-known/acme-challenge/$token", + $key_auth, $challenge->{uri}) }; - # Make sure our file gets deleted and rethrow any error unlink $known_path; - die $@ if $@; + die "$domain: $@" if $@; } -# Get the new certificate and print it in the PEM format +# Get the new certificate and convert it to the PEM format my $der = `openssl req -in '$csr_file' -outform DER`; die 'cannot convert CSR' if $?; ($code, $result) = send_signed("$ca/acme/new-cert", { - resource => 'new-cert', - csr => b64 $der + resource => 'new-cert', csr => b64 $der }); die "cannot sign certificate: $code" if $code != 201; -print "-----BEGIN CERTIFICATE-----\n" - . join("\n", unpack '(A64)*', encode_base64($result, '')) - . "\n-----END CERTIFICATE-----\n"; +my $pem = join("\n", unpack '(A64)*', encode_base64($result, '')); +print "-----BEGIN CERTIFICATE-----\n$pem\n-----END CERTIFICATE-----\n"; |