diff --git a/app/Console/Commands/FixUpAssignedTypeWithoutAssignedTo.php b/app/Console/Commands/FixUpAssignedTypeWithoutAssignedTo.php new file mode 100644 index 0000000000..f368929f16 --- /dev/null +++ b/app/Console/Commands/FixUpAssignedTypeWithoutAssignedTo.php @@ -0,0 +1,32 @@ +whereNotNull('assigned_type')->whereNull('assigned_to')->update(['assigned_type' => null]); + $this->info("Assets with an assigned_type but no assigned_to are fixed"); + } +} diff --git a/app/Events/CheckoutableCheckedIn.php b/app/Events/CheckoutableCheckedIn.php index 48aed2a64d..fedbd49fbe 100644 --- a/app/Events/CheckoutableCheckedIn.php +++ b/app/Events/CheckoutableCheckedIn.php @@ -28,7 +28,7 @@ class CheckoutableCheckedIn $this->checkedOutTo = $checkedOutTo; $this->checkedInBy = $checkedInBy; $this->note = $note; - $this->action_date = $action_date ?? date('Y-m-d'); + $this->action_date = $action_date ?? date('Y-m-d H:i:s'); $this->originalValues = $originalValues; } } diff --git a/app/Http/Controllers/Assets/AssetsController.php b/app/Http/Controllers/Assets/AssetsController.php index e6e6041992..809605bccb 100755 --- a/app/Http/Controllers/Assets/AssetsController.php +++ b/app/Http/Controllers/Assets/AssetsController.php @@ -446,7 +446,7 @@ class AssetsController extends Controller event(new CheckoutableCheckedIn($asset, $target, auth()->user(), 'Checkin on delete', $checkin_at, $originalValues)); DB::table('assets') ->where('id', $asset->id) - ->update(['assigned_to' => null]); + ->update(['assigned_to' => null, 'assigned_type' => null]); } diff --git a/app/Models/Loggable.php b/app/Models/Loggable.php index 4cf5817668..b86dc1cf94 100644 --- a/app/Models/Loggable.php +++ b/app/Models/Loggable.php @@ -95,7 +95,7 @@ trait Loggable $changed = []; $array_to_flip = array_keys($fields_array); - $array_to_flip = array_merge($array_to_flip, ['action_date','name','status_id','location_id','expected_checkin']); + $array_to_flip = array_merge($array_to_flip, ['name','status_id','location_id','expected_checkin']); $originalValues = array_intersect_key($originalValues, array_flip($array_to_flip)); @@ -182,7 +182,7 @@ trait Loggable $log->note = $note; $log->action_date = $action_date; - if (! $log->action_date) { + if (!$action_date) { $log->action_date = date('Y-m-d H:i:s'); } @@ -193,7 +193,7 @@ trait Loggable $changed = []; $array_to_flip = array_keys($fields_array); - $array_to_flip = array_merge($array_to_flip, ['action_date','name','status_id','location_id','expected_checkin']); + $array_to_flip = array_merge($array_to_flip, ['name','status_id','location_id','expected_checkin']); $originalValues = array_intersect_key($originalValues, array_flip($array_to_flip)); diff --git a/app/Observers/AssetObserver.php b/app/Observers/AssetObserver.php index 9f31f3c231..6c07a355ff 100644 --- a/app/Observers/AssetObserver.php +++ b/app/Observers/AssetObserver.php @@ -62,6 +62,7 @@ class AssetObserver $logAction = new Actionlog(); $logAction->item_type = Asset::class; $logAction->item_id = $asset->id; + $logAction->action_date = date('Y-m-d H:i:s'); $logAction->created_at = date('Y-m-d H:i:s'); $logAction->created_by = auth()->id(); $logAction->log_meta = json_encode($changed); @@ -108,6 +109,7 @@ class AssetObserver $logAction = new Actionlog(); $logAction->item_type = Asset::class; // can we instead say $logAction->item = $asset ? $logAction->item_id = $asset->id; + $logAction->action_date = date('Y-m-d H:i:s'); $logAction->created_at = date('Y-m-d H:i:s'); $logAction->created_by = auth()->id(); if($asset->imported) { @@ -128,6 +130,7 @@ class AssetObserver $logAction->item_type = Asset::class; $logAction->item_id = $asset->id; $logAction->created_at = date('Y-m-d H:i:s'); + $logAction->action_date = date('Y-m-d H:i:s'); $logAction->created_by = auth()->id(); $logAction->logaction('delete'); } @@ -143,6 +146,7 @@ class AssetObserver $logAction = new Actionlog(); $logAction->item_type = Asset::class; $logAction->item_id = $asset->id; + $logAction->action_date = date('Y-m-d H:i:s'); $logAction->created_at = date('Y-m-d H:i:s'); $logAction->created_by = auth()->id(); $logAction->logaction('restore'); diff --git a/database/migrations/2025_06_03_053438_fix_assigned_type_without_assigned_to.php b/database/migrations/2025_06_03_053438_fix_assigned_type_without_assigned_to.php new file mode 100644 index 0000000000..9d6a1c8046 --- /dev/null +++ b/database/migrations/2025_06_03_053438_fix_assigned_type_without_assigned_to.php @@ -0,0 +1,23 @@ +whereNotNull('assigned_type')->whereNull('assigned_to')->update(['assigned_type' => null]); + } + + /** + * Reverse the migrations. + */ + public function down(): void + { + + } +}; diff --git a/tests/Feature/Assets/Ui/BulkDeleteAssetsTest.php b/tests/Feature/Assets/Ui/BulkDeleteAssetsTest.php index 747028e5e1..ec8ed33ba8 100644 --- a/tests/Feature/Assets/Ui/BulkDeleteAssetsTest.php +++ b/tests/Feature/Assets/Ui/BulkDeleteAssetsTest.php @@ -137,6 +137,10 @@ class BulkDeleteAssetsTest extends TestCase 'item_type' => Asset::class, ] ); + + $asset->refresh(); + $this->assertNull($asset->assigned_to); + $this->assertNull($asset->assigned_type); } public function testActionLogCreatedUponBulkRestore() diff --git a/tests/Feature/Assets/Ui/DeleteAssetTest.php b/tests/Feature/Assets/Ui/DeleteAssetTest.php index a12e9e2cd0..799643929b 100644 --- a/tests/Feature/Assets/Ui/DeleteAssetTest.php +++ b/tests/Feature/Assets/Ui/DeleteAssetTest.php @@ -48,6 +48,29 @@ class DeleteAssetTest extends TestCase ]); } + public function testActionLogsActionDateIsPopulatedWhenAssetDeleted() + { + $actor = User::factory()->deleteAssets()->create(); + + $asset = Asset::factory()->create(); + + $this->actingAs($actor)->delete(route('hardware.destroy', $asset)); + + $asset->refresh(); + + $this->assertDatabaseHas('action_logs', [ + 'action_date' => $asset->updated_at, + 'created_at' => $asset->updated_at, + 'created_by' => $actor->id, + 'action_type' => 'delete', + 'target_id' => null, + 'target_type' => null, + 'item_type' => Asset::class, + 'item_id' => $asset->id, + ]); + + } + public function testAssetIsCheckedInWhenDeleted() { Event::fake(); @@ -65,6 +88,10 @@ class DeleteAssetTest extends TestCase 'Asset still assigned to user after deletion' ); + $asset->refresh(); + $this->assertNull($asset->assigned_to); + $this->assertNull($asset->assigned_type); + Event::assertDispatched(CheckoutableCheckedIn::class); }