]> BookStack Code Mirror - bookstack/commitdiff
Merge branch 'v0.24-dev'
authorDan Brown <redacted>
Sun, 4 Nov 2018 15:36:40 +0000 (15:36 +0000)
committerDan Brown <redacted>
Sun, 4 Nov 2018 15:36:40 +0000 (15:36 +0000)
118 files changed:
app/Actions/Activity.php [moved from app/Activity.php with 93% similarity]
app/Actions/ActivityService.php [moved from app/Services/ActivityService.php with 96% similarity]
app/Actions/Comment.php [moved from app/Comment.php with 94% similarity]
app/Actions/CommentRepo.php [moved from app/Repos/CommentRepo.php with 77% similarity]
app/Actions/Tag.php [moved from app/Tag.php with 85% similarity]
app/Actions/TagRepo.php [moved from app/Repos/TagRepo.php with 91% similarity]
app/Actions/View.php [moved from app/View.php with 82% similarity]
app/Actions/ViewService.php [moved from app/Services/ViewService.php with 85% similarity]
app/Auth/Access/EmailConfirmationService.php [moved from app/Services/EmailConfirmationService.php with 93% similarity]
app/Auth/Access/Ldap.php [moved from app/Services/Ldap.php with 98% similarity]
app/Auth/Access/LdapService.php [moved from app/Services/LdapService.php with 97% similarity]
app/Auth/Access/SocialAuthService.php [moved from app/Services/SocialAuthService.php with 98% similarity]
app/Auth/Permissions/EntityPermission.php [moved from app/EntityPermission.php with 84% similarity]
app/Auth/Permissions/JointPermission.php [moved from app/JointPermission.php with 80% similarity]
app/Auth/Permissions/PermissionService.php [moved from app/Services/PermissionService.php with 91% similarity]
app/Auth/Permissions/PermissionsRepo.php [moved from app/Repos/PermissionsRepo.php with 95% similarity]
app/Auth/Permissions/RolePermission.php [moved from app/RolePermission.php with 83% similarity]
app/Auth/Role.php [moved from app/Role.php with 79% similarity]
app/Auth/SocialAccount.php [moved from app/SocialAccount.php with 78% similarity]
app/Auth/User.php [moved from app/User.php with 98% similarity]
app/Auth/UserRepo.php [moved from app/Repos/UserRepo.php with 91% similarity]
app/Console/Commands/CleanupImages.php
app/Console/Commands/ClearActivity.php
app/Console/Commands/ClearRevisions.php
app/Console/Commands/CreateAdmin.php
app/Console/Commands/DeleteUsers.php
app/Console/Commands/RegeneratePermissions.php
app/Console/Commands/RegenerateSearch.php
app/Entities/Book.php [moved from app/Book.php with 92% similarity]
app/Entities/Bookshelf.php [moved from app/Bookshelf.php with 91% similarity]
app/Entities/Chapter.php [moved from app/Chapter.php with 90% similarity]
app/Entities/Entity.php [moved from app/Entity.php with 82% similarity]
app/Entities/EntityProvider.php [new file with mode: 0644]
app/Entities/ExportService.php [moved from app/Services/ExportService.php with 94% similarity]
app/Entities/Page.php [moved from app/Page.php with 92% similarity]
app/Entities/PageRevision.php [moved from app/PageRevision.php with 94% similarity]
app/Entities/Repos/EntityRepo.php [moved from app/Repos/EntityRepo.php with 53% similarity]
app/Entities/Repos/PageRepo.php [new file with mode: 0644]
app/Entities/SearchService.php [moved from app/Services/SearchService.php with 81% similarity]
app/Entities/SearchTerm.php [moved from app/SearchTerm.php with 85% similarity]
app/Exceptions/Handler.php
app/Facades/Activity.php [moved from app/Services/Facades/Activity.php with 85% similarity]
app/Facades/Images.php [moved from app/Services/Facades/Images.php with 85% similarity]
app/Facades/Setting.php [moved from app/Services/Facades/Setting.php with 85% similarity]
app/Facades/Views.php [moved from app/Services/Facades/Views.php with 85% similarity]
app/Http/Controllers/AttachmentController.php
app/Http/Controllers/Auth/LoginController.php
app/Http/Controllers/Auth/RegisterController.php
app/Http/Controllers/BookController.php
app/Http/Controllers/BookshelfController.php
app/Http/Controllers/ChapterController.php
app/Http/Controllers/CommentController.php
app/Http/Controllers/Controller.php
app/Http/Controllers/HomeController.php
app/Http/Controllers/ImageController.php
app/Http/Controllers/PageController.php
app/Http/Controllers/PermissionController.php
app/Http/Controllers/SearchController.php
app/Http/Controllers/SettingController.php
app/Http/Controllers/TagController.php
app/Http/Controllers/UserController.php
app/Http/Middleware/TrustProxies.php
app/Notifications/ConfirmEmail.php
app/Notifications/ResetPassword.php
app/Ownable.php
app/Providers/AppServiceProvider.php
app/Providers/AuthServiceProvider.php
app/Providers/BroadcastServiceProvider.php
app/Providers/CustomFacadeProvider.php
app/Providers/EventServiceProvider.php
app/Providers/LdapUserProvider.php
app/Providers/RouteServiceProvider.php
app/Settings/Setting.php [moved from app/Setting.php with 68% similarity]
app/Settings/SettingService.php [moved from app/Services/SettingService.php with 97% similarity]
app/Uploads/Attachment.php [moved from app/Attachment.php with 84% similarity]
app/Uploads/AttachmentService.php [moved from app/Services/AttachmentService.php with 99% similarity]
app/Uploads/Image.php [moved from app/Image.php with 88% similarity]
app/Uploads/ImageRepo.php [moved from app/Repos/ImageRepo.php with 96% similarity]
app/Uploads/ImageService.php [moved from app/Services/ImageService.php with 99% similarity]
app/Uploads/UploadService.php [moved from app/Services/UploadService.php with 93% similarity]
app/helpers.php
config/app.php
config/auth.php
config/services.php
database/factories/ModelFactory.php
database/migrations/2015_12_07_195238_add_image_upload_types.php
database/migrations/2018_08_04_115700_create_bookshelves_table.php
database/seeds/DummyContentSeeder.php
database/seeds/LargeContentSeeder.php
resources/views/components/page-picker.blade.php
resources/views/errors/404.blade.php
resources/views/settings/index.blade.php
tests/ActivityTrackingTest.php
tests/AttachmentTest.php
tests/Auth/AuthTest.php
tests/Auth/LdapTest.php
tests/Auth/SocialAuthTest.php
tests/BrowserKitTest.php
tests/CommandsTest.php
tests/Entity/BookShelfTest.php
tests/Entity/CommentSettingTest.php
tests/Entity/CommentTest.php
tests/Entity/EntitySearchTest.php
tests/Entity/EntityTest.php
tests/Entity/ExportTest.php
tests/Entity/MarkdownTest.php
tests/Entity/PageContentTest.php
tests/Entity/PageDraftTest.php
tests/Entity/PageRevisionTest.php
tests/Entity/SortTest.php
tests/Entity/TagTest.php
tests/ImageTest.php
tests/Permissions/RestrictionsTest.php
tests/Permissions/RolesTest.php
tests/PublicActionTest.php
tests/SharedTestHelpers.php
tests/UserProfileTest.php
version

similarity index 93%
rename from app/Activity.php
rename to app/Actions/Activity.php
index c01da1f6c897c4cf34d3f4a7d7594a5eab0f191c..1ae1811e11461dbd94674c791b0c75143596d8b2 100644 (file)
@@ -1,6 +1,9 @@
 <?php
 
-namespace BookStack;
+namespace BookStack\Actions;
+
+use BookStack\Auth\User;
+use BookStack\Model;
 
 /**
  * @property string  key
similarity index 96%
rename from app/Services/ActivityService.php
rename to app/Actions/ActivityService.php
index 3fc7e7ee0bbf443354aa3079ecf46bdc759a9032..37cd0a6a4ca99a2a1f60f682929fefabe5bfb304 100644 (file)
@@ -1,7 +1,7 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Actions;
 
-use BookStack\Activity;
-use BookStack\Entity;
+use BookStack\Auth\Permissions\PermissionService;
+use BookStack\Entities\Entity;
 use Session;
 
 class ActivityService
@@ -12,7 +12,7 @@ class ActivityService
 
     /**
      * ActivityService constructor.
-     * @param Activity $activity
+     * @param \BookStack\Actions\Activity $activity
      * @param PermissionService $permissionService
      */
     public function __construct(Activity $activity, PermissionService $permissionService)
similarity index 94%
rename from app/Comment.php
rename to app/Actions/Comment.php
index 2800ab21ad3d07a3fca32e28f045eccfad71b787..f138ee4a1ffed5da7bb1ead3a581d9045901179f 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Actions;
+
+use BookStack\Ownable;
 
 class Comment extends Ownable
 {
similarity index 77%
rename from app/Repos/CommentRepo.php
rename to app/Actions/CommentRepo.php
index 7f89e7f8dfb3011eabbf60aca05c8fd5b5c3451d..5ff639e2eb7275aefb281ef7b6e5c029a4e4ae62 100644 (file)
@@ -1,7 +1,6 @@
-<?php namespace BookStack\Repos;
+<?php namespace BookStack\Actions;
 
-use BookStack\Comment;
-use BookStack\Entity;
+use BookStack\Entities\Entity;
 
 /**
  * Class CommentRepo
@@ -11,13 +10,13 @@ class CommentRepo
 {
 
     /**
-     * @var Comment $comment
+     * @var \BookStack\Actions\Comment $comment
      */
     protected $comment;
 
     /**
      * CommentRepo constructor.
-     * @param Comment $comment
+     * @param \BookStack\Actions\Comment $comment
      */
     public function __construct(Comment $comment)
     {
@@ -27,7 +26,7 @@ class CommentRepo
     /**
      * Get a comment by ID.
      * @param $id
-     * @return Comment|\Illuminate\Database\Eloquent\Model
+     * @return \BookStack\Actions\Comment|\Illuminate\Database\Eloquent\Model
      */
     public function getById($id)
     {
@@ -36,9 +35,9 @@ class CommentRepo
 
     /**
      * Create a new comment on an entity.
-     * @param Entity $entity
+     * @param \BookStack\Entities\Entity $entity
      * @param array $data
-     * @return Comment
+     * @return \BookStack\Actions\Comment
      */
     public function create(Entity $entity, $data = [])
     {
@@ -53,7 +52,7 @@ class CommentRepo
 
     /**
      * Update an existing comment.
-     * @param Comment $comment
+     * @param \BookStack\Actions\Comment $comment
      * @param array $input
      * @return mixed
      */
@@ -66,7 +65,7 @@ class CommentRepo
 
     /**
      * Delete a comment from the system.
-     * @param Comment $comment
+     * @param \BookStack\Actions\Comment $comment
      * @return mixed
      */
     public function delete($comment)
@@ -76,7 +75,7 @@ class CommentRepo
 
     /**
      * Get the next local ID relative to the linked entity.
-     * @param Entity $entity
+     * @param \BookStack\Entities\Entity $entity
      * @return int
      */
     protected function getNextLocalId(Entity $entity)
similarity index 85%
rename from app/Tag.php
rename to app/Actions/Tag.php
index 51f622c38f4d4b3245d1bd81e7ae3230943776df..38d0458e46425f53fd13c6421d745c8fe67b0101 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Actions;
+
+use BookStack\Model;
 
 /**
  * Class Attribute
similarity index 91%
rename from app/Repos/TagRepo.php
rename to app/Actions/TagRepo.php
index ab1805ab3a8b9d1ef329174a125a3d72892a3fcb..0cbfa4163bf9120226aafea71e678a4f13b920a8 100644 (file)
@@ -1,8 +1,7 @@
-<?php namespace BookStack\Repos;
+<?php namespace BookStack\Actions;
 
-use BookStack\Tag;
-use BookStack\Entity;
-use BookStack\Services\PermissionService;
+use BookStack\Auth\Permissions\PermissionService;
+use BookStack\Entities\Entity;
 
 /**
  * Class TagRepo
@@ -17,9 +16,9 @@ class TagRepo
 
     /**
      * TagRepo constructor.
-     * @param Tag $attr
-     * @param Entity $ent
-     * @param PermissionService $ps
+     * @param \BookStack\Actions\Tag $attr
+     * @param \BookStack\Entities\Entity $ent
+     * @param \BookStack\Auth\Permissions\PermissionService $ps
      */
     public function __construct(Tag $attr, Entity $ent, PermissionService $ps)
     {
@@ -107,7 +106,7 @@ class TagRepo
 
     /**
      * Save an array of tags to an entity
-     * @param Entity $entity
+     * @param \BookStack\Entities\Entity $entity
      * @param array $tags
      * @return array|\Illuminate\Database\Eloquent\Collection
      */
@@ -128,7 +127,7 @@ class TagRepo
     /**
      * Create a new Tag instance from user input.
      * @param $input
-     * @return Tag
+     * @return \BookStack\Actions\Tag
      */
     protected function newInstanceFromInput($input)
     {
similarity index 82%
rename from app/View.php
rename to app/Actions/View.php
index c02550c7caa8e9d68157656e26c2dc6cd2ecc100..e9841293b5c72a1d20f045b81e8f95a7a534a9e0 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Actions;
+
+use BookStack\Model;
 
 class View extends Model
 {
similarity index 85%
rename from app/Services/ViewService.php
rename to app/Actions/ViewService.php
index cd869018c2839fd7213b731bed259c58b3aabb61..d5f8002fc04fffe84ef7df57109bc83a4e474a63 100644 (file)
@@ -1,7 +1,7 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Actions;
 
-use BookStack\Entity;
-use BookStack\View;
+use BookStack\Auth\Permissions\PermissionService;
+use BookStack\Entities\Entity;
 
 class ViewService
 {
@@ -10,8 +10,8 @@ class ViewService
 
     /**
      * ViewService constructor.
-     * @param View $view
-     * @param PermissionService $permissionService
+     * @param \BookStack\Actions\View $view
+     * @param \BookStack\Auth\Permissions\PermissionService $permissionService
      */
     public function __construct(View $view, PermissionService $permissionService)
     {
@@ -50,12 +50,13 @@ class ViewService
      * Get the entities with the most views.
      * @param int $count
      * @param int $page
-     * @param bool|false|array $filterModel
+     * @param Entity|false|array $filterModel
      * @param string $action - used for permission checking
      * @return
      */
     public function getPopular($count = 10, $page = 0, $filterModel = false, $action = 'view')
     {
+        // TODO - Standardise input filter
         $skipCount = $count * $page;
         $query = $this->permissionService->filterRestrictedEntityRelations($this->view, 'views', 'viewable_id', 'viewable_type', $action)
             ->select('*', 'viewable_id', 'viewable_type', \DB::raw('SUM(views) as view_count'))
@@ -65,7 +66,7 @@ class ViewService
         if ($filterModel && is_array($filterModel)) {
             $query->whereIn('viewable_type', $filterModel);
         } else if ($filterModel) {
-            $query->where('viewable_type', '=', get_class($filterModel));
+            $query->where('viewable_type', '=', $filterModel->getMorphClass());
         }
 
         return $query->with('viewable')->skip($skipCount)->take($count)->get()->pluck('viewable');
@@ -89,7 +90,7 @@ class ViewService
             ->filterRestrictedEntityRelations($this->view, 'views', 'viewable_id', 'viewable_type');
 
         if ($filterModel) {
-            $query = $query->where('viewable_type', '=', get_class($filterModel));
+            $query = $query->where('viewable_type', '=', $filterModel->getMorphClass());
         }
         $query = $query->where('user_id', '=', $user->id);
 
similarity index 93%
rename from app/Services/EmailConfirmationService.php
rename to app/Auth/Access/EmailConfirmationService.php
index 9ee69ef1a4e3434335109f295f396c28241606a5..4df014116c5c3d1c393e6e4594923c0d65a5d519 100644 (file)
@@ -1,11 +1,11 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Auth\Access;
 
-use BookStack\Notifications\ConfirmEmail;
-use BookStack\Repos\UserRepo;
-use Carbon\Carbon;
+use BookStack\Auth\User;
+use BookStack\Auth\UserRepo;
 use BookStack\Exceptions\ConfirmationEmailException;
 use BookStack\Exceptions\UserRegistrationException;
-use BookStack\User;
+use BookStack\Notifications\ConfirmEmail;
+use Carbon\Carbon;
 use Illuminate\Database\Connection as Database;
 
 class EmailConfirmationService
@@ -16,7 +16,7 @@ class EmailConfirmationService
     /**
      * EmailConfirmationService constructor.
      * @param Database $db
-     * @param UserRepo $users
+     * @param \BookStack\Auth\UserRepo $users
      */
     public function __construct(Database $db, UserRepo $users)
     {
@@ -27,7 +27,7 @@ class EmailConfirmationService
     /**
      * Create new confirmation for a user,
      * Also removes any existing old ones.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @throws ConfirmationEmailException
      */
     public function sendConfirmation(User $user)
@@ -88,7 +88,7 @@ class EmailConfirmationService
 
     /**
      * Delete all email confirmations that belong to a user.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @return mixed
      */
     public function deleteConfirmationsByUser(User $user)
similarity index 98%
rename from app/Services/Ldap.php
rename to app/Auth/Access/Ldap.php
index 29270daf5620d169a096fda4516525923e3dde9d..468c376268d5ae3e884317e641ecf8e4166894b1 100644 (file)
@@ -1,4 +1,4 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Auth\Access;
 
 /**
  * Class Ldap
similarity index 97%
rename from app/Services/LdapService.php
rename to app/Auth/Access/LdapService.php
index 16cee9f7dea1c08e7a5c258a7a2a6812143bc2b0..d3a177f8e1dffbac095e4d504550b646182eb690 100644 (file)
@@ -1,9 +1,10 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Auth\Access;
 
+use BookStack\Auth\Access;
+use BookStack\Auth\Role;
+use BookStack\Auth\User;
+use BookStack\Auth\UserRepo;
 use BookStack\Exceptions\LdapException;
-use BookStack\Repos\UserRepo;
-use BookStack\Role;
-use BookStack\User;
 use Illuminate\Contracts\Auth\Authenticatable;
 use Illuminate\Database\Eloquent\Builder;
 
@@ -24,9 +25,9 @@ class LdapService
     /**
      * LdapService constructor.
      * @param Ldap $ldap
-     * @param UserRepo $userRepo
+     * @param \BookStack\Auth\UserRepo $userRepo
      */
-    public function __construct(Ldap $ldap, UserRepo $userRepo)
+    public function __construct(Access\Ldap $ldap, UserRepo $userRepo)
     {
         $this->ldap = $ldap;
         $this->config = config('services.ldap');
@@ -298,7 +299,7 @@ class LdapService
 
     /**
      * Sync the LDAP groups to the user roles for the current user
-     * @param \BookStack\User $user
+     * @param \BookStack\Auth\User $user
      * @param string $username
      * @throws LdapException
      */
@@ -347,7 +348,7 @@ class LdapService
     /**
      * Check a role against an array of group names to see if it matches.
      * Checked against role 'external_auth_id' if set otherwise the name of the role.
-     * @param Role $role
+     * @param \BookStack\Auth\Role $role
      * @param array $groupNames
      * @return bool
      */
similarity index 98%
rename from app/Services/SocialAuthService.php
rename to app/Auth/Access/SocialAuthService.php
index 9017dfebe7c4f1f0f39364ee5ec3e0c6e6d10675..87db1d5c6d4f1bfeadfb28c173da36e777b1b6a9 100644 (file)
@@ -1,11 +1,11 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Auth\Access;
 
-use BookStack\Exceptions\SocialSignInAccountNotUsed;
-use Laravel\Socialite\Contracts\Factory as Socialite;
+use BookStack\Auth\SocialAccount;
+use BookStack\Auth\UserRepo;
 use BookStack\Exceptions\SocialDriverNotConfigured;
+use BookStack\Exceptions\SocialSignInAccountNotUsed;
 use BookStack\Exceptions\UserRegistrationException;
-use BookStack\Repos\UserRepo;
-use BookStack\SocialAccount;
+use Laravel\Socialite\Contracts\Factory as Socialite;
 use Laravel\Socialite\Contracts\User as SocialUser;
 
 class SocialAuthService
@@ -19,7 +19,7 @@ class SocialAuthService
 
     /**
      * SocialAuthService constructor.
-     * @param UserRepo      $userRepo
+     * @param \BookStack\Auth\UserRepo      $userRepo
      * @param Socialite     $socialite
      * @param SocialAccount $socialAccount
      */
similarity index 84%
rename from app/EntityPermission.php
rename to app/Auth/Permissions/EntityPermission.php
index 0f49e07f54fe69d228243d5048d44d5f019639a0..ef61e03ceb24d27edb289166d1ec744a95034f67 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Auth\Permissions;
+
+use BookStack\Model;
 
 class EntityPermission extends Model
 {
similarity index 80%
rename from app/JointPermission.php
rename to app/Auth/Permissions/JointPermission.php
index 6d0b0212e0284cb34bc702b7d6598cb16ea4134a..c48549b8f00c5cac2e9996fa9c4c4e0d483af365 100644 (file)
@@ -1,4 +1,8 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Auth\Permissions;
+
+use BookStack\Auth\Role;
+use BookStack\Entities\Entity;
+use BookStack\Model;
 
 class JointPermission extends Model
 {
similarity index 91%
rename from app/Services/PermissionService.php
rename to app/Auth/Permissions/PermissionService.php
index 045824517e3542b21501ad41d465fcb0800c91a3..d0e6ccceab56640ddbee6b48a5b99b4cf14f815f 100644 (file)
@@ -1,15 +1,14 @@
-<?php namespace BookStack\Services;
-
-use BookStack\Book;
-use BookStack\Bookshelf;
-use BookStack\Chapter;
-use BookStack\Entity;
-use BookStack\EntityPermission;
-use BookStack\JointPermission;
+<?php namespace BookStack\Auth\Permissions;
+
+use BookStack\Auth\Permissions;
+use BookStack\Auth\Role;
+use BookStack\Entities\Book;
+use BookStack\Entities\Bookshelf;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Entity;
+use BookStack\Entities\EntityProvider;
+use BookStack\Entities\Page;
 use BookStack\Ownable;
-use BookStack\Page;
-use BookStack\Role;
-use BookStack\User;
 use Illuminate\Database\Connection;
 use Illuminate\Database\Eloquent\Builder;
 use Illuminate\Database\Query\Builder as QueryBuilder;
@@ -23,17 +22,31 @@ class PermissionService
     protected $userRoles = false;
     protected $currentUserModel = false;
 
-    public $book;
-    public $chapter;
-    public $page;
-    public $bookshelf;
-
+    /**
+     * @var Connection
+     */
     protected $db;
 
+    /**
+     * @var JointPermission
+     */
     protected $jointPermission;
+
+    /**
+     * @var Role
+     */
     protected $role;
+
+    /**
+     * @var EntityPermission
+     */
     protected $entityPermission;
 
+    /**
+     * @var EntityProvider
+     */
+    protected $entityProvider;
+
     protected $entityCache;
 
     /**
@@ -42,29 +55,20 @@ class PermissionService
      * @param EntityPermission $entityPermission
      * @param Role $role
      * @param Connection $db
-     * @param Bookshelf $bookshelf
-     * @param Book $book
-     * @param Chapter $chapter
-     * @param Page $page
+     * @param EntityProvider $entityProvider
      */
     public function __construct(
         JointPermission $jointPermission,
-        EntityPermission $entityPermission,
+        Permissions\EntityPermission $entityPermission,
         Role $role,
         Connection $db,
-        Bookshelf $bookshelf,
-        Book $book,
-        Chapter $chapter,
-        Page $page
+        EntityProvider $entityProvider
     ) {
         $this->db = $db;
         $this->jointPermission = $jointPermission;
         $this->entityPermission = $entityPermission;
         $this->role = $role;
-        $this->bookshelf = $bookshelf;
-        $this->book = $book;
-        $this->chapter = $chapter;
-        $this->page = $page;
+        $this->entityProvider = $entityProvider;
     }
 
     /**
@@ -78,7 +82,7 @@ class PermissionService
 
     /**
      * Prepare the local entity cache and ensure it's empty
-     * @param Entity[] $entities
+     * @param \BookStack\Entities\Entity[] $entities
      */
     protected function readyEntityCache($entities = [])
     {
@@ -104,7 +108,7 @@ class PermissionService
             return $this->entityCache['book']->get($bookId);
         }
 
-        $book = $this->book->find($bookId);
+        $book = $this->entityProvider->book->find($bookId);
         if ($book === null) {
             $book = false;
         }
@@ -115,7 +119,7 @@ class PermissionService
     /**
      * Get a chapter via ID, Checks local cache
      * @param $chapterId
-     * @return Book
+     * @return \BookStack\Entities\Book
      */
     protected function getChapter($chapterId)
     {
@@ -123,7 +127,7 @@ class PermissionService
             return $this->entityCache['chapter']->get($chapterId);
         }
 
-        $chapter = $this->chapter->find($chapterId);
+        $chapter = $this->entityProvider->chapter->find($chapterId);
         if ($chapter === null) {
             $chapter = false;
         }
@@ -172,7 +176,7 @@ class PermissionService
         });
 
         // Chunk through all bookshelves
-        $this->bookshelf->newQuery()->select(['id', 'restricted', 'created_by'])
+        $this->entityProvider->bookshelf->newQuery()->select(['id', 'restricted', 'created_by'])
             ->chunk(50, function ($shelves) use ($roles) {
                 $this->buildJointPermissionsForShelves($shelves, $roles);
             });
@@ -184,7 +188,8 @@ class PermissionService
      */
     protected function bookFetchQuery()
     {
-        return $this->book->newQuery()->select(['id', 'restricted', 'created_by'])->with(['chapters' => function ($query) {
+        return $this->entityProvider->book->newQuery()
+            ->select(['id', 'restricted', 'created_by'])->with(['chapters' => function ($query) {
             $query->select(['id', 'restricted', 'created_by', 'book_id']);
         }, 'pages'  => function ($query) {
             $query->select(['id', 'restricted', 'created_by', 'book_id', 'chapter_id']);
@@ -234,7 +239,7 @@ class PermissionService
 
     /**
      * Rebuild the entity jointPermissions for a particular entity.
-     * @param Entity $entity
+     * @param \BookStack\Entities\Entity $entity
      * @throws \Throwable
      */
     public function buildJointPermissionsForEntity(Entity $entity)
@@ -290,7 +295,7 @@ class PermissionService
         });
 
         // Chunk through all bookshelves
-        $this->bookshelf->newQuery()->select(['id', 'restricted', 'created_by'])
+        $this->entityProvider->bookshelf->newQuery()->select(['id', 'restricted', 'created_by'])
             ->chunk(50, function ($shelves) use ($roles) {
                 $this->buildJointPermissionsForShelves($shelves, $roles);
             });
@@ -329,7 +334,7 @@ class PermissionService
 
     /**
      * Delete all of the entity jointPermissions for a list of entities.
-     * @param Entity[] $entities
+     * @param \BookStack\Entities\Entity[] $entities
      * @throws \Throwable
      */
     protected function deleteManyJointPermissionsForEntities($entities)
@@ -410,7 +415,7 @@ class PermissionService
 
     /**
      * Get the actions related to an entity.
-     * @param Entity $entity
+     * @param \BookStack\Entities\Entity $entity
      * @return array
      */
     protected function getActions(Entity $entity)
@@ -496,7 +501,7 @@ class PermissionService
     /**
      * Create an array of data with the information of an entity jointPermissions.
      * Used to build data for bulk insertion.
-     * @param Entity $entity
+     * @param \BookStack\Entities\Entity $entity
      * @param Role $role
      * @param $action
      * @param $permissionAll
@@ -554,7 +559,7 @@ class PermissionService
     /**
      * Check if an entity has restrictions set on itself or its
      * parent tree.
-     * @param Entity $entity
+     * @param \BookStack\Entities\Entity $entity
      * @param $action
      * @return bool|mixed
      */
@@ -604,7 +609,9 @@ class PermissionService
      */
     public function bookChildrenQuery($book_id, $filterDrafts = false, $fetchPageContent = false)
     {
-        $pageSelect = $this->db->table('pages')->selectRaw($this->page->entityRawQuery($fetchPageContent))->where('book_id', '=', $book_id)->where(function ($query) use ($filterDrafts) {
+        $entities = $this->entityProvider;
+        $pageSelect = $this->db->table('pages')->selectRaw($entities->page->entityRawQuery($fetchPageContent))
+            ->where('book_id', '=', $book_id)->where(function ($query) use ($filterDrafts) {
             $query->where('draft', '=', 0);
             if (!$filterDrafts) {
                 $query->orWhere(function ($query) {
@@ -612,7 +619,7 @@ class PermissionService
                 });
             }
         });
-        $chapterSelect = $this->db->table('chapters')->selectRaw($this->chapter->entityRawQuery())->where('book_id', '=', $book_id);
+        $chapterSelect = $this->db->table('chapters')->selectRaw($entities->chapter->entityRawQuery())->where('book_id', '=', $book_id);
         $query = $this->db->query()->select('*')->from($this->db->raw("({$pageSelect->toSql()} UNION {$chapterSelect->toSql()}) AS U"))
             ->mergeBindings($pageSelect)->mergeBindings($chapterSelect);
 
@@ -635,7 +642,7 @@ class PermissionService
     /**
      * Add restrictions for a generic entity
      * @param string $entityType
-     * @param Builder|Entity $query
+     * @param Builder|\BookStack\Entities\Entity $query
      * @param string $action
      * @return Builder
      */
@@ -703,12 +710,13 @@ class PermissionService
         $this->currentAction = 'view';
         $tableDetails = ['tableName' => $tableName, 'entityIdColumn' => $entityIdColumn];
 
-        $q = $query->where(function ($query) use ($tableDetails) {
-            $query->where(function ($query) use (&$tableDetails) {
-                $query->whereExists(function ($permissionQuery) use (&$tableDetails) {
+        $pageMorphClass = $this->entityProvider->page->getMorphClass();
+        $q = $query->where(function ($query) use ($tableDetails, $pageMorphClass) {
+            $query->where(function ($query) use (&$tableDetails, $pageMorphClass) {
+                $query->whereExists(function ($permissionQuery) use (&$tableDetails, $pageMorphClass) {
                     $permissionQuery->select('id')->from('joint_permissions')
                         ->whereRaw('joint_permissions.entity_id=' . $tableDetails['tableName'] . '.' . $tableDetails['entityIdColumn'])
-                        ->where('entity_type', '=', 'Bookstack\\Page')
+                        ->where('entity_type', '=', $pageMorphClass)
                         ->where('action', '=', $this->currentAction)
                         ->whereIn('role_id', $this->getRoles())
                         ->where(function ($query) {
@@ -726,7 +734,7 @@ class PermissionService
 
     /**
      * Get the current user
-     * @return User
+     * @return \BookStack\Auth\User
      */
     private function currentUser()
     {
similarity index 95%
rename from app/Repos/PermissionsRepo.php
rename to app/Auth/Permissions/PermissionsRepo.php
index 68c9270bec9ab54af7194ba9f9b58cb532f974a5..18d5089bec2f89dcaea0d9258a448d9463041b1b 100644 (file)
@@ -1,10 +1,8 @@
-<?php namespace BookStack\Repos;
+<?php namespace BookStack\Auth\Permissions;
 
+use BookStack\Auth\Permissions;
+use BookStack\Auth\Role;
 use BookStack\Exceptions\PermissionsException;
-use BookStack\RolePermission;
-use BookStack\Role;
-use BookStack\Services\PermissionService;
-use Setting;
 
 class PermissionsRepo
 {
@@ -19,9 +17,9 @@ class PermissionsRepo
      * PermissionsRepo constructor.
      * @param RolePermission $permission
      * @param Role $role
-     * @param PermissionService $permissionService
+     * @param \BookStack\Auth\Permissions\PermissionService $permissionService
      */
-    public function __construct(RolePermission $permission, Role $role, PermissionService $permissionService)
+    public function __construct(RolePermission $permission, Role $role, Permissions\PermissionService $permissionService)
     {
         $this->permission = $permission;
         $this->role = $role;
similarity index 83%
rename from app/RolePermission.php
rename to app/Auth/Permissions/RolePermission.php
index 366c16749f13d79801f040bc006e7084bff3f71d..8b07b3073bf9add0eb1f4a216844c69e05235832 100644 (file)
@@ -1,4 +1,7 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Auth\Permissions;
+
+use BookStack\Auth\Role;
+use BookStack\Model;
 
 class RolePermission extends Model
 {
similarity index 79%
rename from app/Role.php
rename to app/Auth/Role.php
index 54a5bb18016afc69a4d01600372a68add9713f67..c8bb47e4582076ef90769a03a7f72b8e1e605ca4 100644 (file)
@@ -1,4 +1,7 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Auth;
+
+use BookStack\Auth\Permissions\JointPermission;
+use BookStack\Model;
 
 class Role extends Model
 {
@@ -27,7 +30,7 @@ class Role extends Model
      */
     public function permissions()
     {
-        return $this->belongsToMany(RolePermission::class, 'permission_role', 'role_id', 'permission_id');
+        return $this->belongsToMany(Permissions\RolePermission::class, 'permission_role', 'role_id', 'permission_id');
     }
 
     /**
@@ -48,18 +51,18 @@ class Role extends Model
 
     /**
      * Add a permission to this role.
-     * @param RolePermission $permission
+     * @param \BookStack\Auth\Permissions\RolePermission $permission
      */
-    public function attachPermission(RolePermission $permission)
+    public function attachPermission(Permissions\RolePermission $permission)
     {
         $this->permissions()->attach($permission->id);
     }
 
     /**
      * Detach a single permission from this role.
-     * @param RolePermission $permission
+     * @param \BookStack\Auth\Permissions\RolePermission $permission
      */
-    public function detachPermission(RolePermission $permission)
+    public function detachPermission(Permissions\RolePermission $permission)
     {
         $this->permissions()->detach($permission->id);
     }
similarity index 78%
rename from app/SocialAccount.php
rename to app/Auth/SocialAccount.php
index fdba6a04fda2bc90ef439b68384457cf585d4b8b..804dbe6292973c16b7dc068ad00dd353c33fa48d 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Auth;
+
+use BookStack\Model;
 
 class SocialAccount extends Model
 {
similarity index 98%
rename from app/User.php
rename to app/Auth/User.php
index d1e9b38a775e5c2e292bd56a5049fabae9823706..05e77e13d0e4a84e45f0f1f0fd90bdd22bb8e683 100644 (file)
@@ -1,6 +1,8 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Auth;
 
+use BookStack\Model;
 use BookStack\Notifications\ResetPassword;
+use BookStack\Uploads\Image;
 use Illuminate\Auth\Authenticatable;
 use Illuminate\Auth\Passwords\CanResetPassword;
 use Illuminate\Contracts\Auth\Authenticatable as AuthenticatableContract;
similarity index 91%
rename from app/Repos/UserRepo.php
rename to app/Auth/UserRepo.php
index 5143366fe12ee5c41cabcd35cc59a43c5e060940..7c88badb843297a37901a70883179c9a20757447 100644 (file)
@@ -1,10 +1,9 @@
-<?php namespace BookStack\Repos;
+<?php namespace BookStack\Auth;
 
 use Activity;
+use BookStack\Entities\Repos\EntityRepo;
 use BookStack\Exceptions\NotFoundException;
-use BookStack\Image;
-use BookStack\Role;
-use BookStack\User;
+use BookStack\Uploads\Image;
 use Exception;
 use Images;
 
@@ -80,7 +79,7 @@ class UserRepo
      * Creates a new user and attaches a role to them.
      * @param array $data
      * @param boolean $verifyEmail
-     * @return User
+     * @return \BookStack\Auth\User
      */
     public function registerNew(array $data, $verifyEmail = false)
     {
@@ -122,7 +121,7 @@ class UserRepo
 
     /**
      * Checks if the give user is the only admin.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @return bool
      */
     public function isOnlyAdmin(User $user)
@@ -142,7 +141,7 @@ class UserRepo
      * Create a new basic instance of user.
      * @param array $data
      * @param boolean $verifyEmail
-     * @return User
+     * @return \BookStack\Auth\User
      */
     public function create(array $data, $verifyEmail = false)
     {
@@ -157,7 +156,7 @@ class UserRepo
 
     /**
      * Remove the given user from storage, Delete all related content.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @throws Exception
      */
     public function destroy(User $user)
@@ -174,7 +173,7 @@ class UserRepo
 
     /**
      * Get the latest activity for a user.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @param int $count
      * @param int $page
      * @return array
@@ -186,7 +185,7 @@ class UserRepo
 
     /**
      * Get the recently created content for this given user.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @param int $count
      * @return mixed
      */
@@ -207,15 +206,15 @@ class UserRepo
 
     /**
      * Get asset created counts for the give user.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @return array
      */
     public function getAssetCounts(User $user)
     {
         return [
-            'pages'    => $this->entityRepo->page->where('created_by', '=', $user->id)->count(),
-            'chapters' => $this->entityRepo->chapter->where('created_by', '=', $user->id)->count(),
-            'books'    => $this->entityRepo->book->where('created_by', '=', $user->id)->count(),
+            'pages'    => $this->entityRepo->getUserTotalCreated('page', $user),
+            'chapters' => $this->entityRepo->getUserTotalCreated('chapter', $user),
+            'books'    => $this->entityRepo->getUserTotalCreated('book', $user),
         ];
     }
 
index 8e1539702bd23e29b67b63c9bbd4ca01a2c38287..f2e2d9fbd4465a3544e96e54c4649fb54fe81e05 100644 (file)
@@ -2,7 +2,7 @@
 
 namespace BookStack\Console\Commands;
 
-use BookStack\Services\ImageService;
+use BookStack\Uploads\ImageService;
 use Illuminate\Console\Command;
 use Symfony\Component\Console\Output\OutputInterface;
 
@@ -30,7 +30,7 @@ class CleanupImages extends Command
 
     /**
      * Create a new command instance.
-     * @param ImageService $imageService
+     * @param \BookStack\Uploads\ImageService $imageService
      */
     public function __construct(ImageService $imageService)
     {
index 66babd9a94bfe9c4631d5dbeaedbb9e559ff02ae..932ba7ddd19538983bab0a142692985e85ce4f56 100644 (file)
@@ -2,7 +2,7 @@
 
 namespace BookStack\Console\Commands;
 
-use BookStack\Activity;
+use BookStack\Actions\Activity;
 use Illuminate\Console\Command;
 
 class ClearActivity extends Command
index f0c8a5e85b96ea49afadea95166bcfac07bde9e5..15f1fcc0a7138f057d3894c727cb62774a0ef37b 100644 (file)
@@ -2,7 +2,7 @@
 
 namespace BookStack\Console\Commands;
 
-use BookStack\PageRevision;
+use BookStack\Entities\PageRevision;
 use Illuminate\Console\Command;
 
 class ClearRevisions extends Command
index c7a9969e80525dbc6251236aba50e8c4bec041b3..6bfc544698fdc2dba39ddae88f18ac4a154fc0c1 100644 (file)
@@ -2,7 +2,7 @@
 
 namespace BookStack\Console\Commands;
 
-use BookStack\Repos\UserRepo;
+use BookStack\Auth\UserRepo;
 use Illuminate\Console\Command;
 
 class CreateAdmin extends Command
index 6dba83e1379a38198e34dce14ccf4734647ab235..68c5bb738178f6b6fdfdbfeb0dec2d64dc5371f7 100644 (file)
@@ -2,8 +2,8 @@
 
 namespace BookStack\Console\Commands;
 
-use BookStack\User;
-use BookStack\Repos\UserRepo;
+use BookStack\Auth\User;
+use BookStack\Auth\UserRepo;
 use Illuminate\Console\Command;
 
 class DeleteUsers extends Command
index 9cd577a17864b5c3c759f24ae2a07e7fdb6f4f44..430b8fcb05fdad572a4f587548d271a230ea8394 100644 (file)
@@ -2,7 +2,7 @@
 
 namespace BookStack\Console\Commands;
 
-use BookStack\Services\PermissionService;
+use BookStack\Auth\Permissions\PermissionService;
 use Illuminate\Console\Command;
 
 class RegeneratePermissions extends Command
@@ -31,7 +31,7 @@ class RegeneratePermissions extends Command
     /**
      * Create a new command instance.
      *
-     * @param PermissionService $permissionService
+     * @param \BookStack\Auth\\BookStack\Auth\Permissions\PermissionService $permissionService
      */
     public function __construct(PermissionService $permissionService)
     {
index 1a0005544bb5fa8a789dc21b6ab6c628fccafa9f..d27d73edc01dcbf55443f9bbf8f916539d0c5295 100644 (file)
@@ -2,7 +2,7 @@
 
 namespace BookStack\Console\Commands;
 
-use BookStack\Services\SearchService;
+use BookStack\Entities\SearchService;
 use Illuminate\Console\Command;
 
 class RegenerateSearch extends Command
@@ -26,7 +26,7 @@ class RegenerateSearch extends Command
     /**
      * Create a new command instance.
      *
-     * @param SearchService $searchService
+     * @param \BookStack\Entities\SearchService $searchService
      */
     public function __construct(SearchService $searchService)
     {
similarity index 92%
rename from app/Book.php
rename to app/Entities/Book.php
index 4e944ce1088fb1254831f6537df58d2edd2f4544..5ab5142c9f097d5c654f5d99e08b8d2efad2d113 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Entities;
+
+use BookStack\Uploads\Image;
 
 class Book extends Entity
 {
@@ -6,6 +8,15 @@ class Book extends Entity
 
     protected $fillable = ['name', 'description', 'image_id'];
 
+    /**
+     * Get the morph class for this model.
+     * @return string
+     */
+    public function getMorphClass()
+    {
+        return 'BookStack\\Book';
+    }
+
     /**
      * Get the url for this book.
      * @param string|bool $path
similarity index 91%
rename from app/Bookshelf.php
rename to app/Entities/Bookshelf.php
index 9468575c3b9473e557f46ba0e278ba5d61b1acdb..c37e36b59f8aefb125c827b3fbdff227708c9314 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Entities;
+
+use BookStack\Uploads\Image;
 
 class Bookshelf extends Entity
 {
@@ -8,6 +10,15 @@ class Bookshelf extends Entity
 
     protected $fillable = ['name', 'description', 'image_id'];
 
+    /**
+     * Get the morph class for this model.
+     * @return string
+     */
+    public function getMorphClass()
+    {
+        return 'BookStack\\Bookshelf';
+    }
+
     /**
      * Get the books in this shelf.
      * Should not be used directly since does not take into account permissions.
similarity index 90%
rename from app/Chapter.php
rename to app/Entities/Chapter.php
index 88b4c134cf9d7b0a99d54058a7f21526acf4f956..079105ba92a7a5c0d18bdc4ac31085610c8d4ae2 100644 (file)
@@ -1,4 +1,4 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Entities;
 
 class Chapter extends Entity
 {
@@ -6,6 +6,15 @@ class Chapter extends Entity
 
     protected $fillable = ['name', 'description', 'priority', 'book_id'];
 
+    /**
+     * Get the morph class for this model.
+     * @return string
+     */
+    public function getMorphClass()
+    {
+        return 'BookStack\\Chapter';
+    }
+
     /**
      * Get the book this chapter is within.
      * @return \Illuminate\Database\Eloquent\Relations\BelongsTo
similarity index 82%
rename from app/Entity.php
rename to app/Entities/Entity.php
index 252a3e07ab5a04f87acdc377a550aebdd92b1164..21d172e708ad48be7a969a5977c3c4897a9cee33 100644 (file)
@@ -1,7 +1,31 @@
-<?php namespace BookStack;
-
+<?php namespace BookStack\Entities;
+
+use BookStack\Actions\Activity;
+use BookStack\Actions\Comment;
+use BookStack\Actions\Tag;
+use BookStack\Actions\View;
+use BookStack\Auth\Permissions\EntityPermission;
+use BookStack\Auth\Permissions\JointPermission;
+use BookStack\Ownable;
+use Carbon\Carbon;
 use Illuminate\Database\Eloquent\Relations\MorphMany;
 
+/**
+ * Class Entity
+ * The base class for book-like items such as pages, chapters & books.
+ * This is not a database model in itself but extended.
+ *
+ * @property integer $id
+ * @property string $name
+ * @property string $slug
+ * @property Carbon $created_at
+ * @property Carbon $updated_at
+ * @property int $created_by
+ * @property int $updated_by
+ * @property boolean $restricted
+ *
+ * @package BookStack\Entities
+ */
 class Entity extends Ownable
 {
 
@@ -15,6 +39,17 @@ class Entity extends Ownable
      */
     public $searchFactor = 1.0;
 
+    /**
+     * Get the morph class for this model.
+     * Set here since, due to folder changes, the namespace used
+     * in the database no longer matches the class namespace.
+     * @return string
+     */
+    public function getMorphClass()
+    {
+        return 'BookStack\\Entity';
+    }
+
     /**
      * Compares this entity to another given entity.
      * Matches by comparing class and id.
@@ -158,7 +193,7 @@ class Entity extends Ownable
             return null;
         }
 
-        return app('BookStack\\' . $className);
+        return app('BookStack\\Entities\\' . $className);
     }
 
     /**
diff --git a/app/Entities/EntityProvider.php b/app/Entities/EntityProvider.php
new file mode 100644 (file)
index 0000000..46a883e
--- /dev/null
@@ -0,0 +1,89 @@
+<?php namespace BookStack\Entities;
+
+/**
+ * Class EntityProvider
+ *
+ * Provides access to the core entity models.
+ * Wrapped up in this provider since they are often used together
+ * so this is a neater alternative to injecting all in individually.
+ *
+ * @package BookStack\Entities
+ */
+class EntityProvider
+{
+
+    /**
+     * @var Bookshelf
+     */
+    public $bookshelf;
+
+    /**
+     * @var Book
+     */
+    public $book;
+
+    /**
+     * @var Chapter
+     */
+    public $chapter;
+
+    /**
+     * @var Page
+     */
+    public $page;
+
+    /**
+     * @var PageRevision
+     */
+    public $pageRevision;
+
+    /**
+     * EntityProvider constructor.
+     * @param Bookshelf $bookshelf
+     * @param Book $book
+     * @param Chapter $chapter
+     * @param Page $page
+     * @param PageRevision $pageRevision
+     */
+    public function __construct(
+        Bookshelf $bookshelf,
+        Book $book,
+        Chapter $chapter,
+        Page $page,
+        PageRevision $pageRevision
+    ) {
+        $this->bookshelf = $bookshelf;
+        $this->book = $book;
+        $this->chapter = $chapter;
+        $this->page = $page;
+        $this->pageRevision = $pageRevision;
+    }
+
+    /**
+     * Fetch all core entity types as an associated array
+     * with their basic names as the keys.
+     * @return Entity[]
+     */
+    public function all()
+    {
+        return [
+            'bookshelf' => $this->bookshelf,
+            'book' => $this->book,
+            'chapter' => $this->chapter,
+            'page' => $this->page,
+        ];
+    }
+
+    /**
+     * Get an entity instance by it's basic name.
+     * @param string $type
+     * @return Entity
+     */
+    public function get(string $type)
+    {
+        $type = strtolower($type);
+        return $this->all()[$type];
+    }
+
+
+}
\ No newline at end of file
similarity index 94%
rename from app/Services/ExportService.php
rename to app/Entities/ExportService.php
index 01e87f1678ebf7a2616b54b21e9b6cfc9d564a15..09635aa214f0b8e112583e2c747644030e5bd4b1 100644 (file)
@@ -1,9 +1,7 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Entities;
 
-use BookStack\Book;
-use BookStack\Chapter;
-use BookStack\Page;
-use BookStack\Repos\EntityRepo;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Uploads\ImageService;
 
 class ExportService
 {
@@ -13,7 +11,8 @@ class ExportService
 
     /**
      * ExportService constructor.
-     * @param $entityRepo
+     * @param EntityRepo $entityRepo
+     * @param ImageService $imageService
      */
     public function __construct(EntityRepo $entityRepo, ImageService $imageService)
     {
@@ -24,7 +23,7 @@ class ExportService
     /**
      * Convert a page to a self-contained HTML file.
      * Includes required CSS & image content. Images are base64 encoded into the HTML.
-     * @param Page $page
+     * @param \BookStack\Entities\Page $page
      * @return mixed|string
      * @throws \Throwable
      */
@@ -39,7 +38,7 @@ class ExportService
 
     /**
      * Convert a chapter to a self-contained HTML file.
-     * @param Chapter $chapter
+     * @param \BookStack\Entities\Chapter $chapter
      * @return mixed|string
      * @throws \Throwable
      */
@@ -89,7 +88,7 @@ class ExportService
 
     /**
      * Convert a chapter to a PDF file.
-     * @param Chapter $chapter
+     * @param \BookStack\Entities\Chapter $chapter
      * @return mixed|string
      * @throws \Throwable
      */
@@ -108,7 +107,7 @@ class ExportService
 
     /**
      * Convert a book to a PDF file
-     * @param Book $book
+     * @param \BookStack\Entities\Book $book
      * @return string
      * @throws \Throwable
      */
@@ -208,7 +207,7 @@ class ExportService
 
     /**
      * Convert a chapter into a plain text string.
-     * @param Chapter $chapter
+     * @param \BookStack\Entities\Chapter $chapter
      * @return string
      */
     public function chapterToPlainText(Chapter $chapter)
similarity index 92%
rename from app/Page.php
rename to app/Entities/Page.php
index 5c03e7d66f610d21b8499370307314b924bcca3d..ea7df16f4021025b048f91dd4e26f50741310e46 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Entities;
+
+use BookStack\Uploads\Attachment;
 
 class Page extends Entity
 {
@@ -8,6 +10,15 @@ class Page extends Entity
 
     public $textField = 'text';
 
+    /**
+     * Get the morph class for this model.
+     * @return string
+     */
+    public function getMorphClass()
+    {
+        return 'BookStack\\Page';
+    }
+
     /**
      * Converts this page into a simplified array.
      * @return mixed
@@ -115,7 +126,7 @@ class Page extends Entity
 
     /**
      * Get the current revision for the page if existing
-     * @return \BookStack\PageRevision|null
+     * @return \BookStack\Entities\PageRevision|null
      */
     public function getCurrentRevision()
     {
similarity index 94%
rename from app/PageRevision.php
rename to app/Entities/PageRevision.php
index ffcc4f9d25b26ec81eb6fc89db62b4393666e0a6..d30147bfc52b1789f2faf4ecf89d8e3b50345c09 100644 (file)
@@ -1,4 +1,7 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Entities;
+
+use BookStack\Auth\User;
+use BookStack\Model;
 
 class PageRevision extends Model
 {
similarity index 53%
rename from app/Repos/EntityRepo.php
rename to app/Entities/Repos/EntityRepo.php
index d6736886ee2cbf3a4feb4293621957021c8b4cc1..44fb9ad123dba1ee4de72e70a8bd2e2f90126844 100644 (file)
@@ -1,54 +1,30 @@
-<?php namespace BookStack\Repos;
-
-use BookStack\Book;
-use BookStack\Bookshelf;
-use BookStack\Chapter;
-use BookStack\Entity;
+<?php namespace BookStack\Entities\Repos;
+
+use BookStack\Actions\TagRepo;
+use BookStack\Actions\ViewService;
+use BookStack\Auth\Permissions\PermissionService;
+use BookStack\Auth\User;
+use BookStack\Entities\Book;
+use BookStack\Entities\Bookshelf;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Entity;
+use BookStack\Entities\EntityProvider;
+use BookStack\Entities\Page;
+use BookStack\Entities\SearchService;
 use BookStack\Exceptions\NotFoundException;
 use BookStack\Exceptions\NotifyException;
-use BookStack\Page;
-use BookStack\PageRevision;
-use BookStack\Services\AttachmentService;
-use BookStack\Services\PermissionService;
-use BookStack\Services\SearchService;
-use BookStack\Services\ViewService;
-use Carbon\Carbon;
+use BookStack\Uploads\AttachmentService;
 use DOMDocument;
-use DOMXPath;
+use Illuminate\Http\Request;
 use Illuminate\Support\Collection;
 
 class EntityRepo
 {
-    /**
-     * @var Bookshelf
-     */
-    public $bookshelf;
-
-    /**
-     * @var Book $book
-     */
-    public $book;
-
-    /**
-     * @var Chapter
-     */
-    public $chapter;
-
-    /**
-     * @var Page
-     */
-    public $page;
 
     /**
-     * @var PageRevision
+     * @var EntityProvider
      */
-    protected $pageRevision;
-
-    /**
-     * Base entity instances keyed by type
-     * @var []Entity
-     */
-    protected $entities;
+    protected $entityProvider;
 
     /**
      * @var PermissionService
@@ -72,63 +48,36 @@ class EntityRepo
 
     /**
      * EntityRepo constructor.
-     * @param Bookshelf $bookshelf
-     * @param Book $book
-     * @param Chapter $chapter
-     * @param Page $page
-     * @param PageRevision $pageRevision
+     * @param EntityProvider $entityProvider
      * @param ViewService $viewService
      * @param PermissionService $permissionService
      * @param TagRepo $tagRepo
      * @param SearchService $searchService
      */
     public function __construct(
-        Bookshelf $bookshelf,
-        Book $book,
-        Chapter $chapter,
-        Page $page,
-        PageRevision $pageRevision,
+        EntityProvider $entityProvider,
         ViewService $viewService,
         PermissionService $permissionService,
         TagRepo $tagRepo,
         SearchService $searchService
     ) {
-        $this->bookshelf = $bookshelf;
-        $this->book = $book;
-        $this->chapter = $chapter;
-        $this->page = $page;
-        $this->pageRevision = $pageRevision;
-        $this->entities = [
-            'bookshelf' => $this->bookshelf,
-            'page' => $this->page,
-            'chapter' => $this->chapter,
-            'book' => $this->book
-        ];
+        $this->entityProvider = $entityProvider;
         $this->viewService = $viewService;
         $this->permissionService = $permissionService;
         $this->tagRepo = $tagRepo;
         $this->searchService = $searchService;
     }
 
-    /**
-     * Get an entity instance via type.
-     * @param $type
-     * @return Entity
-     */
-    protected function getEntity($type)
-    {
-        return $this->entities[strtolower($type)];
-    }
-
     /**
      * Base query for searching entities via permission system
      * @param string $type
      * @param bool $allowDrafts
+     * @param string $permission
      * @return \Illuminate\Database\Query\Builder
      */
     protected function entityQuery($type, $allowDrafts = false, $permission = 'view')
     {
-        $q = $this->permissionService->enforceEntityRestrictions($type, $this->getEntity($type), $permission);
+        $q = $this->permissionService->enforceEntityRestrictions($type, $this->entityProvider->get($type), $permission);
         if (strtolower($type) === 'page' && !$allowDrafts) {
             $q = $q->where('draft', '=', false);
         }
@@ -152,15 +101,35 @@ class EntityRepo
      * @param integer $id
      * @param bool $allowDrafts
      * @param bool $ignorePermissions
-     * @return Entity
+     * @return \BookStack\Entities\Entity
      */
     public function getById($type, $id, $allowDrafts = false, $ignorePermissions = false)
     {
+        $query = $this->entityQuery($type, $allowDrafts);
+
         if ($ignorePermissions) {
-            $entity = $this->getEntity($type);
-            return $entity->newQuery()->find($id);
+            $query = $this->entityProvider->get($type)->newQuery();
         }
-        return $this->entityQuery($type, $allowDrafts)->find($id);
+
+        return $query->find($id);
+    }
+
+    /**
+     * @param string $type
+     * @param []int $ids
+     * @param bool $allowDrafts
+     * @param bool $ignorePermissions
+     * @return \Illuminate\Database\Eloquent\Builder[]|\Illuminate\Database\Eloquent\Collection|Collection
+     */
+    public function getManyById($type, $ids, $allowDrafts = false, $ignorePermissions = false)
+    {
+        $query = $this->entityQuery($type, $allowDrafts);
+
+        if ($ignorePermissions) {
+            $query = $this->entityProvider->get($type)->newQuery();
+        }
+
+        return $query->whereIn('id', $ids)->get();
     }
 
     /**
@@ -168,7 +137,7 @@ class EntityRepo
      * @param string $type
      * @param string $slug
      * @param string|bool $bookSlug
-     * @return Entity
+     * @return \BookStack\Entities\Entity
      * @throws NotFoundException
      */
     public function getBySlug($type, $slug, $bookSlug = false)
@@ -178,7 +147,7 @@ class EntityRepo
         if (strtolower($type) === 'chapter' || strtolower($type) === 'page') {
             $q = $q->where('book_id', '=', function ($query) use ($bookSlug) {
                 $query->select('id')
-                    ->from($this->book->getTable())
+                    ->from($this->entityProvider->book->getTable())
                     ->where('slug', '=', $bookSlug)->limit(1);
             });
         }
@@ -190,26 +159,6 @@ class EntityRepo
     }
 
 
-    /**
-     * Search through page revisions and retrieve the last page in the
-     * current book that has a slug equal to the one given.
-     * @param string $pageSlug
-     * @param string $bookSlug
-     * @return null|Page
-     */
-    public function getPageByOldSlug($pageSlug, $bookSlug)
-    {
-        $revision = $this->pageRevision->where('slug', '=', $pageSlug)
-            ->whereHas('page', function ($query) {
-                $this->permissionService->enforceEntityRestrictions('page', $query);
-            })
-            ->where('type', '=', 'version')
-            ->where('book_slug', '=', $bookSlug)
-            ->orderBy('created_at', 'desc')
-            ->with('page')->first();
-        return $revision !== null ? $revision->page : null;
-    }
-
     /**
      * Get all entities of a type with the given permission, limited by count unless count is false.
      * @param string $type
@@ -247,7 +196,7 @@ class EntityRepo
      */
     public function getRecentlyCreated($type, $count = 20, $page = 0, $additionalQuery = false)
     {
-        $query = $this->permissionService->enforceEntityRestrictions($type, $this->getEntity($type))
+        $query = $this->permissionService->enforceEntityRestrictions($type, $this->entityProvider->get($type))
             ->orderBy('created_at', 'desc');
         if (strtolower($type) === 'page') {
             $query = $query->where('draft', '=', false);
@@ -268,7 +217,7 @@ class EntityRepo
      */
     public function getRecentlyUpdated($type, $count = 20, $page = 0, $additionalQuery = false)
     {
-        $query = $this->permissionService->enforceEntityRestrictions($type, $this->getEntity($type))
+        $query = $this->permissionService->enforceEntityRestrictions($type, $this->entityProvider->get($type))
             ->orderBy('updated_at', 'desc');
         if (strtolower($type) === 'page') {
             $query = $query->where('draft', '=', false);
@@ -288,7 +237,7 @@ class EntityRepo
      */
     public function getRecentlyViewed($type, $count = 10, $page = 0)
     {
-        $filter = is_bool($type) ? false : $this->getEntity($type);
+        $filter = is_bool($type) ? false : $this->entityProvider->get($type);
         return $this->viewService->getUserRecentlyViewed($count, $page, $filter);
     }
 
@@ -323,7 +272,7 @@ class EntityRepo
      */
     public function getPopular($type, $count = 10, $page = 0)
     {
-        $filter = is_bool($type) ? false : $this->getEntity($type);
+        $filter = is_bool($type) ? false : $this->entityProvider->get($type);
         return $this->viewService->getPopular($count, $page, $filter);
     }
 
@@ -331,19 +280,32 @@ class EntityRepo
      * Get draft pages owned by the current user.
      * @param int $count
      * @param int $page
+     * @return Collection
      */
     public function getUserDraftPages($count = 20, $page = 0)
     {
-        return $this->page->where('draft', '=', true)
+        return $this->entityProvider->page->where('draft', '=', true)
             ->where('created_by', '=', user()->id)
             ->orderBy('updated_at', 'desc')
             ->skip($count * $page)->take($count)->get();
     }
 
+    /**
+     * Get the number of entities the given user has created.
+     * @param string $type
+     * @param User $user
+     * @return int
+     */
+    public function getUserTotalCreated(string $type, User $user)
+    {
+        return $this->entityProvider->get($type)
+            ->where('created_by', '=', $user->id)->count();
+    }
+
     /**
      * Get the child items for a chapter sorted by priority but
      * with draft items floated to the top.
-     * @param Bookshelf $bookshelf
+     * @param \BookStack\Entities\Bookshelf $bookshelf
      * @return \Illuminate\Database\Eloquent\Collection|static[]
      */
     public function getBookshelfChildren(Bookshelf $bookshelf)
@@ -355,7 +317,7 @@ class EntityRepo
      * Get all child objects of a book.
      * Returns a sorted collection of Pages and Chapters.
      * Loads the book slug onto child elements to prevent access database access for getting the slug.
-     * @param Book $book
+     * @param \BookStack\Entities\Book $book
      * @param bool $filterDrafts
      * @param bool $renderPages
      * @return mixed
@@ -368,14 +330,14 @@ class EntityRepo
         $tree = [];
 
         foreach ($q as $index => $rawEntity) {
-            if ($rawEntity->entity_type === 'BookStack\\Page') {
-                $entities[$index] = $this->page->newFromBuilder($rawEntity);
+            if ($rawEntity->entity_type ===  $this->entityProvider->page->getMorphClass()) {
+                $entities[$index] = $this->entityProvider->page->newFromBuilder($rawEntity);
                 if ($renderPages) {
                     $entities[$index]->html = $rawEntity->html;
                     $entities[$index]->html = $this->renderPage($entities[$index]);
                 };
-            } else if ($rawEntity->entity_type === 'BookStack\\Chapter') {
-                $entities[$index] = $this->chapter->newFromBuilder($rawEntity);
+            } else if ($rawEntity->entity_type === $this->entityProvider->chapter->getMorphClass()) {
+                $entities[$index] = $this->entityProvider->chapter->newFromBuilder($rawEntity);
                 $key = $entities[$index]->entity_type . ':' . $entities[$index]->id;
                 $parents[$key] = $entities[$index];
                 $parents[$key]->setAttribute('pages', collect());
@@ -390,7 +352,7 @@ class EntityRepo
             if ($entity->chapter_id === 0 || $entity->chapter_id === '0') {
                 continue;
             }
-            $parentKey = 'BookStack\\Chapter:' . $entity->chapter_id;
+            $parentKey = $this->entityProvider->chapter->getMorphClass() . ':' . $entity->chapter_id;
             if (!isset($parents[$parentKey])) {
                 $tree[] = $entity;
                 continue;
@@ -405,7 +367,7 @@ class EntityRepo
     /**
      * Get the child items for a chapter sorted by priority but
      * with draft items floated to the top.
-     * @param Chapter $chapter
+     * @param \BookStack\Entities\Chapter $chapter
      * @return \Illuminate\Database\Eloquent\Collection|static[]
      */
     public function getChapterChildren(Chapter $chapter)
@@ -417,7 +379,7 @@ class EntityRepo
 
     /**
      * Get the next sequential priority for a new child element in the given book.
-     * @param Book $book
+     * @param \BookStack\Entities\Book $book
      * @return int
      */
     public function getNewBookPriority(Book $book)
@@ -428,7 +390,7 @@ class EntityRepo
 
     /**
      * Get a new priority for a new page to be added to the given chapter.
-     * @param Chapter $chapter
+     * @param \BookStack\Entities\Chapter $chapter
      * @return int
      */
     public function getNewChapterPriority(Chapter $chapter)
@@ -464,7 +426,7 @@ class EntityRepo
      */
     protected function slugExists($type, $slug, $currentId = false, $bookId = false)
     {
-        $query = $this->getEntity($type)->where('slug', '=', $slug);
+        $query = $this->entityProvider->get($type)->where('slug', '=', $slug);
         if (strtolower($type) === 'page' || strtolower($type) === 'chapter') {
             $query = $query->where('book_id', '=', $bookId);
         }
@@ -476,10 +438,11 @@ class EntityRepo
 
     /**
      * Updates entity restrictions from a request
-     * @param $request
-     * @param Entity $entity
+     * @param Request $request
+     * @param \BookStack\Entities\Entity $entity
+     * @throws \Throwable
      */
-    public function updateEntityPermissionsFromRequest($request, Entity $entity)
+    public function updateEntityPermissionsFromRequest(Request $request, Entity $entity)
     {
         $entity->restricted = $request->get('restricted', '') === 'true';
         $entity->permissions()->delete();
@@ -507,12 +470,12 @@ class EntityRepo
      * @param string $type
      * @param array $input
      * @param bool|Book $book
-     * @return Entity
+     * @return \BookStack\Entities\Entity
      */
     public function createFromInput($type, $input = [], $book = false)
     {
         $isChapter = strtolower($type) === 'chapter';
-        $entityModel = $this->getEntity($type)->newInstance($input);
+        $entityModel = $this->entityProvider->get($type)->newInstance($input);
         $entityModel->slug = $this->findSuitableSlug($type, $entityModel->name, false, $isChapter ? $book->id : false);
         $entityModel->created_by = user()->id;
         $entityModel->updated_by = user()->id;
@@ -531,9 +494,9 @@ class EntityRepo
      * Update entity details from request input.
      * Used for books and chapters
      * @param string $type
-     * @param Entity $entityModel
+     * @param \BookStack\Entities\Entity $entityModel
      * @param array $input
-     * @return Entity
+     * @return \BookStack\Entities\Entity
      */
     public function updateFromInput($type, Entity $entityModel, $input = [])
     {
@@ -556,7 +519,7 @@ class EntityRepo
     /**
      * Sync the books assigned to a shelf from a comma-separated list
      * of book IDs.
-     * @param Bookshelf $shelf
+     * @param \BookStack\Entities\Bookshelf $shelf
      * @param string $books
      */
     public function updateShelfBooks(Bookshelf $shelf, string $books)
@@ -581,7 +544,7 @@ class EntityRepo
      * @param integer $newBookId
      * @param Entity $entity
      * @param bool $rebuildPermissions
-     * @return Entity
+     * @return \BookStack\Entities\Entity
      */
     public function changeBook($type, $newBookId, Entity $entity, $rebuildPermissions = false)
     {
@@ -635,191 +598,6 @@ class EntityRepo
         return $slug;
     }
 
-    /**
-     * Get a new draft page instance.
-     * @param Book $book
-     * @param Chapter|bool $chapter
-     * @return Page
-     */
-    public function getDraftPage(Book $book, $chapter = false)
-    {
-        $page = $this->page->newInstance();
-        $page->name = trans('entities.pages_initial_name');
-        $page->created_by = user()->id;
-        $page->updated_by = user()->id;
-        $page->draft = true;
-
-        if ($chapter) {
-            $page->chapter_id = $chapter->id;
-        }
-
-        $book->pages()->save($page);
-        $page = $this->page->find($page->id);
-        $this->permissionService->buildJointPermissionsForEntity($page);
-        return $page;
-    }
-
-    /**
-     * Publish a draft page to make it a normal page.
-     * Sets the slug and updates the content.
-     * @param Page $draftPage
-     * @param array $input
-     * @return Page
-     */
-    public function publishPageDraft(Page $draftPage, array $input)
-    {
-        $draftPage->fill($input);
-
-        // Save page tags if present
-        if (isset($input['tags'])) {
-            $this->tagRepo->saveTagsToEntity($draftPage, $input['tags']);
-        }
-
-        $draftPage->slug = $this->findSuitableSlug('page', $draftPage->name, false, $draftPage->book->id);
-        $draftPage->html = $this->formatHtml($input['html']);
-        $draftPage->text = $this->pageToPlainText($draftPage);
-        $draftPage->draft = false;
-        $draftPage->revision_count = 1;
-
-        $draftPage->save();
-        $this->savePageRevision($draftPage, trans('entities.pages_initial_revision'));
-        $this->searchService->indexEntity($draftPage);
-        return $draftPage;
-    }
-
-    /**
-     * Create a copy of a page in a new location with a new name.
-     * @param Page $page
-     * @param Entity $newParent
-     * @param string $newName
-     * @return Page
-     */
-    public function copyPage(Page $page, Entity $newParent, $newName = '')
-    {
-        $newBook = $newParent->isA('book') ? $newParent : $newParent->book;
-        $newChapter = $newParent->isA('chapter') ? $newParent : null;
-        $copyPage = $this->getDraftPage($newBook, $newChapter);
-        $pageData = $page->getAttributes();
-
-        // Update name
-        if (!empty($newName)) {
-            $pageData['name'] = $newName;
-        }
-
-        // Copy tags from previous page if set
-        if ($page->tags) {
-            $pageData['tags'] = [];
-            foreach ($page->tags as $tag) {
-                $pageData['tags'][] = ['name' => $tag->name, 'value' => $tag->value];
-            }
-        }
-
-        // Set priority
-        if ($newParent->isA('chapter')) {
-            $pageData['priority'] = $this->getNewChapterPriority($newParent);
-        } else {
-            $pageData['priority'] = $this->getNewBookPriority($newParent);
-        }
-
-        return $this->publishPageDraft($copyPage, $pageData);
-    }
-
-    /**
-     * Saves a page revision into the system.
-     * @param Page $page
-     * @param null|string $summary
-     * @return PageRevision
-     */
-    public function savePageRevision(Page $page, $summary = null)
-    {
-        $revision = $this->pageRevision->newInstance($page->toArray());
-        if (setting('app-editor') !== 'markdown') {
-            $revision->markdown = '';
-        }
-        $revision->page_id = $page->id;
-        $revision->slug = $page->slug;
-        $revision->book_slug = $page->book->slug;
-        $revision->created_by = user()->id;
-        $revision->created_at = $page->updated_at;
-        $revision->type = 'version';
-        $revision->summary = $summary;
-        $revision->revision_number = $page->revision_count;
-        $revision->save();
-
-        $revisionLimit = config('app.revision_limit');
-        if ($revisionLimit !== false) {
-            $revisionsToDelete = $this->pageRevision->where('page_id', '=', $page->id)
-                ->orderBy('created_at', 'desc')->skip(intval($revisionLimit))->take(10)->get(['id']);
-            if ($revisionsToDelete->count() > 0) {
-                $this->pageRevision->whereIn('id', $revisionsToDelete->pluck('id'))->delete();
-            }
-        }
-
-        return $revision;
-    }
-
-    /**
-     * Formats a page's html to be tagged correctly
-     * within the system.
-     * @param string $htmlText
-     * @return string
-     */
-    protected function formatHtml($htmlText)
-    {
-        if ($htmlText == '') {
-            return $htmlText;
-        }
-        libxml_use_internal_errors(true);
-        $doc = new DOMDocument();
-        $doc->loadHTML(mb_convert_encoding($htmlText, 'HTML-ENTITIES', 'UTF-8'));
-
-        $container = $doc->documentElement;
-        $body = $container->childNodes->item(0);
-        $childNodes = $body->childNodes;
-
-        // Ensure no duplicate ids are used
-        $idArray = [];
-
-        foreach ($childNodes as $index => $childNode) {
-            /** @var \DOMElement $childNode */
-            if (get_class($childNode) !== 'DOMElement') {
-                continue;
-            }
-
-            // Overwrite id if not a BookStack custom id
-            if ($childNode->hasAttribute('id')) {
-                $id = $childNode->getAttribute('id');
-                if (strpos($id, 'bkmrk') === 0 && array_search($id, $idArray) === false) {
-                    $idArray[] = $id;
-                    continue;
-                };
-            }
-
-            // Create an unique id for the element
-            // Uses the content as a basis to ensure output is the same every time
-            // the same content is passed through.
-            $contentId = 'bkmrk-' . substr(strtolower(preg_replace('/\s+/', '-', trim($childNode->nodeValue))), 0, 20);
-            $newId = urlencode($contentId);
-            $loopIndex = 0;
-            while (in_array($newId, $idArray)) {
-                $newId = urlencode($contentId . '-' . $loopIndex);
-                $loopIndex++;
-            }
-
-            $childNode->setAttribute('id', $newId);
-            $idArray[] = $newId;
-        }
-
-        // Generate inner html as a string
-        $html = '';
-        foreach ($childNodes as $childNode) {
-            $html .= $doc->saveHTML($childNode);
-        }
-
-        return $html;
-    }
-
-
     /**
      * Render the page for viewing, Parsing and performing features such as page transclusion.
      * @param Page $page
@@ -900,17 +678,6 @@ class EntityRepo
         return $html;
     }
 
-    /**
-     * Get the plain text version of a page's content.
-     * @param Page $page
-     * @return string
-     */
-    public function pageToPlainText(Page $page)
-    {
-        $html = $this->renderPage($page);
-        return strip_tags($html);
-    }
-
     /**
      * Search for image usage within page content.
      * @param $imageString
@@ -927,281 +694,9 @@ class EntityRepo
         return count($pages) > 0 ? $pages : false;
     }
 
-    /**
-     * Parse the headers on the page to get a navigation menu
-     * @param String $pageContent
-     * @return array
-     */
-    public function getPageNav($pageContent)
-    {
-        if ($pageContent == '') {
-            return [];
-        }
-        libxml_use_internal_errors(true);
-        $doc = new DOMDocument();
-        $doc->loadHTML(mb_convert_encoding($pageContent, 'HTML-ENTITIES', 'UTF-8'));
-        $xPath = new DOMXPath($doc);
-        $headers = $xPath->query("//h1|//h2|//h3|//h4|//h5|//h6");
-
-        if (is_null($headers)) {
-            return [];
-        }
-
-        $tree = collect([]);
-        foreach ($headers as $header) {
-            $text = $header->nodeValue;
-            $tree->push([
-                'nodeName' => strtolower($header->nodeName),
-                'level' => intval(str_replace('h', '', $header->nodeName)),
-                'link' => '#' . $header->getAttribute('id'),
-                'text' => strlen($text) > 30 ? substr($text, 0, 27) . '...' : $text
-            ]);
-        }
-
-        // Normalise headers if only smaller headers have been used
-        if (count($tree) > 0) {
-            $minLevel = $tree->pluck('level')->min();
-            $tree = $tree->map(function ($header) use ($minLevel) {
-                $header['level'] -= ($minLevel - 2);
-                return $header;
-            });
-        }
-        return $tree->toArray();
-    }
-
-    /**
-     * Updates a page with any fillable data and saves it into the database.
-     * @param Page $page
-     * @param int $book_id
-     * @param array $input
-     * @return Page
-     */
-    public function updatePage(Page $page, $book_id, $input)
-    {
-        // Hold the old details to compare later
-        $oldHtml = $page->html;
-        $oldName = $page->name;
-
-        // Prevent slug being updated if no name change
-        if ($page->name !== $input['name']) {
-            $page->slug = $this->findSuitableSlug('page', $input['name'], $page->id, $book_id);
-        }
-
-        // Save page tags if present
-        if (isset($input['tags'])) {
-            $this->tagRepo->saveTagsToEntity($page, $input['tags']);
-        }
-
-        // Update with new details
-        $userId = user()->id;
-        $page->fill($input);
-        $page->html = $this->formatHtml($input['html']);
-        $page->text = $this->pageToPlainText($page);
-        if (setting('app-editor') !== 'markdown') {
-            $page->markdown = '';
-        }
-        $page->updated_by = $userId;
-        $page->revision_count++;
-        $page->save();
-
-        // Remove all update drafts for this user & page.
-        $this->userUpdatePageDraftsQuery($page, $userId)->delete();
-
-        // Save a revision after updating
-        if ($oldHtml !== $input['html'] || $oldName !== $input['name'] || $input['summary'] !== null) {
-            $this->savePageRevision($page, $input['summary']);
-        }
-
-        $this->searchService->indexEntity($page);
-
-        return $page;
-    }
-
-    /**
-     * The base query for getting user update drafts.
-     * @param Page $page
-     * @param $userId
-     * @return mixed
-     */
-    protected function userUpdatePageDraftsQuery(Page $page, $userId)
-    {
-        return $this->pageRevision->where('created_by', '=', $userId)
-            ->where('type', 'update_draft')
-            ->where('page_id', '=', $page->id)
-            ->orderBy('created_at', 'desc');
-    }
-
-    /**
-     * Checks whether a user has a draft version of a particular page or not.
-     * @param Page $page
-     * @param $userId
-     * @return bool
-     */
-    public function hasUserGotPageDraft(Page $page, $userId)
-    {
-        return $this->userUpdatePageDraftsQuery($page, $userId)->count() > 0;
-    }
-
-    /**
-     * Get the latest updated draft revision for a particular page and user.
-     * @param Page $page
-     * @param $userId
-     * @return mixed
-     */
-    public function getUserPageDraft(Page $page, $userId)
-    {
-        return $this->userUpdatePageDraftsQuery($page, $userId)->first();
-    }
-
-    /**
-     * Get the notification message that informs the user that they are editing a draft page.
-     * @param PageRevision $draft
-     * @return string
-     */
-    public function getUserPageDraftMessage(PageRevision $draft)
-    {
-        $message = trans('entities.pages_editing_draft_notification', ['timeDiff' => $draft->updated_at->diffForHumans()]);
-        if ($draft->page->updated_at->timestamp <= $draft->updated_at->timestamp) {
-            return $message;
-        }
-        return $message . "\n" . trans('entities.pages_draft_edited_notification');
-    }
-
-    /**
-     * Check if a page is being actively editing.
-     * Checks for edits since last page updated.
-     * Passing in a minuted range will check for edits
-     * within the last x minutes.
-     * @param Page $page
-     * @param null $minRange
-     * @return bool
-     */
-    public function isPageEditingActive(Page $page, $minRange = null)
-    {
-        $draftSearch = $this->activePageEditingQuery($page, $minRange);
-        return $draftSearch->count() > 0;
-    }
-
-    /**
-     * A query to check for active update drafts on a particular page.
-     * @param Page $page
-     * @param null $minRange
-     * @return mixed
-     */
-    protected function activePageEditingQuery(Page $page, $minRange = null)
-    {
-        $query = $this->pageRevision->where('type', '=', 'update_draft')
-            ->where('page_id', '=', $page->id)
-            ->where('updated_at', '>', $page->updated_at)
-            ->where('created_by', '!=', user()->id)
-            ->with('createdBy');
-
-        if ($minRange !== null) {
-            $query = $query->where('updated_at', '>=', Carbon::now()->subMinutes($minRange));
-        }
-
-        return $query;
-    }
-
-    /**
-     * Restores a revision's content back into a page.
-     * @param Page $page
-     * @param Book $book
-     * @param  int $revisionId
-     * @return Page
-     */
-    public function restorePageRevision(Page $page, Book $book, $revisionId)
-    {
-        $page->revision_count++;
-        $this->savePageRevision($page);
-        $revision = $page->revisions()->where('id', '=', $revisionId)->first();
-        $page->fill($revision->toArray());
-        $page->slug = $this->findSuitableSlug('page', $page->name, $page->id, $book->id);
-        $page->text = $this->pageToPlainText($page);
-        $page->updated_by = user()->id;
-        $page->save();
-        $this->searchService->indexEntity($page);
-        return $page;
-    }
-
-
-    /**
-     * Save a page update draft.
-     * @param Page $page
-     * @param array $data
-     * @return PageRevision|Page
-     */
-    public function updatePageDraft(Page $page, $data = [])
-    {
-        // If the page itself is a draft simply update that
-        if ($page->draft) {
-            $page->fill($data);
-            if (isset($data['html'])) {
-                $page->text = $this->pageToPlainText($page);
-            }
-            $page->save();
-            return $page;
-        }
-
-        // Otherwise save the data to a revision
-        $userId = user()->id;
-        $drafts = $this->userUpdatePageDraftsQuery($page, $userId)->get();
-
-        if ($drafts->count() > 0) {
-            $draft = $drafts->first();
-        } else {
-            $draft = $this->pageRevision->newInstance();
-            $draft->page_id = $page->id;
-            $draft->slug = $page->slug;
-            $draft->book_slug = $page->book->slug;
-            $draft->created_by = $userId;
-            $draft->type = 'update_draft';
-        }
-
-        $draft->fill($data);
-        if (setting('app-editor') !== 'markdown') {
-            $draft->markdown = '';
-        }
-
-        $draft->save();
-        return $draft;
-    }
-
-    /**
-     * Get a notification message concerning the editing activity on a particular page.
-     * @param Page $page
-     * @param null $minRange
-     * @return string
-     */
-    public function getPageEditingActiveMessage(Page $page, $minRange = null)
-    {
-        $pageDraftEdits = $this->activePageEditingQuery($page, $minRange)->get();
-
-        $userMessage = $pageDraftEdits->count() > 1 ? trans('entities.pages_draft_edit_active.start_a', ['count' => $pageDraftEdits->count()]): trans('entities.pages_draft_edit_active.start_b', ['userName' => $pageDraftEdits->first()->createdBy->name]);
-        $timeMessage = $minRange === null ? trans('entities.pages_draft_edit_active.time_a') : trans('entities.pages_draft_edit_active.time_b', ['minCount'=>$minRange]);
-        return trans('entities.pages_draft_edit_active.message', ['start' => $userMessage, 'time' => $timeMessage]);
-    }
-
-    /**
-     * Change the page's parent to the given entity.
-     * @param Page $page
-     * @param Entity $parent
-     */
-    public function changePageParent(Page $page, Entity $parent)
-    {
-        $book = $parent->isA('book') ? $parent : $parent->book;
-        $page->chapter_id = $parent->isA('chapter') ? $parent->id : 0;
-        $page->save();
-        if ($page->book->id !== $book->id) {
-            $page = $this->changeBook('page', $book->id, $page);
-        }
-        $page->load('book');
-        $this->permissionService->buildJointPermissionsForEntity($book);
-    }
-
     /**
      * Destroy a bookshelf instance
-     * @param Bookshelf $shelf
+     * @param \BookStack\Entities\Bookshelf $shelf
      * @throws \Throwable
      */
     public function destroyBookshelf(Bookshelf $shelf)
@@ -1212,7 +707,7 @@ class EntityRepo
 
     /**
      * Destroy the provided book and all its child entities.
-     * @param Book $book
+     * @param \BookStack\Entities\Book $book
      * @throws NotifyException
      * @throws \Throwable
      */
@@ -1230,7 +725,7 @@ class EntityRepo
 
     /**
      * Destroy a chapter and its relations.
-     * @param Chapter $chapter
+     * @param \BookStack\Entities\Chapter $chapter
      * @throws \Throwable
      */
     public function destroyChapter(Chapter $chapter)
@@ -1272,7 +767,7 @@ class EntityRepo
 
     /**
      * Destroy or handle the common relations connected to an entity.
-     * @param Entity $entity
+     * @param \BookStack\Entities\Entity $entity
      * @throws \Throwable
      */
     protected function destroyEntityCommonRelations(Entity $entity)
@@ -1289,7 +784,7 @@ class EntityRepo
     /**
      * Copy the permissions of a bookshelf to all child books.
      * Returns the number of books that had permissions updated.
-     * @param Bookshelf $bookshelf
+     * @param \BookStack\Entities\Bookshelf $bookshelf
      * @return int
      * @throws \Throwable
      */
diff --git a/app/Entities/Repos/PageRepo.php b/app/Entities/Repos/PageRepo.php
new file mode 100644 (file)
index 0000000..d9f9c27
--- /dev/null
@@ -0,0 +1,508 @@
+<?php namespace BookStack\Entities\Repos;
+
+use BookStack\Entities\Book;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Entity;
+use BookStack\Entities\Page;
+use BookStack\Entities\PageRevision;
+use Carbon\Carbon;
+use DOMDocument;
+use DOMXPath;
+
+class PageRepo extends EntityRepo
+{
+
+    /**
+     * Get page by slug.
+     * @param string $pageSlug
+     * @param string $bookSlug
+     * @return Page
+     * @throws \BookStack\Exceptions\NotFoundException
+     */
+    public function getPageBySlug(string $pageSlug, string $bookSlug)
+    {
+        return $this->getBySlug('page', $pageSlug, $bookSlug);
+    }
+
+    /**
+     * Search through page revisions and retrieve the last page in the
+     * current book that has a slug equal to the one given.
+     * @param string $pageSlug
+     * @param string $bookSlug
+     * @return null|Page
+     */
+    public function getPageByOldSlug(string $pageSlug, string $bookSlug)
+    {
+        $revision = $this->entityProvider->pageRevision->where('slug', '=', $pageSlug)
+            ->whereHas('page', function ($query) {
+                $this->permissionService->enforceEntityRestrictions('page', $query);
+            })
+            ->where('type', '=', 'version')
+            ->where('book_slug', '=', $bookSlug)
+            ->orderBy('created_at', 'desc')
+            ->with('page')->first();
+        return $revision !== null ? $revision->page : null;
+    }
+
+    /**
+     * Updates a page with any fillable data and saves it into the database.
+     * @param Page $page
+     * @param int $book_id
+     * @param array $input
+     * @return Page
+     * @throws \Exception
+     */
+    public function updatePage(Page $page, int $book_id, array $input)
+    {
+        // Hold the old details to compare later
+        $oldHtml = $page->html;
+        $oldName = $page->name;
+
+        // Prevent slug being updated if no name change
+        if ($page->name !== $input['name']) {
+            $page->slug = $this->findSuitableSlug('page', $input['name'], $page->id, $book_id);
+        }
+
+        // Save page tags if present
+        if (isset($input['tags'])) {
+            $this->tagRepo->saveTagsToEntity($page, $input['tags']);
+        }
+
+        // Update with new details
+        $userId = user()->id;
+        $page->fill($input);
+        $page->html = $this->formatHtml($input['html']);
+        $page->text = $this->pageToPlainText($page);
+        if (setting('app-editor') !== 'markdown') {
+            $page->markdown = '';
+        }
+        $page->updated_by = $userId;
+        $page->revision_count++;
+        $page->save();
+
+        // Remove all update drafts for this user & page.
+        $this->userUpdatePageDraftsQuery($page, $userId)->delete();
+
+        // Save a revision after updating
+        if ($oldHtml !== $input['html'] || $oldName !== $input['name'] || $input['summary'] !== null) {
+            $this->savePageRevision($page, $input['summary']);
+        }
+
+        $this->searchService->indexEntity($page);
+
+        return $page;
+    }
+
+    /**
+     * Saves a page revision into the system.
+     * @param Page $page
+     * @param null|string $summary
+     * @return PageRevision
+     * @throws \Exception
+     */
+    public function savePageRevision(Page $page, string $summary = null)
+    {
+        $revision = $this->entityProvider->pageRevision->newInstance($page->toArray());
+        if (setting('app-editor') !== 'markdown') {
+            $revision->markdown = '';
+        }
+        $revision->page_id = $page->id;
+        $revision->slug = $page->slug;
+        $revision->book_slug = $page->book->slug;
+        $revision->created_by = user()->id;
+        $revision->created_at = $page->updated_at;
+        $revision->type = 'version';
+        $revision->summary = $summary;
+        $revision->revision_number = $page->revision_count;
+        $revision->save();
+
+        $revisionLimit = config('app.revision_limit');
+        if ($revisionLimit !== false) {
+            $revisionsToDelete = $this->entityProvider->pageRevision->where('page_id', '=', $page->id)
+                ->orderBy('created_at', 'desc')->skip(intval($revisionLimit))->take(10)->get(['id']);
+            if ($revisionsToDelete->count() > 0) {
+                $this->entityProvider->pageRevision->whereIn('id', $revisionsToDelete->pluck('id'))->delete();
+            }
+        }
+
+        return $revision;
+    }
+
+    /**
+     * Formats a page's html to be tagged correctly
+     * within the system.
+     * @param string $htmlText
+     * @return string
+     */
+    protected function formatHtml(string $htmlText)
+    {
+        if ($htmlText == '') {
+            return $htmlText;
+        }
+        libxml_use_internal_errors(true);
+        $doc = new DOMDocument();
+        $doc->loadHTML(mb_convert_encoding($htmlText, 'HTML-ENTITIES', 'UTF-8'));
+
+        $container = $doc->documentElement;
+        $body = $container->childNodes->item(0);
+        $childNodes = $body->childNodes;
+
+        // Ensure no duplicate ids are used
+        $idArray = [];
+
+        foreach ($childNodes as $index => $childNode) {
+            /** @var \DOMElement $childNode */
+            if (get_class($childNode) !== 'DOMElement') {
+                continue;
+            }
+
+            // Overwrite id if not a BookStack custom id
+            if ($childNode->hasAttribute('id')) {
+                $id = $childNode->getAttribute('id');
+                if (strpos($id, 'bkmrk') === 0 && array_search($id, $idArray) === false) {
+                    $idArray[] = $id;
+                    continue;
+                };
+            }
+
+            // Create an unique id for the element
+            // Uses the content as a basis to ensure output is the same every time
+            // the same content is passed through.
+            $contentId = 'bkmrk-' . substr(strtolower(preg_replace('/\s+/', '-', trim($childNode->nodeValue))), 0, 20);
+            $newId = urlencode($contentId);
+            $loopIndex = 0;
+            while (in_array($newId, $idArray)) {
+                $newId = urlencode($contentId . '-' . $loopIndex);
+                $loopIndex++;
+            }
+
+            $childNode->setAttribute('id', $newId);
+            $idArray[] = $newId;
+        }
+
+        // Generate inner html as a string
+        $html = '';
+        foreach ($childNodes as $childNode) {
+            $html .= $doc->saveHTML($childNode);
+        }
+
+        return $html;
+    }
+
+    /**
+     * Get the plain text version of a page's content.
+     * @param \BookStack\Entities\Page $page
+     * @return string
+     */
+    public function pageToPlainText(Page $page)
+    {
+        $html = $this->renderPage($page);
+        return strip_tags($html);
+    }
+
+    /**
+     * Get a new draft page instance.
+     * @param Book $book
+     * @param Chapter|null $chapter
+     * @return \BookStack\Entities\Page
+     * @throws \Throwable
+     */
+    public function getDraftPage(Book $book, Chapter $chapter = null)
+    {
+        $page = $this->entityProvider->page->newInstance();
+        $page->name = trans('entities.pages_initial_name');
+        $page->created_by = user()->id;
+        $page->updated_by = user()->id;
+        $page->draft = true;
+
+        if ($chapter) {
+            $page->chapter_id = $chapter->id;
+        }
+
+        $book->pages()->save($page);
+        $page = $this->entityProvider->page->find($page->id);
+        $this->permissionService->buildJointPermissionsForEntity($page);
+        return $page;
+    }
+
+    /**
+     * Save a page update draft.
+     * @param Page $page
+     * @param array $data
+     * @return PageRevision|Page
+     */
+    public function updatePageDraft(Page $page, array $data = [])
+    {
+        // If the page itself is a draft simply update that
+        if ($page->draft) {
+            $page->fill($data);
+            if (isset($data['html'])) {
+                $page->text = $this->pageToPlainText($page);
+            }
+            $page->save();
+            return $page;
+        }
+
+        // Otherwise save the data to a revision
+        $userId = user()->id;
+        $drafts = $this->userUpdatePageDraftsQuery($page, $userId)->get();
+
+        if ($drafts->count() > 0) {
+            $draft = $drafts->first();
+        } else {
+            $draft = $this->entityProvider->pageRevision->newInstance();
+            $draft->page_id = $page->id;
+            $draft->slug = $page->slug;
+            $draft->book_slug = $page->book->slug;
+            $draft->created_by = $userId;
+            $draft->type = 'update_draft';
+        }
+
+        $draft->fill($data);
+        if (setting('app-editor') !== 'markdown') {
+            $draft->markdown = '';
+        }
+
+        $draft->save();
+        return $draft;
+    }
+
+    /**
+     * Publish a draft page to make it a normal page.
+     * Sets the slug and updates the content.
+     * @param Page $draftPage
+     * @param array $input
+     * @return Page
+     * @throws \Exception
+     */
+    public function publishPageDraft(Page $draftPage, array $input)
+    {
+        $draftPage->fill($input);
+
+        // Save page tags if present
+        if (isset($input['tags'])) {
+            $this->tagRepo->saveTagsToEntity($draftPage, $input['tags']);
+        }
+
+        $draftPage->slug = $this->findSuitableSlug('page', $draftPage->name, false, $draftPage->book->id);
+        $draftPage->html = $this->formatHtml($input['html']);
+        $draftPage->text = $this->pageToPlainText($draftPage);
+        $draftPage->draft = false;
+        $draftPage->revision_count = 1;
+
+        $draftPage->save();
+        $this->savePageRevision($draftPage, trans('entities.pages_initial_revision'));
+        $this->searchService->indexEntity($draftPage);
+        return $draftPage;
+    }
+
+    /**
+     * The base query for getting user update drafts.
+     * @param Page $page
+     * @param $userId
+     * @return mixed
+     */
+    protected function userUpdatePageDraftsQuery(Page $page, int $userId)
+    {
+        return $this->entityProvider->pageRevision->where('created_by', '=', $userId)
+            ->where('type', 'update_draft')
+            ->where('page_id', '=', $page->id)
+            ->orderBy('created_at', 'desc');
+    }
+
+    /**
+     * Get the latest updated draft revision for a particular page and user.
+     * @param Page $page
+     * @param $userId
+     * @return PageRevision|null
+     */
+    public function getUserPageDraft(Page $page, int $userId)
+    {
+        return $this->userUpdatePageDraftsQuery($page, $userId)->first();
+    }
+
+    /**
+     * Get the notification message that informs the user that they are editing a draft page.
+     * @param PageRevision $draft
+     * @return string
+     */
+    public function getUserPageDraftMessage(PageRevision $draft)
+    {
+        $message = trans('entities.pages_editing_draft_notification', ['timeDiff' => $draft->updated_at->diffForHumans()]);
+        if ($draft->page->updated_at->timestamp <= $draft->updated_at->timestamp) {
+            return $message;
+        }
+        return $message . "\n" . trans('entities.pages_draft_edited_notification');
+    }
+
+    /**
+     * A query to check for active update drafts on a particular page.
+     * @param Page $page
+     * @param int $minRange
+     * @return mixed
+     */
+    protected function activePageEditingQuery(Page $page, int $minRange = null)
+    {
+        $query = $this->entityProvider->pageRevision->where('type', '=', 'update_draft')
+            ->where('page_id', '=', $page->id)
+            ->where('updated_at', '>', $page->updated_at)
+            ->where('created_by', '!=', user()->id)
+            ->with('createdBy');
+
+        if ($minRange !== null) {
+            $query = $query->where('updated_at', '>=', Carbon::now()->subMinutes($minRange));
+        }
+
+        return $query;
+    }
+
+    /**
+     * Check if a page is being actively editing.
+     * Checks for edits since last page updated.
+     * Passing in a minuted range will check for edits
+     * within the last x minutes.
+     * @param Page $page
+     * @param int $minRange
+     * @return bool
+     */
+    public function isPageEditingActive(Page $page, int $minRange = null)
+    {
+        $draftSearch = $this->activePageEditingQuery($page, $minRange);
+        return $draftSearch->count() > 0;
+    }
+
+    /**
+     * Get a notification message concerning the editing activity on a particular page.
+     * @param Page $page
+     * @param int $minRange
+     * @return string
+     */
+    public function getPageEditingActiveMessage(Page $page, int $minRange = null)
+    {
+        $pageDraftEdits = $this->activePageEditingQuery($page, $minRange)->get();
+
+        $userMessage = $pageDraftEdits->count() > 1 ? trans('entities.pages_draft_edit_active.start_a', ['count' => $pageDraftEdits->count()]): trans('entities.pages_draft_edit_active.start_b', ['userName' => $pageDraftEdits->first()->createdBy->name]);
+        $timeMessage = $minRange === null ? trans('entities.pages_draft_edit_active.time_a') : trans('entities.pages_draft_edit_active.time_b', ['minCount'=>$minRange]);
+        return trans('entities.pages_draft_edit_active.message', ['start' => $userMessage, 'time' => $timeMessage]);
+    }
+
+    /**
+     * Parse the headers on the page to get a navigation menu
+     * @param string $pageContent
+     * @return array
+     */
+    public function getPageNav(string $pageContent)
+    {
+        if ($pageContent == '') {
+            return [];
+        }
+        libxml_use_internal_errors(true);
+        $doc = new DOMDocument();
+        $doc->loadHTML(mb_convert_encoding($pageContent, 'HTML-ENTITIES', 'UTF-8'));
+        $xPath = new DOMXPath($doc);
+        $headers = $xPath->query("//h1|//h2|//h3|//h4|//h5|//h6");
+
+        if (is_null($headers)) {
+            return [];
+        }
+
+        $tree = collect([]);
+        foreach ($headers as $header) {
+            $text = $header->nodeValue;
+            $tree->push([
+                'nodeName' => strtolower($header->nodeName),
+                'level' => intval(str_replace('h', '', $header->nodeName)),
+                'link' => '#' . $header->getAttribute('id'),
+                'text' => strlen($text) > 30 ? substr($text, 0, 27) . '...' : $text
+            ]);
+        }
+
+        // Normalise headers if only smaller headers have been used
+        if (count($tree) > 0) {
+            $minLevel = $tree->pluck('level')->min();
+            $tree = $tree->map(function ($header) use ($minLevel) {
+                $header['level'] -= ($minLevel - 2);
+                return $header;
+            });
+        }
+        return $tree->toArray();
+    }
+
+    /**
+     * Restores a revision's content back into a page.
+     * @param Page $page
+     * @param Book $book
+     * @param  int $revisionId
+     * @return Page
+     * @throws \Exception
+     */
+    public function restorePageRevision(Page $page, Book $book, int $revisionId)
+    {
+        $page->revision_count++;
+        $this->savePageRevision($page);
+        $revision = $page->revisions()->where('id', '=', $revisionId)->first();
+        $page->fill($revision->toArray());
+        $page->slug = $this->findSuitableSlug('page', $page->name, $page->id, $book->id);
+        $page->text = $this->pageToPlainText($page);
+        $page->updated_by = user()->id;
+        $page->save();
+        $this->searchService->indexEntity($page);
+        return $page;
+    }
+
+    /**
+     * Change the page's parent to the given entity.
+     * @param Page $page
+     * @param Entity $parent
+     * @throws \Throwable
+     */
+    public function changePageParent(Page $page, Entity $parent)
+    {
+        $book = $parent->isA('book') ? $parent : $parent->book;
+        $page->chapter_id = $parent->isA('chapter') ? $parent->id : 0;
+        $page->save();
+        if ($page->book->id !== $book->id) {
+            $page = $this->changeBook('page', $book->id, $page);
+        }
+        $page->load('book');
+        $this->permissionService->buildJointPermissionsForEntity($book);
+    }
+
+    /**
+     * Create a copy of a page in a new location with a new name.
+     * @param \BookStack\Entities\Page $page
+     * @param \BookStack\Entities\Entity $newParent
+     * @param string $newName
+     * @return \BookStack\Entities\Page
+     * @throws \Throwable
+     */
+    public function copyPage(Page $page, Entity $newParent, string $newName = '')
+    {
+        $newBook = $newParent->isA('book') ? $newParent : $newParent->book;
+        $newChapter = $newParent->isA('chapter') ? $newParent : null;
+        $copyPage = $this->getDraftPage($newBook, $newChapter);
+        $pageData = $page->getAttributes();
+
+        // Update name
+        if (!empty($newName)) {
+            $pageData['name'] = $newName;
+        }
+
+        // Copy tags from previous page if set
+        if ($page->tags) {
+            $pageData['tags'] = [];
+            foreach ($page->tags as $tag) {
+                $pageData['tags'][] = ['name' => $tag->name, 'value' => $tag->value];
+            }
+        }
+
+        // Set priority
+        if ($newParent->isA('chapter')) {
+            $pageData['priority'] = $this->getNewChapterPriority($newParent);
+        } else {
+            $pageData['priority'] = $this->getNewBookPriority($newParent);
+        }
+
+        return $this->publishPageDraft($copyPage, $pageData);
+    }
+}
\ No newline at end of file
similarity index 81%
rename from app/Services/SearchService.php
rename to app/Entities/SearchService.php
index dfde645a1727bcd2c97a60a5090f82919bfd4fcd..9e7cfdd0cdf1c8de852ee88a5464b662580e6f5b 100644 (file)
@@ -1,30 +1,34 @@
-<?php namespace BookStack\Services;
-
-use BookStack\Book;
-use BookStack\Bookshelf;
-use BookStack\Chapter;
-use BookStack\Entity;
-use BookStack\Page;
-use BookStack\SearchTerm;
+<?php namespace BookStack\Entities;
+
+use BookStack\Auth\Permissions\PermissionService;
 use Illuminate\Database\Connection;
+use Illuminate\Database\Eloquent\Builder as EloquentBuilder;
 use Illuminate\Database\Query\Builder;
 use Illuminate\Database\Query\JoinClause;
 use Illuminate\Support\Collection;
 
 class SearchService
 {
+    /**
+     * @var SearchTerm
+     */
     protected $searchTerm;
-    protected $bookshelf;
-    protected $book;
-    protected $chapter;
-    protected $page;
+
+    /**
+     * @var EntityProvider
+     */
+    protected $entityProvider;
+
+    /**
+     * @var Connection
+     */
     protected $db;
-    protected $permissionService;
 
     /**
-     * @var Entity[]
+     * @var PermissionService
      */
-    protected $entities;
+    protected $permissionService;
+
 
     /**
      * Acceptable operators to be used in a query
@@ -35,27 +39,15 @@ class SearchService
     /**
      * SearchService constructor.
      * @param SearchTerm $searchTerm
-     * @param Bookshelf $bookshelf
-     * @param Book $book
-     * @param Chapter $chapter
-     * @param Page $page
+     * @param EntityProvider $entityProvider
      * @param Connection $db
      * @param PermissionService $permissionService
      */
-    public function __construct(SearchTerm $searchTerm, Bookshelf $bookshelf, Book $book, Chapter $chapter, Page $page, Connection $db, PermissionService $permissionService)
+    public function __construct(SearchTerm $searchTerm, EntityProvider $entityProvider, Connection $db, PermissionService $permissionService)
     {
         $this->searchTerm = $searchTerm;
-        $this->bookshelf = $bookshelf;
-        $this->book = $book;
-        $this->chapter = $chapter;
-        $this->page = $page;
+        $this->entityProvider = $entityProvider;
         $this->db = $db;
-        $this->entities = [
-            'bookshelf' => $this->bookshelf,
-            'page' => $this->page,
-            'chapter' => $this->chapter,
-            'book' => $this->book
-        ];
         $this->permissionService = $permissionService;
     }
 
@@ -80,7 +72,7 @@ class SearchService
     public function searchEntities($searchString, $entityType = 'all', $page = 1, $count = 20, $action = 'view')
     {
         $terms = $this->parseSearchString($searchString);
-        $entityTypes = array_keys($this->entities);
+        $entityTypes = array_keys($this->entityProvider->all());
         $entityTypesToSearch = $entityTypes;
 
         if ($entityType !== 'all') {
@@ -177,17 +169,17 @@ class SearchService
      * @param array $terms
      * @param string $entityType
      * @param string $action
-     * @return \Illuminate\Database\Eloquent\Builder
+     * @return EloquentBuilder
      */
     protected function buildEntitySearchQuery($terms, $entityType = 'page', $action = 'view')
     {
-        $entity = $this->getEntity($entityType);
+        $entity = $this->entityProvider->get($entityType);
         $entitySelect = $entity->newQuery();
 
         // Handle normal search terms
         if (count($terms['search']) > 0) {
             $subQuery = $this->db->table('search_terms')->select('entity_id', 'entity_type', \DB::raw('SUM(score) as score'));
-            $subQuery->where('entity_type', '=', 'BookStack\\' . ucfirst($entityType));
+            $subQuery->where('entity_type', '=', $entity->getMorphClass());
             $subQuery->where(function (Builder $query) use ($terms) {
                 foreach ($terms['search'] as $inputTerm) {
                     $query->orWhere('term', 'like', $inputTerm .'%');
@@ -201,9 +193,9 @@ class SearchService
 
         // Handle exact term matching
         if (count($terms['exact']) > 0) {
-            $entitySelect->where(function (\Illuminate\Database\Eloquent\Builder $query) use ($terms, $entity) {
+            $entitySelect->where(function (EloquentBuilder $query) use ($terms, $entity) {
                 foreach ($terms['exact'] as $inputTerm) {
-                    $query->where(function (\Illuminate\Database\Eloquent\Builder $query) use ($inputTerm, $entity) {
+                    $query->where(function (EloquentBuilder $query) use ($inputTerm, $entity) {
                         $query->where('name', 'like', '%'.$inputTerm .'%')
                             ->orWhere($entity->textField, 'like', '%'.$inputTerm .'%');
                     });
@@ -291,14 +283,14 @@ class SearchService
 
     /**
      * Apply a tag search term onto a entity query.
-     * @param \Illuminate\Database\Eloquent\Builder $query
+     * @param EloquentBuilder $query
      * @param string $tagTerm
      * @return mixed
      */
-    protected function applyTagSearch(\Illuminate\Database\Eloquent\Builder $query, $tagTerm)
+    protected function applyTagSearch(EloquentBuilder $query, $tagTerm)
     {
         preg_match("/^(.*?)((".$this->getRegexEscapedOperators().")(.*?))?$/", $tagTerm, $tagSplit);
-        $query->whereHas('tags', function (\Illuminate\Database\Eloquent\Builder $query) use ($tagSplit) {
+        $query->whereHas('tags', function (EloquentBuilder $query) use ($tagSplit) {
             $tagName = $tagSplit[1];
             $tagOperator = count($tagSplit) > 2 ? $tagSplit[3] : '';
             $tagValue = count($tagSplit) > 3 ? $tagSplit[4] : '';
@@ -323,16 +315,6 @@ class SearchService
         return $query;
     }
 
-    /**
-     * Get an entity instance via type.
-     * @param $type
-     * @return Entity
-     */
-    protected function getEntity($type)
-    {
-        return $this->entities[strtolower($type)];
-    }
-
     /**
      * Index the given entity.
      * @param Entity $entity
@@ -352,7 +334,7 @@ class SearchService
 
     /**
      * Index multiple Entities at once
-     * @param Entity[] $entities
+     * @param \BookStack\Entities\Entity[] $entities
      */
     protected function indexEntities($entities)
     {
@@ -380,7 +362,7 @@ class SearchService
     {
         $this->searchTerm->truncate();
 
-        foreach ($this->entities as $entityModel) {
+        foreach ($this->entityProvider->all() as $entityModel) {
             $selectFields = ['id', 'name', $entityModel->textField];
             $entityModel->newQuery()->select($selectFields)->chunk(1000, function ($entities) {
                 $this->indexEntities($entities);
@@ -434,7 +416,7 @@ class SearchService
      * Custom entity search filters
      */
 
-    protected function filterUpdatedAfter(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterUpdatedAfter(EloquentBuilder $query, Entity $model, $input)
     {
         try {
             $date = date_create($input);
@@ -444,7 +426,7 @@ class SearchService
         $query->where('updated_at', '>=', $date);
     }
 
-    protected function filterUpdatedBefore(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterUpdatedBefore(EloquentBuilder $query, Entity $model, $input)
     {
         try {
             $date = date_create($input);
@@ -454,7 +436,7 @@ class SearchService
         $query->where('updated_at', '<', $date);
     }
 
-    protected function filterCreatedAfter(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterCreatedAfter(EloquentBuilder $query, Entity $model, $input)
     {
         try {
             $date = date_create($input);
@@ -464,7 +446,7 @@ class SearchService
         $query->where('created_at', '>=', $date);
     }
 
-    protected function filterCreatedBefore(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterCreatedBefore(EloquentBuilder $query, Entity $model, $input)
     {
         try {
             $date = date_create($input);
@@ -474,7 +456,7 @@ class SearchService
         $query->where('created_at', '<', $date);
     }
 
-    protected function filterCreatedBy(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterCreatedBy(EloquentBuilder $query, Entity $model, $input)
     {
         if (!is_numeric($input) && $input !== 'me') {
             return;
@@ -485,7 +467,7 @@ class SearchService
         $query->where('created_by', '=', $input);
     }
 
-    protected function filterUpdatedBy(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterUpdatedBy(EloquentBuilder $query, Entity $model, $input)
     {
         if (!is_numeric($input) && $input !== 'me') {
             return;
@@ -496,41 +478,41 @@ class SearchService
         $query->where('updated_by', '=', $input);
     }
 
-    protected function filterInName(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterInName(EloquentBuilder $query, Entity $model, $input)
     {
         $query->where('name', 'like', '%' .$input. '%');
     }
 
-    protected function filterInTitle(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterInTitle(EloquentBuilder $query, Entity $model, $input)
     {
         $this->filterInName($query, $model, $input);
     }
 
-    protected function filterInBody(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterInBody(EloquentBuilder $query, Entity $model, $input)
     {
         $query->where($model->textField, 'like', '%' .$input. '%');
     }
 
-    protected function filterIsRestricted(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterIsRestricted(EloquentBuilder $query, Entity $model, $input)
     {
         $query->where('restricted', '=', true);
     }
 
-    protected function filterViewedByMe(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterViewedByMe(EloquentBuilder $query, Entity $model, $input)
     {
         $query->whereHas('views', function ($query) {
             $query->where('user_id', '=', user()->id);
         });
     }
 
-    protected function filterNotViewedByMe(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterNotViewedByMe(EloquentBuilder $query, Entity $model, $input)
     {
         $query->whereDoesntHave('views', function ($query) {
             $query->where('user_id', '=', user()->id);
         });
     }
 
-    protected function filterSortBy(\Illuminate\Database\Eloquent\Builder $query, Entity $model, $input)
+    protected function filterSortBy(EloquentBuilder $query, Entity $model, $input)
     {
         $functionName = camel_case('sort_by_' . $input);
         if (method_exists($this, $functionName)) {
@@ -543,7 +525,7 @@ class SearchService
      * Sorting filter options
      */
 
-    protected function sortByLastCommented(\Illuminate\Database\Eloquent\Builder $query, Entity $model)
+    protected function sortByLastCommented(EloquentBuilder $query, Entity $model)
     {
         $commentsTable = $this->db->getTablePrefix() . 'comments';
         $morphClass = str_replace('\\', '\\\\', $model->getMorphClass());
similarity index 85%
rename from app/SearchTerm.php
rename to app/Entities/SearchTerm.php
index ee6c72190cbb254108d5c5aa6f8dbc879b2e80c4..886c4dbc1fe4a4041859357ebe293b8ecb79177d 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Entities;
+
+use BookStack\Model;
 
 class SearchTerm extends Model
 {
index 0eb62dc31aab20388e8047a39788ee0c3990e4dc..70a53497599d36216ae82bcdd787ab1901247043 100644 (file)
@@ -3,12 +3,12 @@
 namespace BookStack\Exceptions;
 
 use Exception;
+use Illuminate\Auth\Access\AuthorizationException;
 use Illuminate\Auth\AuthenticationException;
-use Illuminate\Validation\ValidationException;
 use Illuminate\Database\Eloquent\ModelNotFoundException;
-use Symfony\Component\HttpKernel\Exception\HttpException;
 use Illuminate\Foundation\Exceptions\Handler as ExceptionHandler;
-use Illuminate\Auth\Access\AuthorizationException;
+use Illuminate\Validation\ValidationException;
+use Symfony\Component\HttpKernel\Exception\HttpException;
 use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
 
 class Handler extends ExceptionHandler
similarity index 85%
rename from app/Services/Facades/Activity.php
rename to app/Facades/Activity.php
index d24e39dbac3d47d5a9536e7c6f58fa4f2895ab98..30e4b785fdb0bdb6712fcc8b448070bd23ba7345 100644 (file)
@@ -1,4 +1,4 @@
-<?php namespace BookStack\Services\Facades;
+<?php namespace BookStack\Facades;
 
 use Illuminate\Support\Facades\Facade;
 
similarity index 85%
rename from app/Services/Facades/Images.php
rename to app/Facades/Images.php
index ff455287c4cc0112c639fc457143d87cb1deefbf..fdbd35a99ad321a680a6619dc22c8db797e9f14c 100644 (file)
@@ -1,4 +1,4 @@
-<?php namespace BookStack\Services\Facades;
+<?php namespace BookStack\Facades;
 
 use Illuminate\Support\Facades\Facade;
 
similarity index 85%
rename from app/Services/Facades/Setting.php
rename to app/Facades/Setting.php
index ec6e484dae33659b2094c372d649dc557a29d0de..80feef89b24dcfe3d784dc097b7416fe0edec72a 100644 (file)
@@ -1,4 +1,4 @@
-<?php namespace BookStack\Services\Facades;
+<?php namespace BookStack\Facades;
 
 use Illuminate\Support\Facades\Facade;
 
similarity index 85%
rename from app/Services/Facades/Views.php
rename to app/Facades/Views.php
index f990bc171149053b95cedb82ac86ddbedb857f1a..f5357112e389c037c345382c13ea8e83031cf9ae 100644 (file)
@@ -1,4 +1,4 @@
-<?php namespace BookStack\Services\Facades;
+<?php namespace BookStack\Facades;
 
 use Illuminate\Support\Facades\Facade;
 
index 74644aa2fd848f0cde64171d3c1e2bd31f2c6c11..0289f8e1d8f09e5bdf1bde68c7437c2e5a4746be 100644 (file)
@@ -1,10 +1,10 @@
 <?php namespace BookStack\Http\Controllers;
 
+use BookStack\Entities\Repos\EntityRepo;
 use BookStack\Exceptions\FileUploadException;
-use BookStack\Attachment;
 use BookStack\Exceptions\NotFoundException;
-use BookStack\Repos\EntityRepo;
-use BookStack\Services\AttachmentService;
+use BookStack\Uploads\Attachment;
+use BookStack\Uploads\AttachmentService;
 use Illuminate\Http\Request;
 
 class AttachmentController extends Controller
@@ -15,7 +15,7 @@ class AttachmentController extends Controller
 
     /**
      * AttachmentController constructor.
-     * @param AttachmentService $attachmentService
+     * @param \BookStack\Uploads\AttachmentService $attachmentService
      * @param Attachment $attachment
      * @param EntityRepo $entityRepo
      */
index c0541c9e29c4c78fa32ef4197d5f7257e06eff3f..e820154e71be2f85b0d771d54b7ae03627022808 100644 (file)
@@ -2,11 +2,11 @@
 
 namespace BookStack\Http\Controllers\Auth;
 
+use BookStack\Auth\Access\LdapService;
+use BookStack\Auth\Access\SocialAuthService;
+use BookStack\Auth\UserRepo;
 use BookStack\Exceptions\AuthException;
 use BookStack\Http\Controllers\Controller;
-use BookStack\Repos\UserRepo;
-use BookStack\Services\LdapService;
-use BookStack\Services\SocialAuthService;
 use Illuminate\Contracts\Auth\Authenticatable;
 use Illuminate\Foundation\Auth\AuthenticatesUsers;
 use Illuminate\Http\Request;
@@ -43,9 +43,9 @@ class LoginController extends Controller
     /**
      * Create a new controller instance.
      *
-     * @param SocialAuthService $socialAuthService
+     * @param \BookStack\Auth\\BookStack\Auth\Access\SocialAuthService $socialAuthService
      * @param LdapService $ldapService
-     * @param UserRepo $userRepo
+     * @param \BookStack\Auth\UserRepo $userRepo
      */
     public function __construct(SocialAuthService $socialAuthService, LdapService $ldapService, UserRepo $userRepo)
     {
index 385994324eae71e78e0be1c916bc588f678dce7b..cdcca116ccd13a382e019dbcc424231e944065ad 100644 (file)
@@ -2,21 +2,19 @@
 
 namespace BookStack\Http\Controllers\Auth;
 
+use BookStack\Auth\SocialAccount;
+use BookStack\Auth\User;
+use BookStack\Auth\UserRepo;
 use BookStack\Exceptions\SocialSignInAccountNotUsed;
 use BookStack\Exceptions\SocialSignInException;
 use BookStack\Exceptions\UserRegistrationException;
-use BookStack\Repos\UserRepo;
-use BookStack\Services\EmailConfirmationService;
-use BookStack\Services\SocialAuthService;
-use BookStack\SocialAccount;
-use BookStack\User;
+use BookStack\Http\Controllers\Controller;
 use Exception;
+use Illuminate\Foundation\Auth\RegistersUsers;
 use Illuminate\Http\Request;
 use Illuminate\Http\Response;
-use Validator;
-use BookStack\Http\Controllers\Controller;
-use Illuminate\Foundation\Auth\RegistersUsers;
 use Laravel\Socialite\Contracts\User as SocialUser;
+use Validator;
 
 class RegisterController extends Controller
 {
@@ -48,11 +46,11 @@ class RegisterController extends Controller
     /**
      * Create a new controller instance.
      *
-     * @param SocialAuthService $socialAuthService
-     * @param EmailConfirmationService $emailConfirmationService
-     * @param UserRepo $userRepo
+     * @param \BookStack\Auth\Access\SocialAuthService $socialAuthService
+     * @param \BookStack\Auth\EmailConfirmationService $emailConfirmationService
+     * @param \BookStack\Auth\UserRepo $userRepo
      */
-    public function __construct(SocialAuthService $socialAuthService, EmailConfirmationService $emailConfirmationService, UserRepo $userRepo)
+    public function __construct(\BookStack\Auth\Access\SocialAuthService $socialAuthService, \BookStack\Auth\Access\EmailConfirmationService $emailConfirmationService, UserRepo $userRepo)
     {
         $this->middleware('guest')->only(['getRegister', 'postRegister', 'socialRegister']);
         $this->socialAuthService = $socialAuthService;
@@ -119,7 +117,7 @@ class RegisterController extends Controller
     /**
      * Create a new user instance after a valid registration.
      * @param  array  $data
-     * @return User
+     * @return \BookStack\Auth\User
      */
     protected function create(array $data)
     {
index ea39a771ec048529bab8995f2967306613132108..44368a9c4fb66afb47dc2ed62b70f7a51719707e 100644 (file)
@@ -1,10 +1,10 @@
 <?php namespace BookStack\Http\Controllers;
 
 use Activity;
-use BookStack\Book;
-use BookStack\Repos\EntityRepo;
-use BookStack\Repos\UserRepo;
-use BookStack\Services\ExportService;
+use BookStack\Auth\UserRepo;
+use BookStack\Entities\Book;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Entities\ExportService;
 use Illuminate\Http\Request;
 use Illuminate\Http\Response;
 use Views;
@@ -19,8 +19,8 @@ class BookController extends Controller
     /**
      * BookController constructor.
      * @param EntityRepo $entityRepo
-     * @param UserRepo $userRepo
-     * @param ExportService $exportService
+     * @param \BookStack\Auth\UserRepo $userRepo
+     * @param \BookStack\Entities\ExportService $exportService
      */
     public function __construct(EntityRepo $entityRepo, UserRepo $userRepo, ExportService $exportService)
     {
@@ -204,7 +204,7 @@ class BookController extends Controller
 
         // Get the books involved in the sort
         $bookIdsInvolved = $bookIdsInvolved->unique()->toArray();
-        $booksInvolved = $this->entityRepo->book->newQuery()->whereIn('id', $bookIdsInvolved)->get();
+        $booksInvolved = $this->entityRepo->getManyById('book', $bookIdsInvolved, false, true);
         // Throw permission error if invalid ids or inaccessible books given.
         if (count($bookIdsInvolved) !== count($booksInvolved)) {
             $this->showPermissionError();
index 8c7f7819e42904d21408e8965b3f6c03599dd07c..5c2898786f05d9d81db7e33130c0c6e5856ec2ea 100644 (file)
@@ -1,11 +1,10 @@
 <?php namespace BookStack\Http\Controllers;
 
 use Activity;
-use BookStack\Book;
-use BookStack\Bookshelf;
-use BookStack\Repos\EntityRepo;
-use BookStack\Repos\UserRepo;
-use BookStack\Services\ExportService;
+use BookStack\Auth\UserRepo;
+use BookStack\Entities\Bookshelf;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Entities\ExportService;
 use Illuminate\Http\Request;
 use Illuminate\Http\Response;
 use Views;
@@ -19,9 +18,9 @@ class BookshelfController extends Controller
 
     /**
      * BookController constructor.
-     * @param EntityRepo $entityRepo
+     * @param \BookStack\Entities\Repos\EntityRepo $entityRepo
      * @param UserRepo $userRepo
-     * @param ExportService $exportService
+     * @param \BookStack\Entities\ExportService $exportService
      */
     public function __construct(EntityRepo $entityRepo, UserRepo $userRepo, ExportService $exportService)
     {
index 1fe231a6597e909198f36fb0d4d1588a7a911836..a50306552443b235d60424c8c818fccaecb0ff4b 100644 (file)
@@ -1,9 +1,9 @@
 <?php namespace BookStack\Http\Controllers;
 
 use Activity;
-use BookStack\Repos\EntityRepo;
-use BookStack\Repos\UserRepo;
-use BookStack\Services\ExportService;
+use BookStack\Auth\UserRepo;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Entities\ExportService;
 use Illuminate\Http\Request;
 use Illuminate\Http\Response;
 use Views;
@@ -19,7 +19,7 @@ class ChapterController extends Controller
      * ChapterController constructor.
      * @param EntityRepo $entityRepo
      * @param UserRepo $userRepo
-     * @param ExportService $exportService
+     * @param \BookStack\Entities\ExportService $exportService
      */
     public function __construct(EntityRepo $entityRepo, UserRepo $userRepo, ExportService $exportService)
     {
index 7bf0a2aacde5f1779b3bf093e7866de18db0cb2d..2039ce7fe9ff749a2e2c76a2eb20b9d96b0701ef 100644 (file)
@@ -1,8 +1,8 @@
 <?php namespace BookStack\Http\Controllers;
 
 use Activity;
-use BookStack\Repos\CommentRepo;
-use BookStack\Repos\EntityRepo;
+use BookStack\Actions\CommentRepo;
+use BookStack\Entities\Repos\EntityRepo;
 use Illuminate\Database\Eloquent\ModelNotFoundException;
 use Illuminate\Http\Request;
 
@@ -13,8 +13,8 @@ class CommentController extends Controller
 
     /**
      * CommentController constructor.
-     * @param EntityRepo $entityRepo
-     * @param CommentRepo $commentRepo
+     * @param \BookStack\Entities\Repos\EntityRepo $entityRepo
+     * @param \BookStack\Actions\CommentRepo $commentRepo
      */
     public function __construct(EntityRepo $entityRepo, CommentRepo $commentRepo)
     {
index 33b57b7d9a56b14f9f406c8566346e01767e0077..80f567eaa80279e8f49599f9703f5ab29e6276c3 100644 (file)
@@ -2,13 +2,13 @@
 
 namespace BookStack\Http\Controllers;
 
+use BookStack\Auth\User;
 use BookStack\Ownable;
 use Illuminate\Foundation\Bus\DispatchesJobs;
+use Illuminate\Foundation\Validation\ValidatesRequests;
 use Illuminate\Http\Exceptions\HttpResponseException;
 use Illuminate\Http\Request;
 use Illuminate\Routing\Controller as BaseController;
-use Illuminate\Foundation\Validation\ValidatesRequests;
-use BookStack\User;
 
 abstract class Controller extends BaseController
 {
index e472503187a61db9f197ab6d2b4323a22009fe31..2bf029b519d76645a4ec807d49d44d0003bf17fb 100644 (file)
@@ -1,8 +1,7 @@
 <?php namespace BookStack\Http\Controllers;
 
 use Activity;
-use BookStack\Repos\EntityRepo;
-use Illuminate\Http\Request;
+use BookStack\Entities\Repos\EntityRepo;
 use Illuminate\Http\Response;
 use Views;
 
index eb92ae9a8a5d6453385e1b1a99cc70686c004eae..4bd1b479c9316f8ac732cec7ff0a565b5082ba5a 100644 (file)
@@ -1,13 +1,12 @@
 <?php namespace BookStack\Http\Controllers;
 
+use BookStack\Entities\Repos\EntityRepo;
 use BookStack\Exceptions\ImageUploadException;
-use BookStack\Exceptions\NotFoundException;
-use BookStack\Repos\EntityRepo;
-use BookStack\Repos\ImageRepo;
+use BookStack\Repos\PageRepo;
+use BookStack\Uploads\Image;
+use BookStack\Uploads\ImageRepo;
 use Illuminate\Filesystem\Filesystem as File;
 use Illuminate\Http\Request;
-use BookStack\Image;
-use BookStack\Repos\PageRepo;
 
 class ImageController extends Controller
 {
@@ -220,7 +219,7 @@ class ImageController extends Controller
 
     /**
      * Show the usage of an image on pages.
-     * @param EntityRepo $entityRepo
+     * @param \BookStack\Entities\Repos\EntityRepo $entityRepo
      * @param $id
      * @return \Illuminate\Http\JsonResponse
      */
index 80bbe56c1afe179935e08abaa73cba137243b388..74595443b130c5137ec5608e89591749e794e2a6 100644 (file)
@@ -1,31 +1,32 @@
 <?php namespace BookStack\Http\Controllers;
 
 use Activity;
+use BookStack\Auth\UserRepo;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Entities\ExportService;
+use BookStack\Entities\Repos\PageRepo;
 use BookStack\Exceptions\NotFoundException;
-use BookStack\Repos\EntityRepo;
-use BookStack\Repos\UserRepo;
-use BookStack\Services\ExportService;
+use GatherContent\Htmldiff\Htmldiff;
 use Illuminate\Http\Request;
 use Illuminate\Http\Response;
 use Views;
-use GatherContent\Htmldiff\Htmldiff;
 
 class PageController extends Controller
 {
 
-    protected $entityRepo;
+    protected $pageRepo;
     protected $exportService;
     protected $userRepo;
 
     /**
      * PageController constructor.
-     * @param EntityRepo $entityRepo
-     * @param ExportService $exportService
+     * @param \BookStack\Entities\Repos\PageRepo $pageRepo
+     * @param \BookStack\Entities\ExportService $exportService
      * @param UserRepo $userRepo
      */
-    public function __construct(EntityRepo $entityRepo, ExportService $exportService, UserRepo $userRepo)
+    public function __construct(PageRepo $pageRepo, ExportService $exportService, UserRepo $userRepo)
     {
-        $this->entityRepo = $entityRepo;
+        $this->pageRepo = $pageRepo;
         $this->exportService = $exportService;
         $this->userRepo = $userRepo;
         parent::__construct();
@@ -42,11 +43,11 @@ class PageController extends Controller
     public function create($bookSlug, $chapterSlug = null)
     {
         if ($chapterSlug !== null) {
-            $chapter = $this->entityRepo->getBySlug('chapter', $chapterSlug, $bookSlug);
+            $chapter = $this->pageRepo->getBySlug('chapter', $chapterSlug, $bookSlug);
             $book = $chapter->book;
         } else {
             $chapter = null;
-            $book = $this->entityRepo->getBySlug('book', $bookSlug);
+            $book = $this->pageRepo->getBySlug('book', $bookSlug);
         }
 
         $parent = $chapter ? $chapter : $book;
@@ -54,7 +55,7 @@ class PageController extends Controller
 
         // Redirect to draft edit screen if signed in
         if ($this->signedIn) {
-            $draft = $this->entityRepo->getDraftPage($book, $chapter);
+            $draft = $this->pageRepo->getDraftPage($book, $chapter);
             return redirect($draft->getUrl());
         }
 
@@ -78,18 +79,18 @@ class PageController extends Controller
         ]);
 
         if ($chapterSlug !== null) {
-            $chapter = $this->entityRepo->getBySlug('chapter', $chapterSlug, $bookSlug);
+            $chapter = $this->pageRepo->getBySlug('chapter', $chapterSlug, $bookSlug);
             $book = $chapter->book;
         } else {
             $chapter = null;
-            $book = $this->entityRepo->getBySlug('book', $bookSlug);
+            $book = $this->pageRepo->getBySlug('book', $bookSlug);
         }
 
         $parent = $chapter ? $chapter : $book;
         $this->checkOwnablePermission('page-create', $parent);
 
-        $page = $this->entityRepo->getDraftPage($book, $chapter);
-        $this->entityRepo->publishPageDraft($page, [
+        $page = $this->pageRepo->getDraftPage($book, $chapter);
+        $this->pageRepo->publishPageDraft($page, [
             'name' => $request->get('name'),
             'html' => ''
         ]);
@@ -104,7 +105,7 @@ class PageController extends Controller
      */
     public function editDraft($bookSlug, $pageId)
     {
-        $draft = $this->entityRepo->getById('page', $pageId, true);
+        $draft = $this->pageRepo->getById('page', $pageId, true);
         $this->checkOwnablePermission('page-create', $draft->parent);
         $this->setPageTitle(trans('entities.pages_edit_draft'));
 
@@ -131,19 +132,19 @@ class PageController extends Controller
         ]);
 
         $input = $request->all();
-        $draftPage = $this->entityRepo->getById('page', $pageId, true);
+        $draftPage = $this->pageRepo->getById('page', $pageId, true);
         $book = $draftPage->book;
 
         $parent = $draftPage->parent;
         $this->checkOwnablePermission('page-create', $parent);
 
         if ($parent->isA('chapter')) {
-            $input['priority'] = $this->entityRepo->getNewChapterPriority($parent);
+            $input['priority'] = $this->pageRepo->getNewChapterPriority($parent);
         } else {
-            $input['priority'] = $this->entityRepo->getNewBookPriority($parent);
+            $input['priority'] = $this->pageRepo->getNewBookPriority($parent);
         }
 
-        $page = $this->entityRepo->publishPageDraft($draftPage, $input);
+        $page = $this->pageRepo->publishPageDraft($draftPage, $input);
 
         Activity::add($page, 'page_create', $book->id);
         return redirect($page->getUrl());
@@ -160,9 +161,9 @@ class PageController extends Controller
     public function show($bookSlug, $pageSlug)
     {
         try {
-            $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+            $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         } catch (NotFoundException $e) {
-            $page = $this->entityRepo->getPageByOldSlug($pageSlug, $bookSlug);
+            $page = $this->pageRepo->getPageByOldSlug($pageSlug, $bookSlug);
             if ($page === null) {
                 throw $e;
             }
@@ -171,9 +172,9 @@ class PageController extends Controller
 
         $this->checkOwnablePermission('page-view', $page);
 
-        $page->html = $this->entityRepo->renderPage($page);
-        $sidebarTree = $this->entityRepo->getBookChildren($page->book);
-        $pageNav = $this->entityRepo->getPageNav($page->html);
+        $page->html = $this->pageRepo->renderPage($page);
+        $sidebarTree = $this->pageRepo->getBookChildren($page->book);
+        $pageNav = $this->pageRepo->getPageNav($page->html);
 
         // check if the comment's are enabled
         $commentsEnabled = !setting('app-disable-comments');
@@ -199,7 +200,7 @@ class PageController extends Controller
      */
     public function getPageAjax($pageId)
     {
-        $page = $this->entityRepo->getById('page', $pageId);
+        $page = $this->pageRepo->getById('page', $pageId);
         return response()->json($page);
     }
 
@@ -208,28 +209,29 @@ class PageController extends Controller
      * @param string $bookSlug
      * @param string $pageSlug
      * @return Response
+     * @throws NotFoundException
      */
     public function edit($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('page-update', $page);
         $this->setPageTitle(trans('entities.pages_editing_named', ['pageName'=>$page->getShortName()]));
         $page->isDraft = false;
 
         // Check for active editing
         $warnings = [];
-        if ($this->entityRepo->isPageEditingActive($page, 60)) {
-            $warnings[] = $this->entityRepo->getPageEditingActiveMessage($page, 60);
+        if ($this->pageRepo->isPageEditingActive($page, 60)) {
+            $warnings[] = $this->pageRepo->getPageEditingActiveMessage($page, 60);
         }
 
         // Check for a current draft version for this user
-        if ($this->entityRepo->hasUserGotPageDraft($page, $this->currentUser->id)) {
-            $draft = $this->entityRepo->getUserPageDraft($page, $this->currentUser->id);
-            $page->name = $draft->name;
-            $page->html = $draft->html;
-            $page->markdown = $draft->markdown;
+        $userPageDraft = $this->pageRepo->getUserPageDraft($page, $this->currentUser->id);
+        if ($userPageDraft !== null) {
+            $page->name = $userPageDraft->name;
+            $page->html = $userPageDraft->html;
+            $page->markdown = $userPageDraft->markdown;
             $page->isDraft = true;
-            $warnings [] = $this->entityRepo->getUserPageDraftMessage($draft);
+            $warnings [] = $this->pageRepo->getUserPageDraftMessage($userPageDraft);
         }
 
         if (count($warnings) > 0) {
@@ -257,9 +259,9 @@ class PageController extends Controller
         $this->validate($request, [
             'name' => 'required|string|max:255'
         ]);
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('page-update', $page);
-        $this->entityRepo->updatePage($page, $page->book->id, $request->all());
+        $this->pageRepo->updatePage($page, $page->book->id, $request->all());
         Activity::add($page, 'page_update', $page->book->id);
         return redirect($page->getUrl());
     }
@@ -272,7 +274,7 @@ class PageController extends Controller
      */
     public function saveDraft(Request $request, $pageId)
     {
-        $page = $this->entityRepo->getById('page', $pageId, true);
+        $page = $this->pageRepo->getById('page', $pageId, true);
         $this->checkOwnablePermission('page-update', $page);
 
         if (!$this->signedIn) {
@@ -282,7 +284,7 @@ class PageController extends Controller
             ], 500);
         }
 
-        $draft = $this->entityRepo->updatePageDraft($page, $request->only(['name', 'html', 'markdown']));
+        $draft = $this->pageRepo->updatePageDraft($page, $request->only(['name', 'html', 'markdown']));
 
         $updateTime = $draft->updated_at->timestamp;
         return response()->json([
@@ -300,7 +302,7 @@ class PageController extends Controller
      */
     public function redirectFromLink($pageId)
     {
-        $page = $this->entityRepo->getById('page', $pageId);
+        $page = $this->pageRepo->getById('page', $pageId);
         return redirect($page->getUrl());
     }
 
@@ -312,7 +314,7 @@ class PageController extends Controller
      */
     public function showDelete($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('page-delete', $page);
         $this->setPageTitle(trans('entities.pages_delete_named', ['pageName'=>$page->getShortName()]));
         return view('pages/delete', ['book' => $page->book, 'page' => $page, 'current' => $page]);
@@ -328,7 +330,7 @@ class PageController extends Controller
      */
     public function showDeleteDraft($bookSlug, $pageId)
     {
-        $page = $this->entityRepo->getById('page', $pageId, true);
+        $page = $this->pageRepo->getById('page', $pageId, true);
         $this->checkOwnablePermission('page-update', $page);
         $this->setPageTitle(trans('entities.pages_delete_draft_named', ['pageName'=>$page->getShortName()]));
         return view('pages/delete', ['book' => $page->book, 'page' => $page, 'current' => $page]);
@@ -343,10 +345,10 @@ class PageController extends Controller
      */
     public function destroy($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $book = $page->book;
         $this->checkOwnablePermission('page-delete', $page);
-        $this->entityRepo->destroyPage($page);
+        $this->pageRepo->destroyPage($page);
 
         Activity::addMessage('page_delete', $book->id, $page->name);
         session()->flash('success', trans('entities.pages_delete_success'));
@@ -362,11 +364,11 @@ class PageController extends Controller
      */
     public function destroyDraft($bookSlug, $pageId)
     {
-        $page = $this->entityRepo->getById('page', $pageId, true);
+        $page = $this->pageRepo->getById('page', $pageId, true);
         $book = $page->book;
         $this->checkOwnablePermission('page-update', $page);
         session()->flash('success', trans('entities.pages_delete_draft_success'));
-        $this->entityRepo->destroyPage($page);
+        $this->pageRepo->destroyPage($page);
         return redirect($book->getUrl());
     }
 
@@ -378,7 +380,7 @@ class PageController extends Controller
      */
     public function showRevisions($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->setPageTitle(trans('entities.pages_revisions_named', ['pageName'=>$page->getShortName()]));
         return view('pages/revisions', ['page' => $page, 'book' => $page->book, 'current' => $page]);
     }
@@ -392,7 +394,7 @@ class PageController extends Controller
      */
     public function showRevision($bookSlug, $pageSlug, $revisionId)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $revision = $page->revisions()->where('id', '=', $revisionId)->first();
         if ($revision === null) {
             abort(404);
@@ -417,7 +419,7 @@ class PageController extends Controller
      */
     public function showRevisionChanges($bookSlug, $pageSlug, $revisionId)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $revision = $page->revisions()->where('id', '=', $revisionId)->first();
         if ($revision === null) {
             abort(404);
@@ -447,9 +449,9 @@ class PageController extends Controller
      */
     public function restoreRevision($bookSlug, $pageSlug, $revisionId)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('page-update', $page);
-        $page = $this->entityRepo->restorePageRevision($page, $page->book, $revisionId);
+        $page = $this->pageRepo->restorePageRevision($page, $page->book, $revisionId);
         Activity::add($page, 'page_restore', $page->book->id);
         return redirect($page->getUrl());
     }
@@ -466,7 +468,7 @@ class PageController extends Controller
      */
     public function destroyRevision($bookSlug, $pageSlug, $revId)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('page-delete', $page);
 
         $revision = $page->revisions()->where('id', '=', $revId)->first();
@@ -497,8 +499,8 @@ class PageController extends Controller
      */
     public function exportPdf($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
-        $page->html = $this->entityRepo->renderPage($page);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
+        $page->html = $this->pageRepo->renderPage($page);
         $pdfContent = $this->exportService->pageToPdf($page);
         return $this->downloadResponse($pdfContent, $pageSlug . '.pdf');
     }
@@ -511,8 +513,8 @@ class PageController extends Controller
      */
     public function exportHtml($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
-        $page->html = $this->entityRepo->renderPage($page);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
+        $page->html = $this->pageRepo->renderPage($page);
         $containedHtml = $this->exportService->pageToContainedHtml($page);
         return $this->downloadResponse($containedHtml, $pageSlug . '.html');
     }
@@ -525,7 +527,7 @@ class PageController extends Controller
      */
     public function exportPlainText($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $pageText = $this->exportService->pageToPlainText($page);
         return $this->downloadResponse($pageText, $pageSlug . '.txt');
     }
@@ -536,7 +538,7 @@ class PageController extends Controller
      */
     public function showRecentlyCreated()
     {
-        $pages = $this->entityRepo->getRecentlyCreatedPaginated('page', 20)->setPath(baseUrl('/pages/recently-created'));
+        $pages = $this->pageRepo->getRecentlyCreatedPaginated('page', 20)->setPath(baseUrl('/pages/recently-created'));
         return view('pages/detailed-listing', [
             'title' => trans('entities.recently_created_pages'),
             'pages' => $pages
@@ -549,7 +551,7 @@ class PageController extends Controller
      */
     public function showRecentlyUpdated()
     {
-        $pages = $this->entityRepo->getRecentlyUpdatedPaginated('page', 20)->setPath(baseUrl('/pages/recently-updated'));
+        $pages = $this->pageRepo->getRecentlyUpdatedPaginated('page', 20)->setPath(baseUrl('/pages/recently-updated'));
         return view('pages/detailed-listing', [
             'title' => trans('entities.recently_updated_pages'),
             'pages' => $pages
@@ -564,7 +566,7 @@ class PageController extends Controller
      */
     public function showRestrict($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('restrictions-manage', $page);
         $roles = $this->userRepo->getRestrictableRoles();
         return view('pages/restrictions', [
@@ -582,7 +584,7 @@ class PageController extends Controller
      */
     public function showMove($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('page-update', $page);
         return view('pages/move', [
             'book' => $page->book,
@@ -600,7 +602,7 @@ class PageController extends Controller
      */
     public function move($bookSlug, $pageSlug, Request $request)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('page-update', $page);
 
         $entitySelection = $request->get('entity_selection', null);
@@ -614,7 +616,7 @@ class PageController extends Controller
 
 
         try {
-            $parent = $this->entityRepo->getById($entityType, $entityId);
+            $parent = $this->pageRepo->getById($entityType, $entityId);
         } catch (\Exception $e) {
             session()->flash(trans('entities.selected_book_chapter_not_found'));
             return redirect()->back();
@@ -622,7 +624,7 @@ class PageController extends Controller
 
         $this->checkOwnablePermission('page-create', $parent);
 
-        $this->entityRepo->changePageParent($page, $parent);
+        $this->pageRepo->changePageParent($page, $parent);
         Activity::add($page, 'page_move', $page->book->id);
         session()->flash('success', trans('entities.pages_move_success', ['parentName' => $parent->name]));
 
@@ -638,7 +640,7 @@ class PageController extends Controller
      */
     public function showCopy($bookSlug, $pageSlug)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('page-update', $page);
         session()->flashInput(['name' => $page->name]);
         return view('pages/copy', [
@@ -657,7 +659,7 @@ class PageController extends Controller
      */
     public function copy($bookSlug, $pageSlug, Request $request)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('page-update', $page);
 
         $entitySelection = $request->get('entity_selection', null);
@@ -669,7 +671,7 @@ class PageController extends Controller
             $entityId = intval($stringExploded[1]);
 
             try {
-                $parent = $this->entityRepo->getById($entityType, $entityId);
+                $parent = $this->pageRepo->getById($entityType, $entityId);
             } catch (\Exception $e) {
                 session()->flash(trans('entities.selected_book_chapter_not_found'));
                 return redirect()->back();
@@ -678,7 +680,7 @@ class PageController extends Controller
 
         $this->checkOwnablePermission('page-create', $parent);
 
-        $pageCopy = $this->entityRepo->copyPage($page, $parent, $request->get('name', ''));
+        $pageCopy = $this->pageRepo->copyPage($page, $parent, $request->get('name', ''));
 
         Activity::add($pageCopy, 'page_create', $pageCopy->book->id);
         session()->flash('success', trans('entities.pages_copy_success'));
@@ -696,9 +698,9 @@ class PageController extends Controller
      */
     public function restrict($bookSlug, $pageSlug, Request $request)
     {
-        $page = $this->entityRepo->getBySlug('page', $pageSlug, $bookSlug);
+        $page = $this->pageRepo->getPageBySlug($pageSlug, $bookSlug);
         $this->checkOwnablePermission('restrictions-manage', $page);
-        $this->entityRepo->updateEntityPermissionsFromRequest($request, $page);
+        $this->pageRepo->updateEntityPermissionsFromRequest($request, $page);
         session()->flash('success', trans('entities.pages_permissions_success'));
         return redirect($page->getUrl());
     }
index 5695705d02b6b1e934a4a3a0b5872f13aa3cd973..9be343c9a76011a5bd5b7a872ad78b1e6a9a8d3c 100644 (file)
@@ -1,7 +1,7 @@
 <?php namespace BookStack\Http\Controllers;
 
+use BookStack\Auth\Permissions\PermissionsRepo;
 use BookStack\Exceptions\PermissionsException;
-use BookStack\Repos\PermissionsRepo;
 use Illuminate\Http\Request;
 
 class PermissionController extends Controller
@@ -11,7 +11,7 @@ class PermissionController extends Controller
 
     /**
      * PermissionController constructor.
-     * @param PermissionsRepo $permissionsRepo
+     * @param \BookStack\Auth\Permissions\PermissionsRepo $permissionsRepo
      */
     public function __construct(PermissionsRepo $permissionsRepo)
     {
index 49f9885adb24c1bb438f5b95f6cd20fd0f7937a7..d8f2dc4d7eac6a1eec6e7f0a584b893f4a32c9a7 100644 (file)
@@ -1,8 +1,8 @@
 <?php namespace BookStack\Http\Controllers;
 
-use BookStack\Repos\EntityRepo;
-use BookStack\Services\SearchService;
-use BookStack\Services\ViewService;
+use BookStack\Actions\ViewService;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Entities\SearchService;
 use Illuminate\Http\Request;
 
 class SearchController extends Controller
@@ -13,7 +13,7 @@ class SearchController extends Controller
 
     /**
      * SearchController constructor.
-     * @param EntityRepo $entityRepo
+     * @param \BookStack\Entities\Repos\EntityRepo $entityRepo
      * @param ViewService $viewService
      * @param SearchService $searchService
      */
@@ -97,7 +97,7 @@ class SearchController extends Controller
             $entities = $this->searchService->searchEntities($searchTerm, 'all', 1, 20, $permission)['results'];
         } else {
             $entityNames = $entityTypes->map(function ($type) {
-                return 'BookStack\\' . ucfirst($type);
+                return 'BookStack\\' . ucfirst($type); // TODO - Extract this elsewhere, too specific and stringy
             })->toArray();
             $entities = $this->viewService->getPopular(20, 0, $entityNames, $permission);
         }
index d9d66042e19ba0bc998d0b74e14b0855b14ff4be..01fb68fe06e509908bd863671eddf0f2c94ba323 100644 (file)
@@ -1,6 +1,6 @@
 <?php namespace BookStack\Http\Controllers;
 
-use BookStack\Services\ImageService;
+use BookStack\Uploads\ImageService;
 use Illuminate\Http\Request;
 use Illuminate\Http\Response;
 use Setting;
index 815d9e8d5c87936d168baf406be87772a6fc3ba1..6abbeeebaa451e437e8b150a2ae496f15fe37827 100644 (file)
@@ -1,6 +1,6 @@
 <?php namespace BookStack\Http\Controllers;
 
-use BookStack\Repos\TagRepo;
+use BookStack\Actions\TagRepo;
 use Illuminate\Http\Request;
 
 class TagController extends Controller
index f6bd13e6f7de8bd15de6505821460355ade582a4..5f5c8365eecc34de70ef0dae569f2c20406a79e2 100644 (file)
@@ -1,11 +1,10 @@
 <?php namespace BookStack\Http\Controllers;
 
-use Exception;
+use BookStack\Auth\Access\SocialAuthService;
+use BookStack\Auth\User;
+use BookStack\Auth\UserRepo;
 use Illuminate\Http\Request;
 use Illuminate\Http\Response;
-use BookStack\Repos\UserRepo;
-use BookStack\Services\SocialAuthService;
-use BookStack\User;
 
 class UserController extends Controller
 {
@@ -16,7 +15,7 @@ class UserController extends Controller
     /**
      * UserController constructor.
      * @param User     $user
-     * @param UserRepo $userRepo
+     * @param \BookStack\Auth\UserRepo $userRepo
      */
     public function __construct(User $user, UserRepo $userRepo)
     {
@@ -101,7 +100,7 @@ class UserController extends Controller
     /**
      * Show the form for editing the specified user.
      * @param  int              $id
-     * @param SocialAuthService $socialAuthService
+     * @param \BookStack\Auth\Access\SocialAuthService $socialAuthService
      * @return Response
      */
     public function edit($id, SocialAuthService $socialAuthService)
index c3102571da2b0d515f87a7c5f42e2373c306c7b2..73c11a82769d861ed0ab1793bd7eb7473466d74b 100644 (file)
@@ -3,8 +3,8 @@
 namespace BookStack\Http\Middleware;
 
 use Closure;
-use Illuminate\Http\Request;
 use Fideloper\Proxy\TrustProxies as Middleware;
+use Illuminate\Http\Request;
 
 class TrustProxies extends Middleware
 {
index 858b12166be9411ed28fe047c739b304f9da9152..f3797e6e228874559439de231fba034fd48d45af 100644 (file)
@@ -3,9 +3,9 @@
 namespace BookStack\Notifications;
 
 use Illuminate\Bus\Queueable;
-use Illuminate\Notifications\Notification;
 use Illuminate\Contracts\Queue\ShouldQueue;
 use Illuminate\Notifications\Messages\MailMessage;
+use Illuminate\Notifications\Notification;
 
 class ConfirmEmail extends Notification implements ShouldQueue
 {
index affd8f07638330d2bc70acfbceb8e2c0150c2980..86e93228f857a64ed5965126cfd0958180665fba 100644 (file)
@@ -2,8 +2,8 @@
 
 namespace BookStack\Notifications;
 
-use Illuminate\Notifications\Notification;
 use Illuminate\Notifications\Messages\MailMessage;
+use Illuminate\Notifications\Notification;
 
 class ResetPassword extends Notification
 {
index fe58e05ed4843121cea591b36d8028ca44460206..e660a0500de165cbc7233bacf3bf9e3b65f9debf 100644 (file)
@@ -1,5 +1,7 @@
 <?php namespace BookStack;
 
+use BookStack\Auth\User;
+
 abstract class Ownable extends Model
 {
     /**
index b06b2f3a25b992322b8172e110f0ecd3ef447cab..6fa0f9a5215b7c27dd0baadbda4e044c3b24fb29 100644 (file)
@@ -1,8 +1,15 @@
 <?php namespace BookStack\Providers;
 
-use BookStack\Services\SettingService;
-use BookStack\Setting;
+use Blade;
+use BookStack\Entities\Book;
+use BookStack\Entities\Bookshelf;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Page;
+use BookStack\Settings\Setting;
+use BookStack\Settings\SettingService;
+use Illuminate\Database\Eloquent\Relations\Relation;
 use Illuminate\Support\ServiceProvider;
+use Schema;
 use Validator;
 
 class AppServiceProvider extends ServiceProvider
@@ -20,12 +27,21 @@ class AppServiceProvider extends ServiceProvider
             return in_array($value->getMimeType(), $imageMimes);
         });
 
-        \Blade::directive('icon', function ($expression) {
+        // Custom blade view directives
+        Blade::directive('icon', function ($expression) {
             return "<?php echo icon($expression); ?>";
         });
 
         // Allow longer string lengths after upgrade to utf8mb4
-        \Schema::defaultStringLength(191);
+        Schema::defaultStringLength(191);
+
+        // Set morph-map due to namespace changes
+        Relation::morphMap([
+            'BookStack\\Bookshelf' => Bookshelf::class,
+            'BookStack\\Book' => Book::class,
+            'BookStack\\Chapter' => Chapter::class,
+            'BookStack\\Page' => Page::class,
+        ]);
     }
 
     /**
index d1fac56e677ff968896b6ce60df441da91b13c91..6e5b6ffde7ca10274b1beef274f2e06cd7283472 100644 (file)
@@ -3,7 +3,7 @@
 namespace BookStack\Providers;
 
 use Auth;
-use BookStack\Services\LdapService;
+use BookStack\Auth\Access\LdapService;
 use Illuminate\Support\ServiceProvider;
 
 class AuthServiceProvider extends ServiceProvider
index 11e3cc6d2cc24c203d057514e44ed3738c33a760..69925e945e82e6eda9dd6d3b3b7e8c75ed6da541 100644 (file)
@@ -3,7 +3,6 @@
 namespace BookStack\Providers;
 
 use Illuminate\Support\ServiceProvider;
-use Illuminate\Support\Facades\Broadcast;
 
 class BroadcastServiceProvider extends ServiceProvider
 {
index c81a5529d8d6d95e842b799adf007aca9ba34727..98b242d219f7bac8d2f8ef6403d3f04dfd88067d 100644 (file)
@@ -2,18 +2,18 @@
 
 namespace BookStack\Providers;
 
-use BookStack\Activity;
-use BookStack\Image;
-use BookStack\Services\ImageService;
-use BookStack\Services\PermissionService;
-use BookStack\Services\ViewService;
-use BookStack\Setting;
-use BookStack\View;
+use BookStack\Actions\Activity;
+use BookStack\Actions\ActivityService;
+use BookStack\Actions\View;
+use BookStack\Actions\ViewService;
+use BookStack\Auth\Permissions\PermissionService;
+use BookStack\Settings\Setting;
+use BookStack\Settings\SettingService;
+use BookStack\Uploads\Image;
+use BookStack\Uploads\ImageService;
 use Illuminate\Contracts\Cache\Repository;
 use Illuminate\Contracts\Filesystem\Factory;
 use Illuminate\Support\ServiceProvider;
-use BookStack\Services\ActivityService;
-use BookStack\Services\SettingService;
 use Intervention\Image\ImageManager;
 
 class CustomFacadeProvider extends ServiceProvider
index 00eeb036c177513e190c9212fd5321760d3c53fb..a826185d82de7bdfa49a7db17bbd9b4ac6c3c84b 100644 (file)
@@ -2,7 +2,6 @@
 
 namespace BookStack\Providers;
 
-use Illuminate\Contracts\Events\Dispatcher as DispatcherContract;
 use Illuminate\Foundation\Support\Providers\EventServiceProvider as ServiceProvider;
 use SocialiteProviders\Manager\SocialiteWasCalled;
 
index 1dc789c3b3bc513c770e514eaf7fbdef42f0b2bb..9c91def2f1f55b650b845f5913fa3563f47092e3 100644 (file)
@@ -2,9 +2,7 @@
 
 namespace BookStack\Providers;
 
-use BookStack\Role;
-use BookStack\Services\LdapService;
-use BookStack\User;
+use BookStack\Auth\Access\LdapService;
 use Illuminate\Contracts\Auth\Authenticatable;
 use Illuminate\Contracts\Auth\UserProvider;
 
@@ -19,7 +17,7 @@ class LdapUserProvider implements UserProvider
     protected $model;
 
     /**
-     * @var LdapService
+     * @var \BookStack\Auth\LdapService
      */
     protected $ldapService;
 
@@ -27,7 +25,7 @@ class LdapUserProvider implements UserProvider
     /**
      * LdapUserProvider constructor.
      * @param             $model
-     * @param LdapService $ldapService
+     * @param \BookStack\Auth\LdapService $ldapService
      */
     public function __construct($model, LdapService $ldapService)
     {
index 88ab23526e6c54aae08b992909859109e3e31e5b..c4c39d5345fa74b80631c7e737e4f928407f32a9 100644 (file)
@@ -2,7 +2,6 @@
 
 namespace BookStack\Providers;
 
-use Illuminate\Routing\Router;
 use Illuminate\Foundation\Support\Providers\RouteServiceProvider as ServiceProvider;
 use Route;
 
similarity index 68%
rename from app/Setting.php
rename to app/Settings/Setting.php
index 0af3652db628dec19cff86439e5ffa0544aff5bd..1a52920eeb73cc6c88e78ad7ec68961ddd30e8cf 100644 (file)
@@ -1,4 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Settings;
+
+use BookStack\Model;
 
 class Setting extends Model
 {
similarity index 97%
rename from app/Services/SettingService.php
rename to app/Settings/SettingService.php
index 7ec3ef93aee582afb74f6faadf997b0cff199c9d..c903bd60a5dc4b811bcf2604965aa3692d020382 100644 (file)
@@ -1,7 +1,5 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Settings;
 
-use BookStack\Setting;
-use BookStack\User;
 use Illuminate\Contracts\Cache\Repository as Cache;
 
 /**
@@ -55,7 +53,7 @@ class SettingService
 
     /**
      * Get a user-specific setting from the database or cache.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @param $key
      * @param bool $default
      * @return bool|string
@@ -174,7 +172,7 @@ class SettingService
 
     /**
      * Put a user-specific setting into the database.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @param $key
      * @param $value
      * @return bool
similarity index 84%
rename from app/Attachment.php
rename to app/Uploads/Attachment.php
index 6749130d9686268dde0ee1299d03d26284a70687..eb9a0fe68e02b60eb605911e12d6c8ca40e3fa87 100644 (file)
@@ -1,4 +1,7 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Uploads;
+
+use BookStack\Entities\Page;
+use BookStack\Ownable;
 
 class Attachment extends Ownable
 {
@@ -18,7 +21,7 @@ class Attachment extends Ownable
 
     /**
      * Get the page this file was uploaded to.
-     * @return Page
+     * @return \Illuminate\Database\Eloquent\Relations\BelongsTo
      */
     public function page()
     {
similarity index 99%
rename from app/Services/AttachmentService.php
rename to app/Uploads/AttachmentService.php
index 3a6f95dcc7aa7f84d4520e32ab1e697695c2ce69..7bafb6c0a26c050daab630a7f9ff692044708725 100644 (file)
@@ -1,7 +1,6 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Uploads;
 
 use BookStack\Exceptions\FileUploadException;
-use BookStack\Attachment;
 use Exception;
 use Symfony\Component\HttpFoundation\File\UploadedFile;
 
similarity index 88%
rename from app/Image.php
rename to app/Uploads/Image.php
index acc82df90a1ec7fcb572dcf3c636499c9ba5b94e..df6d9fb0d151ef00cd8c579bdccc3891e3626974 100644 (file)
@@ -1,5 +1,6 @@
-<?php namespace BookStack;
+<?php namespace BookStack\Uploads;
 
+use BookStack\Ownable;
 use Images;
 
 class Image extends Ownable
similarity index 96%
rename from app/Repos/ImageRepo.php
rename to app/Uploads/ImageRepo.php
index 4ccd719ade8a3e5a54738aa528c076b9a1cc7728..0ef8cad48020dcd8314b19669e9a3f4e2567eb4e 100644 (file)
@@ -1,9 +1,7 @@
-<?php namespace BookStack\Repos;
+<?php namespace BookStack\Uploads;
 
-use BookStack\Image;
-use BookStack\Page;
-use BookStack\Services\ImageService;
-use BookStack\Services\PermissionService;
+use BookStack\Auth\Permissions\PermissionService;
+use BookStack\Entities\Page;
 use Symfony\Component\HttpFoundation\File\UploadedFile;
 
 class ImageRepo
@@ -18,8 +16,8 @@ class ImageRepo
      * ImageRepo constructor.
      * @param Image $image
      * @param ImageService $imageService
-     * @param PermissionService $permissionService
-     * @param Page $page
+     * @param \BookStack\Auth\Permissions\PermissionService $permissionService
+     * @param \BookStack\Entities\Page $page
      */
     public function __construct(Image $image, ImageService $imageService, PermissionService $permissionService, Page $page)
     {
similarity index 99%
rename from app/Services/ImageService.php
rename to app/Uploads/ImageService.php
index 7b73c457c08ec76e5d490e1971b7bb1e230b8189..f109db60068f5b919509a450df371bc8bd50eeee 100644 (file)
@@ -1,14 +1,13 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Uploads;
 
+use BookStack\Auth\User;
 use BookStack\Exceptions\ImageUploadException;
-use BookStack\Image;
-use BookStack\User;
 use DB;
 use Exception;
+use Illuminate\Contracts\Cache\Repository as Cache;
+use Illuminate\Contracts\Filesystem\Factory as FileSystem;
 use Intervention\Image\Exception\NotSupportedException;
 use Intervention\Image\ImageManager;
-use Illuminate\Contracts\Filesystem\Factory as FileSystem;
-use Illuminate\Contracts\Cache\Repository as Cache;
 use Symfony\Component\HttpFoundation\File\UploadedFile;
 
 class ImageService extends UploadService
@@ -281,7 +280,7 @@ class ImageService extends UploadService
 
     /**
      * Save a gravatar image and set a the profile image for a user.
-     * @param User $user
+     * @param \BookStack\Auth\User $user
      * @param int $size
      * @return mixed
      * @throws Exception
similarity index 93%
rename from app/Services/UploadService.php
rename to app/Uploads/UploadService.php
index df597a40fef5dbcb79bac610caabf8528ae0d525..292e61e30ab1a0c0aebdf934a4a69999d9149dff 100644 (file)
@@ -1,9 +1,9 @@
-<?php namespace BookStack\Services;
+<?php namespace BookStack\Uploads;
 
 use Illuminate\Contracts\Filesystem\Factory as FileSystem;
 use Illuminate\Contracts\Filesystem\Filesystem as FileSystemInstance;
 
-class UploadService
+abstract class UploadService
 {
 
     /**
index 4c0521d3a0c65c71785dc065ef834ec3956e631b..aca832ea51656434c84079069ef35da4747051a0 100644 (file)
@@ -30,11 +30,11 @@ function versioned_asset($file = '')
 /**
  * Helper method to get the current User.
  * Defaults to public 'Guest' user if not logged in.
- * @return \BookStack\User
+ * @return \BookStack\Auth\User
  */
 function user()
 {
-    return auth()->user() ?: \BookStack\User::getDefault();
+    return auth()->user() ?: \BookStack\Auth\User::getDefault();
 }
 
 /**
@@ -61,7 +61,7 @@ function userCan($permission, Ownable $ownable = null)
     }
 
     // Check permission on ownable item
-    $permissionService = app(\BookStack\Services\PermissionService::class);
+    $permissionService = app(\BookStack\Auth\Permissions\PermissionService::class);
     return $permissionService->checkOwnableUserAccess($ownable, $permission);
 }
 
@@ -69,11 +69,11 @@ function userCan($permission, Ownable $ownable = null)
  * Helper to access system settings.
  * @param $key
  * @param bool $default
- * @return bool|string|\BookStack\Services\SettingService
+ * @return bool|string|\BookStack\Settings\SettingService
  */
 function setting($key = null, $default = false)
 {
-    $settingService = resolve(\BookStack\Services\SettingService::class);
+    $settingService = resolve(\BookStack\Settings\SettingService::class);
     if (is_null($key)) {
         return $settingService;
     }
index 9b5ac2f8c025f0b1dfd558c1ab59ffa1fc49e2d1..7529697faf700a797a9d9b2bd00dc487a3ab9d27 100755 (executable)
@@ -274,10 +274,10 @@ return [
          * Custom
          */
 
-        'Activity' => BookStack\Services\Facades\Activity::class,
-        'Setting'  => BookStack\Services\Facades\Setting::class,
-        'Views'    => BookStack\Services\Facades\Views::class,
-        'Images'   => BookStack\Services\Facades\Images::class,
+        'Activity' => BookStack\Facades\Activity::class,
+        'Setting'  => BookStack\Facades\Setting::class,
+        'Views'    => BookStack\Facades\Views::class,
+        'Images'   => BookStack\Facades\Images::class,
 
     ],
 
index ceeab5c71d88aecd074316f77f7fdf589e89a3a0..f0e699809a99fe1c722b8a1bc20a7cc78774ade4 100644 (file)
@@ -70,7 +70,7 @@ return [
     'providers' => [
         'users' => [
             'driver' => env('AUTH_METHOD', 'standard') === 'standard' ? 'eloquent' : env('AUTH_METHOD'),
-            'model' => BookStack\User::class,
+            'model' => \BookStack\Auth\User::class,
         ],
 
         // 'users' => [
index 2b0f260cde6b40b8653947626fc19ff37e0a2658..711040386a9ac17c954ad694ac3aece8b11a06de 100644 (file)
@@ -38,7 +38,7 @@ return [
     ],
 
     'stripe'   => [
-        'model'  => BookStack\User::class,
+        'model'  => \BookStack\Auth\User::class,
         'key'    => '',
         'secret' => '',
     ],
index 3d6ed1d633301d36eda41636bf0d7eac563be8bc..de6b0b276899b976afd5f78235a6b5d7ec803f75 100644 (file)
@@ -11,7 +11,7 @@
 |
 */
 
-$factory->define(BookStack\User::class, function ($faker) {
+$factory->define(\BookStack\Auth\User::class, function ($faker) {
     return [
         'name' => $faker->name,
         'email' => $faker->email,
@@ -21,7 +21,7 @@ $factory->define(BookStack\User::class, function ($faker) {
     ];
 });
 
-$factory->define(BookStack\Bookshelf::class, function ($faker) {
+$factory->define(\BookStack\Entities\Bookshelf::class, function ($faker) {
     return [
         'name' => $faker->sentence,
         'slug' => str_random(10),
@@ -29,7 +29,7 @@ $factory->define(BookStack\Bookshelf::class, function ($faker) {
     ];
 });
 
-$factory->define(BookStack\Book::class, function ($faker) {
+$factory->define(\BookStack\Entities\Book::class, function ($faker) {
     return [
         'name' => $faker->sentence,
         'slug' => str_random(10),
@@ -37,7 +37,7 @@ $factory->define(BookStack\Book::class, function ($faker) {
     ];
 });
 
-$factory->define(BookStack\Chapter::class, function ($faker) {
+$factory->define(\BookStack\Entities\Chapter::class, function ($faker) {
     return [
         'name' => $faker->sentence,
         'slug' => str_random(10),
@@ -45,7 +45,7 @@ $factory->define(BookStack\Chapter::class, function ($faker) {
     ];
 });
 
-$factory->define(BookStack\Page::class, function ($faker) {
+$factory->define(\BookStack\Entities\Page::class, function ($faker) {
     $html = '<p>' . implode('</p>', $faker->paragraphs(5)) . '</p>';
     return [
         'name' => $faker->sentence,
@@ -56,21 +56,21 @@ $factory->define(BookStack\Page::class, function ($faker) {
     ];
 });
 
-$factory->define(BookStack\Role::class, function ($faker) {
+$factory->define(\BookStack\Auth\Role::class, function ($faker) {
     return [
         'display_name' => $faker->sentence(3),
         'description' => $faker->sentence(10)
     ];
 });
 
-$factory->define(BookStack\Tag::class, function ($faker) {
+$factory->define(\BookStack\Actions\Tag::class, function ($faker) {
     return [
         'name' => $faker->city,
         'value' => $faker->sentence(3)
     ];
 });
 
-$factory->define(BookStack\Image::class, function ($faker) {
+$factory->define(\BookStack\Uploads\Image::class, function ($faker) {
     return [
         'name' => $faker->slug . '.jpg',
         'url' => $faker->url,
@@ -80,7 +80,7 @@ $factory->define(BookStack\Image::class, function ($faker) {
     ];
 });
 
-$factory->define(BookStack\Comment::class, function($faker) {
+$factory->define(\BookStack\Actions\Comment::class, function($faker) {
     $text = $faker->paragraph(1);
     $html = '<p>' . $text. '</p>';
     return [
index eed937611485d14f0c2c97c37058a510bf2054f9..515bc9d8df7e86fcfd5e5640dbe2b6afbd77f5c3 100644 (file)
@@ -1,6 +1,6 @@
 <?php
 
-use BookStack\Image;
+use BookStack\Uploads\Image;
 use Illuminate\Database\Schema\Blueprint;
 use Illuminate\Database\Migrations\Migration;
 
index e4dca8c0b00a41460c6080aad2e60803ac6b5f63..eab3216bbdfa6cc02e2b180ff094683a73f5cfdd 100644 (file)
@@ -119,11 +119,11 @@ class CreateBookshelvesTable extends Migration
         Schema::dropIfExists('bookshelves');
 
         // Drop related polymorphic items
-        DB::table('activities')->where('entity_type', '=', 'BookStack\Bookshelf')->delete();
-        DB::table('views')->where('viewable_type', '=', 'BookStack\Bookshelf')->delete();
-        DB::table('entity_permissions')->where('restrictable_type', '=', 'BookStack\Bookshelf')->delete();
-        DB::table('tags')->where('entity_type', '=', 'BookStack\Bookshelf')->delete();
-        DB::table('search_terms')->where('entity_type', '=', 'BookStack\Bookshelf')->delete();
-        DB::table('comments')->where('entity_type', '=', 'BookStack\Bookshelf')->delete();
+        DB::table('activities')->where('entity_type', '=', 'BookStack\Entities\Bookshelf')->delete();
+        DB::table('views')->where('viewable_type', '=', 'BookStack\Entities\Bookshelf')->delete();
+        DB::table('entity_permissions')->where('restrictable_type', '=', 'BookStack\Entities\Bookshelf')->delete();
+        DB::table('tags')->where('entity_type', '=', 'BookStack\Entities\Bookshelf')->delete();
+        DB::table('search_terms')->where('entity_type', '=', 'BookStack\Entities\Bookshelf')->delete();
+        DB::table('comments')->where('entity_type', '=', 'BookStack\Entities\Bookshelf')->delete();
     }
 }
index dcf5893529435e219cde412e415d7c7e25f9dbb1..ce3cd1307d6f5279f0f1a37ee830bd5d7c661a80 100644 (file)
@@ -12,39 +12,39 @@ class DummyContentSeeder extends Seeder
     public function run()
     {
         // Create an editor user
-        $editorUser = factory(\BookStack\User::class)->create();
-        $editorRole = \BookStack\Role::getRole('editor');
+        $editorUser = factory(\BookStack\Auth\User::class)->create();
+        $editorRole = \BookStack\Auth\Role::getRole('editor');
         $editorUser->attachRole($editorRole);
 
         // Create a viewer user
-        $viewerUser = factory(\BookStack\User::class)->create();
-        $role = \BookStack\Role::getRole('viewer');
+        $viewerUser = factory(\BookStack\Auth\User::class)->create();
+        $role = \BookStack\Auth\Role::getRole('viewer');
         $viewerUser->attachRole($role);
 
         $byData = ['created_by' => $editorUser->id, 'updated_by' => $editorUser->id];
 
-        factory(\BookStack\Book::class, 5)->create($byData)
+        factory(\BookStack\Entities\Book::class, 5)->create($byData)
             ->each(function($book) use ($editorUser, $byData) {
-                $chapters = factory(\BookStack\Chapter::class, 3)->create($byData)
+                $chapters = factory(\BookStack\Entities\Chapter::class, 3)->create($byData)
                     ->each(function($chapter) use ($editorUser, $book, $byData){
-                        $pages = factory(\BookStack\Page::class, 3)->make(array_merge($byData, ['book_id' => $book->id]));
+                        $pages = factory(\BookStack\Entities\Page::class, 3)->make(array_merge($byData, ['book_id' => $book->id]));
                         $chapter->pages()->saveMany($pages);
                     });
-                $pages = factory(\BookStack\Page::class, 3)->make($byData);
+                $pages = factory(\BookStack\Entities\Page::class, 3)->make($byData);
                 $book->chapters()->saveMany($chapters);
                 $book->pages()->saveMany($pages);
             });
 
-        $largeBook = factory(\BookStack\Book::class)->create(array_merge($byData, ['name' => 'Large book' . str_random(10)]));
-        $pages = factory(\BookStack\Page::class, 200)->make($byData);
-        $chapters = factory(\BookStack\Chapter::class, 50)->make($byData);
+        $largeBook = factory(\BookStack\Entities\Book::class)->create(array_merge($byData, ['name' => 'Large book' . str_random(10)]));
+        $pages = factory(\BookStack\Entities\Page::class, 200)->make($byData);
+        $chapters = factory(\BookStack\Entities\Chapter::class, 50)->make($byData);
         $largeBook->pages()->saveMany($pages);
         $largeBook->chapters()->saveMany($chapters);
 
-        $shelves = factory(\BookStack\Bookshelf::class, 10)->create($byData);
+        $shelves = factory(\BookStack\Entities\Bookshelf::class, 10)->create($byData);
         $largeBook->shelves()->attach($shelves->pluck('id'));
 
-        app(\BookStack\Services\PermissionService::class)->buildJointPermissions();
-        app(\BookStack\Services\SearchService::class)->indexAllEntities();
+        app(\BookStack\Auth\Permissions\PermissionService::class)->buildJointPermissions();
+        app(\BookStack\Entities\SearchService::class)->indexAllEntities();
     }
 }
index 129ede997d5cf358a5dc320bce20125bf1578a1c..136b6cb6a9f6465627bdab0ccab31f7fd8c24112 100644 (file)
@@ -12,16 +12,16 @@ class LargeContentSeeder extends Seeder
     public function run()
     {
         // Create an editor user
-        $editorUser = factory(\BookStack\User::class)->create();
-        $editorRole = \BookStack\Role::getRole('editor');
+        $editorUser = factory(\BookStack\Auth\User::class)->create();
+        $editorRole = \BookStack\Auth\Role::getRole('editor');
         $editorUser->attachRole($editorRole);
 
-        $largeBook = factory(\BookStack\Book::class)->create(['name' => 'Large book' . str_random(10), 'created_by' => $editorUser->id, 'updated_by' => $editorUser->id]);
-        $pages = factory(\BookStack\Page::class, 200)->make(['created_by' => $editorUser->id, 'updated_by' => $editorUser->id]);
-        $chapters = factory(\BookStack\Chapter::class, 50)->make(['created_by' => $editorUser->id, 'updated_by' => $editorUser->id]);
+        $largeBook = factory(\BookStack\Entities\Book::class)->create(['name' => 'Large book' . str_random(10), 'created_by' => $editorUser->id, 'updated_by' => $editorUser->id]);
+        $pages = factory(\BookStack\Entities\Page::class, 200)->make(['created_by' => $editorUser->id, 'updated_by' => $editorUser->id]);
+        $chapters = factory(\BookStack\Entities\Chapter::class, 50)->make(['created_by' => $editorUser->id, 'updated_by' => $editorUser->id]);
         $largeBook->pages()->saveMany($pages);
         $largeBook->chapters()->saveMany($chapters);
-        app(\BookStack\Services\PermissionService::class)->buildJointPermissions();
-        app(\BookStack\Services\SearchService::class)->indexAllEntities();
+        app(\BookStack\Auth\Permissions\PermissionService::class)->buildJointPermissions();
+        app(\BookStack\Entities\SearchService::class)->indexAllEntities();
     }
 }
index 91d8eb64660967382544f61ee849d4e75ba14b5b..7a3285fa76afe1215c1939c639056e6f53193b8f 100644 (file)
@@ -3,7 +3,7 @@
 <div page-picker>
     <div class="input-base">
         <span @if($value) style="display: none" @endif page-picker-default class="text-muted italic">{{ $placeholder }}</span>
-        <a @if(!$value) style="display: none" @endif href="{{ baseUrl('/link/' . $value) }}" target="_blank" class="text-page" page-picker-display>#{{$value}}, {{$value ? \BookStack\Page::find($value)->name : '' }}</a>
+        <a @if(!$value) style="display: none" @endif href="{{ baseUrl('/link/' . $value) }}" target="_blank" class="text-page" page-picker-display>#{{$value}}, {{$value ? \BookStack\Entities\Page::find($value)->name : '' }}</a>
     </div>
     <br>
     <input type="hidden" value="{{$value}}" name="{{$name}}" id="{{$name}}">
index d614edca8e53a1e78d421d3ecc47e379556ad45f..9c431828a810f6b260e9bd91c2246d51c78d90b9 100644 (file)
             <div class="col-md-4">
                 <div class="card">
                     <h3 class="text-muted">@icon('page') {{ trans('entities.pages_popular') }}</h3>
-                    @include('partials.entity-list', ['entities' => Views::getPopular(10, 0, [\BookStack\Page::class]), 'style' => 'compact'])
+                    @include('partials.entity-list', ['entities' => Views::getPopular(10, 0, [\BookStack\Entities\Page::class]), 'style' => 'compact'])
                 </div>
             </div>
             <div class="col-md-4">
                 <div class="card">
                     <h3 class="text-muted">@icon('book') {{ trans('entities.books_popular') }}</h3>
-                    @include('partials.entity-list', ['entities' => Views::getPopular(10, 0, [\BookStack\Book::class]), 'style' => 'compact'])
+                    @include('partials.entity-list', ['entities' => Views::getPopular(10, 0, [\BookStack\Entities\Book::class]), 'style' => 'compact'])
                 </div>
             </div>
             <div class="col-md-4">
                 <div class="card">
                     <h3 class="text-muted">@icon('chapter') {{ trans('entities.chapters_popular') }}</h3>
-                    @include('partials.entity-list', ['entities' => Views::getPopular(10, 0, [\BookStack\Chapter::class]), 'style' => 'compact'])
+                    @include('partials.entity-list', ['entities' => Views::getPopular(10, 0, [\BookStack\Entities\Chapter::class]), 'style' => 'compact'])
                 </div>
             </div>
         </div>
index 3c563a61c975fba2169993658230de7153a001ec..26b81899e8bdb775c43ae9e6bd5dd1a576f66c9e 100644 (file)
                         <div class="form-group">
                             <label for="setting-registration-role">{{ trans('settings.reg_default_role') }}</label>
                             <select id="setting-registration-role" name="setting-registration-role" @if($errors->has('setting-registration-role')) class="neg" @endif>
-                                @foreach(\BookStack\Role::all() as $role)
+                                @foreach(\BookStack\Auth\Role::all() as $role)
                                     <option value="{{$role->id}}" data-role-name="{{ $role->name }}"
-                                            @if(setting('registration-role', \BookStack\Role::first()->id) == $role->id) selected @endif
+                                            @if(setting('registration-role', \BookStack\Auth\Role::first()->id) == $role->id) selected @endif
                                     >
                                         {{ $role->display_name }}
                                     </option>
index bb65fbcf4b8745ec7d9b39c8e0bd5b20de1cbe71..f47bc44a30d7b01d419178dc0e9f83cc414887b6 100644 (file)
@@ -1,12 +1,14 @@
 <?php namespace Tests;
 
 
+use BookStack\Entities\Book;
+
 class ActivityTrackingTest extends BrowserKitTest
 {
 
     public function test_recently_viewed_books()
     {
-        $books = \BookStack\Book::all()->take(10);
+        $books = Book::all()->take(10);
 
         $this->asAdmin()->visit('/books')
             ->dontSeeInElement('#recents', $books[0]->name)
@@ -20,7 +22,7 @@ class ActivityTrackingTest extends BrowserKitTest
 
     public function test_popular_books()
     {
-        $books = \BookStack\Book::all()->take(10);
+        $books = Book::all()->take(10);
 
         $this->asAdmin()->visit('/books')
             ->dontSeeInElement('#popular', $books[0]->name)
index bb3a92706511f2aa814533ec2d7ed8f5c767021d..373d9eb5a9c9ce99655c407dee51664e5b9f43eb 100644 (file)
@@ -1,8 +1,8 @@
 <?php namespace Tests;
 
-use BookStack\Attachment;
-use BookStack\Page;
-use BookStack\Services\PermissionService;
+use BookStack\Uploads\Attachment;
+use BookStack\Entities\Page;
+use BookStack\Auth\Permissions\PermissionService;
 
 class AttachmentTest extends TestCase
 {
@@ -44,8 +44,8 @@ class AttachmentTest extends TestCase
      */
     protected function deleteUploads()
     {
-        $fileService = $this->app->make(\BookStack\Services\AttachmentService::class);
-        foreach (\BookStack\Attachment::all() as $file) {
+        $fileService = $this->app->make(\BookStack\Uploads\AttachmentService::class);
+        foreach (\BookStack\Uploads\Attachment::all() as $file) {
             $fileService->deleteFile($file);
         }
     }
@@ -144,7 +144,7 @@ class AttachmentTest extends TestCase
             'uploaded_to' => $page->id,
         ]);
 
-        $attachmentId = \BookStack\Attachment::first()->id;
+        $attachmentId = \BookStack\Uploads\Attachment::first()->id;
 
         $update = $this->call('PUT', 'attachments/' . $attachmentId, [
             'uploaded_to' => $page->id,
@@ -175,7 +175,7 @@ class AttachmentTest extends TestCase
         $filePath = base_path('storage/' . $this->getUploadPath($fileName));
         $this->assertTrue(file_exists($filePath), 'File at path ' . $filePath . ' does not exist');
 
-        $attachment = \BookStack\Attachment::first();
+        $attachment = \BookStack\Uploads\Attachment::first();
         $this->delete($attachment->getUrl());
 
         $this->assertDatabaseMissing('attachments', [
index b456de964f7c82546f44ed2bf590f39daa3133ab..0aa0e2a23625ea9ab614623065edb116679af9e9 100644 (file)
@@ -1,7 +1,8 @@
 <?php namespace Tests;
 
 use BookStack\Notifications\ConfirmEmail;
-use BookStack\User;
+use BookStack\Auth\User;
+use BookStack\Settings\SettingService;
 use Illuminate\Support\Facades\Notification;
 
 class AuthTest extends BrowserKitTest
@@ -21,7 +22,7 @@ class AuthTest extends BrowserKitTest
 
     public function test_public_viewing()
     {
-        $settings = app('BookStack\Services\SettingService');
+        $settings = app(SettingService::class);
         $settings->put('app-public', 'true');
         $this->visit('/')
             ->seePageIs('/')
@@ -248,7 +249,7 @@ class AuthTest extends BrowserKitTest
 
     public function test_user_cannot_be_deleted_if_last_admin()
     {
-        $adminRole = \BookStack\Role::getRole('admin');
+        $adminRole = \BookStack\Auth\Role::getRole('admin');
         // Ensure we currently only have 1 admin user
         $this->assertEquals(1, $adminRole->users()->count());
         $user = $adminRole->users->first();
index 289daa932cde793e3f1fc3b7ab94fca19dae5936..25d8a59064301d618bc2216495383e880bc3bb2a 100644 (file)
@@ -1,7 +1,7 @@
 <?php namespace Tests;
-use BookStack\Role;
-use BookStack\Services\Ldap;
-use BookStack\User;
+use BookStack\Auth\Role;
+use BookStack\Auth\Access\Ldap;
+use BookStack\Auth\User;
 use Mockery\MockInterface;
 
 class LdapTest extends BrowserKitTest
index 5bfe0c222cb04e2dd35baacc35099b2ee31a5537..572c32f4620ff23756b0f61867ce13c15338f863 100644 (file)
@@ -6,7 +6,7 @@ class SocialAuthTest extends TestCase
     public function test_social_registration()
     {
         // http://docs.mockery.io/en/latest/reference/startup_methods.html
-        $user = factory(\BookStack\User::class)->make();
+        $user = factory(\BookStack\Auth\User::class)->make();
 
         $this->setSettings(['registration-enabled' => 'true']);
         config(['GOOGLE_APP_ID' => 'abc123', 'GOOGLE_APP_SECRET' => '123abc', 'APP_URL' => 'http://localhost']);
@@ -86,7 +86,7 @@ class SocialAuthTest extends TestCase
             'APP_URL' => 'http://localhost'
         ]);
 
-        $user = factory(\BookStack\User::class)->make();
+        $user = factory(\BookStack\Auth\User::class)->make();
         $mockSocialite = \Mockery::mock('Laravel\Socialite\Contracts\Factory');
         $this->app['Laravel\Socialite\Contracts\Factory'] = $mockSocialite;
         $mockSocialDriver = \Mockery::mock('Laravel\Socialite\Contracts\Provider');
@@ -125,7 +125,7 @@ class SocialAuthTest extends TestCase
             'APP_URL' => 'http://localhost', 'services.google.auto_register' => true, 'services.google.auto_confirm' => true
         ]);
 
-        $user = factory(\BookStack\User::class)->make();
+        $user = factory(\BookStack\Auth\User::class)->make();
         $mockSocialite = \Mockery::mock('Laravel\Socialite\Contracts\Factory');
         $this->app['Laravel\Socialite\Contracts\Factory'] = $mockSocialite;
         $mockSocialDriver = \Mockery::mock('Laravel\Socialite\Contracts\Provider');
index 86f61a7647181e1aa3a89e166d3202964c1c4c57..ab0d9d898b31db9a9f167fc7a4b9131ffe722a1f 100644 (file)
@@ -1,8 +1,9 @@
 <?php namespace Tests;
 
-use BookStack\Entity;
-use BookStack\Role;
-use BookStack\Services\PermissionService;
+use BookStack\Entities\Entity;
+use BookStack\Auth\Role;
+use BookStack\Auth\Permissions\PermissionService;
+use BookStack\Settings\SettingService;
 use Illuminate\Contracts\Console\Kernel;
 use Illuminate\Foundation\Testing\DatabaseTransactions;
 use Laravel\BrowserKitTesting\TestCase;
@@ -46,7 +47,7 @@ abstract class BrowserKitTest extends TestCase
      */
     public function getNormalUser()
     {
-        return \BookStack\User::where('system_name', '=', null)->get()->last();
+        return \BookStack\Auth\User::where('system_name', '=', null)->get()->last();
     }
 
     /**
@@ -55,7 +56,7 @@ abstract class BrowserKitTest extends TestCase
      */
     protected function setSettings($settingsArray)
     {
-        $settings = app('BookStack\Services\SettingService');
+        $settings = app(SettingService::class);
         foreach ($settingsArray as $key => $value) {
             $settings->put($key, $value);
         }
@@ -70,9 +71,9 @@ abstract class BrowserKitTest extends TestCase
     protected function createEntityChainBelongingToUser($creatorUser, $updaterUser = false)
     {
         if ($updaterUser === false) $updaterUser = $creatorUser;
-        $book = factory(\BookStack\Book::class)->create(['created_by' => $creatorUser->id, 'updated_by' => $updaterUser->id]);
-        $chapter = factory(\BookStack\Chapter::class)->create(['created_by' => $creatorUser->id, 'updated_by' => $updaterUser->id, 'book_id' => $book->id]);
-        $page = factory(\BookStack\Page::class)->create(['created_by' => $creatorUser->id, 'updated_by' => $updaterUser->id, 'book_id' => $book->id, 'chapter_id' => $chapter->id]);
+        $book = factory(\BookStack\Entities\Book::class)->create(['created_by' => $creatorUser->id, 'updated_by' => $updaterUser->id]);
+        $chapter = factory(\BookStack\Entities\Chapter::class)->create(['created_by' => $creatorUser->id, 'updated_by' => $updaterUser->id, 'book_id' => $book->id]);
+        $page = factory(\BookStack\Entities\Page::class)->create(['created_by' => $creatorUser->id, 'updated_by' => $updaterUser->id, 'book_id' => $book->id, 'chapter_id' => $chapter->id]);
         $restrictionService = $this->app[PermissionService::class];
         $restrictionService->buildJointPermissionsForEntity($book);
         return [
@@ -100,7 +101,7 @@ abstract class BrowserKitTest extends TestCase
      */
     protected function getNewBlankUser($attributes = [])
     {
-        $user = factory(\BookStack\User::class)->create($attributes);
+        $user = factory(\BookStack\Auth\User::class)->create($attributes);
         return $user;
     }
 
index 25516c31732bd04ae2ba9f6dc8743305b6b245be..a884809696d32cd4e4126f7c7c68121738ee905f 100644 (file)
@@ -1,9 +1,10 @@
 <?php namespace Tests;
 
-use BookStack\JointPermission;
-use BookStack\Page;
-use BookStack\Repos\EntityRepo;
-use BookStack\User;
+use BookStack\Auth\Permissions\JointPermission;
+use BookStack\Entities\Page;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Auth\User;
+use BookStack\Entities\Repos\PageRepo;
 
 class CommandsTest extends TestCase
 {
@@ -53,10 +54,10 @@ class CommandsTest extends TestCase
     public function test_clear_revisions_command()
     {
         $this->asEditor();
-        $entityRepo = $this->app[EntityRepo::class];
+        $pageRepo = app(PageRepo::class);
         $page = Page::first();
-        $entityRepo->updatePage($page, $page->book_id, ['name' => 'updated page', 'html' => '<p>new content</p>', 'summary' => 'page revision testing']);
-        $entityRepo->updatePageDraft($page, ['name' => 'updated page', 'html' => '<p>new content in draft</p>', 'summary' => 'page revision testing']);
+        $pageRepo->updatePage($page, $page->book_id, ['name' => 'updated page', 'html' => '<p>new content</p>', 'summary' => 'page revision testing']);
+        $pageRepo->updatePageDraft($page, ['name' => 'updated page', 'html' => '<p>new content in draft</p>', 'summary' => 'page revision testing']);
 
         $this->assertDatabaseHas('page_revisions', [
             'page_id' => $page->id,
index 9071e3c06990e28d82d794d3a4109e51150c2c28..5d71ec6f6a15f12c5c5e1cd7e057f70ccd5de6bb 100644 (file)
@@ -1,7 +1,7 @@
 <?php namespace Tests;
 
-use BookStack\Book;
-use BookStack\Bookshelf;
+use BookStack\Entities\Book;
+use BookStack\Entities\Bookshelf;
 
 class BookShelfTest extends TestCase
 {
index 29df8b3278daf7f2a900ba9e6fdede2db24708b9..2683f57cb601767243b745edd31b2caf1ea4e457 100644 (file)
@@ -5,7 +5,7 @@ class CommentSettingTest extends BrowserKitTest {
 
   public function setUp() {
       parent::setUp();
-      $this->page = \BookStack\Page::first();
+      $this->page = \BookStack\Entities\Page::first();
   }
 
   public function test_comment_disable () {
index 04716c1c29d389cae945b493d0397d49a513dd96..2b943f96f18c853dfd36f805110f7eb0715b0666 100644 (file)
@@ -1,7 +1,7 @@
 <?php namespace Tests;
 
-use BookStack\Page;
-use BookStack\Comment;
+use BookStack\Entities\Page;
+use BookStack\Actions\Comment;
 
 class CommentTest extends TestCase
 {
@@ -23,7 +23,7 @@ class CommentTest extends TestCase
         $this->assertDatabaseHas('comments', [
             'local_id' => 1,
             'entity_id' => $page->id,
-            'entity_type' => 'BookStack\\Page',
+            'entity_type' => Page::newModelInstance()->getMorphClass(),
             'text' => $comment->text,
             'parent_id' => 2
         ]);
index 301f0d02d73ca221f2377523d9c93f6b1790114c..4114d4af9c816dc04f4576185566491bf9c01537 100644 (file)
@@ -1,16 +1,16 @@
 <?php namespace Tests;
 
 
-use BookStack\Bookshelf;
-use BookStack\Chapter;
-use BookStack\Page;
+use BookStack\Entities\Bookshelf;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Page;
 
 class EntitySearchTest extends TestCase
 {
 
     public function test_page_search()
     {
-        $book = \BookStack\Book::all()->first();
+        $book = \BookStack\Entities\Book::all()->first();
         $page = $book->pages->first();
 
         $search = $this->asEditor()->get('/search?term=' . urlencode($page->name));
@@ -54,7 +54,7 @@ class EntitySearchTest extends TestCase
 
     public function test_book_search()
     {
-        $book = \BookStack\Book::first();
+        $book = \BookStack\Entities\Book::first();
         $page = $book->pages->last();
         $chapter = $book->chapters->last();
 
@@ -67,7 +67,7 @@ class EntitySearchTest extends TestCase
 
     public function test_chapter_search()
     {
-        $chapter = \BookStack\Chapter::has('pages')->first();
+        $chapter = \BookStack\Entities\Chapter::has('pages')->first();
         $page = $chapter->pages[0];
 
         $pageTestResp = $this->asEditor()->get('/search/chapter/' . $chapter->id . '?term=' . urlencode($page->name));
@@ -77,11 +77,11 @@ class EntitySearchTest extends TestCase
     public function test_tag_search()
     {
         $newTags = [
-            new \BookStack\Tag([
+            new \BookStack\Actions\Tag([
                 'name' => 'animal',
                 'value' => 'cat'
             ]),
-            new \BookStack\Tag([
+            new \BookStack\Actions\Tag([
                 'name' => 'color',
                 'value' => 'red'
             ])
index f8ca8ea1217d0726b1c33f4078e73a2f667001a2..ef9597d328496aac1ba8ee292917003053e5b426 100644 (file)
@@ -1,10 +1,11 @@
 <?php namespace Tests;
 
-use BookStack\Book;
-use BookStack\Chapter;
-use BookStack\Page;
-use BookStack\Repos\EntityRepo;
-use BookStack\Repos\UserRepo;
+use BookStack\Entities\Book;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Page;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Auth\UserRepo;
+use BookStack\Entities\Repos\PageRepo;
 use Carbon\Carbon;
 
 class EntityTest extends BrowserKitTest
@@ -193,7 +194,7 @@ class EntityTest extends BrowserKitTest
         $entities = $this->createEntityChainBelongingToUser($creator, $updater);
         $this->actingAs($creator);
         app(UserRepo::class)->destroy($creator);
-        app(EntityRepo::class)->savePageRevision($entities['page']);
+        app(PageRepo::class)->savePageRevision($entities['page']);
 
         $this->checkEntitiesViewable($entities);
     }
@@ -206,7 +207,7 @@ class EntityTest extends BrowserKitTest
         $entities = $this->createEntityChainBelongingToUser($creator, $updater);
         $this->actingAs($updater);
         app(UserRepo::class)->destroy($updater);
-        app(EntityRepo::class)->savePageRevision($entities['page']);
+        app(PageRepo::class)->savePageRevision($entities['page']);
 
         $this->checkEntitiesViewable($entities);
     }
index 5fff84b8dfaa79dadc6efec5ff4202ca6f9a97c3..51090650c267514b67a840bd8909e16c5a09a6d4 100644 (file)
@@ -1,8 +1,8 @@
 <?php namespace Tests;
 
 
-use BookStack\Chapter;
-use BookStack\Page;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Page;
 
 class ExportTest extends TestCase
 {
index b85e92565aa69037982e82271c41cf19cd46e9d5..c481e444f59cf563f25791bd3725bac74ee6df1c 100644 (file)
@@ -7,7 +7,7 @@ class MarkdownTest extends BrowserKitTest
     public function setUp()
     {
         parent::setUp();
-        $this->page = \BookStack\Page::first();
+        $this->page = \BookStack\Entities\Page::first();
     }
 
     protected function setMarkdownEditor()
index 8b0e180da724617234b3da246556e2f82d742f84..6a7112bcbac45135353ded3b7e2e4293efff4f70 100644 (file)
@@ -1,7 +1,8 @@
 <?php namespace Tests;
 
-use BookStack\Page;
-use BookStack\Repos\EntityRepo;
+use BookStack\Entities\Page;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Entities\Repos\PageRepo;
 
 class PageContentTest extends TestCase
 {
@@ -71,9 +72,9 @@ class PageContentTest extends TestCase
     {
         $this->asEditor();
 
-        $entityRepo = $this->app[EntityRepo::class];
+        $pageRepo = app(PageRepo::class);
         $page = Page::first();
-        $entityRepo->updatePage($page, $page->book_id, ['name' => 'updated page', 'html' => '<p>new content</p>', 'summary' => 'page revision testing']);
+        $pageRepo->updatePage($page, $page->book_id, ['name' => 'updated page', 'html' => '<p>new content</p>', 'summary' => 'page revision testing']);
         $pageRevision = $page->revisions->last();
 
         $revisionView = $this->get($page->getUrl() . '/revisions/' . $pageRevision->id);
@@ -89,10 +90,10 @@ class PageContentTest extends TestCase
     {
         $this->asEditor();
 
-        $entityRepo = $this->app[EntityRepo::class];
+        $pageRepo = app(PageRepo::class);
         $page = Page::first();
-        $entityRepo->updatePage($page, $page->book_id, ['name' => 'updated page abc123', 'html' => '<p>new contente def456</p>', 'summary' => 'initial page revision testing']);
-        $entityRepo->updatePage($page, $page->book_id, ['name' => 'updated page again', 'html' => '<p>new content</p>', 'summary' => 'page revision testing']);
+        $pageRepo->updatePage($page, $page->book_id, ['name' => 'updated page abc123', 'html' => '<p>new contente def456</p>', 'summary' => 'initial page revision testing']);
+        $pageRepo->updatePage($page, $page->book_id, ['name' => 'updated page again', 'html' => '<p>new content</p>', 'summary' => 'page revision testing']);
         $page =  Page::find($page->id);
 
 
index d9341ace67f406d308026edc56235f175634fa09..1ebd5860b054f2ec153e166cfd5ab4d65cf0e6bd 100644 (file)
@@ -1,16 +1,18 @@
 <?php namespace Tests;
 
 
+use BookStack\Entities\Repos\PageRepo;
+
 class PageDraftTest extends BrowserKitTest
 {
     protected $page;
-    protected $entityRepo;
+    protected $pageRepo;
 
     public function setUp()
     {
         parent::setUp();
-        $this->page = \BookStack\Page::first();
-        $this->entityRepo = app('\BookStack\Repos\EntityRepo');
+        $this->page = \BookStack\Entities\Page::first();
+        $this->pageRepo = app(PageRepo::class);
     }
 
     public function test_draft_content_shows_if_available()
@@ -20,7 +22,7 @@ class PageDraftTest extends BrowserKitTest
             ->dontSeeInField('html', $addedContent);
 
         $newContent = $this->page->html . $addedContent;
-        $this->entityRepo->updatePageDraft($this->page, ['html' => $newContent]);
+        $this->pageRepo->updatePageDraft($this->page, ['html' => $newContent]);
         $this->asAdmin()->visit($this->page->getUrl() . '/edit')
             ->seeInField('html', $newContent);
     }
@@ -33,7 +35,7 @@ class PageDraftTest extends BrowserKitTest
 
         $newContent = $this->page->html . $addedContent;
         $newUser = $this->getEditor();
-        $this->entityRepo->updatePageDraft($this->page, ['html' => $newContent]);
+        $this->pageRepo->updatePageDraft($this->page, ['html' => $newContent]);
         $this->actingAs($newUser)->visit($this->page->getUrl() . '/edit')
             ->dontSeeInField('html', $newContent);
     }
@@ -41,21 +43,21 @@ class PageDraftTest extends BrowserKitTest
     public function test_alert_message_shows_if_editing_draft()
     {
         $this->asAdmin();
-        $this->entityRepo->updatePageDraft($this->page, ['html' => 'test content']);
+        $this->pageRepo->updatePageDraft($this->page, ['html' => 'test content']);
         $this->asAdmin()->visit($this->page->getUrl() . '/edit')
             ->see('You are currently editing a draft');
     }
 
     public function test_alert_message_shows_if_someone_else_editing()
     {
-        $nonEditedPage = \BookStack\Page::take(10)->get()->last();
+        $nonEditedPage = \BookStack\Entities\Page::take(10)->get()->last();
         $addedContent = '<p>test message content</p>';
         $this->asAdmin()->visit($this->page->getUrl() . '/edit')
             ->dontSeeInField('html', $addedContent);
 
         $newContent = $this->page->html . $addedContent;
         $newUser = $this->getEditor();
-        $this->entityRepo->updatePageDraft($this->page, ['html' => $newContent]);
+        $this->pageRepo->updatePageDraft($this->page, ['html' => $newContent]);
 
         $this->actingAs($newUser)
             ->visit($this->page->getUrl() . '/edit')
@@ -67,7 +69,7 @@ class PageDraftTest extends BrowserKitTest
 
     public function test_draft_pages_show_on_homepage()
     {
-        $book = \BookStack\Book::first();
+        $book = \BookStack\Entities\Book::first();
         $this->asAdmin()->visit('/')
             ->dontSeeInElement('#recent-drafts', 'New Page')
             ->visit($book->getUrl() . '/create-page')
@@ -77,7 +79,7 @@ class PageDraftTest extends BrowserKitTest
 
     public function test_draft_pages_not_visible_by_others()
     {
-        $book = \BookStack\Book::first();
+        $book = \BookStack\Entities\Book::first();
         $chapter = $book->chapters->first();
         $newUser = $this->getEditor();
 
index 390042dbf3c61de1fd9ab6105a7f98325a3637e5..015320dd7b1208e7c2ae4aa74d49f13f5498b457 100644 (file)
@@ -1,7 +1,7 @@
 <?php namespace Entity;
 
 
-use BookStack\Page;
+use BookStack\Entities\Page;
 use Tests\TestCase;
 
 class PageRevisionTest extends TestCase
index ea5ab665d0edb732ae2681cdba8dab498089674a..5b23acfd58461adb295af41f71d84272d3397e97 100644 (file)
@@ -1,9 +1,10 @@
 <?php namespace Tests;
 
-use BookStack\Book;
-use BookStack\Chapter;
-use BookStack\Page;
-use BookStack\Repos\EntityRepo;
+use BookStack\Entities\Book;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Page;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Entities\Repos\PageRepo;
 
 class SortTest extends TestCase
 {
@@ -18,8 +19,8 @@ class SortTest extends TestCase
     public function test_drafts_do_not_show_up()
     {
         $this->asAdmin();
-        $entityRepo = app(EntityRepo::class);
-        $draft = $entityRepo->getDraftPage($this->book);
+        $pageRepo = app(PageRepo::class);
+        $draft = $pageRepo->getDraftPage($this->book);
 
         $resp = $this->get($this->book->getUrl());
         $resp->assertSee($draft->name);
index 7e11663882533e120dbcd1138bb47a9b735dceab..70b8c960b73980544b74356d2666c0cd89fee067 100644 (file)
@@ -1,10 +1,10 @@
 <?php namespace Tests;
 
-use BookStack\Book;
-use BookStack\Chapter;
-use BookStack\Tag;
-use BookStack\Page;
-use BookStack\Services\PermissionService;
+use BookStack\Entities\Book;
+use BookStack\Entities\Chapter;
+use BookStack\Actions\Tag;
+use BookStack\Entities\Page;
+use BookStack\Auth\Permissions\PermissionService;
 
 class TagTest extends BrowserKitTest
 {
@@ -13,7 +13,7 @@ class TagTest extends BrowserKitTest
 
     /**
      * Get an instance of a page that has many tags.
-     * @param Tag[]|bool $tags
+     * @param \BookStack\Actions\Tag[]|bool $tags
      * @return mixed
      */
     protected function getEntityWithTags($class, $tags = false)
index 0f1e772e937e86660110f1ca171642872b33d693..38bac2ccacb07e9f6514e6167c9aceb00ea9d716 100644 (file)
@@ -1,9 +1,10 @@
 <?php namespace Tests;
 
-use BookStack\Image;
-use BookStack\Page;
-use BookStack\Repos\EntityRepo;
-use BookStack\Services\ImageService;
+use BookStack\Entities\Repos\PageRepo;
+use BookStack\Uploads\Image;
+use BookStack\Entities\Page;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Uploads\ImageService;
 
 class ImageTest extends TestCase
 {
@@ -250,8 +251,8 @@ class ImageTest extends TestCase
         $upload->assertStatus(200);
         $image = Image::where('type', '=', 'gallery')->first();
 
-        $entityRepo = app(EntityRepo::class);
-        $entityRepo->updatePage($page, $page->book_id, [
+        $pageRepo = app(PageRepo::class);
+        $pageRepo->updatePage($page, $page->book_id, [
             'name' => $page->name,
             'html' => $page->html . "<img src=\"{$image->url}\">",
             'summary' => ''
@@ -263,7 +264,7 @@ class ImageTest extends TestCase
         $this->assertCount(0, $toDelete);
 
         // Save a revision of our page without the image;
-        $entityRepo->updatePage($page, $page->book_id, [
+        $pageRepo->updatePage($page, $page->book_id, [
             'name' => $page->name,
             'html' => "<p>Hello</p>",
             'summary' => ''
index 540125fd11129cd0a80432d9b4ed3987ba9da92b..351132ffef908eb4e0fcf02fc9f98b903116fb97 100644 (file)
@@ -1,16 +1,18 @@
 <?php namespace Tests;
 
-use BookStack\Book;
-use BookStack\Bookshelf;
-use BookStack\Entity;
-use BookStack\User;
-use BookStack\Repos\EntityRepo;
+use BookStack\Entities\Book;
+use BookStack\Entities\Bookshelf;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Entity;
+use BookStack\Auth\User;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Entities\Page;
 
 class RestrictionsTest extends BrowserKitTest
 {
 
     /**
-     * @var User
+     * @var \BookStack\Auth\User
      */
     protected $user;
 
@@ -223,7 +225,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_chapter_view_restriction()
     {
-        $chapter = \BookStack\Chapter::first();
+        $chapter = Chapter::first();
         $chapterPage = $chapter->pages->first();
 
         $chapterUrl = $chapter->getUrl();
@@ -248,7 +250,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_chapter_create_restriction()
     {
-        $chapter = \BookStack\Chapter::first();
+        $chapter = Chapter::first();
 
         $chapterUrl = $chapter->getUrl();
         $this->actingAs($this->user)
@@ -275,7 +277,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_chapter_update_restriction()
     {
-        $chapter = \BookStack\Chapter::first();
+        $chapter = Chapter::first();
         $chapterPage = $chapter->pages->first();
 
         $chapterUrl = $chapter->getUrl();
@@ -300,7 +302,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_chapter_delete_restriction()
     {
-        $chapter = \BookStack\Chapter::first();
+        $chapter = Chapter::first();
         $chapterPage = $chapter->pages->first();
 
         $chapterUrl = $chapter->getUrl();
@@ -325,7 +327,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_page_view_restriction()
     {
-        $page = \BookStack\Page::first();
+        $page = \BookStack\Entities\Page::first();
 
         $pageUrl = $page->getUrl();
         $this->actingAs($this->user)
@@ -345,7 +347,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_page_update_restriction()
     {
-        $page = \BookStack\Chapter::first();
+        $page = Chapter::first();
 
         $pageUrl = $page->getUrl();
         $this->actingAs($this->user)
@@ -365,7 +367,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_page_delete_restriction()
     {
-        $page = \BookStack\Page::first();
+        $page = \BookStack\Entities\Page::first();
 
         $pageUrl = $page->getUrl();
         $this->actingAs($this->user)
@@ -394,7 +396,7 @@ class RestrictionsTest extends BrowserKitTest
             ->seeInDatabase('bookshelves', ['id' => $shelf->id, 'restricted' => true])
             ->seeInDatabase('entity_permissions', [
                 'restrictable_id' => $shelf->id,
-                'restrictable_type' => 'BookStack\Bookshelf',
+                'restrictable_type' => Bookshelf::newModelInstance()->getMorphClass(),
                 'role_id' => '2',
                 'action' => 'view'
             ]);
@@ -411,7 +413,7 @@ class RestrictionsTest extends BrowserKitTest
             ->seeInDatabase('books', ['id' => $book->id, 'restricted' => true])
             ->seeInDatabase('entity_permissions', [
                 'restrictable_id' => $book->id,
-                'restrictable_type' => 'BookStack\Book',
+                'restrictable_type' => Book::newModelInstance()->getMorphClass(),
                 'role_id' => '2',
                 'action' => 'view'
             ]);
@@ -419,7 +421,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_chapter_restriction_form()
     {
-        $chapter = \BookStack\Chapter::first();
+        $chapter = Chapter::first();
         $this->asAdmin()->visit($chapter->getUrl() . '/permissions')
             ->see('Chapter Permissions')
             ->check('restricted')
@@ -428,7 +430,7 @@ class RestrictionsTest extends BrowserKitTest
             ->seeInDatabase('chapters', ['id' => $chapter->id, 'restricted' => true])
             ->seeInDatabase('entity_permissions', [
                 'restrictable_id' => $chapter->id,
-                'restrictable_type' => 'BookStack\Chapter',
+                'restrictable_type' => Chapter::newModelInstance()->getMorphClass(),
                 'role_id' => '2',
                 'action' => 'update'
             ]);
@@ -436,7 +438,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_page_restriction_form()
     {
-        $page = \BookStack\Page::first();
+        $page = \BookStack\Entities\Page::first();
         $this->asAdmin()->visit($page->getUrl() . '/permissions')
             ->see('Page Permissions')
             ->check('restricted')
@@ -445,7 +447,7 @@ class RestrictionsTest extends BrowserKitTest
             ->seeInDatabase('pages', ['id' => $page->id, 'restricted' => true])
             ->seeInDatabase('entity_permissions', [
                 'restrictable_id' => $page->id,
-                'restrictable_type' => 'BookStack\Page',
+                'restrictable_type' => Page::newModelInstance()->getMorphClass(),
                 'role_id' => '2',
                 'action' => 'delete'
             ]);
@@ -453,7 +455,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_restricted_pages_not_visible_in_book_navigation_on_pages()
     {
-        $chapter = \BookStack\Chapter::first();
+        $chapter = Chapter::first();
         $page = $chapter->pages->first();
         $page2 = $chapter->pages[2];
 
@@ -466,7 +468,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_restricted_pages_not_visible_in_book_navigation_on_chapters()
     {
-        $chapter = \BookStack\Chapter::first();
+        $chapter = Chapter::first();
         $page = $chapter->pages->first();
 
         $this->setEntityRestrictions($page, []);
@@ -478,7 +480,7 @@ class RestrictionsTest extends BrowserKitTest
 
     public function test_restricted_pages_not_visible_on_chapter_pages()
     {
-        $chapter = \BookStack\Chapter::first();
+        $chapter = Chapter::first();
         $page = $chapter->pages->first();
 
         $this->setEntityRestrictions($page, []);
index e0f827d0246af435bcc8f93d80c7f56895e35384..95cb7cd5726ec7e54bd31902a86511f6a745386b 100644 (file)
@@ -1,9 +1,9 @@
 <?php namespace Tests;
 
-use BookStack\Bookshelf;
-use BookStack\Page;
-use BookStack\Repos\PermissionsRepo;
-use BookStack\Role;
+use BookStack\Entities\Bookshelf;
+use BookStack\Entities\Page;
+use BookStack\Auth\Permissions\PermissionsRepo;
+use BookStack\Auth\Role;
 use Laravel\BrowserKitTesting\HttpException;
 use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
 
@@ -24,7 +24,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_cannot_delete_admin_role()
     {
-        $adminRole = \BookStack\Role::getRole('admin');
+        $adminRole = \BookStack\Auth\Role::getRole('admin');
         $deletePageUrl = '/settings/roles/delete/' . $adminRole->id;
         $this->asAdmin()->visit($deletePageUrl)
             ->press('Confirm')
@@ -108,7 +108,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_restrictions_manage_all_permission()
     {
-        $page = \BookStack\Page::take(1)->get()->first();
+        $page = \BookStack\Entities\Page::take(1)->get()->first();
         $this->actingAs($this->user)->visit($page->getUrl())
             ->dontSee('Permissions')
             ->visit($page->getUrl() . '/permissions')
@@ -122,7 +122,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_restrictions_manage_own_permission()
     {
-        $otherUsersPage = \BookStack\Page::first();
+        $otherUsersPage = \BookStack\Entities\Page::first();
         $content = $this->createEntityChainBelongingToUser($this->user);
         // Check can't restrict other's content
         $this->actingAs($this->user)->visit($otherUsersPage->getUrl())
@@ -214,7 +214,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_bookshelves_edit_all_permission()
     {
-        $otherShelf = \BookStack\Bookshelf::first();
+        $otherShelf = \BookStack\Entities\Bookshelf::first();
         $this->checkAccessPermission('bookshelf-update-all', [
             $otherShelf->getUrl('/edit')
         ], [
@@ -225,7 +225,7 @@ class RolesTest extends BrowserKitTest
     public function test_bookshelves_delete_own_permission()
     {
         $this->giveUserPermissions($this->user, ['bookshelf-update-all']);
-        $otherShelf = \BookStack\Bookshelf::first();
+        $otherShelf = \BookStack\Entities\Bookshelf::first();
         $ownShelf = $this->newShelf(['name' => 'test-shelf', 'slug' => 'test-shelf']);
         $ownShelf->forceFill(['created_by' => $this->user->id, 'updated_by' => $this->user->id])->save();
         $this->regenEntityPermissions($ownShelf);
@@ -249,7 +249,7 @@ class RolesTest extends BrowserKitTest
     public function test_bookshelves_delete_all_permission()
     {
         $this->giveUserPermissions($this->user, ['bookshelf-update-all']);
-        $otherShelf = \BookStack\Bookshelf::first();
+        $otherShelf = \BookStack\Entities\Bookshelf::first();
         $this->checkAccessPermission('bookshelf-delete-all', [
             $otherShelf->getUrl('/delete')
         ], [
@@ -279,7 +279,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_books_edit_own_permission()
     {
-        $otherBook = \BookStack\Book::take(1)->get()->first();
+        $otherBook = \BookStack\Entities\Book::take(1)->get()->first();
         $ownBook = $this->createEntityChainBelongingToUser($this->user)['book'];
         $this->checkAccessPermission('book-update-own', [
             $ownBook->getUrl() . '/edit'
@@ -295,7 +295,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_books_edit_all_permission()
     {
-        $otherBook = \BookStack\Book::take(1)->get()->first();
+        $otherBook = \BookStack\Entities\Book::take(1)->get()->first();
         $this->checkAccessPermission('book-update-all', [
             $otherBook->getUrl() . '/edit'
         ], [
@@ -306,7 +306,7 @@ class RolesTest extends BrowserKitTest
     public function test_books_delete_own_permission()
     {
         $this->giveUserPermissions($this->user, ['book-update-all']);
-        $otherBook = \BookStack\Book::take(1)->get()->first();
+        $otherBook = \BookStack\Entities\Book::take(1)->get()->first();
         $ownBook = $this->createEntityChainBelongingToUser($this->user)['book'];
         $this->checkAccessPermission('book-delete-own', [
             $ownBook->getUrl() . '/delete'
@@ -327,7 +327,7 @@ class RolesTest extends BrowserKitTest
     public function test_books_delete_all_permission()
     {
         $this->giveUserPermissions($this->user, ['book-update-all']);
-        $otherBook = \BookStack\Book::take(1)->get()->first();
+        $otherBook = \BookStack\Entities\Book::take(1)->get()->first();
         $this->checkAccessPermission('book-delete-all', [
             $otherBook->getUrl() . '/delete'
         ], [
@@ -342,7 +342,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_chapter_create_own_permissions()
     {
-        $book = \BookStack\Book::take(1)->get()->first();
+        $book = \BookStack\Entities\Book::take(1)->get()->first();
         $ownBook = $this->createEntityChainBelongingToUser($this->user)['book'];
         $this->checkAccessPermission('chapter-create-own', [
             $ownBook->getUrl('/create-chapter')
@@ -364,7 +364,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_chapter_create_all_permissions()
     {
-        $book = \BookStack\Book::take(1)->get()->first();
+        $book = \BookStack\Entities\Book::take(1)->get()->first();
         $this->checkAccessPermission('chapter-create-all', [
             $book->getUrl('/create-chapter')
         ], [
@@ -380,7 +380,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_chapter_edit_own_permission()
     {
-        $otherChapter = \BookStack\Chapter::take(1)->get()->first();
+        $otherChapter = \BookStack\Entities\Chapter::take(1)->get()->first();
         $ownChapter = $this->createEntityChainBelongingToUser($this->user)['chapter'];
         $this->checkAccessPermission('chapter-update-own', [
             $ownChapter->getUrl() . '/edit'
@@ -396,7 +396,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_chapter_edit_all_permission()
     {
-        $otherChapter = \BookStack\Chapter::take(1)->get()->first();
+        $otherChapter = \BookStack\Entities\Chapter::take(1)->get()->first();
         $this->checkAccessPermission('chapter-update-all', [
             $otherChapter->getUrl() . '/edit'
         ], [
@@ -407,7 +407,7 @@ class RolesTest extends BrowserKitTest
     public function test_chapter_delete_own_permission()
     {
         $this->giveUserPermissions($this->user, ['chapter-update-all']);
-        $otherChapter = \BookStack\Chapter::take(1)->get()->first();
+        $otherChapter = \BookStack\Entities\Chapter::take(1)->get()->first();
         $ownChapter = $this->createEntityChainBelongingToUser($this->user)['chapter'];
         $this->checkAccessPermission('chapter-delete-own', [
             $ownChapter->getUrl() . '/delete'
@@ -429,7 +429,7 @@ class RolesTest extends BrowserKitTest
     public function test_chapter_delete_all_permission()
     {
         $this->giveUserPermissions($this->user, ['chapter-update-all']);
-        $otherChapter = \BookStack\Chapter::take(1)->get()->first();
+        $otherChapter = \BookStack\Entities\Chapter::take(1)->get()->first();
         $this->checkAccessPermission('chapter-delete-all', [
             $otherChapter->getUrl() . '/delete'
         ], [
@@ -445,8 +445,8 @@ class RolesTest extends BrowserKitTest
 
     public function test_page_create_own_permissions()
     {
-        $book = \BookStack\Book::first();
-        $chapter = \BookStack\Chapter::first();
+        $book = \BookStack\Entities\Book::first();
+        $chapter = \BookStack\Entities\Chapter::first();
 
         $entities = $this->createEntityChainBelongingToUser($this->user);
         $ownBook = $entities['book'];
@@ -470,7 +470,7 @@ class RolesTest extends BrowserKitTest
 
         foreach ($accessUrls as $index => $url) {
             $this->actingAs($this->user)->visit($url);
-            $expectedUrl = \BookStack\Page::where('draft', '=', true)->orderBy('id', 'desc')->first()->getUrl();
+            $expectedUrl = \BookStack\Entities\Page::where('draft', '=', true)->orderBy('id', 'desc')->first()->getUrl();
             $this->seePageIs($expectedUrl);
         }
 
@@ -492,8 +492,8 @@ class RolesTest extends BrowserKitTest
 
     public function test_page_create_all_permissions()
     {
-        $book = \BookStack\Book::take(1)->get()->first();
-        $chapter = \BookStack\Chapter::take(1)->get()->first();
+        $book = \BookStack\Entities\Book::take(1)->get()->first();
+        $chapter = \BookStack\Entities\Chapter::take(1)->get()->first();
         $baseUrl = $book->getUrl() . '/page';
         $createUrl = $book->getUrl('/create-page');
 
@@ -514,7 +514,7 @@ class RolesTest extends BrowserKitTest
 
         foreach ($accessUrls as $index => $url) {
             $this->actingAs($this->user)->visit($url);
-            $expectedUrl = \BookStack\Page::where('draft', '=', true)->orderBy('id', 'desc')->first()->getUrl();
+            $expectedUrl = \BookStack\Entities\Page::where('draft', '=', true)->orderBy('id', 'desc')->first()->getUrl();
             $this->seePageIs($expectedUrl);
         }
 
@@ -533,7 +533,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_page_edit_own_permission()
     {
-        $otherPage = \BookStack\Page::take(1)->get()->first();
+        $otherPage = \BookStack\Entities\Page::take(1)->get()->first();
         $ownPage = $this->createEntityChainBelongingToUser($this->user)['page'];
         $this->checkAccessPermission('page-update-own', [
             $ownPage->getUrl() . '/edit'
@@ -549,7 +549,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_page_edit_all_permission()
     {
-        $otherPage = \BookStack\Page::take(1)->get()->first();
+        $otherPage = \BookStack\Entities\Page::take(1)->get()->first();
         $this->checkAccessPermission('page-update-all', [
             $otherPage->getUrl() . '/edit'
         ], [
@@ -560,7 +560,7 @@ class RolesTest extends BrowserKitTest
     public function test_page_delete_own_permission()
     {
         $this->giveUserPermissions($this->user, ['page-update-all']);
-        $otherPage = \BookStack\Page::take(1)->get()->first();
+        $otherPage = \BookStack\Entities\Page::take(1)->get()->first();
         $ownPage = $this->createEntityChainBelongingToUser($this->user)['page'];
         $this->checkAccessPermission('page-delete-own', [
             $ownPage->getUrl() . '/delete'
@@ -582,7 +582,7 @@ class RolesTest extends BrowserKitTest
     public function test_page_delete_all_permission()
     {
         $this->giveUserPermissions($this->user, ['page-update-all']);
-        $otherPage = \BookStack\Page::take(1)->get()->first();
+        $otherPage = \BookStack\Entities\Page::take(1)->get()->first();
         $this->checkAccessPermission('page-delete-all', [
             $otherPage->getUrl() . '/delete'
         ], [
@@ -598,7 +598,7 @@ class RolesTest extends BrowserKitTest
 
     public function test_public_role_visible_in_user_edit_screen()
     {
-        $user = \BookStack\User::first();
+        $user = \BookStack\Auth\User::first();
         $this->asAdmin()->visit('/settings/users/' . $user->id)
             ->seeElement('#roles-admin')
             ->seeElement('#roles-public');
@@ -633,8 +633,8 @@ class RolesTest extends BrowserKitTest
     public function test_image_delete_own_permission()
     {
         $this->giveUserPermissions($this->user, ['image-update-all']);
-        $page = \BookStack\Page::first();
-        $image = factory(\BookStack\Image::class)->create(['uploaded_to' => $page->id, 'created_by' => $this->user->id, 'updated_by' => $this->user->id]);
+        $page = \BookStack\Entities\Page::first();
+        $image = factory(\BookStack\Uploads\Image::class)->create(['uploaded_to' => $page->id, 'created_by' => $this->user->id, 'updated_by' => $this->user->id]);
 
         $this->actingAs($this->user)->json('delete', '/images/' . $image->id)
             ->seeStatusCode(403);
@@ -650,8 +650,8 @@ class RolesTest extends BrowserKitTest
     {
         $this->giveUserPermissions($this->user, ['image-update-all']);
         $admin = $this->getAdmin();
-        $page = \BookStack\Page::first();
-        $image = factory(\BookStack\Image::class)->create(['uploaded_to' => $page->id, 'created_by' => $admin->id, 'updated_by' => $admin->id]);
+        $page = \BookStack\Entities\Page::first();
+        $image = factory(\BookStack\Uploads\Image::class)->create(['uploaded_to' => $page->id, 'created_by' => $admin->id, 'updated_by' => $admin->id]);
 
         $this->actingAs($this->user)->json('delete', '/images/' . $image->id)
             ->seeStatusCode(403);
@@ -672,7 +672,7 @@ class RolesTest extends BrowserKitTest
     {
         // To cover issue fixed in f99c8ff99aee9beb8c692f36d4b84dc6e651e50a.
         $page = Page::first();
-        $viewerRole = \BookStack\Role::getRole('viewer');
+        $viewerRole = \BookStack\Auth\Role::getRole('viewer');
         $viewer = $this->getViewer();
         $this->actingAs($viewer)->visit($page->getUrl())->assertResponseStatus(200);
 
@@ -690,14 +690,14 @@ class RolesTest extends BrowserKitTest
     {
         $admin = $this->getAdmin();
         // Book links
-        $book = factory(\BookStack\Book::class)->create(['created_by' => $admin->id, 'updated_by' => $admin->id]);
+        $book = factory(\BookStack\Entities\Book::class)->create(['created_by' => $admin->id, 'updated_by' => $admin->id]);
         $this->updateEntityPermissions($book);
         $this->actingAs($this->getViewer())->visit($book->getUrl())
             ->dontSee('Create a new page')
             ->dontSee('Add a chapter');
 
         // Chapter links
-        $chapter = factory(\BookStack\Chapter::class)->create(['created_by' => $admin->id, 'updated_by' => $admin->id, 'book_id' => $book->id]);
+        $chapter = factory(\BookStack\Entities\Chapter::class)->create(['created_by' => $admin->id, 'updated_by' => $admin->id, 'book_id' => $book->id]);
         $this->updateEntityPermissions($chapter);
         $this->actingAs($this->getViewer())->visit($chapter->getUrl())
             ->dontSee('Create a new page')
@@ -781,7 +781,7 @@ class RolesTest extends BrowserKitTest
     }
 
     private function addComment($page) {
-        $comment = factory(\BookStack\Comment::class)->make();
+        $comment = factory(\BookStack\Actions\Comment::class)->make();
         $url = "/ajax/page/$page->id/comment";
         $request = [
             'text' => $comment->text,
@@ -794,7 +794,7 @@ class RolesTest extends BrowserKitTest
     }
 
     private function updateComment($commentId) {
-        $comment = factory(\BookStack\Comment::class)->make();
+        $comment = factory(\BookStack\Actions\Comment::class)->make();
         $url = "/ajax/comment/$commentId";
         $request = [
             'text' => $comment->text,
index dadb37e46ce2cac9082d98b05fef2615fee972db..671b5ee420453d266618b09a2f795de1c124d7dc 100644 (file)
@@ -6,18 +6,18 @@ class PublicActionTest extends BrowserKitTest
     public function test_app_not_public()
     {
         $this->setSettings(['app-public' => 'false']);
-        $book = \BookStack\Book::orderBy('name', 'asc')->first();
+        $book = \BookStack\Entities\Book::orderBy('name', 'asc')->first();
         $this->visit('/books')->seePageIs('/login');
         $this->visit($book->getUrl())->seePageIs('/login');
 
-        $page = \BookStack\Page::first();
+        $page = \BookStack\Entities\Page::first();
         $this->visit($page->getUrl())->seePageIs('/login');
     }
 
     public function test_books_viewable()
     {
         $this->setSettings(['app-public' => 'true']);
-        $books = \BookStack\Book::orderBy('name', 'asc')->take(10)->get();
+        $books = \BookStack\Entities\Book::orderBy('name', 'asc')->take(10)->get();
         $bookToVisit = $books[1];
 
         // Check books index page is showing
@@ -34,7 +34,7 @@ class PublicActionTest extends BrowserKitTest
     public function test_chapters_viewable()
     {
         $this->setSettings(['app-public' => 'true']);
-        $chapterToVisit = \BookStack\Chapter::first();
+        $chapterToVisit = \BookStack\Entities\Chapter::first();
         $pageToVisit = $chapterToVisit->pages()->first();
 
         // Check chapters index page is showing
@@ -52,15 +52,15 @@ class PublicActionTest extends BrowserKitTest
     public function test_public_page_creation()
     {
         $this->setSettings(['app-public' => 'true']);
-        $publicRole = \BookStack\Role::getSystemRole('public');
+        $publicRole = \BookStack\Auth\Role::getSystemRole('public');
         // Grant all permissions to public
         $publicRole->permissions()->detach();
-        foreach (\BookStack\RolePermission::all() as $perm) {
+        foreach (\BookStack\Auth\Permissions\RolePermission::all() as $perm) {
             $publicRole->attachPermission($perm);
         }
-        $this->app[\BookStack\Services\PermissionService::class]->buildJointPermissionForRole($publicRole);
+        $this->app[\BookStack\Auth\Permissions\PermissionService::class]->buildJointPermissionForRole($publicRole);
 
-        $chapter = \BookStack\Chapter::first();
+        $chapter = \BookStack\Entities\Chapter::first();
         $this->visit($chapter->book->getUrl());
         $this->visit($chapter->getUrl())
             ->click('New Page')
@@ -71,7 +71,7 @@ class PublicActionTest extends BrowserKitTest
             'name' => 'My guest page'
         ])->seePageIs($chapter->book->getUrl('/page/my-guest-page/edit'));
 
-        $user = \BookStack\User::getDefault();
+        $user = \BookStack\Auth\User::getDefault();
         $this->seeInDatabase('pages', [
             'name' => 'My guest page',
             'chapter_id' => $chapter->id,
@@ -82,7 +82,7 @@ class PublicActionTest extends BrowserKitTest
 
     public function test_content_not_listed_on_404_for_public_users()
     {
-        $page = \BookStack\Page::first();
+        $page = \BookStack\Entities\Page::first();
         $this->asAdmin()->visit($page->getUrl());
         \Auth::logout();
         view()->share('pageTitle', '');
index ad983423c6f1122fcf056a6a15cdc48c4bfd22c5..8e903be11a3089ed25a3c1ed77c7890924b25657 100644 (file)
@@ -1,15 +1,16 @@
 <?php namespace Tests;
 
-use BookStack\Book;
-use BookStack\Bookshelf;
-use BookStack\Chapter;
-use BookStack\Entity;
-use BookStack\Page;
-use BookStack\Repos\EntityRepo;
-use BookStack\Repos\PermissionsRepo;
-use BookStack\Role;
-use BookStack\Services\PermissionService;
-use BookStack\Services\SettingService;
+use BookStack\Entities\Book;
+use BookStack\Entities\Bookshelf;
+use BookStack\Entities\Chapter;
+use BookStack\Entities\Entity;
+use BookStack\Entities\Page;
+use BookStack\Entities\Repos\EntityRepo;
+use BookStack\Auth\Permissions\PermissionsRepo;
+use BookStack\Auth\Role;
+use BookStack\Auth\Permissions\PermissionService;
+use BookStack\Entities\Repos\PageRepo;
+use BookStack\Settings\SettingService;
 
 trait SharedTestHelpers
 {
@@ -67,7 +68,7 @@ trait SharedTestHelpers
      */
     protected function getViewer($attributes = [])
     {
-        $user = \BookStack\Role::getRole('viewer')->users()->first();
+        $user = \BookStack\Auth\Role::getRole('viewer')->users()->first();
         if (!empty($attributes)) $user->forceFill($attributes)->save();
         return $user;
     }
@@ -78,17 +79,17 @@ trait SharedTestHelpers
      */
     protected function regenEntityPermissions(Entity $entity)
     {
-        $this->app[PermissionService::class]->buildJointPermissionsForEntity($entity);
+        app(PermissionService::class)->buildJointPermissionsForEntity($entity);
         $entity->load('jointPermissions');
     }
 
     /**
      * Create and return a new bookshelf.
      * @param array $input
-     * @return Bookshelf
+     * @return \BookStack\Entities\Bookshelf
      */
     public function newShelf($input = ['name' => 'test shelf', 'description' => 'My new test shelf']) {
-        return $this->app[EntityRepo::class]->createFromInput('bookshelf', $input, false);
+        return app(EntityRepo::class)->createFromInput('bookshelf', $input, false);
     }
 
     /**
@@ -97,17 +98,17 @@ trait SharedTestHelpers
      * @return Book
      */
     public function newBook($input = ['name' => 'test book', 'description' => 'My new test book']) {
-        return $this->app[EntityRepo::class]->createFromInput('book', $input, false);
+        return app(EntityRepo::class)->createFromInput('book', $input, false);
     }
 
     /**
      * Create and return a new test chapter
      * @param array $input
      * @param Book $book
-     * @return Chapter
+     * @return \BookStack\Entities\Chapter
      */
     public function newChapter($input = ['name' => 'test chapter', 'description' => 'My new test chapter'], Book $book) {
-        return $this->app[EntityRepo::class]->createFromInput('chapter', $input, $book);
+        return app(EntityRepo::class)->createFromInput('chapter', $input, $book);
     }
 
     /**
@@ -117,9 +118,9 @@ trait SharedTestHelpers
      */
     public function newPage($input = ['name' => 'test page', 'html' => 'My new test page']) {
         $book = Book::first();
-        $entityRepo = $this->app[EntityRepo::class];
-        $draftPage = $entityRepo->getDraftPage($book);
-        return $entityRepo->publishPageDraft($draftPage, $input);
+        $pageRepo = app(PageRepo::class);
+        $draftPage = $pageRepo->getDraftPage($book);
+        return $pageRepo->publishPageDraft($draftPage, $input);
     }
 
     /**
@@ -164,10 +165,10 @@ trait SharedTestHelpers
 
     /**
      * Give the given user some permissions.
-     * @param \BookStack\User $user
+     * @param \BookStack\Auth\User $user
      * @param array $permissions
      */
-    protected function giveUserPermissions(\BookStack\User $user, $permissions = [])
+    protected function giveUserPermissions(\BookStack\Auth\User $user, $permissions = [])
     {
         $newRole = $this->createNewRole($permissions);
         $user->attachRole($newRole);
index c1e254090f27ac1d336001fd7e5630a6813bcc27..0c29f63c5953d1752acbaeb6d890e83ad985d7ea 100644 (file)
@@ -7,7 +7,7 @@ class UserProfileTest extends BrowserKitTest
     public function setUp()
     {
         parent::setUp();
-        $this->user = \BookStack\User::all()->last();
+        $this->user = \BookStack\Auth\User::all()->last();
     }
 
     public function test_profile_page_shows_name()
@@ -87,7 +87,7 @@ class UserProfileTest extends BrowserKitTest
 
     public function test_guest_profile_cannot_be_deleted()
     {
-        $guestUser = \BookStack\User::getDefault();
+        $guestUser = \BookStack\Auth\User::getDefault();
         $this->asAdmin()->visit('/settings/users/' . $guestUser->id . '/delete')
             ->see('Delete User')->see('Guest')
             ->press('Confirm')
diff --git a/version b/version
index 648d222611c66aceafe93f87d4732cab0b0ae249..5e55414e45330856406520f2dd93b94f170af846 100644 (file)
--- a/version
+++ b/version
@@ -1 +1 @@
-v0.22-dev
+v0.25-dev