Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.

Saeedsikandar's avatar

How do I filter booked slots in carbon/carbonPeriod ?

I'm working on a project, Where the requirement is slot based booking system and I want to filter booked slots with carbon period

in my research I found this reference Filtering Carbon Period

public function test_slots(){
        $startDate = Carbon::parse('2021-01-01 00:00:00');
        $period = $startDate->toPeriod('2021-01-02 00:00:00', 60, 'minutes');

        $period->prependFilter(function($date){
            	$start_time = $date->copy()->setTimeFromTimeString('12:00');
      		    $end_time = $date->copy()->setTimeFromTimeString('18:00');
           	
				return $date->greaterThan($start_time) && $date->lessThan($end_time);
        });

        foreach($period as $slot) echo $slot->format( g i:s A') . '<br>';
    }

output of code

1 00:00 PM
2 00:00 PM
3 00:00 PM
4 00:00 PM
5 00:00 PM

above method return all slots between those two timestamps but I want to remove all the slots between those two slots and return all slots which not in between both slots

I saw in this method dates copy from but I want some thing copy-exclude. required output

6 00:00 PM
7 00:00 PM
8 00:00 PM
9 00:00 PM
10 00:00 PM
... 
...
... 
12 00:00 AM

above method return all slots between those two timestamps but I want to remove all the slots between those two slots and return all slots which not in between both slots

I saw in this method dates copy from but I want some thing copy-exclude.

does carbon period provide something for this purpose or should wrote custom helper ?

0 likes
5 replies
webrobert's avatar

does carbon period provide something

not that I am aware of.

$bookedSlots = collect([
    $startDate->copy()->setTimeFromTimeString('13:00'),
    $startDate->copy()->setTimeFromTimeString('17:00')
]);

$period->filter( fn($date) => $bookedSlots->doesntContain($date) );

OR

$period->prependFilter( fn($date) => $bookedSlots->doesntContain($date) );
Saeedsikandar's avatar

@webrobert now it's return all slots didn't remove slots between 13:00 to 17:00

 public function test_slots(){
        $startDate = Carbon::parse('2021-01-01 00:00:00');
        $period = $startDate->toPeriod('2021-01-02 00:00:00', 60, 'minutes');

        $bookedSlots = collect([
            $startDate->copy()->setTimeFromTimeString('13:00'),
            $startDate->copy()->setTimeFromTimeString('17:00')
        ]);

        $period->prependFilter( fn($date) => $bookedSlots->doesntContain($date) );

        foreach($period as $slot) echo $slot->format('g i:s A') . '<br>';
    }

Output

12 00:00 AM
1 00:00 AM
2 00:00 AM
3 00:00 AM
4 00:00 AM
5 00:00 AM
6 00:00 AM
7 00:00 AM
8 00:00 AM
9 00:00 AM
10 00:00 AM
11 00:00 AM
12 00:00 PM
2 00:00 PM
3 00:00 PM
4 00:00 PM
6 00:00 PM
7 00:00 PM
8 00:00 PM
9 00:00 PM
10 00:00 PM
11 00:00 PM
12 00:00 AM

did I do something wrong in here ?

webrobert's avatar

@Saeedsikandar, no the code was to remove booked slots. Look

you can check BOTH...

$startDate = Carbon::parse('2021-01-01 00:00:00');
$period = $startDate->toPeriod('2021-01-02 00:00:00', 60, 'minutes');

$bookedSlots = collect([
    $startDate->copy()->setTimeFromTimeString('13:00'),
    $startDate->copy()->setTimeFromTimeString('17:00')
]);

$period->prependFilter( function($date) use ($bookedSlots) {
    $start_time = $date->copy()->setTimeFromTimeString('12:00');
    $end_time = $date->copy()->setTimeFromTimeString('18:00');

    return $date->greaterThan($start_time) &&
           $date->lessThan($end_time) &&
           $bookedSlots->doesntContain($date);
});

$openSlots = collect($period)->map( fn($slot) => $slot->format('g i:s A') );

dd($openSlots->toArray());
1 like
webrobert's avatar
Level 51

there is also a between method, I think its a bit easier to read...

$period->prependFilter( fn($time) =>
    $bookedSlots->doesntContain($time) &&

    $time->between(
        $time->copy()->setTimeFromTimeString('13:00'), 
        $time->copy()->setTimeFromTimeString('17:00')
    )
);
2 likes
Saeedsikandar's avatar

@webrobert perfectly done thanks alot, it helps a lot and clears my thinking and use of carbon and collection

1 like

Please or to participate in this conversation.