Page MenuHomePhorge

PasswordResetTest.php
No OneTemporary

Size
9 KB
Referenced Files
None
Subscribers
None

PasswordResetTest.php

<?php
namespace Tests\Browser;
use App\User;
use App\VerificationCode;
use Tests\Browser\Pages\Dashboard;
use Tests\Browser\Pages\Home;
use Tests\Browser\Pages\PasswordReset;
use Tests\DuskTestCase;
use Laravel\Dusk\Browser;
use Illuminate\Foundation\Testing\DatabaseMigrations;
class PasswordResetTest extends DuskTestCase
{
/**
* {@inheritDoc}
*
* @return void
*/
public function setUp(): void
{
parent::setUp();
$user = User::firstOrCreate(['email' => 'passwordresettestdusk@' . \config('app.domain')]);
$user->setSetting('external_email', 'external@domain.tld');
}
/**
* {@inheritDoc}
*
* @return void
*/
public function tearDown(): void
{
User::where('email', 'passwordresettestdusk@' . \config('app.domain'))->delete();
}
/**
* Test the link from logon to password-reset page
*
* @return void
*/
public function testPasswordResetLinkOnLogon()
{
$this->browse(function (Browser $browser) {
$browser->visit(new Home());
$browser->assertSeeLink('Forgot password?');
$browser->clickLink('Forgot password?');
$browser->on(new PasswordReset());
$browser->assertVisible('@step1');
});
}
/**
* Test 1st step of password-reset
*
* @return void
*/
public function testPasswordResetStep1()
{
$this->browse(function (Browser $browser) {
$browser->visit(new PasswordReset());
$browser->assertVisible('@step1');
// Here we expect email input and submit button
$browser->with('@step1', function ($step) {
$step->assertVisible('#reset_email');
$step->assertFocused('#reset_email');
$step->assertVisible('[type=submit]');
});
// Submit empty form
$browser->with('@step1', function ($step) {
$step->click('[type=submit]');
$step->assertFocused('#reset_email');
});
// Submit invalid email
// We expect email input to have is-invalid class added, with .invalid-feedback element
$browser->with('@step1', function ($step) use ($browser) {
$step->type('#reset_email', '@test');
$step->click('[type=submit]');
$step->waitFor('#reset_email.is-invalid');
$step->waitFor('#reset_email + .invalid-feedback');
$browser->waitFor('.toast-error');
$browser->click('.toast-error'); // remove the toast
});
// Submit valid data
$browser->with('@step1', function ($step) {
$step->type('#reset_email', 'passwordresettestdusk@' . \config('app.domain'));
$step->click('[type=submit]');
$step->assertMissing('#reset_email.is-invalid');
$step->assertMissing('#reset_email + .invalid-feedback');
});
$browser->waitUntilMissing('@step2 #reset_code[value=""]');
$browser->waitFor('@step2');
$browser->assertMissing('@step1');
});
}
/**
* Test 2nd Step of the password reset process
*
* @depends testPasswordResetStep1
* @return void
*/
public function testPasswordResetStep2()
{
$this->browse(function (Browser $browser) {
$browser->assertVisible('@step2');
// Here we expect one text input, Back and Continue buttons
$browser->with('@step2', function ($step) {
$step->assertVisible('#reset_short_code');
$step->assertFocused('#reset_short_code');
$step->assertVisible('[type=button]');
$step->assertVisible('[type=submit]');
});
// Test Back button functionality
$browser->click('@step2 [type=button]');
$browser->waitFor('@step1');
$browser->assertFocused('@step1 #reset_email');
$browser->assertMissing('@step2');
// Submit valid Step 1 data (again)
$browser->with('@step1', function ($step) {
$step->type('#reset_email', 'passwordresettestdusk@' . \config('app.domain'));
$step->click('[type=submit]');
});
$browser->waitFor('@step2');
$browser->assertMissing('@step1');
// Submit invalid code
// We expect code input to have is-invalid class added, with .invalid-feedback element
$browser->with('@step2', function ($step) use ($browser) {
$step->type('#reset_short_code', 'XXXXX');
$step->click('[type=submit]');
$browser->waitFor('.toast-error');
$step->assertVisible('#reset_short_code.is-invalid');
$step->assertVisible('#reset_short_code + .invalid-feedback');
$step->assertFocused('#reset_short_code');
$browser->click('.toast-error'); // remove the toast
});
// Submit valid code
// We expect error state on code input to be removed, and Step 3 form visible
$browser->with('@step2', function ($step) {
// Get the code and short_code from database
// FIXME: Find a nice way to read javascript data without using hidden inputs
$code = $step->value('#reset_code');
$this->assertNotEmpty($code);
$code = VerificationCode::find($code);
$step->type('#reset_short_code', $code->short_code);
$step->click('[type=submit]');
$step->assertMissing('#reset_short_code.is-invalid');
$step->assertMissing('#reset_short_code + .invalid-feedback');
});
$browser->waitFor('@step3');
$browser->assertMissing('@step2');
});
}
/**
* Test 3rd Step of the password reset process
*
* @depends testPasswordResetStep2
* @return void
*/
public function testPasswordResetStep3()
{
$this->browse(function (Browser $browser) {
$browser->assertVisible('@step3');
// Here we expect 2 text inputs, Back and Continue buttons
$browser->with('@step3', function ($step) {
$step->assertVisible('#reset_password');
$step->assertVisible('#reset_confirm');
$step->assertVisible('[type=button]');
$step->assertVisible('[type=submit]');
$step->assertFocused('#reset_password');
});
// Test Back button
$browser->click('@step3 [type=button]');
$browser->waitFor('@step2');
$browser->assertFocused('@step2 #reset_short_code');
$browser->assertMissing('@step3');
$browser->assertMissing('@step1');
// TODO: Test form reset when going back
// Because the verification code is removed in tearDown()
// we'll start from the beginning (Step 1)
$browser->click('@step2 [type=button]');
$browser->waitFor('@step1');
$browser->assertFocused('@step1 #reset_email');
$browser->assertMissing('@step3');
$browser->assertMissing('@step2');
// Submit valid data
$browser->with('@step1', function ($step) {
$step->type('#reset_email', 'passwordresettestdusk@' . \config('app.domain'));
$step->click('[type=submit]');
});
$browser->waitFor('@step2');
$browser->waitUntilMissing('@step2 #reset_code[value=""]');
// Submit valid code again
$browser->with('@step2', function ($step) {
$code = $step->value('#reset_code');
$this->assertNotEmpty($code);
$code = VerificationCode::find($code);
$step->type('#reset_short_code', $code->short_code);
$step->click('[type=submit]');
});
$browser->waitFor('@step3');
// Submit invalid data
$browser->with('@step3', function ($step) use ($browser) {
$step->assertFocused('#reset_password');
$step->type('#reset_password', '12345678');
$step->type('#reset_confirm', '123456789');
$step->click('[type=submit]');
$browser->waitFor('.toast-error');
$step->assertVisible('#reset_password.is-invalid');
$step->assertVisible('#reset_password + .invalid-feedback');
$step->assertFocused('#reset_password');
$browser->click('.toast-error'); // remove the toast
});
// Submit valid data
$browser->with('@step3', function ($step) {
$step->type('#reset_confirm', '12345678');
$step->click('[type=submit]');
});
$browser->waitUntilMissing('@step3');
// At this point we should be auto-logged-in to dashboard
$dashboard = new Dashboard();
$dashboard->assert($browser);
// FIXME: Is it enough to be sure user is logged in?
});
}
}

File Metadata

Mime Type
text/x-php
Expires
Wed, Jun 17, 8:47 AM (8 m, 42 s)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
939807
Default Alt Text
PasswordResetTest.php (9 KB)

Event Timeline