Skip to content

Instantly share code, notes, and snippets.

@akramabdulrahman
Last active June 18, 2017 20:07
Show Gist options
  • Save akramabdulrahman/2af825c98786ed0161bae9df64864111 to your computer and use it in GitHub Desktop.
Save akramabdulrahman/2af825c98786ed0161bae9df64864111 to your computer and use it in GitHub Desktop.
abu sofian challenge
<?php
require '../vendor/autoload.php';
use Carbon\Carbon;
const DATE_FORMAT = 'd/m/Y';
const TIME_FORMAT = 'H:i:s';
Carbon::setWeekStartsAt(Carbon::SATURDAY);
$user = [
"workHours" => [
["from" => "08:00:00", "to" => "16:00:00"],
["from" => "08:00:00", "to" => "16:00:00"],
["from" => "08:00:00", "to" => "16:00:00"],
["from" => "08:00:00", "to" => "16:00:00"],
["from" => "08:00:00", "to" => "16:00:00"],
["from" => "08:00:00", "to" => "16:00:00"],
["from" => "08:00:00", "to" => "16:00:00"],
["from" => "08:00:00", "to" => "16:00:00"],
["from" => "08:00:00", "to" => "16:00:00"],
],
"sessions" => [
[
"date" => "17/6/2017", "status" => "approved",
"from" => "09:00:00", "end" => "11:00:00",
],
[
"date" => "17/6/2017", "status" => "new",
"from" => "12:00:00", "end" => "02:00:00",
],
],
];
function freeAt($user, $newSession)
{
//the wrapping should be done in data postprocessing and not within the function
//wrap work hours times into carbon objects
$user['workHours'] = collect($user['workHours'])->map(function ($item) {
$item['from'] = Carbon::createFromFormat(TIME_FORMAT, ($item['from']));
$item['to'] = Carbon::createFromFormat(TIME_FORMAT, ($item['to']));
return $item;
});
//wrap sessions date and times into carbon objects
$user['sessions'] = collect($user['sessions'])->map(function ($item) {
return [
'date' => Carbon::createFromFormat(DATE_FORMAT, ($item['date'])),
'from' => Carbon::createFromFormat(TIME_FORMAT, ($item['from'])),
'end' => Carbon::createFromFormat(TIME_FORMAT, ($item['end'])),
'status' => $item['status']
];
});
//wrap newSession date and times into carbon objects
$newSession['date'] = Carbon::createFromFormat(DATE_FORMAT, ($newSession['date']));
$newSession['from'] = Carbon::createFromFormat(TIME_FORMAT, ($newSession['from']));
$newSession['end'] = Carbon::createFromFormat(TIME_FORMAT, ($newSession['end']));
//saturday index is 6 , monday is 0 , map workHours array to 7 days of week
$index = ($newSession['date']->dayOfWeek) % 6;
$withinWorkHrs = !empty($user['workHours'][$index]) && // week day has working hours
// check if the proposed date is within the working hours of that day
($newSession['from']->between(
$user['workHours'][$index]['from']->subMinutes(30),
$user['workHours'][$index]['to']->addMinutes(30))
&&
$newSession['end']->between(
$user['workHours'][$index]['from']->subMinutes(30),
$user['workHours'][$index]['to']->addMinutes(30)
));
if (!$withinWorkHrs) return false; // chosen day doesn't have working hours
return collect($user['sessions'])
->where('date', $newSession['date'])
->where('status', 'approved')
->pipe(function ($result) use ($newSession) {
//if proposed day isn't in approved sessions , then that appointment is free
return $result->isEmpty() ? true :
//check each session for intersections in time intervals
$result->filter(function ($item) use ($newSession) {
return
!($newSession['from']->between(
$item['from']->subMinutes(30),
$item['end']->addMinutes(30)))
&&
!($newSession['end']->between(
$item['from']->subMinutes(30),
$item['end']->addMinutes(30)
));
});
})->isEmpty();
}
var_dump(freeAt($user, [
"date" => "17/6/2017", "status" => "new",
"from" => "10:30:00", "end" => "11:00:00",
]));
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment