Move signing to its own function

merge-requests/5/head
Terence Eden 2024-02-14 09:45:04 +00:00
rodzic a4360594df
commit 74bf3d1a68
1 zmienionych plików z 56 dodań i 64 usunięć

120
index.php
Wyświetl plik

@ -222,42 +222,14 @@
"object" => "https://{$server}/{$username}",
]
];
$message_json = json_encode( $message );
// The Accept is sent to the server of the user who requested the follow
// TODO: The path doesn't *always* end with/inbox
$host = $inbox_host;
$path = parse_url( $inbox_actor, PHP_URL_PATH ) . "/inbox";
// Set up signing
$keyId = "https://{$server}/{$username}#main-key";
// Generate signing variables
$hash = hash( 'sha256', $message_json, true );
$digest = base64_encode( $hash );
$date = date( 'D, d M Y H:i:s \G\M\T' );
$signer = openssl_get_privatekey( $key_private );
$stringToSign = "(request-target): post $path\nhost: $host\ndate: $date\ndigest: SHA-256=$digest";
openssl_sign(
$stringToSign,
$signature,
$signer,
OPENSSL_ALGO_SHA256
);
$signature_b64 = base64_encode( $signature );
$header = 'keyId="' . $keyId . '",algorithm="rsa-sha256",headers="(request-target) host date digest",signature="' . $signature_b64 . '"';
// Header for POST reply
$headers = array(
"Host: {$host}",
"Date: {$date}",
"Digest: SHA-256={$digest}",
"Signature: {$header}",
"Content-Type: application/activity+json",
"Accept: application/activity+json",
);
// Get the signed headers
$headers = generate_signed_headers( $message, $host, $path );
// Specify the URL of the remote server's inbox
// TODO: The path doesn't *always* end with /inbox
@ -267,7 +239,7 @@
$ch = curl_init( $remoteServerUrl );
curl_setopt( $ch, CURLOPT_RETURNTRANSFER, true );
curl_setopt( $ch, CURLOPT_CUSTOMREQUEST, "POST" );
curl_setopt( $ch, CURLOPT_POSTFIELDS, $message_json );
curl_setopt( $ch, CURLOPT_POSTFIELDS, json_encode($message) );
curl_setopt( $ch, CURLOPT_HTTPHEADER, $headers );
$response = curl_exec( $ch );
@ -290,6 +262,53 @@
);
}
function generate_signed_headers( $message, $host, $path ) {
global $server, $username, $key_private;
// Encode the message to JSON
$message_json = json_encode( $message );
// Location of the Public Key
$keyId = "https://{$server}/{$username}#main-key";
// Generate signing variables
$hash = hash( 'sha256', $message_json, true );
$digest = base64_encode( $hash );
$date = date( 'D, d M Y H:i:s \G\M\T' );
// Get the Private Key
$signer = openssl_get_privatekey( $key_private );
// Sign the path, host, date, and digest
$stringToSign = "(request-target): post $path\nhost: $host\ndate: $date\ndigest: SHA-256=$digest";
// The signing function returns the variable $signature
// https://www.php.net/manual/en/function.openssl-sign.php
openssl_sign(
$stringToSign,
$signature,
$signer,
OPENSSL_ALGO_SHA256
);
// Encode the signature
$signature_b64 = base64_encode( $signature );
// Full signature header
$signature_header = 'keyId="' . $keyId . '",algorithm="rsa-sha256",headers="(request-target) host date digest",signature="' . $signature_b64 . '"';
// Header for POST reply
$headers = array(
"Host: {$host}",
"Date: {$date}",
"Digest: SHA-256={$digest}",
"Signature: {$signature_header}",
"Content-Type: application/activity+json",
"Accept: application/activity+json",
);
return $headers;
}
function write() {
// Display an HTML form for the user to enter a message.
echo <<< HTML
@ -361,7 +380,6 @@ HTML;
],
"object" => $note
];
$message_json = json_encode($message);
// Create the context for the permalink
$note = [ "@context" => "https://www.w3.org/ns/activitystreams", ...$note ];
@ -385,37 +403,10 @@ HTML;
// Each POST to an inbox needs to be signed separately
foreach ( $hosts as $host ) {
$path = '/inbox';
// Set up signing
$privateKey = $key_private;
$keyId = "https://{$server}/{$username}#main-key";
$hash = hash( "sha256", $message_json, true );
$digest = base64_encode( $hash );
$date = date( 'D, d M Y H:i:s \G\M\T' );
$signer = openssl_get_privatekey( $key_private );
$stringToSign = "(request-target): post $path\nhost: $host\ndate: $date\ndigest: SHA-256=$digest";
openssl_sign(
$stringToSign,
$signature,
$signer,
OPENSSL_ALGO_SHA256
);
$signature_b64 = base64_encode( $signature );
$header = 'keyId="' . $keyId . '",algorithm="rsa-sha256",headers="(request-target) host date digest",signature="' . $signature_b64 . '"';
// Header for POST reply
$headers = array(
"Host: {$host}",
"Date: {$date}",
"Digest: SHA-256={$digest}",
"Signature: {$header}",
"Content-Type: application/activity+json",
"Accept: application/activity+json",
);
// Get the signed headers
$headers = generate_signed_headers( $message, $host, $path );
// Specify the URL of the remote server
$remoteServerUrl = "https://{$host}{$path}";
@ -424,7 +415,7 @@ HTML;
curl_setopt( $ch, CURLOPT_RETURNTRANSFER, true );
curl_setopt( $ch, CURLOPT_CUSTOMREQUEST, "POST" );
curl_setopt( $ch, CURLOPT_POSTFIELDS, $message_json );
curl_setopt( $ch, CURLOPT_POSTFIELDS, json_encode($message) );
curl_setopt( $ch, CURLOPT_HTTPHEADER, $headers );
// Add the handle to the multi-handle
@ -447,6 +438,7 @@ HTML;
die();
}
// "One to stun, two to kill, three to make sure"
die();
die();
die();