farm-2.x-dev/modules/asset/sensor/tests/src/Functional/SensorDataApiTest.php
modules/asset/sensor/tests/src/Functional/SensorDataApiTest.php
<?php
namespace Drupal\Tests\farm_sensor\Functional;
use Drupal\asset\Entity\Asset;
use Drupal\asset\Entity\AssetInterface;
use Drupal\Component\Serialization\Json;
use Drupal\Core\Url;
use Drupal\Tests\farm_test\Functional\FarmBrowserTestBase;
use GuzzleHttp\RequestOptions;
/**
* Test the Sensor data API.
*
* @group farm
*/
class SensorDataApiTest extends FarmBrowserTestBase {
/**
* The Sensor asset for testing.
*
* @var \Drupal\asset\Entity\AssetInterface
*/
protected $asset;
/**
* {@inheritdoc}
*/
protected static $modules = [
'farm_sensor',
];
/**
* {@inheritdoc}
*/
protected function setUp(): void {
parent::setUp();
$this->asset = Asset::create([
'type' => 'sensor',
'name' => $this->randomMachineName(),
]);
$this->asset->save();
}
/**
* Test API GET requests.
*/
public function testApiGet() {
// Build the path.
$uri = $this->buildPath($this->asset);
$url = Url::fromUri($uri);
// Build a private_key query param.
$private_key = [RequestOptions::QUERY => ['private_key' => $this->asset->get('private_key')->value]];
// Make a request.
$response = $this->processRequest('GET', $url);
// Assert that access is denied.
$this->assertEquals(403, $response->getStatusCode());
// Make a request with the private key.
$response = $this->processRequest('GET', $url, $private_key);
// Assert valid response.
$this->assertEquals(200, $response->getStatusCode());
$data = Json::decode($response->getBody());
$this->assertEquals(0, count($data));
// Make the sensor public.
$this->asset->set('public', TRUE)->save();
// Test that data can be accessed without the private key.
$response = $this->processRequest('GET', $url);
$this->assertEquals(200, $response->getStatusCode());
$data = Json::decode($response->getBody());
$this->assertEquals(0, count($data));
}
/**
* Test API POST requests.
*/
public function testApiPost() {
// Build the path.
$uri = $this->buildPath($this->asset);
$url = Url::fromUri($uri);
// Build a private_key query param.
$private_key = [RequestOptions::QUERY => ['private_key' => $this->asset->get('private_key')->value]];
// Make the asset public. This should not matter for posting data.
$this->asset->set('public', TRUE)->save();
// Test data.
$test_data = ['test_1' => 100, 'test_2' => 200];
// Make a request without a private key.
$payload = [RequestOptions::BODY => Json::encode($test_data)];
$response = $this->processRequest('POST', $url, $payload);
// Assert that access is denied.
$this->assertEquals(403, $response->getStatusCode());
// Post data with a private key.
$response = $this->processRequest('POST', $url, $private_key + $payload);
$this->assertEquals(201, $response->getStatusCode());
// Assert that new data streams were created.
$this->asset = Asset::load($this->asset->id());
$data_streams = $this->asset->get('data_stream')->referencedEntities();
$this->assertEquals(2, count($data_streams));
// Assert that new data was saved in DB.
$response = $this->processRequest('GET', $url);
$data = Json::decode($response->getBody());
$this->assertEquals(2, count($data));
// More test data.
$test_data = ['test_1' => 101, 'test_2' => 201];
// Post data with a private key.
$payload = [RequestOptions::BODY => Json::encode($test_data)];
$response = $this->processRequest('POST', $url, $private_key + $payload);
$this->assertEquals(201, $response->getStatusCode());
// Assert that no new data streams were created.
$this->asset = Asset::load($this->asset->id());
$data_streams = $this->asset->get('data_stream')->referencedEntities();
$this->assertEquals(2, count($data_streams));
// Assert that new data was saved in DB.
$response = $this->processRequest('GET', $url);
$data = Json::decode($response->getBody());
$this->assertEquals(4, count($data));
}
/**
* Helper function to build the path to the sensor API.
*
* @param \Drupal\asset\Entity\AssetInterface $asset
* The asset.
*
* @return string
* The path.
*/
protected function buildPath(AssetInterface $asset) {
return "base://asset/{$asset->uuid()}/data/basic";
}
/**
* Process a request.
*
* @param string $method
* HTTP method.
* @param \Drupal\Core\Url $url
* URL to request.
* @param array $request_options
* Request options to apply.
*
* @return \GuzzleHttp\Psr7\Response
* The response.
*
* @see \Drupal\Tests\jsonapi\Functional\JsonApiRequestTestTrait
*/
protected function processRequest(string $method, Url $url, array $request_options = []) {
$this->refreshVariables();
$request_options[RequestOptions::HTTP_ERRORS] = FALSE;
$client = $this->getSession()->getDriver()->getClient()->getClient();
return $client->request($method, $url->setAbsolute(TRUE)->toString(), $request_options);
}
}
