PluginProbe
Booktics – Appointment Booking Calendar for Service Businesses / 1.0.3
Booktics – Appointment Booking Calendar for Service Businesses v1.0.3
1.0.29 1.0.28 1.0.27 1.0.26 1.0.25 1.0.24 1.0.23 1.0.22 1.0.21 1.0.20 1.0.19 trunk 1.0.0 1.0.1 1.0.10 1.0.11 1.0.12 1.0.13 1.0.14 1.0.15 1.0.16 1.0.17 1.0.18 1.0.2 1.0.3 All 31 releases
booktics / base / services / schedule-manager.php

schedule-manager.php in Booktics – Appointment Booking Calendar for Service Businesses 1.0.3, at base/services/schedule-manager.php

368 lines 9.1 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace Booktics\Services;
4
5 use Booktics\Abstracts\Booktics_Database;
6 use Booktics\Contracts\Database_Interface;
7 use DateTime;
8 use Exception;
9 use InvalidArgumentException;
10
11 /**
12 * Schedule Manager for team member and service
13 *
14 * @package Booktics/Services
15 */
16 class Schedule_Manager {
17
18 /**
19 * Store Team member id
20 *
21 * @var int
22 */
23 private $team_member_id = 0;
24
25 /**
26 * Store Service id
27 *
28 * @var int
29 */
30 private $service_id = 0;
31
32 /**
33 * Store duration of each slot
34 *
35 * @var int
36 */
37 private $duration = 30;
38
39 /**
40 * Store schedules map
41 *
42 * @var array
43 */
44 private $schedules = array();
45
46 /**
47 * Store custom schedule map
48 *
49 * @var array
50 */
51 private $custom_schedules = array();
52
53 /**
54 * Store holidays map
55 *
56 * @var array
57 */
58 private $holidays = array();
59
60 /**
61 * Week day map
62 *
63 * @var array
64 */
65 public static $day_map = array(
66 'Mon' => 1,
67 'Tue' => 2,
68 'Wed' => 3,
69 'Thu' => 4,
70 'Fri' => 5,
71 'Sat' => 6,
72 'Sun' => 7,
73 );
74
75 /**
76 * WP Database instance
77 *
78 * @var Database_Interface
79 */
80 private $database;
81
82 /**
83 * Schedule data
84 *
85 * @var array
86 */
87 private $schedule_data;
88
89 /**
90 * Construct object and set schedule data
91 *
92 * @param $schedule_data
93 */
94 private function __construct( $schedule_data ) {
95 $this->database = new Booktics_Database();
96 $this->schedule_data = $schedule_data;
97 $this->init(
98 $this->schedule_data['schedule'] ?? array(),
99 $this->schedule_data['custom'] ?? array(),
100 $this->schedule_data['holiday'] ?? array()
101 );
102 }
103
104 /**
105 * Make a schedule manager instance
106 *
107 * @param $schedule_data
108 *
109 * @return self
110 */
111 public static function make( $schedule_data ): self {
112 return new static( $schedule_data );
113 }
114
115 /**
116 * Initialize schedules, Custom Schedules and holidays
117 *
118 * @param $schedules
119 * @param $custom_schedules
120 * @param $holidays
121 *
122 * @return void
123 */
124 private function init( $schedules, $custom_schedules, $holidays ): void {
125 $this->schedules = $schedules;
126
127 if ( ! empty( $custom_schedules ) ) {
128 foreach ( $custom_schedules as $custom_data ) {
129 if ( ! is_array( $custom_data ) || count( $custom_data ) < 2 ) {
130 continue;
131 }
132 $start = $custom_data[0];
133 $end = $custom_data[1];
134 if ( ! isset( $custom_data[2] ) ) {
135 $end = $start;
136 $time_period = $custom_data[1];
137 } else {
138 $time_period = $custom_data[2];
139 }
140
141 $this->add_custom_schedule( $start, $end, $time_period );
142 }
143 }
144
145 if ( ! empty( $holidays ) ) {
146 foreach ( $holidays as $holiday_data ) {
147 if ( ! is_array( $holiday_data ) || empty( $holiday_data ) ) {
148 continue;
149 }
150 $start = $holiday_data[0];
151 $end = $holiday_data[1] ?? $holiday_data[0];
152
153 $this->with_holidays( $start, $end );
154 }
155 }
156 }
157
158 /**
159 * Set team member id for team member schedule
160 *
161 * @param int $team_member_id
162 *
163 * @return $this
164 */
165 public function with_team_member_id( int $team_member_id ): self {
166 if ( $team_member_id <= 0 ) {
167 throw new InvalidArgumentException( 'Team member ID must be positive' );
168 }
169 $this->team_member_id = $team_member_id;
170
171 return $this;
172 }
173
174 /**
175 * Set service id for service schedule
176 *
177 * @param int $service_id
178 *
179 * @return $this
180 */
181 public function with_service_id( int $service_id ): self {
182 if ( $service_id <= 0 ) {
183 throw new InvalidArgumentException( 'Service ID must be positive' );
184 }
185 $this->service_id = $service_id;
186
187 return $this;
188 }
189
190 /**
191 * Set schedule map to store
192 *
193 * @param array $schedules
194 *
195 * @return $this
196 */
197 public function with_schedules( array $schedules ): self {
198 $this->schedules = $schedules;
199
200 return $this;
201 }
202
203 /**
204 * Set holidays map to store
205 *
206 * @param string $start_date
207 * @param string $end_date
208 *
209 * @return $this
210 */
211 public function with_holidays( string $start_date, string $end_date ): self {
212 $this->holidays[] = array(
213 'start_date' => $start_date,
214 'end_date' => $end_date,
215 );
216
217 return $this;
218 }
219
220 /**
221 * Set a custom schedule map to store
222 *
223 * @param string $start_date
224 * @param string $end_date
225 * @param array $schedule
226 *
227 * @return $this
228 */
229 public function add_custom_schedule( string $start_date, string $end_date, array $schedule ): self {
230 $this->custom_schedules[] = array(
231 'start_date' => $start_date,
232 'end_date' => $end_date,
233 'schedule' => $schedule,
234 );
235
236 return $this;
237 }
238
239 /**
240 * Execute schedule save action
241 *
242 * @return void
243 * @throws Exception
244 */
245 public function save(): void {
246 $this->database->begin_transaction();
247 try {
248 $this->clear_existing_schedules();
249 $this->save_schedules();
250 $this->database->commit();
251 } catch ( Exception $e ) {
252 $this->database->roll_back();
253 throw $e;
254 }
255 }
256
257 /**
258 * Remove existing schedules from database
259 *
260 * @return void
261 */
262 private function clear_existing_schedules(): void {
263 $this->database->delete(
264 booktics_get_table_name( 'booktics_schedules' ), array(
265 'service_id' => $this->service_id,
266 'team_member_id' => $this->team_member_id,
267 )
268 );
269 }
270
271 /**
272 * Insert Schedule into database
273 *
274 * @return void
275 * @throws Exception
276 */
277 private function save_schedules(): void {
278 $records = $this->build_schedule_records();
279
280 if ( empty( $records ) ) {
281 return;
282 }
283
284 $this->database->insert_batch( booktics_get_table_name( 'booktics_schedules' ), $records );
285 }
286
287 /**
288 * build map for schedule records
289 *
290 * @return array
291 * @throws Exception
292 */
293 private function build_schedule_records(): array {
294 $records = array();
295
296 foreach ( $this->schedules as $day_name => $day_values ) {
297 $formatted_day_name = ucfirst( substr( strtolower( $day_name ), 0, 3 ) );
298 $day_number = static::$day_map[ $formatted_day_name ];
299 foreach ( $day_values as $day_value ) {
300 $records[] = $this->create_schedule_record(
301 $day_value['start_time'] ?? '0',
302 $day_value['end_time'] ?? '0',
303 $day_number,
304 0
305 );
306 }
307 }
308
309 if ( count( $this->custom_schedules ) > 0 ) {
310 foreach ( $this->custom_schedules as $custom_schedule ) {
311 $dates = booktics_date_range_loop( $custom_schedule['start_date'], $custom_schedule['end_date'] );
312 foreach ( $dates as $date ) {
313 $day_name = ( new DateTime( $date ) )->format( 'D' );
314 $day_number = static::$day_map[ $day_name ];
315 $records[] = $this->create_schedule_record(
316 $custom_schedule['schedule']['start_time'],
317 $custom_schedule['schedule']['end_time'],
318 $day_number,
319 $date
320 );
321 }
322 }
323 }
324
325 foreach ( $this->holidays as $holiday ) {
326 $dates = booktics_date_range_loop( $holiday['start_date'], $holiday['end_date'] );
327 foreach ( $dates as $date ) {
328 $day_name = ( new DateTime( $date ) )->format( 'D' );
329 $day_number = static::$day_map[ $day_name ];
330 $records[] = $this->create_schedule_record(
331 '0',
332 '0',
333 $day_number,
334 $date
335 );
336 }
337 }
338
339 return $records;
340 }
341
342 /**
343 * Format schedule records
344 *
345 * @param string $start_time
346 * @param string $end_time
347 * @param string $week_day
348 * @param string $custom_date
349 *
350 * @return array
351 */
352 private function create_schedule_record(
353 string $start_time,
354 string $end_time,
355 string $week_day,
356 string $custom_date
357 ): array {
358 return array(
359 'team_member_id' => $this->team_member_id,
360 'service_id' => $this->service_id,
361 'start_time' => $start_time,
362 'end_time' => $end_time,
363 'week_day' => $week_day,
364 'custom_date' => $custom_date,
365 );
366 }
367 }
368