PluginProbe ʕ •ᴥ•ʔ
Booking for Appointments and Events Calendar – Amelia / 2.4.6
Booking for Appointments and Events Calendar – Amelia v2.4.6
2.4.7 2.4.6 2.4.5 2.4.4 2.4.3 2.4.2 2.4.1 2.4 trunk 1.2.1 1.2.10 1.2.11 1.2.12 1.2.13 1.2.14 1.2.15 1.2.16 1.2.17 1.2.18 1.2.19 1.2.2 1.2.20 1.2.21 1.2.22 1.2.23 1.2.24 1.2.25 1.2.26 1.2.27 1.2.28 1.2.29 1.2.3 1.2.30 1.2.31 1.2.32 1.2.33 1.2.34 1.2.35 1.2.36 1.2.37 1.2.38 1.2.4 1.2.5 1.2.6 1.2.7 1.2.8 1.2.9 2.0 2.0.1 2.0.2 2.1 2.1.1 2.1.2 2.1.3 2.2 2.2.1 2.3
ameliabooking / src / Application / Commands / Booking / Appointment / UpdateAppointmentTimeCommandHandler.php
ameliabooking / src / Application / Commands / Booking / Appointment Last commit date
AddAppointmentCommand.php 1 year ago AddAppointmentCommandHandler.php 6 days ago AddBookingCommand.php 1 year ago AddBookingCommandHandler.php 6 days ago ApproveBookingRemotelyCommand.php 1 year ago ApproveBookingRemotelyCommandHandler.php 3 months ago CancelBookingCommand.php 1 year ago CancelBookingCommandHandler.php 6 days ago CancelBookingRemotelyCommand.php 1 year ago CancelBookingRemotelyCommandHandler.php 2 months ago DeleteAppointmentCommand.php 1 year ago DeleteAppointmentCommandHandler.php 1 year ago DeleteBookingCommand.php 1 year ago DeleteBookingCommandHandler.php 11 months ago DeleteBookingRemotelyCommand.php 11 months ago DeleteBookingRemotelyCommandHandler.php 7 months ago GetAppointmentBookingsCommand.php 7 months ago GetAppointmentBookingsCommandHandler.php 6 days ago GetAppointmentCommand.php 7 years ago GetAppointmentCommandHandler.php 6 days ago GetAppointmentsCommand.php 1 year ago GetAppointmentsCommandHandler.php 6 days ago GetIcsCommand.php 7 months ago GetIcsCommandHandler.php 4 years ago GetTimeSlotsCommand.php 1 year ago GetTimeSlotsCommandHandler.php 3 weeks ago ReassignBookingCommand.php 1 year ago ReassignBookingCommandHandler.php 6 days ago RejectBookingRemotelyCommand.php 1 year ago RejectBookingRemotelyCommandHandler.php 6 months ago SuccessfulBookingCommand.php 1 year ago SuccessfulBookingCommandHandler.php 1 year ago UpdateAppointmentCommand.php 1 year ago UpdateAppointmentCommandHandler.php 6 days ago UpdateAppointmentNoteCommand.php 4 months ago UpdateAppointmentNoteCommandHandler.php 6 days ago UpdateAppointmentStatusCommand.php 1 year ago UpdateAppointmentStatusCommandHandler.php 6 days ago UpdateAppointmentTimeCommand.php 1 year ago UpdateAppointmentTimeCommandHandler.php 6 days ago UpdateBookingStatusCommand.php 1 year ago UpdateBookingStatusCommandHandler.php 6 months ago
UpdateAppointmentTimeCommandHandler.php
275 lines
1 <?php
2
3 namespace AmeliaBooking\Application\Commands\Booking\Appointment;
4
5 use AmeliaBooking\Application\Commands\CommandHandler;
6 use AmeliaBooking\Application\Commands\CommandResult;
7 use AmeliaBooking\Application\Common\Exceptions\AccessDeniedException;
8 use AmeliaBooking\Application\Services\Bookable\BookableApplicationService;
9 use AmeliaBooking\Application\Services\Booking\AppointmentApplicationService;
10 use AmeliaBooking\Application\Services\Booking\BookingApplicationService;
11 use AmeliaBooking\Application\Services\Payment\PaymentApplicationService;
12 use AmeliaBooking\Application\Services\User\UserApplicationService;
13 use AmeliaBooking\Domain\Common\Exceptions\BookingCancellationException;
14 use AmeliaBooking\Domain\Common\Exceptions\InvalidArgumentException;
15 use AmeliaBooking\Domain\Entity\Bookable\Service\Service;
16 use AmeliaBooking\Domain\Entity\Booking\Appointment\Appointment;
17 use AmeliaBooking\Domain\Entity\Booking\Appointment\CustomerBooking;
18 use AmeliaBooking\Domain\Entity\Entities;
19 use AmeliaBooking\Domain\Entity\User\AbstractUser;
20 use AmeliaBooking\Domain\Entity\User\Provider;
21 use AmeliaBooking\Domain\Services\DateTime\DateTimeService;
22 use AmeliaBooking\Domain\Services\Reservation\ReservationServiceInterface;
23 use AmeliaBooking\Domain\Services\Settings\SettingsService;
24 use AmeliaBooking\Domain\ValueObjects\BooleanValueObject;
25 use AmeliaBooking\Domain\ValueObjects\DateTime\DateTimeValue;
26 use AmeliaBooking\Domain\ValueObjects\Number\Float\Price;
27 use AmeliaBooking\Infrastructure\Common\Exceptions\NotFoundException;
28 use AmeliaBooking\Infrastructure\Common\Exceptions\QueryExecutionException;
29 use AmeliaBooking\Infrastructure\Repository\Booking\Appointment\AppointmentRepository;
30 use AmeliaBooking\Infrastructure\Repository\Booking\Appointment\CustomerBookingRepository;
31 use AmeliaBooking\Infrastructure\Repository\User\UserRepository;
32 use AmeliaBooking\Infrastructure\WP\Translations\FrontendStrings;
33
34 /**
35 * Class UpdateAppointmentTimeCommandHandler
36 *
37 * @package AmeliaBooking\Application\Commands\Booking\Appointment
38 */
39 class UpdateAppointmentTimeCommandHandler extends CommandHandler
40 {
41 /**
42 * @var array
43 */
44 public $mandatoryFields = [
45 'bookingStart'
46 ];
47
48 /**
49 * @param UpdateAppointmentTimeCommand $command
50 *
51 * @return CommandResult
52 *
53 * @throws AccessDeniedException
54 * @throws InvalidArgumentException
55 * @throws QueryExecutionException
56 * @throws NotFoundException
57 */
58 public function handle(UpdateAppointmentTimeCommand $command)
59 {
60 /** @var AbstractUser $user */
61 $user = $command->authorize();
62
63 $this->checkMandatoryFields($command);
64
65 $result = new CommandResult();
66
67 /** @var UserApplicationService $userAS */
68 $userAS = $this->container->get('application.user.service');
69 /** @var SettingsService $settingsDS */
70 $settingsDS = $this->container->get('domain.settings.service');
71 /** @var AppointmentRepository $appointmentRepo */
72 $appointmentRepo = $this->container->get('domain.booking.appointment.repository');
73 /** @var AppointmentApplicationService $appointmentAS */
74 $appointmentAS = $this->container->get('application.booking.appointment.service');
75 /** @var BookableApplicationService $bookableAS */
76 $bookableAS = $this->container->get('application.bookable.service');
77 /** @var BookingApplicationService $bookingAS */
78 $bookingAS = $this->container->get('application.booking.booking.service');
79 /** @var ReservationServiceInterface $reservationService */
80 $reservationService = $this->container->get('application.reservation.service')->get(Entities::APPOINTMENT);
81 /** @var PaymentApplicationService $paymentAS */
82 $paymentAS = $this->container->get('application.payment.service');
83
84 if ($userAS->isCustomer($user) && !$settingsDS->getSetting('roles', 'allowCustomerReschedule')) {
85 throw new AccessDeniedException('You are not allowed to update appointment');
86 }
87
88 /** @var Appointment $appointment */
89 $appointment = $appointmentRepo->getById((int)$command->getArg('id'));
90
91 if ($userAS->isProvider($user) && $user->getId()->getValue() !== $appointment->getProviderId()->getValue()) {
92 throw new AccessDeniedException('You are not allowed to update appointment');
93 }
94
95 $oldAppointment = clone $appointment;
96
97 $initialBookingStart = $appointment->getBookingStart()->getValue();
98 $initialBookingEnd = $appointment->getBookingEnd()->getValue();
99
100 /** @var Service $service */
101 $service = $bookableAS->getAppointmentService(
102 $appointment->getServiceId()->getValue(),
103 $appointment->getProviderId()->getValue()
104 );
105
106 $isUserWithOnlyOneBooking = true;
107
108 /** @var CustomerBooking $booking */
109 foreach ($appointment->getBookings()->getItems() as $booking) {
110 if (
111 $userAS->isAmeliaUser($user) &&
112 $userAS->isCustomer($user) &&
113 $bookingAS->isBookingApprovedOrPending($booking->getStatus()->getValue()) &&
114 ($user->getId() && $booking->getCustomerId()->getValue() !== $user->getId()->getValue())
115 ) {
116 $isUserWithOnlyOneBooking = false;
117
118 break;
119 }
120 }
121
122 /** @var CustomerBooking $booking */
123 foreach ($appointment->getBookings()->getItems() as $booking) {
124 if (
125 $userAS->isAmeliaUser($user) &&
126 $userAS->isCustomer($user) &&
127 $bookingAS->isBookingApprovedOrPending($booking->getStatus()->getValue()) &&
128 ($service->getMinCapacity()->getValue() !== 1 || $service->getMaxCapacity()->getValue() !== 1 || !$isUserWithOnlyOneBooking) &&
129 ($user->getId() && $booking->getCustomerId()->getValue() !== $user->getId()->getValue())
130 ) {
131 throw new AccessDeniedException('You are not allowed to update appointment');
132 }
133 }
134
135 if ($userAS->isCustomer($user)) {
136 $minimumRescheduleTimeInSeconds = $settingsDS
137 ->getEntitySettings($service->getSettings())
138 ->getGeneralSettings()
139 ->getMinimumTimeRequirementPriorToRescheduling();
140
141 try {
142 $reservationService->inspectMinimumCancellationTime(
143 $appointment->getBookingStart()->getValue(),
144 $minimumRescheduleTimeInSeconds
145 );
146 } catch (BookingCancellationException $e) {
147 $result->setResult(CommandResult::RESULT_ERROR);
148 $result->setMessage('You are not allowed to update booking');
149 $result->setData(
150 [
151 'rescheduleBookingUnavailable' => true
152 ]
153 );
154
155 return $result;
156 }
157 }
158
159 $bookingStart = $command->getField('bookingStart');
160
161 if ($command->getField('timeZone')) {
162 $bookingStart = DateTimeService::getDateTimeObjectInTimeZone(
163 $bookingStart,
164 $command->getField('timeZone')
165 )->setTimezone(DateTimeService::getTimeZone())->format('Y-m-d H:i:s');
166 }
167
168 $bookingStartInUtc = DateTimeService::getCustomDateTimeObject(
169 $bookingStart
170 )->setTimezone(new \DateTimeZone('UTC'))->format('Y-m-d H:i');
171
172 // Convert UTC slot to slot in TimeZone based on Settings
173 if ($command->getField('utcOffset') !== null && $settingsDS->getSetting('general', 'showClientTimeZone')) {
174 $bookingStart = DateTimeService::getCustomDateTimeFromUtc(
175 $bookingStart
176 );
177 }
178
179 $appointment->setBookingStart(
180 new DateTimeValue(
181 DateTimeService::getCustomDateTimeObject(
182 $bookingStart
183 )
184 )
185 );
186
187 $appointment->setBookingEnd(
188 new DateTimeValue(
189 DateTimeService::getCustomDateTimeObject($bookingStart)
190 ->modify('+' . $appointmentAS->getAppointmentLengthTime($appointment, $service) . ' second')
191 )
192 );
193
194 if (!$appointmentAS->canBeBooked($appointment, $userAS->isCustomer($user), null, null)) {
195 $result->setResult(CommandResult::RESULT_ERROR);
196 $result->setMessage(FrontendStrings::getCommonStrings()['time_slot_unavailable']);
197 $result->setData(
198 [
199 'timeSlotUnavailable' => true
200 ]
201 );
202
203 return $result;
204 }
205
206 do_action('amelia_before_booking_rescheduled', $oldAppointment->toArray(), null, $bookingStart);
207
208 $appointmentRepo->update((int)$command->getArg('id'), $appointment);
209
210 /** @var CustomerBooking $booking */
211 foreach ($appointment->getBookings()->getItems() as $booking) {
212 $paymentAS->updateBookingPaymentDate($booking, $bookingStartInUtc);
213
214 if ($appointmentAS->isPeriodCustomPricing($service)) {
215 /** @var UserRepository $userRepository */
216 $userRepository = $this->getContainer()->get('domain.users.repository');
217
218 /** @var CustomerBookingRepository $bookingRepository */
219 $bookingRepository = $this->container->get('domain.booking.customerBooking.repository');
220
221 /** @var Provider $provider */
222 $provider = $userRepository->getById($appointment->getProviderId()->getValue());
223
224 $price = $appointmentAS->getBookingPriceForService(
225 $service,
226 null,
227 $provider,
228 $appointment->getBookingStart()->getValue()->format('Y-m-d H:i:s')
229 );
230
231 $booking->setPrice(new Price($price));
232
233 $bookingRepository->updatePrice($booking->getId()->getValue(), $booking);
234 }
235 }
236
237 $appointment->setRescheduled(new BooleanValueObject(true));
238
239 $appointment->setInitialBookingStart(
240 new DateTimeValue($initialBookingStart)
241 );
242
243 $appointment->setInitialBookingEnd(
244 new DateTimeValue($initialBookingEnd)
245 );
246
247 $bookingAS->bookingRescheduled(
248 $appointment->getId()->getValue(),
249 Entities::APPOINTMENT,
250 null,
251 Entities::CUSTOMER
252 );
253
254 $bookingAS->bookingRescheduled(
255 $appointment->getId()->getValue(),
256 Entities::APPOINTMENT,
257 $appointment->getProviderId()->getValue(),
258 Entities::PROVIDER
259 );
260
261
262 do_action('amelia_after_booking_rescheduled', $oldAppointment->toArray(), null, $bookingStart);
263
264 $result->setResult(CommandResult::RESULT_SUCCESS);
265 $result->setMessage('Successfully updated appointment time');
266 $result->setData(
267 [
268 Entities::APPOINTMENT => $appointment->toArray(),
269 ]
270 );
271
272 return $result;
273 }
274 }
275