Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,9 @@ The format is based on Keep a Changelog.
### Added
- Added `Response::back()` and the `back()` helper, which redirect to the referrer and fall back to `base_url()` when the request has none, or when the referrer is not on the application origin (same scheme, host and port), which is compared with `base_url()`: behind a proxy that terminates TLS, or where the `Host` header is not pinned, set `app.base_url`. They take the old input to keep for the next request, read with `old()` as after `redirectWith()`, and an optional status code (`back($data, $code)`) (#540)

### Changed
- The `DemoWeb` and `Toolkit` module templates redirect back with `back()` instead of `redirect(get_referrer() ?? base_url())` and `redirectWith(get_referrer() ?? base_url(), $data)`, so generated code gets the same-origin check. Modules generated before keep their code (#541)

## [3.1.0] - 2026-10-24

### Added
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ class CommentController extends BaseController
$this->commentService->addComment($commentDto);

session()->setFlash('success', t('common.comment_added'));
return redirect(get_referrer() ?? base_url());
return back();
}

/**
Expand All @@ -48,7 +48,7 @@ class CommentController extends BaseController
$this->commentService->deleteComment($uuid);

session()->setFlash('success', t('common.comment_deleted'));
return redirect(get_referrer() ?? base_url());
return back();
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ class Comment extends BaseMiddleware
$data = $request->all();

session()->setFlash('error', $this->validator->getErrors());
return redirectWith(get_referrer() ?? base_url(), $data);
return back($data);
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,7 @@ class Editor extends BaseMiddleware
unset($data['image']);

session()->setFlash('error', $this->validator->getErrors());
return redirectWith(get_referrer() ?? base_url(), $data);
return back($data);
}
}

2 changes: 1 addition & 1 deletion src/Module/Templates/DemoWeb/src/Middlewares/Reset.php.tpl
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ class Reset extends BaseMiddleware
}

session()->setFlash('error', $message);
return redirect(get_referrer() ?? base_url());
return back();
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,7 @@ class DatabaseController extends BaseController

$this->databaseService->createTableRow($tableName, $newData);

return redirect(get_referrer() ?? base_url());
return back();
}

public function update(Request $request): Response
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ class CreateTable extends BaseMiddleware
protected function respondWithError(Request $request, $message): Response
{
session()->setFlash('error', $message);
return redirect(get_referrer() ?? base_url());
return back();
}

/**
Expand Down
73 changes: 73 additions & 0 deletions tests/Unit/Module/Templates/RedirectTemplatesTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
<?php

namespace Quantum\Tests\Unit\Module\Templates;

use RecursiveDirectoryIterator;
use RecursiveIteratorIterator;
use PHPUnit\Framework\TestCase;

class RedirectTemplatesTest extends TestCase
{
/**
* @dataProvider redirectTemplateProvider
*/
public function testTemplatesDoNotRepeatTheManualReferrerFallback(string $template): void
{
$files = $this->templateFiles($template);

$this->assertNotEmpty($files);

foreach ($files as $file) {
$this->assertDoesNotMatchRegularExpression(
'/get_referrer\(\)\s*\?\?\s*base_url\(\)/',
(string) file_get_contents($file),
$file
);
}
}

/**
* @dataProvider redirectTemplateProvider
*/
public function testTemplatesGoBackWithTheBackRedirect(string $template): void
{
$backRedirects = 0;

foreach ($this->templateFiles($template) as $file) {
$backRedirects += preg_match_all('/return back\(/', (string) file_get_contents($file));
}

$this->assertGreaterThan(0, $backRedirects);
}

/**
* @return array<string, array{0: string}>
*/
public function redirectTemplateProvider(): array
{
return [
'demo-web' => ['DemoWeb'],
'toolkit' => ['Toolkit'],
];
}

/**
* @return array<int, string>
*/
private function templateFiles(string $template): array
{
$files = [];

$iterator = new RecursiveIteratorIterator(
new RecursiveDirectoryIterator(dirname(__DIR__, 4) . '/src/Module/Templates/' . $template . '/src')
);

foreach ($iterator as $file) {
if ($file->isFile() && str_ends_with($file->getFilename(), '.php.tpl')) {
$files[] = $file->getPathname();
}
}

return $files;
}
}
Loading