create([ 'email' => uniqid('inv_', true).'@test.example', 'password' => bcrypt('password'), ]); $user->forceFill([ 'admin' => $adminLevel, 'confirmed' => true, 'active' => true, 'wizard' => 100, 'blocked' => false, ])->save(); return $user->fresh(); } function ensureCountry(): Country { return Country::query()->firstOrCreate( ['code' => 'DE'], [ 'phone' => '00', 'en' => 'Germany', 'de' => 'Deutschland', 'es' => 'Germany', 'fr' => 'Germany', 'it' => 'Germany', 'ru' => 'Germany', 'active' => true, ] ); } test('locations full CRUD as superadmin', function () { $user = makeUser(8); $this->actingAs($user, 'user'); $this->get(route('admin.inventory.locations.index'))->assertSuccessful(); $this->get(route('admin.inventory.locations.create'))->assertSuccessful(); $this->post(route('admin.inventory.locations.store'), [ 'name' => 'CRUD-Lager-A', 'active' => '1', ])->assertRedirect(route('admin.inventory.locations.index')); $location = Location::query()->where('name', 'CRUD-Lager-A')->firstOrFail(); $this->get(route('admin.inventory.locations.edit', $location))->assertSuccessful(); $this->put(route('admin.inventory.locations.update', $location), [ 'name' => 'CRUD-Lager-B', 'active' => '1', ])->assertRedirect(route('admin.inventory.locations.index')); $location->refresh(); expect($location->name)->toBe('CRUD-Lager-B'); $this->delete(route('admin.inventory.locations.destroy', $location)) ->assertRedirect(route('admin.inventory.locations.index')); expect(Location::query()->whereKey($location->id)->exists())->toBeFalse(); }); test('material qualities full CRUD as superadmin', function () { $user = makeUser(8); $this->actingAs($user, 'user'); $this->get(route('admin.inventory.material-qualities.index'))->assertSuccessful(); $this->get(route('admin.inventory.material-qualities.create'))->assertSuccessful(); $this->post(route('admin.inventory.material-qualities.store'), [ 'name' => 'CRUD-Qualität', 'pos' => 7, ])->assertRedirect(route('admin.inventory.material-qualities.index')); $model = MaterialQuality::query()->where('name', 'CRUD-Qualität')->firstOrFail(); expect($model->pos)->toBe(7); $this->get(route('admin.inventory.material-qualities.edit', $model))->assertSuccessful(); $this->put(route('admin.inventory.material-qualities.update', $model), [ 'name' => 'CRUD-Qualität-upd', 'pos' => 8, ])->assertRedirect(route('admin.inventory.material-qualities.index')); $model->refresh(); expect($model->name)->toBe('CRUD-Qualität-upd'); expect($model->pos)->toBe(8); $this->delete(route('admin.inventory.material-qualities.destroy', $model)) ->assertRedirect(route('admin.inventory.material-qualities.index')); expect(MaterialQuality::query()->whereKey($model->id)->exists())->toBeFalse(); }); test('packaging materials full CRUD as superadmin', function () { $user = makeUser(8); $this->actingAs($user, 'user'); $this->get(route('admin.inventory.packaging-materials.index'))->assertSuccessful(); $this->get(route('admin.inventory.packaging-materials.create'))->assertSuccessful(); $this->post(route('admin.inventory.packaging-materials.store'), [ 'name' => 'CRUD-Verpackungsmat', 'pos' => 3, ])->assertRedirect(route('admin.inventory.packaging-materials.index')); $model = PackagingMaterial::query()->where('name', 'CRUD-Verpackungsmat')->firstOrFail(); $this->get(route('admin.inventory.packaging-materials.edit', $model))->assertSuccessful(); $this->put(route('admin.inventory.packaging-materials.update', $model), [ 'name' => 'CRUD-Verpackungsmat-upd', 'pos' => 4, ])->assertRedirect(route('admin.inventory.packaging-materials.index')); $model->refresh(); expect($model->name)->toBe('CRUD-Verpackungsmat-upd'); $this->delete(route('admin.inventory.packaging-materials.destroy', $model)) ->assertRedirect(route('admin.inventory.packaging-materials.index')); expect(PackagingMaterial::query()->whereKey($model->id)->exists())->toBeFalse(); }); test('supplier categories full CRUD as admin', function () { $user = makeUser(7); $this->actingAs($user, 'user'); $this->get(route('admin.inventory.supplier-categories.index'))->assertSuccessful(); $this->get(route('admin.inventory.supplier-categories.create'))->assertSuccessful(); $this->post(route('admin.inventory.supplier-categories.store'), [ 'name' => 'CRUD-Lief-Kat', 'pos' => 2, ])->assertRedirect(route('admin.inventory.supplier-categories.index')); $model = SupplierCategory::query()->where('name', 'CRUD-Lief-Kat')->firstOrFail(); $this->get(route('admin.inventory.supplier-categories.edit', $model))->assertSuccessful(); $this->put(route('admin.inventory.supplier-categories.update', $model), [ 'name' => 'CRUD-Lief-Kat-upd', 'pos' => 3, ])->assertRedirect(route('admin.inventory.supplier-categories.index')); $model->refresh(); expect($model->name)->toBe('CRUD-Lief-Kat-upd'); $this->delete(route('admin.inventory.supplier-categories.destroy', $model)) ->assertRedirect(route('admin.inventory.supplier-categories.index')); expect(SupplierCategory::query()->whereKey($model->id)->exists())->toBeFalse(); }); test('suppliers full CRUD with category sync as admin', function () { $country = ensureCountry(); $cat = SupplierCategory::query()->create(['name' => 'CRUD-Kat-Sup', 'pos' => 1]); $user = makeUser(7); $this->actingAs($user, 'user'); $this->get(route('admin.inventory.suppliers.index'))->assertSuccessful(); $this->get(route('admin.inventory.suppliers.create'))->assertSuccessful(); $this->post(route('admin.inventory.suppliers.store'), [ 'name' => 'CRUD-Lieferant', 'country_id' => (string) $country->id, 'active' => '1', 'supplier_category_ids' => [(string) $cat->id], 'email' => 'crud@example.test', ])->assertRedirect(route('admin.inventory.suppliers.index')); $supplier = Supplier::query()->where('name', 'CRUD-Lieferant')->firstOrFail(); expect($supplier->supplierCategories()->pluck('supplier_categories.id')->all())->toEqual([$cat->id]); $this->get(route('admin.inventory.suppliers.edit', $supplier))->assertSuccessful(); $this->put(route('admin.inventory.suppliers.update', $supplier), [ 'name' => 'CRUD-Lieferant-upd', 'country_id' => (string) $country->id, 'active' => '1', 'supplier_category_ids' => [(string) $cat->id], 'email' => 'crud-upd@example.test', ])->assertRedirect(route('admin.inventory.suppliers.index')); $supplier->refresh(); expect($supplier->name)->toBe('CRUD-Lieferant-upd'); $this->delete(route('admin.inventory.suppliers.destroy', $supplier)) ->assertRedirect(route('admin.inventory.suppliers.index')); expect(Supplier::query()->whereKey($supplier->id)->exists())->toBeFalse(); expect(Supplier::withTrashed()->whereKey($supplier->id)->exists())->toBeTrue(); }); test('packaging items full CRUD as admin', function () { $material = PackagingMaterial::factory()->create(['name' => 'CRUD-PM-'.uniqid('', true)]); $supplier = Supplier::factory()->create(); $product = Product::query()->create([ 'name' => 'CRUD-Produkt', 'title' => 'CRUD-Produkt', 'active' => true, ]); $user = makeUser(7); $this->actingAs($user, 'user'); $this->get(route('admin.inventory.packaging-items.index'))->assertSuccessful(); $this->get(route('admin.inventory.packaging-items.create'))->assertSuccessful(); $this->post(route('admin.inventory.packaging-items.store'), [ 'packaging_material_id' => (string) $material->id, 'supplier_id' => (string) $supplier->id, 'name' => 'CRUD-Verpack-Art', 'category' => 'packaging', 'weight_grams' => '12.5', 'min_stock_alert' => '100', 'product_id' => (string) $product->id, 'active' => '1', ])->assertRedirect(route('admin.inventory.packaging-items.index', ['category' => 'packaging'])); $item = PackagingItem::query()->where('name', 'CRUD-Verpack-Art')->firstOrFail(); expect($item->packaging_material_id)->toBe($material->id); expect($item->product_id)->toBe($product->id); $this->get(route('admin.inventory.packaging-items.edit', $item))->assertSuccessful(); $this->put(route('admin.inventory.packaging-items.update', $item), [ 'packaging_material_id' => (string) $material->id, 'supplier_id' => '', 'name' => 'CRUD-Verpack-Art-upd', 'category' => 'shipping', 'weight_grams' => '5', 'min_stock_alert' => '', 'product_id' => '', 'active' => '1', ])->assertRedirect(route('admin.inventory.packaging-items.index', ['category' => 'shipping'])); $item->refresh(); expect($item->name)->toBe('CRUD-Verpack-Art-upd'); expect($item->category)->toBe('shipping'); expect($item->supplier_id)->toBeNull(); expect($item->product_id)->toBeNull(); $this->delete(route('admin.inventory.packaging-items.destroy', $item)) ->assertRedirect(route('admin.inventory.packaging-items.index', ['category' => 'shipping'])); expect(PackagingItem::query()->whereKey($item->id)->exists())->toBeFalse(); expect(PackagingItem::withTrashed()->whereKey($item->id)->exists())->toBeTrue(); }); test('admin cannot access superadmin inventory routes', function () { $user = makeUser(7); $this->actingAs($user, 'user'); $this->get(route('admin.inventory.locations.index'))->assertRedirect(route('home')); }); test('admin cannot store locations', function () { $user = makeUser(7); $this->actingAs($user, 'user'); $this->post(route('admin.inventory.locations.store'), [ 'name' => 'Forbidden-Lager', 'active' => '1', ])->assertRedirect(route('home')); expect(Location::query()->where('name', 'Forbidden-Lager')->exists())->toBeFalse(); }); test('copyreader cannot access inventory suppliers', function () { $user = makeUser(1); $this->actingAs($user, 'user'); $this->get(route('admin.inventory.suppliers.index'))->assertRedirect(route('home')); });