tests
This commit is contained in:
parent
a687d7ac4d
commit
9a9a901d46
67
tests/Browser/RealtimeChatTest.php
Normal file
67
tests/Browser/RealtimeChatTest.php
Normal file
@ -0,0 +1,67 @@
|
||||
<?php
|
||||
|
||||
namespace Tests\Browser;
|
||||
|
||||
use App\Models\User;
|
||||
use App\Models\Dynamic;
|
||||
use App\Models\Ledger;
|
||||
use Laravel\Dusk\Browser;
|
||||
use Tests\DuskTestCase;
|
||||
|
||||
test('multiple sessions can communicate in real time through websockets', function () {
|
||||
// 1. Create realistic database state
|
||||
$owner = User::factory()->create([
|
||||
'name' => 'TU Test User',
|
||||
'email' => 'test-owner@example.com',
|
||||
'password' => bcrypt('password'),
|
||||
]);
|
||||
|
||||
$participant = User::factory()->create([
|
||||
'name' => 'Submissive Bob',
|
||||
'email' => 'test-sub@example.com',
|
||||
'password' => bcrypt('password'),
|
||||
]);
|
||||
|
||||
$dynamic = Dynamic::create([
|
||||
'name' => 'The Test Sanctuary',
|
||||
'rules' => 'Rules for realtime testing.',
|
||||
]);
|
||||
|
||||
$dynamic->participants()->attach($owner->id, ['role' => 'owner']);
|
||||
$dynamic->participants()->attach($participant->id, ['role' => 'participant']);
|
||||
|
||||
// 2. Spawn two separate browser sessions/browsers in parallel
|
||||
$this->browse(function (Browser $sessionA, Browser $sessionB) use ($dynamic, $owner, $participant) {
|
||||
|
||||
// --- SESSION A: Owner ---
|
||||
$sessionA->loginAs($owner)
|
||||
->visit(route('dynamics.show', $dynamic))
|
||||
->waitForText('The Test Sanctuary')
|
||||
->assertSee('TU Test User'); // Verify loaded in as Owner
|
||||
|
||||
// --- SESSION B: Participant ---
|
||||
$sessionB->loginAs($participant)
|
||||
->visit(route('dynamics.show', $dynamic))
|
||||
->waitForText('The Test Sanctuary')
|
||||
->assertSee('Submissive Bob'); // Verify loaded in as Submissive/Participant
|
||||
|
||||
// --- REAL-TIME COMMUNICATING ---
|
||||
// Owner types and sends a message in chat
|
||||
$sessionA->type('#content', 'Hello Submissive Bob, did you complete your daily chores?')
|
||||
->click('.c-chat__button')
|
||||
->waitForText('Hello Submissive Bob');
|
||||
|
||||
// Since websockets broadcast in real-time, Session B receives it without reloading
|
||||
$sessionB->waitForText('Hello Submissive Bob', 5)
|
||||
->assertSee('Hello Submissive Bob, did you complete your daily chores?');
|
||||
|
||||
// Participant replies in real-time
|
||||
$sessionB->type('#content', 'Yes Master, everything is complete and logged in the ledger!')
|
||||
->click('.c-chat__button')
|
||||
->waitForText('Yes Master, everything is complete');
|
||||
|
||||
// Session A receives the reply in real-time without reloading
|
||||
$sessionA->waitForText('Yes Master, everything is complete', 5)
|
||||
->assertSee('Yes Master, everything is complete and logged in the ledger!');
|
||||
});
|
||||
});
|
||||
44
tests/DuskTestCase.php
Normal file
44
tests/DuskTestCase.php
Normal file
@ -0,0 +1,44 @@
|
||||
<?php
|
||||
|
||||
namespace Tests;
|
||||
|
||||
use Laravel\Dusk\TestCase as BaseTestCase;
|
||||
use Facebook\WebDriver\Chrome\ChromeOptions;
|
||||
use Facebook\WebDriver\Remote\RemoteWebDriver;
|
||||
use Facebook\WebDriver\Remote\DesiredCapabilities;
|
||||
|
||||
abstract class DuskTestCase extends BaseTestCase
|
||||
{
|
||||
/**
|
||||
* Prepare for Dusk test execution.
|
||||
*
|
||||
* @beforeClass
|
||||
*/
|
||||
public static function prepare(): void
|
||||
{
|
||||
if (! static::runningInSail()) {
|
||||
static::startChromeDriver();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Create the RemoteWebDriver instance.
|
||||
*/
|
||||
protected function driver(): RemoteWebDriver
|
||||
{
|
||||
$options = (new ChromeOptions)->addArguments(collect([
|
||||
$this->shouldStartMaximized() ? '--start-maximized' : '--window-size=1920,1080',
|
||||
'--disable-gpu',
|
||||
'--headless=new',
|
||||
'--no-sandbox',
|
||||
'--disable-dev-shm-usage',
|
||||
])->unless(static::runningInSail(), function (collect $arguments) {
|
||||
return $arguments->push('--disable-smooth-scrolling');
|
||||
})->all());
|
||||
|
||||
return RemoteWebDriver::create(
|
||||
$_ENV['DUSK_DRIVER_URL'] ?? env('DUSK_DRIVER_URL') ?? 'http://localhost:9515',
|
||||
DesiredCapabilities::chrome()->setCapability(ChromeOptions::CAPABILITY, $options)
|
||||
);
|
||||
}
|
||||
}
|
||||
75
tests/Feature/MediaTest.php
Normal file
75
tests/Feature/MediaTest.php
Normal file
@ -0,0 +1,75 @@
|
||||
<?php
|
||||
|
||||
use App\Models\User;
|
||||
use App\Models\Dynamic;
|
||||
use App\Models\Ledger;
|
||||
use App\Models\Mutation;
|
||||
use App\Models\Message;
|
||||
use App\Models\Media;
|
||||
use Illuminate\Http\UploadedFile;
|
||||
use Illuminate\Support\Facades\Storage;
|
||||
|
||||
test('media can be attached to mutations, ledgers, and messages', function () {
|
||||
Storage::fake('public');
|
||||
|
||||
$user = User::factory()->create();
|
||||
$dynamic = Dynamic::factory()->create();
|
||||
$dynamic->participants()->attach($user->id, ['role' => 'owner']);
|
||||
$ledger = Ledger::factory()->create(['dynamic_id' => $dynamic->id]);
|
||||
|
||||
$this->actingAs($user);
|
||||
|
||||
// 1. Test attaching media to a mutation
|
||||
$file1 = UploadedFile::fake()->image('proof1.jpg');
|
||||
$file2 = UploadedFile::fake()->image('proof2.png');
|
||||
|
||||
$response = $this->post(route('dynamics.ledgers.mutations.store', [$dynamic, $ledger]), [
|
||||
'amount' => 50,
|
||||
'description' => 'Completed deep clean',
|
||||
'media' => [$file1, $file2],
|
||||
]);
|
||||
|
||||
$response->assertSessionHasNoErrors();
|
||||
$response->assertRedirect();
|
||||
|
||||
$mutation = Mutation::firstWhere('description', 'Completed deep clean');
|
||||
expect($mutation)->not->toBeNull();
|
||||
expect($mutation->media)->toHaveCount(2);
|
||||
expect($mutation->media->first()->file_name)->toBe('proof1.jpg');
|
||||
expect($mutation->media->last()->file_name)->toBe('proof2.png');
|
||||
|
||||
Storage::disk('public')->assertExists($mutation->media->first()->file_path);
|
||||
Storage::disk('public')->assertExists($mutation->media->last()->file_path);
|
||||
|
||||
// 2. Test attaching media to a ledger
|
||||
$file3 = UploadedFile::fake()->image('rules.jpg');
|
||||
$response = $this->post(route('dynamics.ledgers.store', $dynamic), [
|
||||
'name' => 'Worship Ledger',
|
||||
'rules' => 'Specific rules',
|
||||
'alignment' => 'neutral',
|
||||
'media' => [$file3],
|
||||
]);
|
||||
|
||||
$response->assertSessionHasNoErrors();
|
||||
$response->assertRedirect();
|
||||
|
||||
$newLedger = Ledger::firstWhere('name', 'Worship Ledger');
|
||||
expect($newLedger)->not->toBeNull();
|
||||
expect($newLedger->media)->toHaveCount(1);
|
||||
expect($newLedger->media->first()->file_name)->toBe('rules.jpg');
|
||||
|
||||
// 3. Test attaching media to a chat message
|
||||
$chat = $dynamic->chat;
|
||||
$file4 = UploadedFile::fake()->image('chat_img.jpg');
|
||||
$response = $this->post(route('chats.messages.store', $chat), [
|
||||
'content' => 'Check this out!',
|
||||
'media' => [$file4],
|
||||
]);
|
||||
|
||||
$response->assertRedirect();
|
||||
|
||||
$message = Message::firstWhere('content', 'Check this out!');
|
||||
expect($message)->not->toBeNull();
|
||||
expect($message->media)->toHaveCount(1);
|
||||
expect($message->media->first()->file_name)->toBe('chat_img.jpg');
|
||||
});
|
||||
Loading…
x
Reference in New Issue
Block a user