Skip to content

Commit cdd164e

Browse files
committed
Slugs: Added test to cover history lookup permission usage
1 parent c908169 commit cdd164e

File tree

3 files changed

+54
-0
lines changed

3 files changed

+54
-0
lines changed

app/Entities/Models/SlugHistory.php

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44

55
use BookStack\App\Model;
66
use BookStack\Permissions\Models\JointPermission;
7+
use Illuminate\Database\Eloquent\Factories\HasFactory;
78
use Illuminate\Database\Eloquent\Relations\HasMany;
89

910
/**
@@ -15,6 +16,8 @@
1516
*/
1617
class SlugHistory extends Model
1718
{
19+
use HasFactory;
20+
1821
protected $table = 'slug_history';
1922

2023
public function jointPermissions(): HasMany
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
<?php
2+
3+
namespace Database\Factories\Entities\Models;
4+
5+
use BookStack\Entities\Models\Book;
6+
use Illuminate\Database\Eloquent\Factories\Factory;
7+
8+
/**
9+
* @extends \Illuminate\Database\Eloquent\Factories\Factory<\BookStack\Entities\Models\SlugHistory>
10+
*/
11+
class SlugHistoryFactory extends Factory
12+
{
13+
protected $model = \BookStack\Entities\Models\SlugHistory::class;
14+
15+
/**
16+
* Define the model's default state.
17+
*
18+
* @return array<string, mixed>
19+
*/
20+
public function definition(): array
21+
{
22+
return [
23+
'sluggable_id' => Book::factory(),
24+
'sluggable_type' => 'book',
25+
'slug' => $this->faker->slug(),
26+
'parent_slug' => null,
27+
];
28+
}
29+
}

tests/Entity/SlugTest.php

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
namespace Tests\Entity;
44

5+
use BookStack\Entities\Models\SlugHistory;
56
use Tests\TestCase;
67

78
class SlugTest extends TestCase
@@ -111,6 +112,27 @@ public function test_old_book_slugs_in_chapter_urls_redirect_to_current_chapter_
111112
->assertRedirect("/books/super-test-book/chapter/{$chapter->slug}");
112113
}
113114

115+
public function test_slug_lookup_controlled_by_permissions()
116+
{
117+
$editor = $this->users->editor();
118+
$pageA = $this->entities->page();
119+
$pageB = $this->entities->page();
120+
121+
SlugHistory::factory()->create(['sluggable_id' => $pageA->id, 'sluggable_type' => 'page', 'slug' => 'monkey', 'parent_slug' => 'animals', 'created_at' => now()]);
122+
SlugHistory::factory()->create(['sluggable_id' => $pageB->id, 'sluggable_type' => 'page', 'slug' => 'monkey', 'parent_slug' => 'animals', 'created_at' => now()->subDay()]);
123+
124+
// Defaults to latest where visible
125+
$this->actingAs($editor)->get("/books/animals/page/monkey")->assertRedirect($pageA->getUrl());
126+
127+
$this->permissions->disableEntityInheritedPermissions($pageA);
128+
129+
// Falls back to other entry where the latest is not visible
130+
$this->actingAs($editor)->get("/books/animals/page/monkey")->assertRedirect($pageB->getUrl());
131+
132+
// Original still accessible where permissions allow
133+
$this->asAdmin()->get("/books/animals/page/monkey")->assertRedirect($pageA->getUrl());
134+
}
135+
114136
public function test_slugs_recorded_in_history_on_page_update()
115137
{
116138
$page = $this->entities->page();

0 commit comments

Comments
 (0)