| 1 |
<?php |
| 2 |
|
| 3 |
if ( ! defined( 'ABSPATH' ) ) exit; // Exit if accessed directly // FixIn: 9.8.0.4. |
| 4 |
|
| 5 |
// --------------------------------------------------------------------------------------------------------------------- |
| 6 |
// == Ajax Response on creation of new booking |
| 7 |
// --------------------------------------------------------------------------------------------------------------------- |
| 8 |
|
| 9 |
/** |
| 10 |
* Response to Ajax request, about loading calendar data |
| 11 |
* |
| 12 |
* @return void |
| 13 |
*/ |
| 14 |
function ajax_WPBC_AJX_BOOKING__CREATE() { |
| 15 |
|
| 16 |
/** |
| 17 |
* Tip / translation / |
| 18 |
* Please note, translation was loaded on hook add_action( 'plugins_loaded', 'wpbc_load_translation', 1000 ); and use $_REQUEST['wpbc_ajx_locale'], so do not worry about it. |
| 19 |
*/ |
| 20 |
|
| 21 |
// Security ------------------------------------------------------------------------------------------------------ // in Ajax Post: 'nonce': _wpbc.get_secure_param( 'nonce' ), |
| 22 |
$action_name = 'wpbc_calendar_load_ajx' . '_wpbcnonce'; |
| 23 |
$nonce_post_key = 'nonce'; |
| 24 |
if ( wpbc_is_use_nonce_at_front_end() ) { // FixIn: 10.1.1.2. |
| 25 |
$result_check = check_ajax_referer( $action_name, $nonce_post_key ); |
| 26 |
} |
| 27 |
|
| 28 |
// Response AJAX parameters |
| 29 |
$ajx_data_arr = array(); |
| 30 |
$ajx_data_arr['status'] = 'ok'; |
| 31 |
|
| 32 |
$admin_uri = ltrim( str_replace( get_site_url( null, '', 'admin' ), '', admin_url( 'admin.php?' ) ), '/' ); // 'wp-admin/admin.php?' |
| 33 |
$server_http_referer_uri = ( ( isset( $_SERVER['HTTP_REFERER'] ) ) ? sanitize_text_field( $_SERVER['HTTP_REFERER'] ) : '' ); /* phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.MissingUnslash */ /* FixIn: sanitize_unslash */ |
| 34 |
// Local parameters |
| 35 |
$local_params = array(); |
| 36 |
$local_params['is_from_admin_panel'] = ( false !== strpos( $server_http_referer_uri, $admin_uri ) ); // true | false |
| 37 |
$local_params['user_id'] = ( isset( $_REQUEST['wpbc_ajx_user_id'] ) ) ? intval( $_REQUEST['wpbc_ajx_user_id'] ) : wpbc_get_current_user_id(); // 1 |
| 38 |
|
| 39 |
// Request parameters |
| 40 |
$user_request = new WPBC_AJX__REQUEST( array( // Using this class here only for escaping variables |
| 41 |
'db_option_name' => 'booking__wpbc_booking_create__request_params', // Not necessary, because we not save request, only sanitize it |
| 42 |
'user_id' => $local_params['user_id'], // Not necessary, because we not save request, only sanitize it |
| 43 |
'request_rules_structure' => array( |
| 44 |
'resource_id' => array( 'validate' => 'd', 'default' => 1 ), // 'digit_or_csd' |
| 45 |
|
| 46 |
'aggregate_resource_id_arr' => array( 'validate' => 'digit_or_csd', 'default' => '' ), |
| 47 |
|
| 48 |
'dates_ddmmyy_csv' => array( 'validate' => 'csv_dates', 'default' => '' ), // FixIn: 9.9.1.1. |
| 49 |
'formdata' => array( 'validate' => 'strong', 'default' => '' ), |
| 50 |
'booking_hash' => array( 'validate' => 'strong', 'default' => '' ), |
| 51 |
'custom_form' => array( 'validate' => 'strong', 'default' => '' ), |
| 52 |
|
| 53 |
'captcha_chalange' => array( 'validate' => 'strong', 'default' => '' ), |
| 54 |
'captcha_user_input' => array( 'validate' => 'strong', 'default' => '' ), |
| 55 |
|
| 56 |
'is_emails_send' => array( 'validate' => 'd', 'default' => 1 ), |
| 57 |
'active_locale' => array( 'validate' => 'strong', 'default' => '' ) |
| 58 |
) |
| 59 |
)); |
| 60 |
|
| 61 |
// Escape of request params in Ajax Post. We use prefix 'calendar_request_params', if Ajax sent - $_REQUEST['calendar_request_params']['resource_id'], ... |
| 62 |
$request_prefix = 'calendar_request_params'; |
| 63 |
|
| 64 |
//$_REQUEST['calendar_request_params']['dates_ddmmyy_csv'] .= "'%2b(select+'box'+from(select+sleep(2)+from+dual+where+1=1*)a)%2b'-02-21+00:00:00"; |
| 65 |
|
| 66 |
$request_params = $user_request->get_sanitized__in_request__value_or_default( $request_prefix ); // NOT Direct: $_REQUEST['calendar_request_params']['resource_id'] |
| 67 |
$server_http_referer_uri = ( ( isset( $_SERVER['HTTP_REFERER'] ) ) ? sanitize_text_field( $_SERVER['HTTP_REFERER'] ) : '' ); /* phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.MissingUnslash */ /* FixIn: sanitize_unslash */ |
| 68 |
$request_params['request_uri'] = $server_http_referer_uri; // Parameter needed for Error in booking saving and reloading calendar again with these actual parameters. |
| 69 |
|
| 70 |
// <editor-fold defaultstate="collapsed" desc=" :: ERROR :: <- CAPTCHA " > |
| 71 |
// phpcs:ignore WordPress.Security.NonceVerification.Recommended, WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.InputNotValidated, WordPress.Security.ValidatedSanitizedInput.MissingUnslash, WordPress.Security.ValidatedSanitizedInput.InputNotSanitized |
| 72 |
wpbc_captcha__in_ajx__check( $request_params, $local_params['is_from_admin_panel'], $_REQUEST[ $request_prefix ] ); |
| 73 |
// </editor-fold> |
| 74 |
|
| 75 |
// <editor-fold defaultstate="collapsed" desc=" :: ERROR :: <- BOOKING_RESOURCE ID " > |
| 76 |
if ( $request_params['resource_id'] <= 0 ) { |
| 77 |
$ajx_data_arr['status'] = 'error'; |
| 78 |
$ajx_data_arr['status_error'] = 'resource_id_incorrect'; |
| 79 |
// phpcs:ignore WordPress.Security.NonceVerification.Recommended, WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.InputNotValidated, WordPress.Security.ValidatedSanitizedInput.MissingUnslash, WordPress.Security.ValidatedSanitizedInput.InputNotSanitized |
| 80 |
$ajx_data_arr['ajx_after_action_message'] = 'Wrong ID of booking resource: ' . ' [ request ID: ' . $_REQUEST['calendar_request_params']['resource_id'] . ' | parsed ID: ' . $request_params['resource_id'] . ' ]'; |
| 81 |
$ajx_data_arr['ajx_after_action_message_status'] = 'error'; |
| 82 |
wp_send_json( array( |
| 83 |
'ajx_data' => $ajx_data_arr, |
| 84 |
// phpcs:ignore WordPress.Security.ValidatedSanitizedInput.InputNotValidated, WordPress.Security.ValidatedSanitizedInput.MissingUnslash, WordPress.Security.ValidatedSanitizedInput.InputNotSanitized |
| 85 |
'ajx_search_params' => $_REQUEST[ $request_prefix ], |
| 86 |
'ajx_cleaned_params' => $request_params, |
| 87 |
'resource_id' => $request_params['resource_id'], |
| 88 |
) ); |
| 89 |
} |
| 90 |
// </editor-fold> |
| 91 |
|
| 92 |
$server_http_referer_uri = ( ( isset( $_SERVER['HTTP_REFERER'] ) ) ? sanitize_text_field( $_SERVER['HTTP_REFERER'] ) : '' ); /* phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.MissingUnslash */ /* FixIn: sanitize_unslash */ |
| 93 |
$request_save_params = array( |
| 94 |
'resource_id' => $request_params['resource_id'], |
| 95 |
'dates_ddmmyy_csv' => $request_params['dates_ddmmyy_csv'], |
| 96 |
'form_data' => $request_params['formdata'], |
| 97 |
'aggregate_resource_id_arr' => $request_params['aggregate_resource_id_arr'], // Optional can be '' |
| 98 |
|
| 99 |
'booking_hash' => $request_params['booking_hash'], |
| 100 |
'custom_form' => $request_params['custom_form'], |
| 101 |
|
| 102 |
'is_emails_send' => $request_params['is_emails_send'], |
| 103 |
'is_show_payment_form' => 1, |
| 104 |
'user_id' => $local_params['user_id'], |
| 105 |
'request_uri' => $server_http_referer_uri |
| 106 |
); |
| 107 |
$booking_save_arr = wpbc_booking_save( $request_save_params ); |
| 108 |
|
| 109 |
// <editor-fold defaultstate="collapsed" desc=" :: ERROR :: <- BOOKING " > |
| 110 |
if ( 'ok' !== $booking_save_arr['ajx_data']['status'] ) { |
| 111 |
|
| 112 |
wp_send_json( array( 'ajx_data' => $booking_save_arr['ajx_data'], |
| 113 |
// phpcs:ignore WordPress.Security.ValidatedSanitizedInput.InputNotValidated, WordPress.Security.ValidatedSanitizedInput.MissingUnslash, WordPress.Security.ValidatedSanitizedInput.InputNotSanitized |
| 114 |
'ajx_search_params' => $_REQUEST[ $request_prefix ], |
| 115 |
'ajx_cleaned_params' => $request_params, |
| 116 |
'resource_id' => $request_params['resource_id'] |
| 117 |
)); |
| 118 |
} |
| 119 |
// </editor-fold> |
| 120 |
|
| 121 |
$ajx_data_arr = $booking_save_arr['ajx_data']; |
| 122 |
|
| 123 |
|
| 124 |
|
| 125 |
// TODO: If we have the calendar with specific capacity, then maybe showing by dots (the booked child booking resources) the slots and not the time slot ! |
| 126 |
|
| 127 |
if ( empty( $ajx_data_arr['ajx_after_action_message_status'] ) ) { |
| 128 |
$ajx_data_arr['ajx_after_action_message_status'] = 'success'; |
| 129 |
} |
| 130 |
if ( empty( $ajx_data_arr['ajx_after_action_message'] ) ) { |
| 131 |
$ajx_data_arr['ajx_after_action_message'] = ''; |
| 132 |
} |
| 133 |
|
| 134 |
// $ajx_data_arr['ajx_after_action_message'] .= __( 'Booking was created with ID: ' . $booking_save_arr[ 'booking_id' ] , 'booking' ); |
| 135 |
// $ajx_data_arr['ajx_after_action_message'] .= '<hr>Total time: <strong>' . $booking_save_arr['php_performance']['total'] . ' s. </strong>'; |
| 136 |
// $ajx_data_arr['ajx_after_action_message'] .= str_replace( array( ',', '{', '}' ), '<br>', wp_json_encode( $booking_save_arr['php_performance'] ) ); |
| 137 |
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////// |
| 138 |
|
| 139 |
|
| 140 |
|
| 141 |
/* if admin edit ? |
| 142 |
var my_message = '<?php echo esc_js( __('Updated successfully' ,'booking') ) ; ?>'; |
| 143 |
wpbc_admin_show_message( my_message, 'success', 3000 ); |
| 144 |
location.href='<?php echo wpbc_get_bookings_url() ;?>&tab=vm_booking_listing&wh_booking_id=<?php echo $is_edit_booking['booking_id'] ; ?>'; |
| 145 |
*/ |
| 146 |
|
| 147 |
|
| 148 |
// ----------------------------------------------------------------------------------------------------------------- |
| 149 |
// == Ajax === |
| 150 |
// ----------------------------------------------------------------------------------------------------------------- |
| 151 |
/** |
| 152 |
* Send JSON. It will make "wp_json_encode" - so pass only array, and This function call wp_die( '', '', array( 'response' => null, ) ) . |
| 153 |
* Pass JS OBJ: response_data in "jQuery.post " function on success. |
| 154 |
* |
| 155 |
* Other End Ajax actions: |
| 156 |
* $error_obj = new WP_Error( 'WPBC_CREATE', __( 'test error.' ), 'some/data' ); wp_send_json_error( $error_obj ); |
| 157 |
* wp_send_json_error( array( 'message' => 'invalid-api-key' ) ); |
| 158 |
* wp_send_json_success( array( 'message' =>'Ok:)' ) ); |
| 159 |
*/ |
| 160 |
wp_send_json( array( |
| 161 |
'booking_id' => $booking_save_arr['booking_id'], |
| 162 |
'resource_id' => $request_params['resource_id'], |
| 163 |
'ajx_data' => $ajx_data_arr, |
| 164 |
'ajx_confirmation' => $booking_save_arr['confirmation'], |
| 165 |
|
| 166 |
// For debug purpose <- comment in live serv |
| 167 |
'php_process_times' => $booking_save_arr['php_performance'], |
| 168 |
'booking_arr' => $booking_save_arr ['booking_arr'], |
| 169 |
|
| 170 |
// Not needed ? |
| 171 |
// 'ajx_search_params' => $_REQUEST[ $request_prefix ], |
| 172 |
// 'ajx_cleaned_params' => $request_params, |
| 173 |
|
| 174 |
) ); |
| 175 |
} |
| 176 |
|
| 177 |
// Ajax Hooks |
| 178 |
if ( is_admin() && ( defined( 'DOING_AJAX' ) ) && ( DOING_AJAX ) ) { |
| 179 |
add_action( 'wp_ajax_nopriv_' . 'WPBC_AJX_BOOKING__CREATE', 'ajax_' . 'WPBC_AJX_BOOKING__CREATE' ); // Client (not logged in) |
| 180 |
add_action( 'wp_ajax_' . 'WPBC_AJX_BOOKING__CREATE', 'ajax_' . 'WPBC_AJX_BOOKING__CREATE' ); // Logged In users (or admin panel) |
| 181 |
} |
| 182 |
|
| 183 |
|
| 184 |
// --------------------------------------------------------------------------------------------------------------------- |
| 185 |
// == Save Booking |
| 186 |
// --------------------------------------------------------------------------------------------------------------------- |
| 187 |
|
| 188 |
/** |
| 189 |
* Save Booking - ADD NEW or UPDATE exist booking |
| 190 |
* |
| 191 |
* @param $request_params = [ |
| 192 |
* resource_id = 2 REQUIRED Default: 1 |
| 193 |
* dates_ddmmyy_csv = '27.10.2023, 28.10.2023, 29.10.2023' REQUIRED |
| 194 |
* form_data = 'text^selected_short_dates_hint2^Fri, ...9, 2023~text^...' REQUIRED |
| 195 |
* booking_hash = '' Optional Default: '' |
| 196 |
* custom_form = '' Optional Default: '' |
| 197 |
* is_emails_send = 1 Optional Default: 1 |
| 198 |
* is_show_payment_form => 1 Optional Default: 1 |
| 199 |
* user_id = 1 Optional Default: 0 or ID of logged-in user |
| 200 |
* request_uri = 'http://beta/resource-id2/', // Optional Default: for front-end: $_SERVER['REQUEST_URI'] | ajax: $_SERVER['HTTP_REFERER'] |
| 201 |
* |
| 202 |
* 'sync_gid' => 'ghjgjgjgh5f5f45f' // Really Optional: can be passed only during import .ics |
| 203 |
* 'is_approve_booking' => 0 // Really Optional: 0 | 1 |
| 204 |
* 'save_booking_even_if_unavailable' => 0 // Really Optional: 0 | 1, if 1 then force save booking even if dates unavailable. |
| 205 |
* ] |
| 206 |
* |
| 207 |
* @return [] ok: [ |
| 208 |
* |
| 209 |
* ] |
| 210 |
* error: [ |
| 211 |
* 'ajx_data': [ 'status':'error', 'status_error':'booking_can_not_save', 'ajx_after_action_message': 'Can not save booking', 'ajx_after_action_message_status': 'warning' ] |
| 212 |
* ] |
| 213 |
* |
| 214 |
* Example: |
| 215 |
* |
| 216 |
* wpbc_booking_save( array( |
| 217 |
* 'resource_id' => 2, |
| 218 |
* 'dates_ddmmyy_csv' => '04.10.2023, 05.10.2023, 06.10.2023', |
| 219 |
* 'form_data' => 'text^cost_hint2^150.00฿~selectbox-multiple^rangetime2[]^14:00 - 16:00~text^name2^John~text^secondname2^Smith~email^email2^john.smith@server.com~selectbox-one^visitors2^2~selectbox-one^children2^0~textarea^details2^test', |
| 220 |
* 'booking_hash' => '', |
| 221 |
* 'custom_form' => '', |
| 222 |
* 'is_emails_send' => 1, |
| 223 |
* 'is_show_payment_form' => 1, |
| 224 |
* 'user_id' => 1, |
| 225 |
* 'request_uri' => 'http://beta/resource-id2/' |
| 226 |
* ) ); |
| 227 |
* |
| 228 |
*/ |
| 229 |
function wpbc_booking_save( $request_params ){ |
| 230 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 231 |
$php_performance = php_performance_START( 'total', array() ); |
| 232 |
// </editor-fold> |
| 233 |
$ajx_data_arr = array(); |
| 234 |
$ajx_data_arr['status'] = 'ok'; |
| 235 |
|
| 236 |
// ----------------------------------------------------------------------------------------------------------------- |
| 237 |
// 1. Direct Clean Params |
| 238 |
// ----------------------------------------------------------------------------------------------------------------- |
| 239 |
$server_request_uri = ( ( isset( $_SERVER['REQUEST_URI'] ) ) ? sanitize_text_field( $_SERVER['REQUEST_URI'] ) : '' ); /* phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.MissingUnslash */ /* FixIn: sanitize_unslash */ |
| 240 |
$server_http_referer_uri = ( ( isset( $_SERVER['HTTP_REFERER'] ) ) ? sanitize_text_field( $_SERVER['HTTP_REFERER'] ) : '' ); /* phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.ValidatedSanitizedInput.MissingUnslash */ /* FixIn: sanitize_unslash */ |
| 241 |
$validate_arr_rules = array( |
| 242 |
'resource_id' => array( 'validate' => 'd', 'default' => 1 ), // INT |
| 243 |
'dates_ddmmyy_csv' => array( 'validate' => 'csv_dates', 'default' => '' ), // FixIn: 9.9.1.1. |
| 244 |
'form_data' => array( 'validate' => 'strong', 'default' => '' ), |
| 245 |
'booking_hash' => array( 'validate' => 'strong', 'default' => '' ), |
| 246 |
'custom_form' => array( 'validate' => 'strong', 'default' => '' ), |
| 247 |
'is_emails_send' => array( 'validate' => 'd', 'default' => 1 ), // 0 | 1 |
| 248 |
'is_show_payment_form' => array( 'validate' => 'd', 'default' => 1 ), // 0 | 1 |
| 249 |
'user_id' => array( 'validate' => 'd', 'default' => wpbc_get_current_user_id() ), // INT |
| 250 |
'request_uri' => array( 'validate' => 'strong', 'default' => ( ( defined( 'DOING_AJAX' ) ) && ( DOING_AJAX ) ) ? $server_http_referer_uri : $server_request_uri ), // front-end: $server_request_uri | ajax: $server_http_referer_uri |
| 251 |
// Really Optional: |
| 252 |
'aggregate_resource_id_arr' => array( 'validate' => 'digit_or_csd', 'default' => '' ), |
| 253 |
//TODO: this parameter does not transfer during saving, so here will be always default value 'bookings_only' // FixIn: 10.0.0.7. |
| 254 |
'aggregate_type' => array( 'validate' => 'strong', 'default' => 'bookings_only' ), // Optional. 'all' | 'bookings_only' <- it is depends on shortcode parameter: options="{aggregate type=bookings_only}" |
| 255 |
'is_approve_booking' => array( 'validate' => 'd', 'default' => 0 ), // 0 | 1 |
| 256 |
'save_booking_even_if_unavailable' => array( 'validate' => 'd', 'default' => 0 ), // 0 | 1 |
| 257 |
'sync_gid' => array( 'validate' => 'strong', 'default' => '' ), |
| 258 |
'is_use_booking_recurrent_time' => array( 'validate' => 'd', 'default' => intval( ( 'On' === get_bk_option( 'booking_recurrent_time' ) ) ) ) |
| 259 |
); |
| 260 |
$re_cleaned_params = wpbc_sanitize_params_in_arr( $request_params, $validate_arr_rules ); |
| 261 |
|
| 262 |
$admin_uri = ltrim( str_replace( get_site_url( null, '', 'admin' ), '', admin_url( 'admin.php?' ) ), '/' ); // wp-admin/admin.php? |
| 263 |
|
| 264 |
|
| 265 |
// ----------------------------------------------------------------------------------------------------------------- |
| 266 |
// Local parameters |
| 267 |
// ----------------------------------------------------------------------------------------------------------------- |
| 268 |
$local_params = array(); |
| 269 |
$local_params['is_from_admin_panel'] = ( false !== strpos( $re_cleaned_params['request_uri'], $admin_uri ) ); // true | false |
| 270 |
$local_params['user_id'] = $re_cleaned_params['user_id']; // 1 |
| 271 |
$local_params['sync_gid'] = $re_cleaned_params['sync_gid']; // '' |
| 272 |
$local_params['is_approve_booking'] = $re_cleaned_params['is_approve_booking']; // 0 | 1 |
| 273 |
$local_params['is_use_booking_recurrent_time'] = ( 1 === $re_cleaned_params['is_use_booking_recurrent_time'] ); // false | true |
| 274 |
|
| 275 |
// ----------------------------------------------------------------------------------------------------------------- |
| 276 |
// Parse Local parameters for later use |
| 277 |
// ----------------------------------------------------------------------------------------------------------------- |
| 278 |
/** |
| 279 |
* Get parsed booking form: = [ name = "John", secondname = "Smith", email = "john.smith@server.com", visitors = "2",... ] |
| 280 |
*/ |
| 281 |
$local_params['structured_booking_data_arr'] = wpbc_get_parsed_booking_data_arr( $re_cleaned_params["form_data"], $re_cleaned_params["resource_id"], array( 'get' => 'value' ) ); |
| 282 |
$local_params['all_booking_data_arr'] = wpbc_get_parsed_booking_data_arr( $re_cleaned_params["form_data"], $re_cleaned_params["resource_id"] ); |
| 283 |
// Important! : [ 64800, 72000 ] |
| 284 |
$local_params['time_as_seconds_arr'] = wpbc_get_in_booking_form__time_to_book_as_seconds_arr( $local_params['structured_booking_data_arr'] ); |
| 285 |
// [ "18:00:00", "20:00:00" ] |
| 286 |
$time_as_seconds_arr = $local_params['time_as_seconds_arr']; |
| 287 |
$time_as_seconds_arr[0] = ( 0 != $time_as_seconds_arr[0] ) ? $time_as_seconds_arr[0] + 1 : $time_as_seconds_arr[0]; // set check in time with ended 1 second |
| 288 |
$time_as_seconds_arr[1] = ( ( 24 * 60 * 60 ) != $time_as_seconds_arr[1] ) ? $time_as_seconds_arr[1] + 2 : $time_as_seconds_arr[1]; // set check out time with ended 2 seconds |
| 289 |
if ( ( 0 != $time_as_seconds_arr[0] ) && ( ( 24 * 60 * 60 ) == $time_as_seconds_arr[1] ) ) { |
| 290 |
//FixIn: 10.0.0.49 - in case if we have start time != 00:00 and end time as 24:00 then set end time as 23:59:52 |
| 291 |
$time_as_seconds_arr[1] += - 8; |
| 292 |
} |
| 293 |
$local_params['time_as_his_arr'] = array( |
| 294 |
wpbc_transform__seconds__in__24_hours_his( $time_as_seconds_arr[0] ), |
| 295 |
wpbc_transform__seconds__in__24_hours_his( $time_as_seconds_arr[1] ) |
| 296 |
); |
| 297 |
// [ '2023-09-10', '2023-09-11' ] |
| 298 |
$local_params['dates_only_sql_arr'] = wpbc_convert_dates_str__dd_mm_yyyy__to__yyyy_mm_dd( $re_cleaned_params["dates_ddmmyy_csv"] ); |
| 299 |
$local_params['dates_only_sql_arr'] = explode( ',', $local_params['dates_only_sql_arr'] ); |
| 300 |
|
| 301 |
$local_params['is_show_payment_form'] = $re_cleaned_params["is_show_payment_form"]; |
| 302 |
|
| 303 |
// FixIn: 9.9.0.35. |
| 304 |
if ( $local_params['is_show_payment_form'] ) { |
| 305 |
$local_params['is_show_payment_form'] = ( false !== strpos( $re_cleaned_params['request_uri'], 'is_show_payment_form=Off' ) ) |
| 306 |
? 0 |
| 307 |
: $local_params['is_show_payment_form']; // 1|0 |
| 308 |
} |
| 309 |
|
| 310 |
// Get EDIT booking data |
| 311 |
$local_params['edit_resource_id'] = ''; |
| 312 |
$local_params['skip_booking_id'] = ''; |
| 313 |
$local_params['is_edit_booking'] = 0; |
| 314 |
$local_params['is_duplicate_booking'] = 0; |
| 315 |
$is_edit_booking = wpbc_get_data__if_edit_booking( $re_cleaned_params['booking_hash'], $re_cleaned_params['request_uri'] ); |
| 316 |
if ( false !== $is_edit_booking ) { |
| 317 |
$local_params['edit_resource_id'] = $is_edit_booking['resource_id']; // can be parent booking resource, where we edit the booking |
| 318 |
$local_params['skip_booking_id'] = $is_edit_booking['booking_id']; // booking ID |
| 319 |
$local_params['is_edit_booking'] = $is_edit_booking['booking_id']; // booking ID |
| 320 |
if ( |
| 321 |
( ! empty( $local_params['structured_booking_data_arr']['wpbc_other_action'] ) ) |
| 322 |
&& ( 'duplicate_booking' === $local_params['structured_booking_data_arr']['wpbc_other_action'] ) |
| 323 |
){ |
| 324 |
$local_params['is_duplicate_booking'] = 1; |
| 325 |
} |
| 326 |
} |
| 327 |
// It can be request resource ID or if we edit booking, it can be 'edit resource' - (e.g. child resource) |
| 328 |
$local_params['initial_resource_id'] = ( ! empty( $local_params['edit_resource_id'] ) ) ? $local_params['edit_resource_id'] : $re_cleaned_params['resource_id']; |
| 329 |
|
| 330 |
// 2 |
| 331 |
$local_params['how_many_items_to_book'] = wpbc_get__how_many_items_to_book__in_booking_form( $local_params['structured_booking_data_arr'], $local_params['initial_resource_id'] ); |
| 332 |
|
| 333 |
|
| 334 |
$local_params['aggregate_resource_id_arr'] = explode( ',', $re_cleaned_params['aggregate_resource_id_arr'] ); |
| 335 |
$local_params['aggregate_resource_id_arr'] = array_filter( $local_params['aggregate_resource_id_arr'] ); // All entries of array equal to FALSE (0, '', '0' ) will be removed. |
| 336 |
$local_params['aggregate_resource_id_arr'] = array_unique( $local_params['aggregate_resource_id_arr'] ); // Erase duplicates |
| 337 |
|
| 338 |
// ----------------------------------------------------------------------------------------------------------------- |
| 339 |
// Here GO |
| 340 |
// ----------------------------------------------------------------------------------------------------------------- |
| 341 |
|
| 342 |
// Force - resource saving parameters, instead of wpbc__where_to_save_booking() |
| 343 |
if ( ! empty( $re_cleaned_params["save_booking_even_if_unavailable"] ) ) { |
| 344 |
|
| 345 |
$local_params['how_many_items_to_book'] = 1; |
| 346 |
|
| 347 |
$dates_keys_arr = array_values( $local_params['dates_only_sql_arr'] ); // [ '2023-09-23', '2023-09-24' ] |
| 348 |
|
| 349 |
$resources_in_dates = array_fill_keys( $dates_keys_arr , array( $local_params['initial_resource_id'] ) ); // [ 2023-09-23 = [ 2 ], 2023-09-24 = [ 2 ] ] |
| 350 |
|
| 351 |
$where_to_save_booking = array(); |
| 352 |
$where_to_save_booking['result'] = 'ok'; |
| 353 |
$where_to_save_booking['resources_in_dates'] = $resources_in_dates; // [ 2023-09-23 = [ 2, 10, 11 ], 2023-09-24 = [ 2, 10, 11 ] |
| 354 |
$where_to_save_booking['time_to_book'] = $local_params['time_as_his_arr']; // [ "00:00:00", "24:00:00" ] |
| 355 |
$where_to_save_booking['main__resource_id'] = $local_params['initial_resource_id']; // here edit or request (parent/single) resource |
| 356 |
|
| 357 |
} else { |
| 358 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 359 |
$php_performance = php_performance_START( 'wpbc__where_to_save_booking' , $php_performance ); |
| 360 |
// </editor-fold> |
| 361 |
|
| 362 |
/** |
| 363 |
* Get slots [] where we can save booking = [ 'resources_in_dates' => [ 2023-10-18 = [ 2, 12, 10, 11 ] |
| 364 |
* 2023-10-19 = [ 2, 12, 10, 11 ] |
| 365 |
* 2023-10-20 = [ 2, 12, 10, 11 ] |
| 366 |
* ], |
| 367 |
* 'time_to_book' => [ "14:00:01" , "12:00:01" ], |
| 368 |
* 'result' => 'ok' |
| 369 |
* 'main__resource_id' => 2 |
| 370 |
* ] |
| 371 |
* OR |
| 372 |
* [ 'result' => 'error', 'message' => 'Booking can not be saved ...' ] |
| 373 |
*/ |
| 374 |
$where_to_save_booking = wpbc__where_to_save_booking( array( |
| 375 |
'resource_id' => $local_params['initial_resource_id'], // 2 //TODO: If edit booking. What to pass 'edit' or 'parent' resource ID? |
| 376 |
'skip_booking_id' => $local_params['skip_booking_id'], // '', | 125 if edit booking |
| 377 |
'dates_only_sql_arr' => $local_params['dates_only_sql_arr'], // [ "2023-10-18", "2023-10-25", "2023-11-25" ] |
| 378 |
'time_as_seconds_arr' => $local_params['time_as_seconds_arr'], // [ 36000, 39600 ] |
| 379 |
'how_many_items_to_book' => $local_params['how_many_items_to_book'], // 1 |
| 380 |
'request_uri' => $re_cleaned_params['request_uri'], // 'http://beta/resource-id2/' |
| 381 |
'is_use_booking_recurrent_time' => $local_params['is_use_booking_recurrent_time'], // true | false |
| 382 |
'as_single_resource' => false, // false |
| 383 |
'aggregate_resource_id_arr' => $local_params['aggregate_resource_id_arr'], // Optional can be '' |
| 384 |
'aggregate_type' => $re_cleaned_params['aggregate_type'], //TODO: this parameter does not transfer during saving, so here will be always default value 'bookings_only' // FixIn: 10.0.0.7. |
| 385 |
'custom_form' => $re_cleaned_params['custom_form'] // FixIn: 10.0.0.10. |
| 386 |
)); |
| 387 |
// <editor-fold defaultstate="collapsed" desc=" :: ERROR :: <- NO SLOTS TO SAVE " > |
| 388 |
if ( 'error' == $where_to_save_booking['result'] ) { |
| 389 |
$ajx_data_arr['status'] = 'error'; |
| 390 |
$ajx_data_arr['status_error'] = 'booking_can_not_save'; |
| 391 |
$ajx_data_arr['ajx_after_action_message'] = $where_to_save_booking['message']; |
| 392 |
$ajx_data_arr['ajx_after_action_message_status'] = 'warning'; |
| 393 |
return array( 'ajx_data' => $ajx_data_arr ); |
| 394 |
} |
| 395 |
// </editor-fold> |
| 396 |
|
| 397 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 398 |
$php_performance = php_performance_END( 'wpbc__where_to_save_booking' , $php_performance ); |
| 399 |
// </editor-fold> |
| 400 |
} |
| 401 |
|
| 402 |
|
| 403 |
// Get parameters, from REQUEST |
| 404 |
$create_params = $local_params; |
| 405 |
$create_params['resource_id'] = ( ! empty( $local_params['edit_resource_id'] ) ) |
| 406 |
? $local_params['edit_resource_id'] // If we edit, then use original resource ??? |
| 407 |
: $where_to_save_booking['main__resource_id']; // Here is important TIP, resource can be where is free, and not where we submit |
| 408 |
/** |
| 409 |
* TODO: I think it's resolved! Just test about this situation, when we edit the booking - and it's means that we have $local_params['edit_resource_id'] |
| 410 |
* but what, if $where_to_save_booking do not contain this $local_params['edit_resource_id'] as available resource. |
| 411 |
* or even we have $local_params['edit_resource_id'] = 2 and $where_to_save_booking contain resources like [ 1, 2, 3, 4 ] |
| 412 |
* we make booking for 3 slots |
| 413 |
* in this case, main resource will be 2 |
| 414 |
* but then when we loop resources in wpbc_db__booking_save() we will save child booking resources for dates like: 2, 3, 4 ( and it's wrong ) |
| 415 |
* "(205, '2023-10-04 00:00:00', 0, NULL)" <- main resource '2' e.g. $local_params['edit_resource_id'] = 2 |
| 416 |
* "(205, '2023-10-04 00:00:00', 0, 2)" ? <- child resource '2' e.g. [ .., 2, .. ] in $where_to_save_booking WHICH IS WRONG |
| 417 |
*/ |
| 418 |
$create_params['is_emails_send'] = $re_cleaned_params['is_emails_send']; |
| 419 |
$create_params['custom_form'] = $re_cleaned_params['custom_form']; |
| 420 |
|
| 421 |
make_bk_action( 'check_multiuser_params_for_client_side', $create_params['resource_id'] ); // Activate working with specific user in WP MU |
| 422 |
|
| 423 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 424 |
$php_performance = php_performance_START( 'wpbc_db__booking_save' , $php_performance ); |
| 425 |
// </editor-fold> |
| 426 |
|
| 427 |
// ----------------------------------------------------------------------------------------------------------------- |
| 428 |
// == CREATE_THE 'NEW_BOOKING' == |
| 429 |
// ----------------------------------------------------------------------------------------------------------------- |
| 430 |
$create_booking_params = array( |
| 431 |
'resource_id' => $create_params['resource_id'], |
| 432 |
'custom_form' => $create_params['custom_form'], |
| 433 |
'all_booking_data_arr' => $create_params['all_booking_data_arr'], |
| 434 |
'dates_only_sql_arr' => $create_params['dates_only_sql_arr'], |
| 435 |
'time_as_his_arr' => $create_params['time_as_his_arr'], |
| 436 |
'is_from_admin_panel' => $create_params['is_from_admin_panel'], |
| 437 |
'is_edit_booking' => $create_params['is_edit_booking'], |
| 438 |
'is_duplicate_booking' => $create_params['is_duplicate_booking'], |
| 439 |
'is_approve_booking' => $create_params['is_approve_booking'], |
| 440 |
'how_many_items_to_book' => $create_params['how_many_items_to_book'], |
| 441 |
'is_use_booking_recurrent_time' => $create_params['is_use_booking_recurrent_time'] // true | false |
| 442 |
); |
| 443 |
if ( ! empty( $create_params['sync_gid'] ) ) { $create_booking_params['sync_gid'] = $create_params['sync_gid']; } |
| 444 |
|
| 445 |
$booking_new_arr = wpbc_db__booking_save( $create_booking_params, $where_to_save_booking ); |
| 446 |
|
| 447 |
// <editor-fold defaultstate="collapsed" desc=" :: ERROR :: <- BOOKING CREATION " > |
| 448 |
if ( 'ok' !== $booking_new_arr['status'] ) { |
| 449 |
$ajx_data_arr['status'] = $booking_new_arr['status']; |
| 450 |
$ajx_data_arr['status_error'] = 'booking_can_not_save'; |
| 451 |
$ajx_data_arr['ajx_after_action_message'] = $booking_new_arr['message']; |
| 452 |
$ajx_data_arr['ajx_after_action_message_status'] = 'error'; |
| 453 |
return array( 'ajx_data' => $ajx_data_arr ); |
| 454 |
} |
| 455 |
// </editor-fold> |
| 456 |
|
| 457 |
// FixIn: 9.9.0.36. |
| 458 |
if ( |
| 459 |
( 0 !== $create_params['is_edit_booking'] ) // If edit booking |
| 460 |
&& ( 1 != $create_params['is_duplicate_booking'] ) // If not duplicate |
| 461 |
) { |
| 462 |
// Log the cost info. |
| 463 |
$is_add_timezone_offset = true; |
| 464 |
$booking_note = wpbc_date_localized( gmdate( 'Y-m-d H:i:s' ), '[Y-m-d H:i]', $is_add_timezone_offset ) . ' '; |
| 465 |
$booking_note .= __( 'The booking has been edited', 'booking' ) . '. | Edit URL: ' . esc_url_raw( $re_cleaned_params['request_uri'] ) . ''; |
| 466 |
make_bk_action( 'wpdev_make_update_of_remark', $booking_new_arr['booking_id'], $booking_note, true ); |
| 467 |
} |
| 468 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 469 |
$php_performance = php_performance_END( 'wpbc_db__booking_save' , $php_performance ); |
| 470 |
// </editor-fold> |
| 471 |
|
| 472 |
// ----------------------------------------------------------------------------------------------------------------- |
| 473 |
// Get payment form(s) and Update COST of the booking |
| 474 |
// ----------------------------------------------------------------------------------------------------------------- |
| 475 |
$payment_params = array(); |
| 476 |
|
| 477 |
// Usually we have this: ( $str_dates__dd_mm_yyyy == $create_params['dates_only_sql_arr'] ) - but for ensure, use saved dates, e.g. $str_dates__dd_mm_yyyy |
| 478 |
$payment_params['booked_dates_times_arr'] = array( |
| 479 |
'dates_ymd_arr' => array_keys( $where_to_save_booking['resources_in_dates'] ), // [ 2023-10-20=>[], 2023-10-25=>[] ] -> [ "2023-10-20", "2023-10-25" ] |
| 480 |
'times_his_arr' => $where_to_save_booking['time_to_book'] // ['16:00:01', '18:00:02'] |
| 481 |
); |
| 482 |
$str_dates__dd_mm_yyyy = wpbc_convert_dates_arr__yyyy_mm_dd__to__dd_mm_yyyy( $payment_params['booked_dates_times_arr']['dates_ymd_arr'] ); // ['2023-10-20','2023-10-25'] => ['20.10.2023','25.10.2023'] |
| 483 |
$payment_params['str_dates__dd_mm_yyyy'] = implode( ',', $str_dates__dd_mm_yyyy ); // REQUIRED -- '14.11.2023, 15.11.2023, 16.11.2023, 17.11.2023' |
| 484 |
$payment_params['booking_id'] = $booking_new_arr['booking_id']; // REQUIRED -- '2' |
| 485 |
$payment_params['resource_id'] = $create_params['resource_id']; // REQUIRED -- '2' can be child resource (changed in wpbc_where_to_save() ) |
| 486 |
$payment_params['initial_resource_id'] = $local_params['initial_resource_id']; // REQUIRED -- '2' initial calendar - parent resource |
| 487 |
$payment_params['form_data'] = $booking_new_arr['form_data']; // we re-save it, because here can be sync_guid and custom form new data from wpbc_db__booking_save(..) // REQUIRED -- 'text^selected_short_timedates_hint4^06/11/2018 14:00...' |
| 488 |
$payment_params['times_array'] = array( |
| 489 |
explode( ':', $where_to_save_booking['time_to_book'][0] ), // ["10","00","00"] |
| 490 |
explode( ':', $where_to_save_booking['time_to_book'][1] ) // ["12","00","00"] |
| 491 |
); |
| 492 |
// Additional options |
| 493 |
$payment_params['is_edit_booking'] = $create_params['is_edit_booking']; // => 0 0 | int - ID of the booking |
| 494 |
$payment_params['custom_form'] = $create_params['custom_form']; // => '' '' | 'some_name' |
| 495 |
$payment_params['is_duplicate_booking'] = $create_params['is_duplicate_booking']; // => 0 0 | 1 |
| 496 |
$payment_params['is_from_admin_panel'] = $create_params['is_from_admin_panel']; // => false true | false |
| 497 |
$payment_params['is_show_payment_form'] = $create_params['is_show_payment_form']; // => 1 0 | 1 |
| 498 |
if ( $payment_params['is_from_admin_panel'] ) { |
| 499 |
// $payment_params['is_show_payment_form'] = 0; // FixIn: 9.9.0.21. |
| 500 |
} |
| 501 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 502 |
$php_performance = php_performance_START( 'wpbc_maybe_get_payment_form' , $php_performance ); |
| 503 |
// </editor-fold> |
| 504 |
|
| 505 |
// GET PAYMENT FORMS =============================================================================================== |
| 506 |
if ( function_exists( 'wpbc_maybe_get_payment_form' ) ) { |
| 507 |
|
| 508 |
$response__payment_form__arr = wpbc_maybe_get_payment_form( $payment_params ); |
| 509 |
|
| 510 |
// <editor-fold defaultstate="collapsed" desc=" :: ERROR :: <- COSTS || PAYMENT_SYSTEMS " > |
| 511 |
if ( |
| 512 |
( ! empty( $response__payment_form__arr['status'] ) ) |
| 513 |
&& ( 'ok' != $response__payment_form__arr['status'] ) |
| 514 |
) { |
| 515 |
$ajx_data_arr['status'] = $response__payment_form__arr['status']; |
| 516 |
$ajx_data_arr['status_error'] = 'booking_can_not_save'; |
| 517 |
$ajx_data_arr['ajx_after_action_message'] = $response__payment_form__arr['message']; |
| 518 |
$ajx_data_arr['ajx_after_action_message_status'] = 'error'; |
| 519 |
return array( 'ajx_data' => $ajx_data_arr ); |
| 520 |
} |
| 521 |
// </editor-fold> |
| 522 |
|
| 523 |
if ( ! empty( $response__payment_form__arr['costs_arr']['form_data'] ) ) { |
| 524 |
$payment_params['form_data'] = $response__payment_form__arr['costs_arr']['form_data']; // we re-save it, because here can be [cost_correction] shortcode data |
| 525 |
} |
| 526 |
//TODO: Do we really need this in output $ajx_data_arr ???, because it stored in $confirmation |
| 527 |
if ( ! empty( $response__payment_form__arr['gateways_output_arr'] ) ) { |
| 528 |
$ajx_data_arr['gateways_output_arr'] = $response__payment_form__arr['gateways_output_arr']; |
| 529 |
} |
| 530 |
if ( function_exists( 'wpbc_if_zero_cost__approve_booking_dates' ) ) { |
| 531 |
wpbc_if_zero_cost__approve_booking_dates( $payment_params['booking_id'] ); |
| 532 |
} |
| 533 |
|
| 534 |
} else { |
| 535 |
$response__payment_form__arr = $payment_params; |
| 536 |
$response__payment_form__arr['status'] = 'ok'; |
| 537 |
} |
| 538 |
|
| 539 |
|
| 540 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 541 |
$php_performance = php_performance_END( 'wpbc_maybe_get_payment_form' , $php_performance ); |
| 542 |
|
| 543 |
$php_performance = php_performance_START( 'emails_sending' , $php_performance ); |
| 544 |
// </editor-fold> |
| 545 |
|
| 546 |
// ----------------------------------------------------------------------------------------------------------------- |
| 547 |
// == Emails === |
| 548 |
// ----------------------------------------------------------------------------------------------------------------- |
| 549 |
if ( 1 == $re_cleaned_params['is_emails_send'] ) { |
| 550 |
|
| 551 |
$email_content = $payment_params['form_data']; |
| 552 |
|
| 553 |
// If we output any text, then probably it's errors or warnings, we need to catch them |
| 554 |
ob_start(); |
| 555 |
ob_clean(); |
| 556 |
|
| 557 |
if ( |
| 558 |
( 0 === $local_params['is_edit_booking'] ) |
| 559 |
|| ( 1 === $local_params['is_duplicate_booking'] ) // FixIn: 10.0.0.42. |
| 560 |
){ |
| 561 |
|
| 562 |
// New booking to Admin |
| 563 |
wpbc_send_email_new_admin( $payment_params['booking_id'], $payment_params['resource_id'], $email_content ); |
| 564 |
|
| 565 |
// New pending to Visitor |
| 566 |
wpbc_send_email_new_visitor( $payment_params['booking_id'], $payment_params['resource_id'], $email_content ) ; |
| 567 |
|
| 568 |
$is_booking_approved = wpbc_is_booking_approved( $payment_params['booking_id'] ); |
| 569 |
if ( $is_booking_approved ) { |
| 570 |
// New approved to Visitor / Admin |
| 571 |
wpbc_send_email_approved( $payment_params['booking_id'], 1 ); |
| 572 |
} |
| 573 |
|
| 574 |
do_action( 'wpbc_booking_is_approved_during_creation' , $payment_params['booking_id'] , (int) $is_booking_approved ); // FixIn: 10.10.1.1. |
| 575 |
|
| 576 |
// Payment request from admin panel, if needed |
| 577 |
if( |
| 578 |
( $payment_params['is_from_admin_panel'] ) |
| 579 |
&& ( 'On' == get_bk_option( 'booking_payment_request_auto_send_in_bap' ) ) |
| 580 |
&& ( function_exists( 'wpbc_send_email_payment_request' ) ) |
| 581 |
){ |
| 582 |
$payment_reason = ''; |
| 583 |
$is_send = wpbc_send_email_payment_request( $payment_params['booking_id'], $payment_params['resource_id'], $email_content , $payment_reason ); |
| 584 |
} |
| 585 |
|
| 586 |
|
| 587 |
|
| 588 |
} else { |
| 589 |
|
| 590 |
// Edited booking to Visitor / Admin |
| 591 |
if ( function_exists( 'wpbc_send_email_modified' ) ) { |
| 592 |
wpbc_send_email_modified( $payment_params['booking_id'], $payment_params['resource_id'], $email_content ); |
| 593 |
} |
| 594 |
} |
| 595 |
|
| 596 |
$errors_on_email_sending_html = ob_get_contents(); |
| 597 |
ob_end_clean(); |
| 598 |
|
| 599 |
if ( ! empty( $errors_on_email_sending_html ) ) { |
| 600 |
// Show these messages as warning after creation of the booking |
| 601 |
$errors_on_email_sending_html = wp_strip_all_tags( $errors_on_email_sending_html ); |
| 602 |
$errors_on_email_sending_html = esc_attr( $errors_on_email_sending_html ); |
| 603 |
$errors_on_email_sending_html = str_replace( "\\n", '', $errors_on_email_sending_html ); |
| 604 |
|
| 605 |
$ajx_data_arr['ajx_after_action_message_status'] = 'warning'; |
| 606 |
$ajx_data_arr['ajx_after_action_message'] = $errors_on_email_sending_html; |
| 607 |
} |
| 608 |
} |
| 609 |
|
| 610 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 611 |
$php_performance = php_performance_END( 'emails_sending' , $php_performance ); |
| 612 |
// </editor-fold> |
| 613 |
|
| 614 |
// ----------------------------------------------------------------------------------------------------------------- |
| 615 |
// == Track booking - New | Edit === |
| 616 |
// ----------------------------------------------------------------------------------------------------------------- |
| 617 |
/** |
| 618 |
* Useful hook for Google Ads Conversion tracking. How to use this hook? |
| 619 |
* |
| 620 |
* Add code similar to this in your functions.php file in your theme, or in some other php file: |
| 621 |
* |
| 622 |
// Track adding new booking |
| 623 |
// |
| 624 |
// @param $params = array ( |
| 625 |
// 'str_dates__dd_mm_yyyy' => '08.10.2023,09.10.2023,10.10.2023,11.10.2023', |
| 626 |
// 'booking_id' => 254, |
| 627 |
// 'resource_id' => 11, // child or parent or single |
| 628 |
// 'initial_resource_id' => 2, // parent or single |
| 629 |
// 'form_data' => 'text^selected_short_dates_hint11^Sun...', |
| 630 |
// 'times_array' => array ( array ( '14', '00', '01' ), array( '12', '00', '02' ) ), |
| 631 |
// 'is_edit_booking' => 0, |
| 632 |
// 'custom_form' => '', |
| 633 |
// 'is_duplicate_booking' => 0, |
| 634 |
// 'is_from_admin_panel' => false, |
| 635 |
// 'is_show_payment_form' => 1 |
| 636 |
// ) |
| 637 |
function my_booking_tracking( $params ){ |
| 638 |
// Your code here |
| 639 |
?><!-- Google Code for Booking Conversion Page --> |
| 640 |
<script type="text/javascript"> |
| 641 |
// Insert bellow your Google Conversion Code |
| 642 |
</script><?php |
| 643 |
} |
| 644 |
add_action( 'wpbc_track_new_booking', 'my_booking_tracking' ); |
| 645 |
* |
| 646 |
* |
| 647 |
* |
| 648 |
* Useful hook booking edit tracking |
| 649 |
* |
| 650 |
* Add code similar to this in your functions.php file in your theme, or in some other php file: |
| 651 |
* |
| 652 |
// Track edit existing booking |
| 653 |
// |
| 654 |
// @param $params = array ( |
| 655 |
// 'str_dates__dd_mm_yyyy' => '08.10.2023,09.10.2023,10.10.2023,11.10.2023', |
| 656 |
// 'booking_id' => 254, |
| 657 |
// 'resource_id' => 11, // child or parent or single |
| 658 |
// 'initial_resource_id' => 2, // parent or single |
| 659 |
// 'form_data' => 'text^selected_short_dates_hint11^Sun...', |
| 660 |
// 'times_array' => array ( array ( '14', '00', '01' ), array( '12', '00', '02' ) ), |
| 661 |
// 'is_edit_booking' => 1, |
| 662 |
// 'custom_form' => '', |
| 663 |
// 'is_duplicate_booking' => 0, |
| 664 |
// 'is_from_admin_panel' => false, |
| 665 |
// 'is_show_payment_form' => 1 |
| 666 |
// ) |
| 667 |
function my_edit_booking_tracking( $params ){ |
| 668 |
// Your code here |
| 669 |
?><!-- Google Code for Booking Conversion Page --> |
| 670 |
<script type="text/javascript"> |
| 671 |
// Insert bellow your Google Conversion Code |
| 672 |
</script><?php |
| 673 |
|
| 674 |
} |
| 675 |
add_action( 'wpbc_track_edit_booking', 'my_edit_booking_tracking' ); |
| 676 |
*/ |
| 677 |
if ( 0 === $local_params['is_edit_booking'] ) { |
| 678 |
do_action( 'wpbc_track_new_booking', $payment_params ); |
| 679 |
} else { |
| 680 |
do_action( 'wpbc_track_edit_booking', $payment_params ); |
| 681 |
} |
| 682 |
|
| 683 |
|
| 684 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 685 |
$php_performance = php_performance_START( 'confirmation' , $php_performance ); |
| 686 |
// </editor-fold> |
| 687 |
|
| 688 |
// <editor-fold defaultstate="collapsed" desc=" == Confirmation data == " > |
| 689 |
|
| 690 |
|
| 691 |
$confirmation_params_arr = array( |
| 692 |
'is_from_admin_panel' => $payment_params['is_from_admin_panel'], |
| 693 |
|
| 694 |
'booking_id' => $booking_new_arr['booking_id'], // 16102023 |
| 695 |
'resource_id' => $payment_params['resource_id'], // 1 |
| 696 |
'form_data' => $payment_params['form_data'], // 'text^selected_short_dates_hint11^Sun...', |
| 697 |
'dates_ymd_arr' => $payment_params['booked_dates_times_arr']['dates_ymd_arr'], // [ '2023-10-20', '2023-10-25' ] |
| 698 |
'times_his_arr' => $payment_params['booked_dates_times_arr']['times_his_arr'], // [ '16:00:01', '18:00:02' ] |
| 699 |
|
| 700 |
'total_cost' => ( isset( $response__payment_form__arr['costs_arr'] ) && isset( $response__payment_form__arr['costs_arr']['total_cost'] ) ) |
| 701 |
? $response__payment_form__arr['costs_arr']['total_cost'] |
| 702 |
: 0, |
| 703 |
'deposit_cost' => ( isset( $response__payment_form__arr['costs_arr'] ) && isset( $response__payment_form__arr['costs_arr']['deposit_cost'] ) ) |
| 704 |
? $response__payment_form__arr['costs_arr']['deposit_cost'] |
| 705 |
: 0, |
| 706 |
'booking_summary' => ( ( ! empty( $response__payment_form__arr['gateways_output_arr'] ) ) && ( ! empty( $response__payment_form__arr['gateways_output_arr']['booking_summary'] ) ) ) |
| 707 |
? $response__payment_form__arr['gateways_output_arr']['booking_summary'] |
| 708 |
: '', |
| 709 |
'gateway_rows' => ( ( ! empty( $response__payment_form__arr['gateways_output_arr'] ) ) && ( ! empty( $response__payment_form__arr['gateways_output_arr']['gateway_rows'] ) ) ) |
| 710 |
? $response__payment_form__arr['gateways_output_arr']['gateway_rows'] |
| 711 |
: '' |
| 712 |
); |
| 713 |
// It will not show payment form in Booking > Add booking page and if defined, do not make redirect |
| 714 |
if ( $payment_params['is_from_admin_panel'] ) { |
| 715 |
|
| 716 |
$confirmation_params_arr['ty_is_redirect'] = 'message'; // Do not make redirect, if it's in admin panel! |
| 717 |
|
| 718 |
// But if we edit / duplicate the booking, then do redirection to Booking Listing page // FixIn: 9.9.0.3. |
| 719 |
if ( |
| 720 |
( 0 !== $local_params['is_edit_booking'] ) |
| 721 |
// && ( empty( $local_params['is_duplicate_booking'] ) ) |
| 722 |
){ |
| 723 |
$confirmation_params_arr['ty_is_redirect'] = 'page'; |
| 724 |
$confirmation_params_arr['ty_url'] = wpbc_get_bookings_url() . '&tab=vm_booking_listing&wh_booking_id=' . $confirmation_params_arr['booking_id']; |
| 725 |
} |
| 726 |
} |
| 727 |
$confirmation = wpbc_booking_confirmation( $confirmation_params_arr ); |
| 728 |
|
| 729 |
// </editor-fold> |
| 730 |
|
| 731 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 732 |
$php_performance = php_performance_END( 'confirmation' , $php_performance ); |
| 733 |
// </editor-fold> |
| 734 |
|
| 735 |
|
| 736 |
make_bk_action( 'finish_check_multiuser_params_for_client_side', $create_params['resource_id'] ); // Deactivate working with specific user in WP MU |
| 737 |
|
| 738 |
|
| 739 |
// <editor-fold defaultstate="collapsed" desc=" = PERFORMANCE = " > |
| 740 |
$php_performance = php_performance_END( 'total' , $php_performance ); |
| 741 |
$php_performance['other_code'] = - 1 * array_reduce( $php_performance, |
| 742 |
function ( $sum, $item ) { |
| 743 |
$sum += $item; |
| 744 |
return $sum; |
| 745 |
} |
| 746 |
, - 2 * $php_performance['total'] ); // PERFORMANCE OTHER - after TOTAL |
| 747 |
// </editor-fold> |
| 748 |
|
| 749 |
|
| 750 |
return array( 'ajx_data' => $ajx_data_arr, // [ 'status' => "ok", 'wpbc_payment_output' => "<p>Dear John<br..." ] |
| 751 |
'booking_id' => $booking_new_arr['booking_id'], // 254 |
| 752 |
'booking_arr' => $payment_params, |
| 753 |
'php_performance' => $php_performance, // [ ... ] |
| 754 |
'confirmation' => $confirmation // [ ] |
| 755 |
); |
| 756 |
} |
| 757 |
|
| 758 |
|
| 759 |
// --------------------------------------------------------------------------------------------------------------------- |
| 760 |
// New booking creation sub functions |
| 761 |
// --------------------------------------------------------------------------------------------------------------------- |
| 762 |
|
| 763 |
/** |
| 764 |
* Save booking in DB |
| 765 |
* |
| 766 |
* @param array $create_params = [ |
| 767 |
* 'resource_id' => 10, |
| 768 |
* 'dates_only_sql_arr' => [ '2023-10-04', '2023-10-05', '2023-10-06'], |
| 769 |
* 'time_as_his_arr' => [ '14:00:01', '16:00:02' ], |
| 770 |
* 'is_from_admin_panel' => false, |
| 771 |
* 'is_edit_booking' => 0, |
| 772 |
* 'is_duplicate_booking' => 0, |
| 773 |
* 'is_approve_booking' => 0, |
| 774 |
* 'how_many_items_to_book' => 2, |
| 775 |
* 'custom_form' => '', |
| 776 |
* 'is_use_booking_recurrent_time' => false, |
| 777 |
* 'all_booking_data_arr' => [ 'rangetime' => [ |
| 778 |
* 'type' => 'selectbox-multiple', |
| 779 |
* 'original_name' => 'rangetime2[]', //NOTE: here RESOURCE ID (2) can be from Parent resource, but resource_id can rely on child (10) resource |
| 780 |
* 'name' => 'rangetime', |
| 781 |
* 'value' => '14:00 - 16:00', |
| 782 |
* ], |
| 783 |
* 'name' => [ 'type' => 'text', 'original_name' => 'name2', ... ], |
| 784 |
* ... |
| 785 |
* ] |
| 786 |
* ] |
| 787 |
* |
| 788 |
* @param $where_to_save_booking = [ |
| 789 |
* 'result' = 'ok', |
| 790 |
* 'main__resource_id' = 2 |
| 791 |
* 'resources_in_dates' = [ 2023-10-18 = [ 2, 12, 10, 11 ] |
| 792 |
* 2023-10-19 = [ 2, 12, 10, 11 ] |
| 793 |
* 2023-10-20 = [ 2, 12, 10, 11 ] |
| 794 |
* ], |
| 795 |
* 'time_to_book' = [ "14:00:01" , "16:00:02" ] |
| 796 |
* ] |
| 797 |
* |
| 798 |
* @return [ |
| 799 |
* 'status' => 'ok' 'ok' | 'error' | 'warning' |
| 800 |
* 'booking_id' => 100 int |
| 801 |
* 'message' => '' 'If error, then here can be description of error' |
| 802 |
* 'form_data' => If 'ok' form data can be different here, 'custom_form' parameter, so it can add 'wpbc_custom_booking_form' field for identification, what custom booking form was used, |
| 803 |
* ] |
| 804 |
*/ |
| 805 |
function wpbc_db__booking_save( $create_params, $where_to_save_booking ) { |
| 806 |
|
| 807 |
/** |
| 808 |
* Tip: $create_params['all_booking_data_arr'] - contain: [ 'field_name' => [ 'type' = "checkbox", 'original_name' = "fixed_fee2[]", 'name' = "fixed_fee", 'value' = "true" ] , ... ] |
| 809 |
* $create_params['structured_booking_data_arr'] - contain: [ 'field_name' => 'field_value' , ... ] |
| 810 |
*/ |
| 811 |
|
| 812 |
// <editor-fold defaultstate="collapsed" desc=" :: ERROR :: <- 'Wrong resource ID " > |
| 813 |
if ( empty( $create_params['resource_id'] ) ) { |
| 814 |
return array( 'status' => 'error', 'message' => 'Wrong ID of booking resource: ' . $create_params['resource_id'] ); |
| 815 |
} |
| 816 |
// </editor-fold> |
| 817 |
|
| 818 |
|
| 819 |
$defaults = array( |
| 820 |
'is_use_booking_recurrent_time' => ( 'On' === get_bk_option( 'booking_recurrent_time' ) ) |
| 821 |
); |
| 822 |
$create_params = wp_parse_args( $create_params, $defaults ); |
| 823 |
|
| 824 |
|
| 825 |
$sql_field_arr = array(); |
| 826 |
|
| 827 |
|
| 828 |
|
| 829 |
// Is it was used custom booking form ? |
| 830 |
if ( ! empty( $create_params['custom_form'] ) ) { |
| 831 |
$create_params['all_booking_data_arr']['wpbc_custom_booking_form'] = array( |
| 832 |
'type' => 'text', |
| 833 |
'original_name' => 'wpbc_custom_booking_form' . $create_params['resource_id'], |
| 834 |
'name' => 'wpbc_custom_booking_form', |
| 835 |
'value' => $create_params['custom_form'] |
| 836 |
); |
| 837 |
} |
| 838 |
|
| 839 |
if ( ! empty( $create_params['sync_gid'] ) ) { |
| 840 |
/** |
| 841 |
* Such fields are comming from '../wp-content/plugins/booking/core/sync/wpbc-gcal-class.php' in function run() |
| 842 |
*/ |
| 843 |
|
| 844 |
// Escape any XSS injection from values in booking form |
| 845 |
list( $create_params['sync_gid'] ) = wpbc_escape_any_xss_in_arr( array( $create_params['sync_gid'] ) ); |
| 846 |
|
| 847 |
$sql_field_arr[] = array( 'name' => 'sync_gid', 'type' => '%s', 'value' => $create_params['sync_gid'] ); |
| 848 |
} |
| 849 |
|
| 850 |
// Escape any XSS injection from values in booking form |
| 851 |
$create_params['all_booking_data_arr'] = wpbc_escape_any_xss_in_arr( $create_params['all_booking_data_arr'] ); |
| 852 |
|
| 853 |
|
| 854 |
//Set LAST check out day as AVAILABLE - remove it |
| 855 |
if ( |
| 856 |
( 'On' === get_bk_option( 'booking_last_checkout_day_available' ) ) |
| 857 |
&& ( ! empty( $create_params['dates_only_sql_arr'] ) ) |
| 858 |
&& ( count( $create_params['dates_only_sql_arr'] ) > 1 ) |
| 859 |
) { |
| 860 |
unset( $create_params['dates_only_sql_arr'][ ( count( $create_params['dates_only_sql_arr'] ) - 1 ) ] ); // Remove LAST selected day in calendar // FixIn: 6.2.3.6. |
| 861 |
// Delete last item // FixIn: 9.9.0.19. |
| 862 |
$resources_in_dates_last_key = key( array_slice( $where_to_save_booking['resources_in_dates'], - 1, 1, true ) ); |
| 863 |
unset( $where_to_save_booking['resources_in_dates'][ $resources_in_dates_last_key ] ); |
| 864 |
} |
| 865 |
|
| 866 |
// :: ERROR :: |
| 867 |
if ( empty( $create_params['dates_only_sql_arr'] ) ) { // No dates :? |
| 868 |
return array( 'status' => 'error', 'message' => 'Sent request with no dates.' ); |
| 869 |
} |
| 870 |
|
| 871 |
// <editor-fold defaultstate="collapsed" desc=" :: ERROR :: <- CHECK_IN_DATE_OLDER_THAN_CHECK_OUT " > |
| 872 |
if ( count( $create_params['dates_only_sql_arr'] ) == 1 ) { // Is it single selected date ? |
| 873 |
|
| 874 |
// Is 'check in' date/time older than 'check out' date/time when SINGLE day for booking? Then show error. |
| 875 |
|
| 876 |
/** |
| 877 |
* If we are having "change over" days activated and selected only 1 day in calendar, |
| 878 |
* then we can have error: "Warning! Number of check in != check out times.", because "check in" day older than "check out" date. |
| 879 |
*/ |
| 880 |
|
| 881 |
$is_apply__check_in_out__10s = false; |
| 882 |
$datestamp_check_in = wpbc_convert__sql_date__to_seconds( $create_params['dates_only_sql_arr'][0] . ' ' . $create_params['time_as_his_arr'][0], $is_apply__check_in_out__10s ); |
| 883 |
$datestamp_check_out = wpbc_convert__sql_date__to_seconds( $create_params['dates_only_sql_arr'][0] . ' ' . $create_params['time_as_his_arr'][1], $is_apply__check_in_out__10s ); |
| 884 |
|
| 885 |
|
| 886 |
if ( $datestamp_check_in > $datestamp_check_out ) { |
| 887 |
$error_message = sprintf( 'Error! Your check in date %s older than check out date %s. <br>Try to select more dates or use different time.' |
| 888 |
, '<strong>' . wpbc_convert__seconds__to_sql_date( $datestamp_check_in, $is_apply__check_in_out__10s ) . '</strong>' |
| 889 |
, '<strong>' . wpbc_convert__seconds__to_sql_date( $datestamp_check_out, $is_apply__check_in_out__10s ) . '</strong>' |
| 890 |
); |
| 891 |
$error_message .= '<br>' . '<strong>Settings that can be reason of the issue:</strong> '; |
| 892 |
if( 'On' === get_bk_option( 'booking_last_checkout_day_available' )){ |
| 893 |
$error_message .= '<br>' . 'You have enabled <strong>"Set check out date as available"</strong> option at Booking > Settings General page in "Calendar" section. '; |
| 894 |
} |
| 895 |
if ( 'On' === get_bk_option( 'booking_range_selection_time_is_active' ) ){ |
| 896 |
$error_message .= '<br>' . 'You have enabled <strong>"Use changeover days"</strong> option at Booking > Settings General page in "Calendar" section with check-in/out times: ' . get_bk_option( 'booking_range_selection_start_time' ) . '/' . get_bk_option( 'booking_range_selection_end_time' ); |
| 897 |
} |
| 898 |
if ( $create_params['is_use_booking_recurrent_time'] ) { |
| 899 |
$error_message .= '<br>' . 'You have enabled <strong>"Use time selections as recurrent time slots"</strong> option at Booking > Settings General page in "Calendar" section. '; |
| 900 |
} |
| 901 |
return array( 'status' => 'error', 'message' => $error_message ); |
| 902 |
} |
| 903 |
} |
| 904 |
// </editor-fold> |
| 905 |
|
| 906 |
// Compose form data for DB. Can be different resource: 'selectbox-multiple^rangetime10[]^14..' <-> 'selectbox-multiple^rangetime2[]^14..' -> 'rangetime10' - child res. Previously 'rangetime2' - parent |
| 907 |
$form_data = wpbc_encode_booking_data_to_string( $create_params['all_booking_data_arr'], $create_params['resource_id'] ); |
| 908 |
|
| 909 |
|
| 910 |
// ----------------------------------------------------------------------------------------------------------------- |
| 911 |
// APPROVED / PENDING |
| 912 |
// ----------------------------------------------------------------------------------------------------------------- |
| 913 |
// Is approve booking |
| 914 |
$auto_approve_new_bookings_is_active = trim( get_bk_option( 'booking_auto_approve_new_bookings_is_active' ) ); |
| 915 |
$is_approved_dates = ( $auto_approve_new_bookings_is_active == 'On' ) ? 1 : intval( $create_params['is_approve_booking'] ); |
| 916 |
|
| 917 |
// Auto approve only for specific booking resources |
| 918 |
/** |
| 919 |
* How to use "Auto approve bookings only for specific booking resources" ? |
| 920 |
* Add code similar to this in your functions.php file in your theme, or in some other php file: |
| 921 |
* |
| 922 |
function my_wpbc_get_booking_resources_arr_to_auto_approve( $resources_to_approve ) { |
| 923 |
$resources_to_approve = array( 9, 12, 33 ); // Array of booking resources ID, which you need to auto approve |
| 924 |
return $resources_to_approve; |
| 925 |
} |
| 926 |
add_filter( 'wpbc_get_booking_resources_arr_to_auto_approve', 'my_wpbc_get_booking_resources_arr_to_auto_approve' ); |
| 927 |
*/ |
| 928 |
$booking_resources_to_approve = array(); |
| 929 |
$booking_resources_to_approve = apply_filters( 'wpbc_get_booking_resources_arr_to_auto_approve', $booking_resources_to_approve ); // FixIn: 8.5.2.27. |
| 930 |
if ( in_array( $create_params['resource_id'], $booking_resources_to_approve ) ) { |
| 931 |
$is_approved_dates = 1; |
| 932 |
} |
| 933 |
|
| 934 |
if ( |
| 935 |
( $create_params['is_from_admin_panel'] ) // true | false |
| 936 |
&& ( get_bk_option( 'booking_auto_approve_bookings_if_added_in_admin_panel' ) == 'On' ) |
| 937 |
){ // FixIn: 8.1.3.27. |
| 938 |
$is_approved_dates = 1; |
| 939 |
} |
| 940 |
|
| 941 |
// If the booking auto-approved, then we need to mark it as "Read". |
| 942 |
if ( $is_approved_dates ) { |
| 943 |
$sql_field_arr[] = array( |
| 944 |
'name' => 'is_new', |
| 945 |
'type' => '%d', |
| 946 |
'value' => 0, |
| 947 |
); |
| 948 |
} |
| 949 |
|
| 950 |
// <editor-fold defaultstate="collapsed" desc=" == Save Booking == " > |
| 951 |
// ----------------------------------------------------------------------------------------------------------------- |
| 952 |
// Save Booking |
| 953 |
// ----------------------------------------------------------------------------------------------------------------- |
| 954 |
global $wpdb; |
| 955 |
|
| 956 |
$sql_field_arr[] = array( 'name' => 'form', 'type' => '%s', 'value' => $form_data ); |
| 957 |
$sql_field_arr[] = array( 'name' => 'booking_type', 'type' => '%d', 'value' => $create_params['resource_id'] ); |
| 958 |
$sql_field_arr[] = array( 'name' => 'modification_date', 'type' => '%s', 'value' => gmdate( 'Y-m-d H:i:s' ) ); |
| 959 |
$sql_field_arr[] = array( 'name' => 'sort_date', 'type' => '%s', 'value' => $create_params['dates_only_sql_arr'][0] . ' ' . $create_params['time_as_his_arr'][0] ); |
| 960 |
$sql_field_arr[] = array( 'name' => 'hash', 'type' => 'MD5(%s)', 'value' => time() . '_' . wp_rand( 1000, 1000000 ) ); |
| 961 |
|
| 962 |
|
| 963 |
if ( |
| 964 |
( 0 == $create_params['is_edit_booking'] ) || // If not edit, then INSERT. |
| 965 |
( 1 == $create_params['is_duplicate_booking'] ) // If duplicate, then INSERT. |
| 966 |
) { |
| 967 |
// Saved only for new booking creation. |
| 968 |
$sql_field_arr[] = array( |
| 969 |
'name' => 'creation_date', |
| 970 |
'type' => '%s', |
| 971 |
'value' => gmdate( 'Y-m-d H:i:s' ), |
| 972 |
); |
| 973 |
|
| 974 |
$sql_prepare_arr = array(); |
| 975 |
$sql_prepare_arr['name'] = array_map( function ( $value ) { return $value['name']; }, $sql_field_arr ); |
| 976 |
$sql_prepare_arr['type'] = array_map( function ( $value ) { return $value['type']; }, $sql_field_arr ); |
| 977 |
$sql_prepare_arr['value'] = array_map( function ( $value ) { return $value['value']; }, $sql_field_arr ); |
| 978 |
|
| 979 |
$sql_prepare_arr['name'] = implode( ', ', $sql_prepare_arr['name'] ); |
| 980 |
$sql_prepare_arr['type'] = implode( ', ', $sql_prepare_arr['type'] ); |
| 981 |
/* phpcs:ignore WordPress.DB.PreparedSQL.InterpolatedNotPrepared, WordPress.DB.PreparedSQL.NotPrepared, WordPress.DB.PreparedSQLPlaceholders.UnfinishedPrepare */ |
| 982 |
$sql = $wpdb->prepare( "INSERT INTO {$wpdb->prefix}booking " . " ( {$sql_prepare_arr['name']} )" . " VALUES ( {$sql_prepare_arr['type']} )", $sql_prepare_arr['value'] ); |
| 983 |
// phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching, WordPress.DB.PreparedSQL.NotPrepared |
| 984 |
if ( false === $wpdb->query( $sql ) ) { |
| 985 |
return array( 'status' => 'error', 'message' => 'Error. INSERT New Data in DB.' . ' FILE:' . __FILE__ . ' LINE:' . __LINE__ . ' SQL:' . $sql ); |
| 986 |
} |
| 987 |
// Get ID of booking |
| 988 |
$booking_id = (int) $wpdb->insert_id; |
| 989 |
|
| 990 |
} else { // Edit - UPDATE |
| 991 |
|
| 992 |
$booking_id = (int) $create_params['is_edit_booking']; |
| 993 |
|
| 994 |
$sql_prepare_arr = array(); |
| 995 |
$sql_prepare_arr['set'] = array_map( function ( $value ) { return $value['name'] . '=' . $value['type']; }, $sql_field_arr ); |
| 996 |
$sql_prepare_arr['value'] = array_map( function ( $value ) { return $value['value']; }, $sql_field_arr ); |
| 997 |
|
| 998 |
$sql_prepare_arr['set'] = implode( ', ', $sql_prepare_arr['set'] ); |
| 999 |
|
| 1000 |
// phpcs:ignore WordPress.DB.PreparedSQL.InterpolatedNotPrepared, WordPress.DB.PreparedSQLPlaceholders.UnfinishedPrepare |
| 1001 |
$sql = $wpdb->prepare( "UPDATE {$wpdb->prefix}booking SET {$sql_prepare_arr['set']} WHERE booking_id={$booking_id};", $sql_prepare_arr['value'] ); |
| 1002 |
// phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching, WordPress.DB.PreparedSQL.NotPrepared |
| 1003 |
if ( false === $wpdb->query( $sql ) ) { |
| 1004 |
return array( 'status' => 'error', |
| 1005 |
'message' => 'Error. UPDATE Exist Data in DB.' . ' FILE:' . __FILE__ . ' LINE:' . __LINE__ . ' SQL:' . $sql, |
| 1006 |
); |
| 1007 |
} |
| 1008 |
|
| 1009 |
// Check if dates previously was approved. |
| 1010 |
$slct_sql = "SELECT approved FROM {$wpdb->prefix}bookingdates WHERE booking_id IN ({$booking_id}) LIMIT 0,1"; |
| 1011 |
// phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching, WordPress.DB.PreparedSQL.NotPrepared |
| 1012 |
$slct_sql_results = $wpdb->get_results( $slct_sql ); |
| 1013 |
$is_approved_dates = ( count( $slct_sql_results ) > 0 ) ? $slct_sql_results[0]->approved : $is_approved_dates; |
| 1014 |
|
| 1015 |
|
| 1016 |
$delete_sql = "DELETE FROM {$wpdb->prefix}bookingdates WHERE booking_id IN ({$booking_id})"; |
| 1017 |
// phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching, WordPress.DB.PreparedSQL.NotPrepared |
| 1018 |
if ( false === $wpdb->query( $delete_sql ) ) { |
| 1019 |
return array( 'status' => 'error', 'message' => 'Error. DELETE Old Dates in DB.' . ' FILE:' . __FILE__ . ' LINE:' . __LINE__ . ' SQL:' . $delete_sql ); |
| 1020 |
} |
| 1021 |
} |
| 1022 |
// </editor-fold> |
| 1023 |
|
| 1024 |
|
| 1025 |
// <editor-fold defaultstate="collapsed" desc=" == Compose D A T E S for DB == " > |
| 1026 |
// ----------------------------------------------------------------------------------------------------------------- |
| 1027 |
// Compose D A T E S for DB |
| 1028 |
// ----------------------------------------------------------------------------------------------------------------- |
| 1029 |
|
| 1030 |
if ( class_exists( 'wpdev_bk_biz_l' ) ) { |
| 1031 |
$field_names_arr = array( 'booking_id', 'booking_date', 'approved', 'type_id' ); |
| 1032 |
} else { |
| 1033 |
$field_names_arr = array( 'booking_id', 'booking_date', 'approved' ); |
| 1034 |
} |
| 1035 |
$field_names = implode( ', ', $field_names_arr ); |
| 1036 |
|
| 1037 |
$dates_sql = "INSERT INTO {$wpdb->prefix}bookingdates ( {$field_names} ) VALUES "; |
| 1038 |
$insert_dates_arr = array(); |
| 1039 |
|
| 1040 |
$how_many_items_to_book = $create_params['how_many_items_to_book']; |
| 1041 |
// $i - INDEX of child booking resource to book (if $how_many_items_to_book=1, then index always = 0 ) in [ 'resources_in_dates' = [ '2023-10-18' = [ 9, 12, 10, 11 ], ... ]...] - e.g. here = 9 |
| 1042 |
for( $i = 0; $i < $how_many_items_to_book; $i++) { |
| 1043 |
|
| 1044 |
$date_number = 0; |
| 1045 |
foreach ( $where_to_save_booking['resources_in_dates'] as $only_date_sql => $resources_in_date_arr ) { |
| 1046 |
|
| 1047 |
$date_resource_id = $resources_in_date_arr[ $i ]; |
| 1048 |
|
| 1049 |
// $create_params['resource_id'] <- Main resource (saved in wp_booking ) |
| 1050 |
// $only_date_sql <- '2023-09-12' |
| 1051 |
// $date_resource_id <- Child resource (need to save in wp_bookingdates) OR if ( $create_params['resource_id'] == $date_resource_id ) then NULL |
| 1052 |
|
| 1053 |
// --------------------------------------------------------------------------------------------------------- |
| 1054 |
// Is full day booking: |
| 1055 |
if ( |
| 1056 |
( '00:00' === substr( $where_to_save_booking['time_to_book'][0], 0, 5 ) ) |
| 1057 |
&& ( |
| 1058 |
( '24:00' === substr( $where_to_save_booking['time_to_book'][1], 0, 5 ) ) |
| 1059 |
|| ( '00:00' === substr( $where_to_save_booking['time_to_book'][1], 0, 5 ) ) |
| 1060 |
) |
| 1061 |
){ |
| 1062 |
// Full days ******************************************************************************************* |
| 1063 |
$full_date_sql = $only_date_sql . ' 00:00:00'; |
| 1064 |
|
| 1065 |
$insert_dates_arr[] = wpbc_prepare_date_row( $booking_id, $full_date_sql, $is_approved_dates, $date_resource_id, $create_params['resource_id'] ); |
| 1066 |
|
| 1067 |
} else { // Times |
| 1068 |
|
| 1069 |
if ( |
| 1070 |
( $create_params['is_use_booking_recurrent_time'] ) // Activated option to book times as 'time-slots' OR |
| 1071 |
|| ( 1 === count( $where_to_save_booking['resources_in_dates'] ) ) // Selected only 1 date, so use time as time-slot |
| 1072 |
) { |
| 1073 |
// Time slots in each day ************************************************************************** |
| 1074 |
|
| 1075 |
// Start Time |
| 1076 |
$full_date_sql = $only_date_sql . ' ' . $where_to_save_booking['time_to_book'][0]; |
| 1077 |
$insert_dates_arr[] = wpbc_prepare_date_row( $booking_id, $full_date_sql, $is_approved_dates, $date_resource_id, $create_params['resource_id'] ); |
| 1078 |
|
| 1079 |
// End Time |
| 1080 |
$full_date_sql = $only_date_sql . ' ' . $where_to_save_booking['time_to_book'][1]; |
| 1081 |
$insert_dates_arr[] = wpbc_prepare_date_row( $booking_id, $full_date_sql, $is_approved_dates, $date_resource_id, $create_params['resource_id'] ); |
| 1082 |
|
| 1083 |
} else { |
| 1084 |
// Check in/out ************************************************************************************ |
| 1085 |
|
| 1086 |
if ( 0 == $date_number ) { // Is check in ? |
| 1087 |
|
| 1088 |
$full_date_sql = $only_date_sql . ' ' . $where_to_save_booking['time_to_book'][0]; |
| 1089 |
|
| 1090 |
} else if ( ( count( $where_to_save_booking['resources_in_dates'] ) - 1 ) == $date_number ) { // Is check out ? |
| 1091 |
|
| 1092 |
$full_date_sql = $only_date_sql . ' ' . $where_to_save_booking['time_to_book'][1]; |
| 1093 |
|
| 1094 |
} else { // Middle date - Full Date |
| 1095 |
$full_date_sql = $only_date_sql . ' 00:00:00'; |
| 1096 |
} |
| 1097 |
|
| 1098 |
$insert_dates_arr[] = wpbc_prepare_date_row( $booking_id, $full_date_sql, $is_approved_dates, $date_resource_id, $create_params['resource_id'] ); |
| 1099 |
|
| 1100 |
} |
| 1101 |
} |
| 1102 |
// --------------------------------------------------------------------------------------------------------- |
| 1103 |
$date_number++; |
| 1104 |
} |
| 1105 |
} |
| 1106 |
|
| 1107 |
$dates_sql .= implode( ', ', $insert_dates_arr ); |
| 1108 |
// phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching, WordPress.DB.PreparedSQL.NotPrepared |
| 1109 |
if ( false === $wpdb->query( $dates_sql ) ) { |
| 1110 |
return array( 'status' => 'error', 'message' => 'Error. INSERT "D A T E S" in DB.' . ' FILE:' . __FILE__ . ' LINE:' . __LINE__ . ' SQL:' . $dates_sql ); |
| 1111 |
} |
| 1112 |
|
| 1113 |
// ----------------------------------------------------------------------------------------------------------------- |
| 1114 |
// End D A T E S |
| 1115 |
// ----------------------------------------------------------------------------------------------------------------- |
| 1116 |
// </editor-fold> |
| 1117 |
|
| 1118 |
|
| 1119 |
return array( |
| 1120 |
'status' => 'ok' |
| 1121 |
, 'booking_id' => $booking_id |
| 1122 |
, 'form_data' => $form_data |
| 1123 |
, 'message' => '' |
| 1124 |
); |
| 1125 |
} |
| 1126 |
|
| 1127 |
|
| 1128 |
/** |
| 1129 |
* Get SQL ROWs of VALUES for INSERT to DB |
| 1130 |
* |
| 1131 |
* @param int $booking_id 101 ID of the booking |
| 1132 |
* @param string $full_date_sql '2023-09-12 10:00:01' SQL date |
| 1133 |
* @param int $is_approved_dates 1 1 - approved, 0 - pending |
| 1134 |
* @param int $date_resource_id ( >= biz_l ): 4 ID of child booking resource (if we save ONE booking in SEVERAL booking resources) field 'type_id' in wp_bookingdates |
| 1135 |
* @param int $main_resource_id ( >= biz_l ): 1 ID of main (parent booking resource) |
| 1136 |
* |
| 1137 |
* @return string - SQL for dates VALUES to insert |
| 1138 |
*/ |
| 1139 |
function wpbc_prepare_date_row( $booking_id, $full_date_sql, $is_approved_dates, $date_resource_id, $main_resource_id ) { |
| 1140 |
|
| 1141 |
global $wpdb; |
| 1142 |
|
| 1143 |
if ( class_exists( 'wpdev_bk_biz_l' ) ) { |
| 1144 |
$insert_dates_arr = ( $main_resource_id != $date_resource_id ) |
| 1145 |
? $wpdb->prepare( "(%d, %s, %d, %d)", $booking_id, $full_date_sql, $is_approved_dates, $date_resource_id ) |
| 1146 |
: $wpdb->prepare( "(%d, %s, %d, NULL)", $booking_id, $full_date_sql, $is_approved_dates ); |
| 1147 |
} else { |
| 1148 |
$insert_dates_arr = $wpdb->prepare( "(%d, %s, %d)", $booking_id, $full_date_sql, $is_approved_dates ); |
| 1149 |
} |
| 1150 |
|
| 1151 |
return $insert_dates_arr; |
| 1152 |
} |
| 1153 |
|
| 1154 |
|
| 1155 |
// --------------------------------------------------------------------------------------------------------------------- |
| 1156 |
// Support |
| 1157 |
// --------------------------------------------------------------------------------------------------------------------- |
| 1158 |
|
| 1159 |
/** |
| 1160 |
* Get booking_id and resource_id if we are editing the booking, by booking hash |
| 1161 |
* |
| 1162 |
* @param $booking_hash |
| 1163 |
* @param $server_request_url |
| 1164 |
* |
| 1165 |
* @return array | false false if not edit Otherwise [ 'booking_id': 100, 'resource_id': 3 ] |
| 1166 |
*/ |
| 1167 |
function wpbc_get_data__if_edit_booking( $booking_hash, $server_request_url ) { |
| 1168 |
|
| 1169 |
$is_edit_booking = false; |
| 1170 |
if ( ! empty( $booking_hash ) ) { |
| 1171 |
|
| 1172 |
$my_booking_id_type = wpbc_hash__get_booking_id__resource_id( $booking_hash ); |
| 1173 |
if ( $my_booking_id_type !== false ) { |
| 1174 |
|
| 1175 |
$is_edit_booking = array(); |
| 1176 |
$is_edit_booking['booking_id'] = intval( $my_booking_id_type[0] ); |
| 1177 |
$is_edit_booking['resource_id'] = intval( $my_booking_id_type[1] ); |
| 1178 |
|
| 1179 |
//TODO: test it. Check situation when we have editing "child booking resource", so need to re-update calendar and form to have it for parent resource. // FixIn: 6.1.1.9. |
| 1180 |
// FixIn: 10.10.1.2 |
| 1181 |
//if ( strpos( $server_request_url, 'resource_no_update' ) === false ) { // FixIn: 9.4.2.3. |
| 1182 |
|
| 1183 |
if ( ( function_exists( 'wpbc_is_this_child_resource' ) ) && ( wpbc_is_this_child_resource( $is_edit_booking['resource_id'] ) ) ) { |
| 1184 |
$bk_parent_br_id = wpbc_get_parent_resource( $is_edit_booking['resource_id'] ); |
| 1185 |
|
| 1186 |
$is_edit_booking['resource_id'] = intval( $bk_parent_br_id ); |
| 1187 |
} |
| 1188 |
//} |
| 1189 |
} |
| 1190 |
} |
| 1191 |
return $is_edit_booking; |
| 1192 |
} |
| 1193 |
|
| 1194 |
|
| 1195 |
/** |
| 1196 |
* Get how many items to book. Usually it's from [selectbox visitors "1" ... ] field. |
| 1197 |
* |
| 1198 |
* @param booking_form_data__arr = [ |
| 1199 |
* selected_short_dates_hint = "September 27, 2023 - September 28, 2023" |
| 1200 |
* days_number_hint = "2" |
| 1201 |
* rangetime = "16:00 - 18:00" |
| 1202 |
* starttime = "21:00" |
| 1203 |
* durationtime = "00:30" |
| 1204 |
* name = "John" |
| 1205 |
* secondname = "Smith" |
| 1206 |
* email = "john.smith@server.com" |
| 1207 |
* visitors = "1" |
| 1208 |
* children = "0" |
| 1209 |
* details = "" |
| 1210 |
* ] |
| 1211 |
* |
| 1212 |
* @return int |
| 1213 |
*/ |
| 1214 |
function wpbc_get__how_many_items_to_book__in_booking_form( $booking_form_data__arr, $resource_id ){ |
| 1215 |
|
| 1216 |
$how_many_items_to_book = 1; |
| 1217 |
|
| 1218 |
//TODO: Check about some URL parameter: '&resource_no_update' to book parent resource as single resource! // FixIn: 10.10.1.2 |
| 1219 |
if ( |
| 1220 |
( class_exists( 'wpdev_bk_biz_l' ) ) |
| 1221 |
&& ( 0 !== wpbc_get_child_resources_number( $resource_id ) ) // Here several child booking resources |
| 1222 |
) { |
| 1223 |
$booking_capacity_field = wpbc_get__booking_capacity_field__name(); |
| 1224 |
if ( |
| 1225 |
( ! empty( $booking_capacity_field ) ) |
| 1226 |
&& ( isset( $booking_form_data__arr[ $booking_capacity_field ] ) ) |
| 1227 |
){ |
| 1228 |
$how_many_items_to_book = intval( $booking_form_data__arr[ $booking_capacity_field ] ); // Get value of how many booking resources to book |
| 1229 |
$how_many_items_to_book = ( $how_many_items_to_book > 0 ) ? $how_many_items_to_book : 1; |
| 1230 |
} |
| 1231 |
} |
| 1232 |
|
| 1233 |
return $how_many_items_to_book; |
| 1234 |
} |
| 1235 |
|
| 1236 |
|
| 1237 |
/** |
| 1238 |
* Get capacity field -- 'pure name' |
| 1239 |
* |
| 1240 |
* @return string - field name, or empty string - '' if not defined |
| 1241 |
* |
| 1242 |
* In DB, we are saved field name type and possible name of custom booking form in format: 'custom_form_name^field_type^capacity_field_name' -> 'minimal^select^adults' |
| 1243 |
* or for standard form: 'select^visitors' |
| 1244 |
* and here we get only field name: 'visitors' |
| 1245 |
*/ |
| 1246 |
function wpbc_get__booking_capacity_field__name() { |
| 1247 |
|
| 1248 |
if ( class_exists( 'wpdev_bk_biz_l' ) ) { |
| 1249 |
|
| 1250 |
if ( 'On' == get_bk_option( 'booking_quantity_control' ) ) { |
| 1251 |
|
| 1252 |
$booking_capacity_field = get_bk_option( 'booking_capacity_field' ); |
| 1253 |
|
| 1254 |
if ( ! empty( $booking_capacity_field ) ) { |
| 1255 |
|
| 1256 |
$booking_capacity_field = explode( '^', $booking_capacity_field ); |
| 1257 |
|
| 1258 |
if ( ! empty( $booking_capacity_field ) ) { |
| 1259 |
|
| 1260 |
$booking_capacity_field_name = $booking_capacity_field[ count( $booking_capacity_field ) - 1 ]; |
| 1261 |
|
| 1262 |
return $booking_capacity_field_name; |
| 1263 |
} |
| 1264 |
} |
| 1265 |
} |
| 1266 |
} |
| 1267 |
return ''; |
| 1268 |
} |
| 1269 |
|
| 1270 |
|
| 1271 |
/** |
| 1272 |
* Get time for booking from the booking form, as array of seconds: [ 0, 24 * 60 * 60 ] OR [ 10*60*60, 14*60*60 ]. If timefields not exist, then get time for full day booking. |
| 1273 |
* @param $booking_form_data__arr |
| 1274 |
* |
| 1275 |
* @return array [ 0, 24 * 60 * 60 ] OR [ 10*60*60, 14*60*60 ] <- start and end time in seconds |
| 1276 |
* |
| 1277 |
* Example: |
| 1278 |
* |
| 1279 |
* // Firstly, we need to Get parsed booking form: [ name = "John", secondname = "Smith", email = "john.smith@server.com", visitors = "2",... ] |
| 1280 |
* $structured_booking_data_arr = wpbc_get_parsed_booking_data_arr( $params["form_data"], $params["resource_id"], array( 'get' => 'value' ) ); |
| 1281 |
* |
| 1282 |
* // Now get start/end times as seconds: [ 64800, 72000 ] |
| 1283 |
* $time_as_seconds_arr = wpbc_get_in_booking_form__time_to_book_as_seconds_arr( $structured_booking_data_arr ); |
| 1284 |
*/ |
| 1285 |
function wpbc_get_in_booking_form__time_to_book_as_seconds_arr( $booking_form_data__arr ){ |
| 1286 |
|
| 1287 |
$selected_time_fields = wpbc_get__selected_time_fields__in_booking_form__as_arr( $booking_form_data__arr ); |
| 1288 |
|
| 1289 |
// 2.2 Get selected SECONDS to book --------------------------------------------------------------------------- |
| 1290 |
$time_as_seconds_arr = array( 0, 24 * 60 * 60 ); // Full day booking by default |
| 1291 |
|
| 1292 |
foreach ( $selected_time_fields as $time_fields_obj ) { // { times_as_seconds: [ 21600, 23400 ], value_option_24h: '06:00 - 06:30', name: 'rangetime'} |
| 1293 |
|
| 1294 |
if ( false !== strpos( $time_fields_obj['name'], 'rangetime' ) ) { |
| 1295 |
$time_as_seconds_arr[ 0 ] = $time_fields_obj['times_as_seconds'][ 0 ]; |
| 1296 |
$time_as_seconds_arr[ 1 ] = $time_fields_obj['times_as_seconds'][ 1 ]; |
| 1297 |
//break; // If we have range-time then skip this loop |
| 1298 |
} |
| 1299 |
if ( false !== strpos( $time_fields_obj['name'], 'starttime' ) ) { |
| 1300 |
$time_as_seconds_arr[ 0 ] = $time_fields_obj['times_as_seconds'][ 0 ]; |
| 1301 |
} |
| 1302 |
if ( false !== strpos( $time_fields_obj['name'], 'endtime' ) ) { |
| 1303 |
$time_as_seconds_arr[ 1 ] = $time_fields_obj['times_as_seconds'][ 0 ]; |
| 1304 |
} |
| 1305 |
} |
| 1306 |
|
| 1307 |
// For duration time we need to make a new loop, because we need to be sure that was defined START_TIME before this, |
| 1308 |
// and end time was NOT defined, e.g. == (otherwise it's means that we already used END_TIME or RANGE_TIME) |
| 1309 |
if ( |
| 1310 |
( ( 0 ) !== $time_as_seconds_arr[ 0 ] ) |
| 1311 |
&& ( (24 * 60 * 60 ) === $time_as_seconds_arr[ 1 ] ) |
| 1312 |
){ |
| 1313 |
foreach ( $selected_time_fields as $time_fields_obj ) { // { times_as_seconds: [ 21600 ], value_option_24h: '06:00', name: 'durationtime'} |
| 1314 |
|
| 1315 |
if ( false !== strpos( $time_fields_obj['name'], 'durationtime' ) ) { |
| 1316 |
$time_as_seconds_arr[ 1 ] = $time_as_seconds_arr[ 0 ] + $time_fields_obj['times_as_seconds'][ 0 ]; |
| 1317 |
break; |
| 1318 |
} |
| 1319 |
} |
| 1320 |
} |
| 1321 |
|
| 1322 |
return $time_as_seconds_arr; |
| 1323 |
} |
| 1324 |
|
| 1325 |
|
| 1326 |
/** |
| 1327 |
* Get all time fields in the booking form as array of objects |
| 1328 |
* |
| 1329 |
* @param booking_form_data__arr = [ |
| 1330 |
* selected_short_dates_hint = "September 27, 2023 - September 28, 2023" |
| 1331 |
* days_number_hint = "2" |
| 1332 |
* rangetime = "16:00 - 18:00" |
| 1333 |
* starttime = "21:00" |
| 1334 |
* durationtime = "00:30" |
| 1335 |
* name = "John" |
| 1336 |
* secondname = "Smith" |
| 1337 |
* email = "john.smith@server.com" |
| 1338 |
* visitors = "1" |
| 1339 |
* children = "0" |
| 1340 |
* details = "" |
| 1341 |
* ] |
| 1342 |
* @returns [] |
| 1343 |
* |
| 1344 |
* Example: |
| 1345 |
* [ |
| 1346 |
* [ |
| 1347 |
* name = "rangetime" |
| 1348 |
* value_option_24h = "16:00 - 18:00" |
| 1349 |
* times_as_seconds = [ 57600, 64800 ] |
| 1350 |
* ] |
| 1351 |
* [ |
| 1352 |
* name = "starttime" |
| 1353 |
* value_option_24h = "21:00" |
| 1354 |
* times_as_seconds = [ 75600 ] |
| 1355 |
* ] |
| 1356 |
* [ |
| 1357 |
* name = "durationtime" |
| 1358 |
* value_option_24h = "00:30" |
| 1359 |
* times_as_seconds = [ 1800 ] |
| 1360 |
* ] |
| 1361 |
* ] |
| 1362 |
*/ |
| 1363 |
function wpbc_get__selected_time_fields__in_booking_form__as_arr( $booking_form_data__arr ){ |
| 1364 |
|
| 1365 |
/** |
| 1366 |
* Fields with [] like this select[name="rangetime1[]"] |
| 1367 |
* it's when we have 'multiple' in shortcode: [select* rangetime multiple "06:00 - 06:30" ... ] |
| 1368 |
*/ |
| 1369 |
$time_fields_arr = array( 'rangetime', 'starttime', 'endtime', 'durationtime' ); |
| 1370 |
|
| 1371 |
$time_fields_obj_arr = array(); |
| 1372 |
|
| 1373 |
// Loop all Time Fields |
| 1374 |
for ( $ctf = 0; $ctf < count( $time_fields_arr ); $ctf ++ ) { |
| 1375 |
|
| 1376 |
$time_field = $time_fields_arr[ $ctf ]; |
| 1377 |
if ( isset( $booking_form_data__arr[ $time_field ] ) ) { |
| 1378 |
|
| 1379 |
$value_option_seconds_arr = explode( '-', $booking_form_data__arr[ $time_field ] ); |
| 1380 |
$times_as_seconds_arr = array(); |
| 1381 |
|
| 1382 |
foreach ( $value_option_seconds_arr as $time_val ) { |
| 1383 |
$time_val = trim( $time_val ); |
| 1384 |
if ( ! empty( $time_val ) ) { |
| 1385 |
$start_end_times_arr = explode( ':', $time_val ); |
| 1386 |
$time_in_seconds = intval( $start_end_times_arr[0] ) * 60 * 60 + intval( $start_end_times_arr[1] ) * 60; |
| 1387 |
$times_as_seconds_arr[] = $time_in_seconds; |
| 1388 |
} |
| 1389 |
} |
| 1390 |
|
| 1391 |
if (! empty($times_as_seconds_arr)) { |
| 1392 |
|
| 1393 |
$time_fields_obj_arr[] = array( |
| 1394 |
'name' => $time_field, |
| 1395 |
'value_option_24h' => $booking_form_data__arr[ $time_field ], |
| 1396 |
'times_as_seconds' => $times_as_seconds_arr |
| 1397 |
); |
| 1398 |
} |
| 1399 |
} |
| 1400 |
} |
| 1401 |
|
| 1402 |
return $time_fields_obj_arr; |
| 1403 |
} |
| 1404 |
|
| 1405 |
|
| 1406 |
//TODO: 2023-10-13 16:37 |
| 1407 |
// - create new function for confirmation section |
| 1408 |
// - Update payment request |
| 1409 |
// - create redirection to the "Thank you." page and show there conformation, and payment request" |
| 1410 |
// - define in the settings new Stripe and PayPal button design as default ! |
| 1411 |
// - Be sure that 'booking_log_booking_actions' active by default |
| 1412 |
// - test it in dark theme |
| 1413 |
// - test closing booked dates if all time slot was booked - it's relative to 'different time slots in dif dates' |
| 1414 |
// - add migrate support old dates selection variables |
| 1415 |
// - check and remove other global Js vars |
| 1416 |
// - Create wizard booking form style with steps ? |
| 1417 |
// - Check Booking > Availability page relative new functionality of calendar_load ! |
| 1418 |
// - Update last func in wpbc-booking-new.php and remove it. |
| 1419 |
// - Test capacity in dates and time slots |
| 1420 |
// - Next 9.9 Customizer Wizard |
| 1421 |
// - Next 9.9 Update search admin UI |
| 1422 |
// - Next 9.9 - update functionality in Search functionality based on similar to where_to_save function. |
| 1423 |
// - Next 9.9 refactor Dates functions. |
| 1424 |
// Done. - Next 9.9 Update Booking > Settings General page to show tabs vertically in left column |
| 1425 |
// Create the same navigation panel at the Pro Booking > Settings > Form page. At left column custom forms, at top tolbar selectio of Booking form and "Content of booking fields data" form. |
| 1426 |
// Create the same navigation for Emails. |
| 1427 |
/** |
| 1428 |
* TODO: Performance improvement: |
| 1429 |
* "other_code": 0.003080129623413086 |
| 1430 |
* "wpbc__where_to_save_booking": 0.060331106185913086 |
| 1431 |
* "wpbc_db__booking_save": 0.023384809494018555 |
| 1432 |
* "wpbc_maybe_get_payment_form": 1.3650128841400146 <- |
| 1433 |
* "emails_sending": 1.5024309158325195 <- |
| 1434 |
* "total": 2.9542438983917236 |
| 1435 |
*/ |
| 1436 |
|