You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

78 lines
2.2 KiB
PHP

<?php
namespace Eater\Glim\Service;
use Eater\Glim\Model\Server as ServerModel;
use GuzzleHttp\Client as HttpClient;
use Eater\Glim\Core;
class Server extends Main
{
const MANAGEMENT_PORT = 7864;
private $httpClient = null;
private function getHttpClient() {
if ($this->httpClient === null) {
$this->httpClient = new HttpClient();
}
return $this->httpClient;
}
/**
* @param ServerModel $server
* @throws \Exception
*/
public function deliverSignedCertificate(ServerModel $server) {
$response = $this->doSignedRequest($server, '/deliver-crt', [
'certficate' => $server->getCertificate()
]);
if ($response->getStatusCode() !== 200) {
throw new \Exception('Delivering signed certificate failed (' . $response->getStatusCode() . '): ' . $response->getBody()->getContents());
}
}
/**
* @param ServerModel $server
* @param string $path
* @param string $data
* @return \Psr\Http\Message\ResponseInterface
* @throws \Exception
*/
public function doSignedRequest(ServerModel $server, $path, $data) {
$client = $this->getHttpClient();
/** @var CA $ca */
$ca = $this->get('ca');
$data['signature'] = bin2hex($ca->signWithCA($server->getFingerprint()));
$json = json_encode($data);
$password = bin2hex(openssl_random_pseudo_bytes(32));
$pubKey = openssl_get_publickey($server->getPublicKey());
$success = openssl_public_encrypt($password, $crypted, $pubKey, OPENSSL_PKCS1_PADDING);
if (!$success) {
throw new \Exception('Encrypting data failed: ' . openssl_error_string() . openssl_error_string());
}
$this->get('logger')->addDebug('Password: ' . $password);
$body = [
bin2hex($crypted),
bin2hex(openssl_encrypt($server->getCertificate(), 'aes-256-cbc', $password, 'help'))
];
$this->get('logger')->addDebug('Help: ' . var_export([$json, $body], true));
return $client->post('http://' . $server->getExternalIp() . ':' . static::MANAGEMENT_PORT . $path, [
'json' => $body
]);
}
}