Skip to content

Commit

Permalink
#443 - employment, medical and ohs history (#451)
Browse files Browse the repository at this point in the history
* #443 - added tests for user history

* #443 - added console command for migrating data

* #443 - cr fixes

* #443 - fix: code review fixes

* #443 - fix: fixes after code review - fixed validation and edit view

* #443 - fix: fixes
  • Loading branch information
kamilpiech97 authored Jun 28, 2024
1 parent 83e4f9f commit e2d7ddd
Show file tree
Hide file tree
Showing 22 changed files with 1,223 additions and 196 deletions.
49 changes: 49 additions & 0 deletions app/Console/Commands/MigrateProfileDataIntoUserHistory.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
<?php

declare(strict_types=1);

namespace Toby\Console\Commands;

use Illuminate\Console\Command;
use Toby\Enums\UserHistoryType;
use Toby\Models\User;

class MigrateProfileDataIntoUserHistory extends Command
{
protected $signature = "toby:move-user-data-to-history";
protected $description = "Move profile data to user history";

public function handle(): void
{
$users = User::query()
->with("profile")
->get();

foreach ($users as $user) {
$this->moveMedicalDataToHistory($user);
$this->moveOhsDataToHistory($user);
}
}

private function moveMedicalDataToHistory(User $user): void
{
if ($user->profile->last_medical_exam_date && $user->profile->next_medical_exam_date) {
$user->histories()->create([
"from" => $user->profile->last_medical_exam_date,
"to" => $user->profile->next_medical_exam_date,
"type" => UserHistoryType::MedicalExam,
]);
}
}

private function moveOhsDataToHistory(User $user): void
{
if ($user->profile->last_ohs_training_date && $user->profile->next_ohs_training_date) {
$user->histories()->create([
"from" => $user->profile->last_ohs_training_date,
"to" => $user->profile->next_ohs_training_date,
"type" => UserHistoryType::OhsTraining,
]);
}
}
}
29 changes: 29 additions & 0 deletions app/Enums/UserHistoryType.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
<?php

declare(strict_types=1);

namespace Toby\Enums;

enum UserHistoryType: string
{
case Employment = "employment";
case MedicalExam = "medical_exam";
case OhsTraining = "ohs_training";

public function label(): string
{
return __($this->value);
}

public static function casesToSelect(): array
{
$cases = collect(UserHistoryType::cases());

return $cases->map(
fn(UserHistoryType $enum): array => [
"label" => $enum->label(),
"value" => $enum->value,
],
)->toArray();
}
}
1 change: 1 addition & 0 deletions app/Http/Controllers/UserController.php
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ public function index(Request $request): Response
$status = $request->query("status", "active");

$users = User::query()
->with("histories")
->search($searchText)
->status($status)
->orderByProfileField("last_name")
Expand Down
86 changes: 86 additions & 0 deletions app/Http/Controllers/UserHistoryController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
<?php

declare(strict_types=1);

namespace Toby\Http\Controllers;

use Illuminate\Http\RedirectResponse;
use Inertia\Response;
use Toby\Enums\EmploymentForm;
use Toby\Enums\UserHistoryType;
use Toby\Http\Requests\UserHistoryRequest;
use Toby\Http\Resources\UserHistoryResource;
use Toby\Models\User;
use Toby\Models\UserHistory;

class UserHistoryController extends Controller
{
public function index(User $user): Response
{
$this->authorize("manageUsers");

$history = $user->histories()
->orderBy("from", "desc")
->get();

return inertia("UserHistory/Index", [
"history" => UserHistoryResource::collection($history),
"userId" => $user->id,
]);
}

public function create(User $user): Response
{
$this->authorize("manageUsers");

return inertia("UserHistory/Create", [
"types" => UserHistoryType::casesToSelect(),
"employmentForms" => EmploymentForm::casesToSelect(),
"userId" => $user->id,
]);
}

public function store(UserHistoryRequest $request, User $user): RedirectResponse
{
$this->authorize("manageUsers");

$user->histories()->create($request->data());

return redirect()
->route("users.history", $user)
->with("success", __("User history created."));
}

public function edit(UserHistory $history): Response
{
$this->authorize("manageUsers");

return inertia("UserHistory/Edit", [
"history" => UserHistoryResource::make($history),
"types" => UserHistoryType::casesToSelect(),
"employmentForms" => EmploymentForm::casesToSelect(),
]);
}

public function update(UserHistoryRequest $request, UserHistory $history): RedirectResponse
{
$this->authorize("manageUsers");

$history->update($request->data());

return redirect()
->route("users.history", $history->user_id)
->with("success", __("User history updated."));
}

public function destroy(UserHistory $history): RedirectResponse
{
$this->authorize("manageUsers");

$history->delete();

return redirect()
->back()
->with("success", __("User history deleted."));
}
}
35 changes: 35 additions & 0 deletions app/Http/Requests/UserHistoryRequest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
<?php

declare(strict_types=1);

namespace Toby\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;
use Illuminate\Validation\Rules\Enum;
use Toby\Enums\EmploymentForm;
use Toby\Enums\UserHistoryType;

class UserHistoryRequest extends FormRequest
{
public function rules(): array
{
return [
"from" => ["required", "date"],
"to" => ["nullable", "date", "after:from", "required_if:type," . UserHistoryType::MedicalExam->value . "," . UserHistoryType::OhsTraining->value],
"comment" => ["nullable", "string", "max:255"],
"type" => ["required", new Enum(UserHistoryType::class)],
"employmentForm" => [new Enum(EmploymentForm::class), "required_if:type," . UserHistoryType::Employment->value],
];
}

public function data(): array
{
return [
"from" => $this->get("from"),
"to" => $this->get("to"),
"type" => $this->get("type"),
"employment_form" => $this->get("type") === UserHistoryType::Employment->value ? $this->get("employmentForm") : null,
"comment" => $this->get("comment"),
];
}
}
6 changes: 0 additions & 6 deletions app/Http/Requests/UserRequest.php
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,6 @@ public function rules(): array
"employmentDate" => ["required", "date_format:Y-m-d"],
"birthday" => ["required", "date_format:Y-m-d", "before:today"],
"slackId" => [],
"nextMedicalExamDate" => ["nullable", "after:lastMedicalExamDate"],
"nextOhsTrainingDate" => ["nullable", "after:lastOhsTrainingDate"],
];
}

Expand All @@ -47,10 +45,6 @@ public function profileData(): array
"employment_date" => $this->get("employmentDate"),
"birthday" => $this->get("birthday"),
"slack_id" => $this->get("slackId"),
"last_medical_exam_date" => $this->get("lastMedicalExamDate"),
"next_medical_exam_date" => $this->get("nextMedicalExamDate"),
"last_ohs_training_date" => $this->get("lastOhsTrainingDate"),
"next_ohs_training_date" => $this->get("nextOhsTrainingDate"),
];
}
}
27 changes: 27 additions & 0 deletions app/Http/Resources/UserHistoryResource.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
<?php

declare(strict_types=1);

namespace Toby\Http\Resources;

use Illuminate\Http\Resources\Json\JsonResource;

class UserHistoryResource extends JsonResource
{
public static $wrap = null;

public function toArray($request): array
{
return [
"id" => $this->id,
"from" => $this->from->format("d.m.Y"),
"to" => $this->to?->format("d.m.Y"),
"type" => $this->type->value,
"typeLabel" => $this->type->label(),
"employmentFormLabel" => $this->employment_form?->label(),
"employmentForm" => $this->employment_form?->value,
"comment" => $this->comment,
"userId" => $this->user_id,
];
}
}
11 changes: 7 additions & 4 deletions app/Http/Resources/UserResource.php
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,9 @@ class UserResource extends JsonResource

public function toArray($request): array
{
$lastMedicalExam = $this->lastMedicalExam();
$lastOhsTraining = $this->lastOhsTraining();

return [
"id" => $this->id,
"name" => $this->profile->full_name,
Expand All @@ -23,10 +26,10 @@ public function toArray($request): array
"lastActiveAt" => $this->last_active_at?->toDateTimeString(),
"employmentForm" => $this->profile->employment_form->label(),
"employmentDate" => $this->profile->employment_date->toDisplayString(),
"lastMedicalExamDate" => $this->profile->last_medical_exam_date?->toDisplayString(),
"nextMedicalExamDate" => $this->profile->next_medical_exam_date?->toDisplayString(),
"lastOhsTrainingDate" => $this->profile->last_ohs_training_date?->toDisplayString(),
"nextOhsTrainingDate" => $this->profile->next_ohs_training_date?->toDisplayString(),
"lastMedicalExamDate" => $lastMedicalExam?->from?->toDisplayString(),
"nextMedicalExamDate" => $lastMedicalExam?->to?->toDisplayString(),
"lastOhsTrainingDate" => $lastOhsTraining?->from?->toDisplayString(),
"nextOhsTrainingDate" => $lastOhsTraining?->to?->toDisplayString(),
];
}
}
22 changes: 22 additions & 0 deletions app/Models/User.php
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
use Spatie\Permission\Traits\HasRoles;
use Toby\Enums\EmploymentForm;
use Toby\Enums\Role;
use Toby\Enums\UserHistoryType;
use Toby\Notifications\Notifiable as NotifiableInterface;

/**
Expand Down Expand Up @@ -80,6 +81,27 @@ public function vacations(): HasMany
return $this->hasMany(Vacation::class);
}

public function histories(): HasMany
{
return $this->hasMany(UserHistory::class);
}

public function lastMedicalExam(): ?UserHistory
{
return $this->histories()
->where("type", UserHistoryType::MedicalExam)
->orderBy("from", "desc")
->first();
}

public function lastOhsTraining(): ?UserHistory
{
return $this->histories()
->where("type", UserHistoryType::OhsTraining)
->orderBy("from", "desc")
->first();
}

public function keys(): HasMany
{
return $this->hasMany(Key::class);
Expand Down
40 changes: 40 additions & 0 deletions app/Models/UserHistory.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
<?php

declare(strict_types=1);

namespace Toby\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;
use Illuminate\Support\Carbon;
use Toby\Enums\EmploymentForm;
use Toby\Enums\UserHistoryType;

/**
* @property int $id
* @property int $user_id
* @property string $comment
* @property Carbon $from
* @property Carbon $to
* @property UserHistoryType $type
* @property EmploymentForm $employment_form
* @property User $user
*/
class UserHistory extends Model
{
use HasFactory;

protected $guarded = [];
protected $casts = [
"from" => "date:Y-m-d",
"to" => "date:Y-m-d",
"type" => UserHistoryType::class,
"employment_form" => EmploymentForm::class,
];

public function user(): BelongsTo
{
return $this->belongsTo(User::class);
}
}
30 changes: 30 additions & 0 deletions database/factories/UserHistoryFactory.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
<?php

declare(strict_types=1);

namespace Database\Factories;

use Illuminate\Database\Eloquent\Factories\Factory;
use Toby\Enums\EmploymentForm;
use Toby\Enums\UserHistoryType;
use Toby\Models\User;
use Toby\Models\UserHistory;

class UserHistoryFactory extends Factory
{
protected $model = UserHistory::class;

public function definition(): array
{
$type = $this->faker->randomElement(UserHistoryType::cases());

return [
"user_id" => User::factory(),
"from" => $this->faker->date(),
"to" => $this->faker->date(),
"type" => $type,
"employment_form" => $type->is(UserHistoryType::Employment) ? $this->faker->randomElement(EmploymentForm::cases()) : null,
"comment" => $this->faker->sentence(),
];
}
}
Loading

0 comments on commit e2d7ddd

Please sign in to comment.