View source
<?php
namespace Drupal\acquia_contenthub_diagnostic\Plugin\ContentHubRequirement;
use Drupal\acquia_contenthub_diagnostic\ContentHubRequirementBase;
use GuzzleHttp\Psr7\Request as GuzzleRequest;
use Symfony\Component\HttpFoundation\Request;
class EndpointAccessibilityRequirement extends ContentHubRequirementBase {
const REQUEST_OPTIONS = [
'verify' => FALSE,
'cookies' => FALSE,
'allow_redirects' => FALSE,
'http_errors' => FALSE,
];
protected $description = '';
protected $domain = '';
protected $clientManager;
public function verify() {
if (!$this->moduleHandler
->moduleExists('acquia_contenthub')) {
return REQUIREMENT_OK;
}
$this->clientManager = \Drupal::service('acquia_contenthub.client_manager');
if (!$this->clientManager
->isConnected()) {
$this
->setValue($this
->t('Endpoint validation failed'));
$this
->setDescription($this
->t('Client Manager not connected. Configure Content Hub and try again.'));
return REQUIREMENT_ERROR;
}
$this->domain = $this
->getDomain();
try {
$this
->testWebhookEndpoint();
$this
->testContentViewEndpoint();
if ($this->description) {
$this
->setValue($this
->t('Endpoint validation failed'));
$this
->setDescription($this->description);
return REQUIREMENT_ERROR;
}
} catch (\Exception $e) {
$this
->setValue($this
->t('Cannot validate endpoints'));
$this
->setDescription($this
->t('Verify your server and site configuration and try again. Error: @error', [
'@error' => $e
->getMessage(),
]));
return REQUIREMENT_ERROR;
}
return REQUIREMENT_OK;
}
protected function testWebhookEndpoint() {
$endpoint_name = 'Webhook Endpoint';
$endpoint_url = '/acquia-contenthub/webhook';
$client = \Drupal::httpClient();
$response = $client
->get($this->domain . $endpoint_url, static::REQUEST_OPTIONS);
$status_code = $response
->getStatusCode();
$this->description .= $this
->parseStatusCode($status_code, $endpoint_name, $endpoint_url);
}
protected function testContentViewEndpoint() {
$endpoint_name = 'Content View Endpoint';
$test_nid = $this
->getTestNid();
if ($test_nid) {
$endpoint_url = $this->domain . '/acquia-contenthub/display/node/' . $test_nid . '/default';
$authorization = $this
->getAuthorizationHeader($endpoint_url);
$request = new GuzzleRequest('GET', $endpoint_url, [
'authorization' => $authorization,
]);
$client = \Drupal::httpClient();
$response = $client
->send($request, static::REQUEST_OPTIONS);
$status_code = $response
->getStatusCode();
$this->description .= $this
->parseStatusCode($status_code, $endpoint_name, $endpoint_url);
}
else {
$endpoint_url = '/acquia-contenthub/display/node/{entity_id}/default';
$this->description .= $this
->t("@endpoint_name (@endpoint_url) requires a node to exist on the site in order to test. Create a node and try again.", [
'@endpoint_name' => $endpoint_name,
'@endpoint_url' => $endpoint_url,
]);
}
}
protected function getTestNid() {
$nodes = \Drupal::entityQuery('node')
->condition('status', 1)
->range(0, 1)
->execute();
if (count($nodes)) {
return array_pop($nodes);
}
return FALSE;
}
protected function parseStatusCode($status_code, $endpoint_name, $endpoint_url) {
if ($status_code == 200) {
return '';
}
elseif (substr($status_code, 0, 1) == 3) {
return $this
->t("@endpoint_name (@endpoint_url) received a @status_code response indicating a redirect. The Content Hub service will not follow redirects.\n", [
'@endpoint_name' => $endpoint_name,
'@endpoint_url' => $endpoint_url,
'@status_code' => $status_code,
]);
}
elseif ($status_code == 401) {
return $this
->t("@endpoint_name (@endpoint_url) received a 401 response indicating that credentials are required. Disable the Shield module or any other authentication method being used on the endpoint.\n", [
'@endpoint_name' => $endpoint_name,
'@endpoint_url' => $endpoint_url,
]);
}
elseif ($status_code == 404) {
return $this
->t("@endpoint_name (@endpoint_url) received a 404 response indicating that the endpoint cannot be reached.\n", [
'@endpoint_name' => $endpoint_name,
'@endpoint_url' => $endpoint_url,
]);
}
else {
return $this
->t("@endpoint_name (@endpoint_url) received a @status_code response. Please ensure a 200 response is sent.\n", [
'@endpoint_name' => $endpoint_name,
'@endpoint_url' => $endpoint_url,
'@status_code' => $status_code,
]);
}
}
protected function getAuthorizationHeader($endpoint, $method = 'GET') {
$request = Request::create($endpoint, $method);
$subscription = \Drupal::service('acquia_contenthub.acquia_contenthub_subscription');
$shared_secret = $subscription
->getSharedSecret();
$signature = $this->clientManager
->getRequestSignature($request, $shared_secret);
return 'Acquia ContentHub:' . $signature;
}
}