feat: add loa requests
This commit adds a feature that allows users to request periods of inactivity from their managers. This is effectively known as a leave of absence. The commit also introduces new permissions and migrations, therefore, you'll need to adapt your database according to these changes.
This commit is contained in:
@@ -2,6 +2,8 @@
|
||||
|
||||
namespace App;
|
||||
|
||||
use App\Exceptions\AbsenceNotActionableException;
|
||||
use Illuminate\Database\Eloquent\Casts\Attribute;
|
||||
use Illuminate\Database\Eloquent\Factories\HasFactory;
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
use Illuminate\Database\Eloquent\Relations\BelongsTo;
|
||||
@@ -25,4 +27,99 @@ class Absence extends Model
|
||||
{
|
||||
return $this->belongsTo('App\User', 'requesterID', 'id');
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Determines whether this model can be setApproved(), setDeclined() or setCancelled()
|
||||
*
|
||||
* @param bool $toCancel Switch the check to cancellability check
|
||||
* @return bool
|
||||
*/
|
||||
public function isActionable(bool $toCancel = false): bool
|
||||
{
|
||||
if ($toCancel)
|
||||
{
|
||||
return in_array($this->getRawOriginal('status'), ['PENDING', 'APPROVED']);
|
||||
}
|
||||
|
||||
return $this->getRawOriginal('status') == 'PENDING';
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Sets the Absence's status as approved
|
||||
*
|
||||
* @return Absence
|
||||
* @throws AbsenceNotActionableException
|
||||
*/
|
||||
public function setApproved(): Absence
|
||||
{
|
||||
if ($this->isActionable())
|
||||
{
|
||||
return tap($this)->update([
|
||||
'status' => 'APPROVED'
|
||||
]);
|
||||
}
|
||||
|
||||
throw new AbsenceNotActionableException('This absence is not actionable!');
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Sets the absence's status as declined
|
||||
*
|
||||
* @return Absence
|
||||
* @throws AbsenceNotActionableException
|
||||
*/
|
||||
public function setDeclined(): Absence
|
||||
{
|
||||
if ($this->isActionable()) {
|
||||
return tap($this)->update([
|
||||
'status' => 'DECLINED'
|
||||
]);
|
||||
}
|
||||
|
||||
throw new AbsenceNotActionableException('This absence is not actionable!');
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Sets the absence's status as cancelled
|
||||
*
|
||||
* @return Absence
|
||||
* @throws AbsenceNotActionableException Thrown when the switch to this status would be invalid
|
||||
*/
|
||||
public function setCancelled(): Absence
|
||||
{
|
||||
if ($this->isActionable(true)) {
|
||||
return tap($this)->update([
|
||||
'status' => 'CANCELLED'
|
||||
]);
|
||||
}
|
||||
|
||||
throw new AbsenceNotActionableException('This absence is not actionable!');
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the absence's status as ended
|
||||
*
|
||||
* @return Absence
|
||||
*/
|
||||
public function setEnded(): Absence
|
||||
{
|
||||
return tap($this)->update([
|
||||
'status' => 'ENDED'
|
||||
]);
|
||||
}
|
||||
|
||||
|
||||
// Look out when retrieving this value;
|
||||
//If you need the unaltered version of it, either adapt to its formatting or call getRawOriginal()
|
||||
protected function status(): Attribute {
|
||||
return Attribute::make(
|
||||
get: fn($value) => ucfirst(strtolower($value))
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user