<?php

namespace Tests\Feature;

use App\Facades\Settings;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Mtc\MercuryDataModels\Vehicle;
use Tests\TestCase;

class SalesForceTest extends TestCase
{
    use RefreshDatabase;

    protected $tenancy = true;

    public function testIntegrationDisabled()
    {
        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'foo',
            'config_key' => 'sales-force-inbound-vehicle-notifications-enabled',
            'type' => 'boolean',
            'value' => false,
        ]);

        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'Bearer token',
            'config_key' => 'sales-force-inbound-vehicle-notifications-bearer-token',
            'type' => 'secret',
            'value' => 'abc123',
            'validation_rules' => [
                "required_if:sales-force-inbound-vehicle-notifications-enabled,true"
            ]
        ]);

        $response = $this->postJson(route('tenant.notifications.sales-force.notify-vehicle', tenant('id')), [
            'vehicle_id' => 1,
            'price' => 12345,
            'is_published' => true,
            'is_reserved' => true,
            'is_sold' => true,
        ], [
            'Authorization' => 'Bearer abc123',
        ]);

        $response->assertStatus(403);
    }

    public function testNotificationUnauthorised()
    {
        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'foo',
            'config_key' => 'sales-force-inbound-vehicle-notifications-enabled',
            'type' => 'boolean',
            'value' => true,
        ]);

        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'Bearer token',
            'config_key' => 'sales-force-inbound-vehicle-notifications-bearer-token',
            'type' => 'secret',
            'value' => 'abc123',
            'validation_rules' => [
                "required_if:sales-force-inbound-vehicle-notifications-enabled,true"
            ]
        ]);

        $response = $this->postJson(route('tenant.notifications.sales-force.notify-vehicle', tenant('id')), [
            // missing required parameters
        ], [
            'Authorization' => 'Bearer xyz999',
        ]);

        $response->assertStatus(403);
    }

    public function testNotificationEmptyToken()
    {
        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'foo',
            'config_key' => 'sales-force-inbound-vehicle-notifications-enabled',
            'type' => 'boolean',
            'value' => true,
        ]);

        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'Bearer token',
            'config_key' => 'sales-force-inbound-vehicle-notifications-bearer-token',
            'type' => 'secret',
            'value' => '',
            'validation_rules' => [
                "required_if:sales-force-inbound-vehicle-notifications-enabled,true"
            ]
        ]);

        $response = $this->postJson(route('tenant.notifications.sales-force.notify-vehicle', tenant('id')), [
            'vehicle_id' => 1,
            'price' => 12345,
            'is_published' => true,
            'is_reserved' => true,
            'is_sold' => true,
        ], [
            'Authorization' => 'Bearer ',
        ]);

        $response->assertStatus(403);
    }

    public function testNotificationMissingParameters()
    {
        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'foo',
            'config_key' => 'sales-force-inbound-vehicle-notifications-enabled',
            'type' => 'boolean',
            'value' => true,
        ]);

        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'Bearer token',
            'config_key' => 'sales-force-inbound-vehicle-notifications-bearer-token',
            'type' => 'secret',
            'value' => 'abc123',
            'validation_rules' => [
                "required_if:sales-force-inbound-vehicle-notifications-enabled,true"
            ]
        ]);

        $response = $this->postJson(route('tenant.notifications.sales-force.notify-vehicle', tenant('id')), [
            // missing required parameters
        ], [
            'Authorization' => 'Bearer abc123',
        ]);

        $response->assertStatus(422);
        $this->assertArrayHasKey('errors', $response->json());
        $this->assertArrayHasKey('vehicle_id', $response->json('errors'));
        $this->assertArrayHasKey('price', $response->json('errors'));
        $this->assertArrayHasKey('is_published', $response->json('errors'));
        $this->assertArrayHasKey('is_reserved', $response->json('errors'));
        $this->assertArrayHasKey('is_sold', $response->json('errors'));
    }

    public function testNotificationIncorrectParameterTypes()
    {
        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'foo',
            'config_key' => 'sales-force-inbound-vehicle-notifications-enabled',
            'type' => 'boolean',
            'value' => true,
        ]);

        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'Bearer token',
            'config_key' => 'sales-force-inbound-vehicle-notifications-bearer-token',
            'type' => 'secret',
            'value' => 'abc123',
            'validation_rules' => [
                "required_if:sales-force-inbound-vehicle-notifications-enabled,true"
            ]
        ]);

        $response = $this->postJson(route('tenant.notifications.sales-force.notify-vehicle', tenant('id')), [
            'vehicle_id' => 1,
            'price' => 12345,
            'is_published' => 'true',
            'is_reserved' => 'true',
            'is_sold' => 'false',
        ], [
            'Authorization' => 'Bearer abc123',
        ]);

        $response->assertStatus(422);
        $this->assertArrayHasKey('errors', $response->json());
        $this->assertArrayHasKey('is_published', $response->json('errors'));
        $this->assertArrayHasKey('is_reserved', $response->json('errors'));
        $this->assertArrayHasKey('is_sold', $response->json('errors'));
    }

    public function testNotificationGoodRequest()
    {
        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'foo',
            'config_key' => 'sales-force-inbound-vehicle-notifications-enabled',
            'type' => 'boolean',
            'value' => true,
        ]);

        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'Bearer token',
            'config_key' => 'sales-force-inbound-vehicle-notifications-bearer-token',
            'type' => 'secret',
            'value' => 'abc123',
            'validation_rules' => [
                "required_if:sales-force-inbound-vehicle-notifications-enabled,true"
            ]
        ]);

        $response = $this->postJson(route('tenant.notifications.sales-force.notify-vehicle', tenant('id')), [
            'vehicle_id' => 1,
            'price' => 12345,
            'is_published' => true,
            'is_reserved' => true,
            'is_sold' => true,
        ], [
            'Authorization' => 'Bearer abc123',
        ]);

        $response->assertStatus(200);
    }

    public function testVehicleUpdatePriceAndPublished()
    {
        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'foo',
            'config_key' => 'sales-force-inbound-vehicle-notifications-enabled',
            'type' => 'boolean',
            'value' => true,
        ]);

        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'Bearer token',
            'config_key' => 'sales-force-inbound-vehicle-notifications-bearer-token',
            'type' => 'secret',
            'value' => 'abc123',
            'validation_rules' => [
                "required_if:sales-force-inbound-vehicle-notifications-enabled,true"
            ]
        ]);

        $vehicle = Vehicle::factory()->create([
            'uuid' => 'foo',
            'price' => 12345,
            'is_published' => false,
            'is_reserved' => false,
            'is_sold' => false,
        ]);

        $response = $this->postJson(route('tenant.notifications.sales-force.notify-vehicle', tenant('id')), [
            'vehicle_id' => $vehicle->uuid,
            'price' => 555.67,
            'is_published' => true,
            'is_reserved' => false,
            'is_sold' => false,
        ], [
            'Authorization' => 'Bearer abc123',
        ]);

        $response->assertStatus(200);

        $vehicle->refresh();

        $this->assertEquals(555.67, $vehicle->price);
        $this->assertTrue($vehicle->is_published);
        $this->assertFalse($vehicle->is_reserved);
        $this->assertFalse($vehicle->is_sold);
    }

    public function testVehicleUpdateReserved()
    {
        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'foo',
            'config_key' => 'sales-force-inbound-vehicle-notifications-enabled',
            'type' => 'boolean',
            'value' => true,
        ]);

        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'Bearer token',
            'config_key' => 'sales-force-inbound-vehicle-notifications-bearer-token',
            'type' => 'secret',
            'value' => 'abc123',
            'validation_rules' => [
                "required_if:sales-force-inbound-vehicle-notifications-enabled,true"
            ]
        ]);

        $vehicle = Vehicle::factory()->create([
            'uuid' => 'foo',
            'price' => 12345,
            'is_published' => true,
            'is_reserved' => false,
            'is_sold' => false,
        ]);

        $response = $this->postJson(route('tenant.notifications.sales-force.notify-vehicle', tenant('id')), [
            'vehicle_id' => $vehicle->uuid,
            'price' => 12345,
            'is_published' => true,
            'is_reserved' => true,
            'is_sold' => false,
        ], [
            'Authorization' => 'Bearer abc123',
        ]);

        $response->assertStatus(200);

        $vehicle->refresh();

        $this->assertEquals(12345, $vehicle->price);
        $this->assertTrue($vehicle->is_published);
        $this->assertTrue($vehicle->is_reserved);
        $this->assertFalse($vehicle->is_sold);
    }

    public function testVehicleUpdateSold()
    {
        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'foo',
            'config_key' => 'sales-force-inbound-vehicle-notifications-enabled',
            'type' => 'boolean',
            'value' => true,
        ]);

        Settings::make([
            'tab' => 'Automotive',
            'section' => 'DMS vehicle sync',
            'group' => 'SalesForce',
            'name' => 'Bearer token',
            'config_key' => 'sales-force-inbound-vehicle-notifications-bearer-token',
            'type' => 'secret',
            'value' => 'abc123',
            'validation_rules' => [
                "required_if:sales-force-inbound-vehicle-notifications-enabled,true"
            ]
        ]);

        $vehicle = Vehicle::factory()->create([
            'uuid' => 'foo',
            'price' => 12345,
            'is_published' => true,
            'is_reserved' => true,
            'is_sold' => false,
        ]);

        $response = $this->postJson(route('tenant.notifications.sales-force.notify-vehicle', tenant('id')), [
            'vehicle_id' => $vehicle->uuid,
            'price' => 12345,
            'is_published' => false,
            'is_reserved' => false,
            'is_sold' => true,
        ], [
            'Authorization' => 'Bearer abc123',
        ]);

        $response->assertStatus(200);

        $vehicle->refresh();

        $this->assertEquals(12345, $vehicle->price);
        $this->assertFalse($vehicle->is_published);
        $this->assertFalse($vehicle->is_reserved);
        $this->assertTrue($vehicle->is_sold);
    }
}
