diff --git a/app/Console/Commands/TestGenerator.php b/app/Console/Commands/TestGenerator.php index e2a940b..a678eb8 100644 --- a/app/Console/Commands/TestGenerator.php +++ b/app/Console/Commands/TestGenerator.php @@ -46,6 +46,7 @@ class TestGenerator extends Command $models = $this->getSelectedModels(); + // if (!is_dir('tests/Feature/' . ucfirst($model))) { // mkdir('tests/Feature/' . ucfirst($model), 0777, true); // } else { diff --git a/app/Http/Controllers/CollectionController.php b/app/Http/Controllers/CollectionController.php index f389947..2fe3b5f 100644 --- a/app/Http/Controllers/CollectionController.php +++ b/app/Http/Controllers/CollectionController.php @@ -2,8 +2,10 @@ namespace App\Http\Controllers; +use App\Documents\PolicyDocument; use App\Http\Resources\CollectionResource; use App\Models\Collection; +use App\Utilities\Polices\BasePolicy; use Illuminate\Http\Request; class CollectionController extends Controller @@ -11,23 +13,30 @@ class CollectionController extends Controller public function show(Collection $collection) { + + BasePolicy::allow(app('modelDocument')?->getPolicy,$collection); + return new CollectionResource($collection); } public function store(Request $request) { + BasePolicy::allow(app('modelDocument')?->storePolicy); $collection = Collection::create($request->all()); return new CollectionResource($collection); } public function update(Request $request, Collection $collection) { + BasePolicy::allow(app('modelDocument')?->updatePolicy, $collection); + $collection->update($request->all()); return new CollectionResource($collection); } public function destroy(Collection $collection) { + BasePolicy::allow(app('modelDocument')?->{$collection->trashed() ? 'restorePolicy' : 'deletePolicy'},$collection); if ($collection->trashed()) { return $collection->restore(); } diff --git a/app/Http/Kernel.php b/app/Http/Kernel.php index 35fb8b0..9217b71 100644 --- a/app/Http/Kernel.php +++ b/app/Http/Kernel.php @@ -45,7 +45,7 @@ class Kernel extends HttpKernel // \Laravel\Sanctum\Http\Middleware\EnsureFrontendRequestsAreStateful::class, 'throttle:api', \Illuminate\Routing\Middleware\SubstituteBindings::class, - // BindModelDocumentMiddleware::class, + BindModelDocumentMiddleware::class, BindCollectionModelMiddleware::class, BindFileModelMiddleware::class, ], diff --git a/app/Models/Collection.php b/app/Models/Collection.php index 5582875..f6d097a 100644 --- a/app/Models/Collection.php +++ b/app/Models/Collection.php @@ -2,6 +2,8 @@ namespace App\Models; +use App\Models\Traits\Validatable; +use App\Models\Traits\ValidationMaker; use Illuminate\Database\Eloquent\Casts\Attribute; use Illuminate\Database\Eloquent\Factories\HasFactory; use Illuminate\Database\Eloquent\Model; diff --git a/database/factories/CollectionFactory.php b/database/factories/CollectionFactory.php index 4f853d3..6f9b49d 100644 --- a/database/factories/CollectionFactory.php +++ b/database/factories/CollectionFactory.php @@ -10,6 +10,7 @@ use Illuminate\Database\Eloquent\Factories\Factory; */ class CollectionFactory extends Factory { + use BaseFactory; /** * Define the model's default state. * @@ -21,17 +22,17 @@ class CollectionFactory extends Factory "name" => fake()->name(), "public" => "public", "disk" => "local", - "count" => rand(3,18), - "tmp_support" => rand(0,1), + "count" => rand(3, 18), + "tmp_support" => rand(0, 1), "remove_tmp_time" => 132, - "max_file_size" => rand(300,2000), - "min_file_size" => rand(300,2000), - "max_width" => rand(300,2000), - "min_width" => rand(300,2000), - "max_height" => rand(300,2000), - "min_height" => rand(300,2000), - "alt_required" => rand(0,1), - "description_required" => rand(0,1), + "max_file_size" => rand(300, 2000), + "min_file_size" => rand(300, 2000), + "max_width" => rand(300, 2000), + "min_width" => rand(300, 2000), + "max_height" => rand(300, 2000), + "min_height" => rand(300, 2000), + "alt_required" => rand(0, 1), + "description_required" => rand(0, 1), "exts" => [ "jpg", "jpeg", @@ -49,4 +50,25 @@ class CollectionFactory extends Factory "expire_date" => "2022-07-27 09:17:59" ]; } + + public function testGeneratorConfig() + { + return [ + 'store' => '', + 'update' => '', + 'show' => '', + 'delete' => '', + ]; + } + + public function dependencyProvider() + { + return []; + } + public function list() + { + return [ + 'name:gt' + ]; + } } diff --git a/routes/api.php b/routes/api.php index b6df73b..e35bb99 100644 --- a/routes/api.php +++ b/routes/api.php @@ -30,7 +30,7 @@ Route::get('newTmp/{uuid}', function ($uuid) { Route::group(['as' => 'api.'], function () { Route::apiResource('collections', CollectionController::class); - Route::delete('collections/{collection}', [CollectionController::class, "destroy"])->withTrashed(); + Route::delete('collections/{collection}', [CollectionController::class, "destroy"])->withTrashed()->name('collections.destroy'); Route::get('{collection_name}/{uuid}.{extention}', [FileController::class, 'show'])->name('files.show'); // Route::get('{collection_name}/{path}', [FileController::class, 'private'])->name('files.private'); Route::post('{collection_name}/{model_id?}', [FileController::class, 'store'])->name('files.store'); diff --git a/tests/Feature/Collection/CollectionDeleteTest.php b/tests/Feature/Collection/CollectionDeleteTest.php new file mode 100644 index 0000000..f48347b --- /dev/null +++ b/tests/Feature/Collection/CollectionDeleteTest.php @@ -0,0 +1,56 @@ +modelWithPolicy('collections', ['permission:collections.delete']) + ->loginAs(['collections.delete']) + ->deleteJson(route("api.collections.destroy", $collection = $this->one(Collection::class))) + ->assertOk(); + + $this->loginAsAdmin() + ->getJson(route("api.collections.show", $collection)) + ->assertNotFound(); + } + + public function test_collection_restore_success() + { + $this->modelWithPolicy('collections', ['permission:collections.restore']) + ->loginAsUser(['collections.restore']) + ->deleteJson(route("api.collections.destroy", $collection = $this->trashed(Collection::class))) + ->assertOk(); + + $this->loginAsAdmin() + ->getJson(route("api.collections.show", $collection)) + ->assertOk(); + } + + public function test_collection_delete_forbidden() + { + $this->modelWithPolicy('collections', ['permission:collections.delete']) + ->loginAs(['wrong.permission']) + ->deleteJson(route("api.collections.destroy", $collection = $this->one(Collection::class))) + ->assertForbidden(); + } + + public function test_collection_restore_forbidden() + { + $this->modelWithPolicy('collections', ['permission:collections.restore']) + ->loginAs(['wrong.permission']) + ->deleteJson(route("api.collections.destroy", $collection = $this->trashed(Collection::class))) + ->assertForbidden(); + } + + public function test_collection_delete_notFound() + { + $this->loginAsAdmin() + ->deleteJson(route("api.collections.destroy", 0)) + ->assertNotFound(); + } +} diff --git a/tests/Feature/Collection/CollectionShowTest.php b/tests/Feature/Collection/CollectionShowTest.php new file mode 100644 index 0000000..64d7525 --- /dev/null +++ b/tests/Feature/Collection/CollectionShowTest.php @@ -0,0 +1,34 @@ +modelWithPolicy('collections', ['permission:collections.show']) + ->loginAs(['collections.show']) + ->getJson(route("api.collections.show", $collection = $this->one(Collection::class))) + ->assertOk(); + } + + public function test_collection_show_not_found() + { + $this->modelWithPolicy('collections', ['permission:collections.show']) + ->loginAs(['collections.show']) + ->getJson(route("api.collections.show", 0)) + ->assertNotFound(); + } + + public function test_collection_show_forbidden() + { + $this->modelWithPolicy('collections', ['permission:collections.show']) + ->loginAs(['wrong.permission']) + ->getJson(route("api.collections.show", $collection = $this->one(Collection::class)), []) + ->assertForbidden(); + } +} diff --git a/tests/Feature/Collection/CollectionStoreTest.php b/tests/Feature/Collection/CollectionStoreTest.php new file mode 100644 index 0000000..28dd875 --- /dev/null +++ b/tests/Feature/Collection/CollectionStoreTest.php @@ -0,0 +1,40 @@ +modelWithPolicy('collections', ['permission:collections.store']) + ->loginAs(['collections.store']) + ->postJson(route('api.collections.store'), $collection = $this->make(Collection::class)) + ->assertCreated(); + } + + /** + * @testWith + * ["name:gt"] + */ + public function test_collection_store_unprocessable($field) + { + $this->modelWithPolicy('collections', ['permission:collections.store']) + ->loginAsAdmin() + ->postJson(route("api.collections.store"), $collection = $this->make(collection::class, smash: $field, withDependency: true)) + ->assertUnprocessable(); + + } + + public function test_collection_store_forbidden() + { + $this->modelWithPolicy('collections', ['permission:collections.store']) + ->loginAs(['wrong.permission']) + ->postJson(route("api.collections.store"), []) + ->assertForbidden(); + } +} diff --git a/tests/Feature/Collection/CollectionUpdateTest.php b/tests/Feature/Collection/CollectionUpdateTest.php new file mode 100644 index 0000000..7da3e24 --- /dev/null +++ b/tests/Feature/Collection/CollectionUpdateTest.php @@ -0,0 +1,55 @@ +modelWithPolicy('collections', ['permission:collections.update']) + ->loginAs(['collections.update']) + ->putJson( + route("api.collections.update", $collection = $this->one(Collection::class)), + $update = $this->make(Collection::class, withDependency: true) + ) + ->assertOk(); + } + + /** + * @testWith + * ["name:gt"] + */ + public function test_collection_update_unprocessable($field) + { + $this->modelWithPolicy('collections', ['permission:collections.update']) + ->loginAs(['collections.update'])->putJson( + route("api.collections.update", $collection = $this->one(Collection::class)), + $update = $this->make(collection::class, smash: $field, withDependency: true) + ) + ->assertUnprocessable(); + } + + public function test_collection_update_forbidden() + { + $this->modelWithPolicy('collections', ['permission:collections.update']) + ->loginAs(['wrong.permission']) + ->putJson( + route("api.collections.update", $collection = $this->one(Collection::class)), + [] + ) + ->assertForbidden(); + } + + public function test_collection_update_not_found() + { + $this->loginAsUser(['collections.update']) + ->putJson(route("api.collections.update", 0), []) + ->assertNotFound(); + } +}