| | |
| | | <?php |
| | | namespace JVBase\integrations; |
| | | |
| | | use JVBase\meta\MetaForm; |
| | | use JVBase\meta\MetaManager; |
| | | use JVBase\meta\Form; |
| | | use JVBase\meta\Meta; |
| | | use Exception; |
| | | use JVBase\registry\PostTypeRegistrar; |
| | | use WP_Error; |
| | |
| | | */ |
| | | protected function exchangeOAuthCode(string $code): ?array |
| | | { |
| | | error_log('Exchanging tokens with credentials: '.print_r($this->credentials, true)); |
| | | |
| | | $this->ensureInitialized(); |
| | | |
| | | // Prepare the request body as an array |
| | |
| | | } |
| | | |
| | | $data = json_decode(wp_remote_retrieve_body($response), true); |
| | | error_log('OAuth Response: '.print_r($data, true)); |
| | | if (isset($data['access_token'])) { |
| | | return [ |
| | | 'access_token' => $data['access_token'], |
| | |
| | | |
| | | $data = json_decode(wp_remote_retrieve_body($response), true); |
| | | |
| | | error_log('RefreshAccessToken Response: '.print_r($data, true)); |
| | | if (isset($data['access_token'])) { |
| | | $this->credentials['access_token'] = $data['access_token']; |
| | | $this->credentials['expires_at'] = time() + ($data['expires_in'] ?? 2592000); // 30 days |
| | |
| | | { |
| | | // Skip if we don't have credentials yet (during OAuth flow) |
| | | if (empty($this->credentials['access_token'])) { |
| | | error_log('[Square] Skipping loadLocations - no access token yet'); |
| | | return; |
| | | } |
| | | try { |
| | |
| | | if (is_singular(BASE.'dash') || is_post_type_archive(BASE.'dash')) { |
| | | return $actions; |
| | | } |
| | | $meta = new MetaForm(); |
| | | $form = '<aside id="cart" class="right"> |
| | | $form = '<aside id="cart" class="right main"> |
| | | <form id="checkout" data-form-id="checkout" data-save="checkout">'; |
| | | |
| | | $tabs = [ |
| | |
| | | 'description' => 'Securely checkout with your name, email, and payments processed by Square.', |
| | | 'content' => '<div class="checkout-section"> |
| | | <h3>Customer Information</h3> |
| | | '.$meta->return('cart_name', null, [ |
| | | '.Form::render('cart_name', null, [ |
| | | 'type' => 'text', |
| | | 'label' => 'Your Name', |
| | | 'required' => true, |
| | | 'autocomplete' => 'name' |
| | | ]). |
| | | $meta->return('cart_email', null, [ |
| | | Form::render('cart_email', null, [ |
| | | 'type' => 'email', |
| | | 'label' => 'Your Email', |
| | | 'required' => true, |
| | | 'autocomplete'=> 'email', |
| | | ]). |
| | | $meta->return('cart_phone', null, [ |
| | | Form::render('cart_phone', null, [ |
| | | 'type' => 'tel', |
| | | 'label' => 'Your Phone', |
| | | 'required' => true, |
| | | 'autocomplete'=> 'phone' |
| | | ]).' |
| | | <h3>Pickup Details</h3>'. |
| | | $meta->return('pickup_time', null, [ |
| | | Form::render('pickup_time', null, [ |
| | | 'type' => 'datetime', |
| | | 'label' => 'Pickup Type', |
| | | 'min' => '11:00', |
| | | 'max' => '20:00', |
| | | 'required' => true, |
| | | ]). |
| | | $meta->return('special_instructions', null, [ |
| | | Form::render('special_instructions', null, [ |
| | | 'type' => 'textarea', |
| | | 'label' => 'Special Instructions', |
| | | 'quill' => true, |
| | |
| | | <label for="quantity"></label> |
| | | <div class="quantity field" data-min="0" data-max="50" data-step="1" data-price="17" data-id=""> |
| | | |
| | | <button type="button" class="decrease"aria-label="Decrease Add to Order">'.jvbIcon('minus').'</button> |
| | | <button type="button" class="decrease"aria-label="Decrease Add to Order">'.jvbIcon('minus-square').'</button> |
| | | |
| | | <input type="number" id="quantity" name="quantity" value="0" min="0" max="50" step="1" class="quantity-input"> |
| | | |
| | | <button type="button" class="increase" aria-label="Increase Add to Order">'.jvbIcon('add').'</button> |
| | | <button type="button" class="increase" aria-label="Increase Add to Order">'.jvbIcon('plus-square').'</button> |
| | | </div> |
| | | </td> |
| | | <td class="price"> |
| | |
| | | |
| | | $actions[] = [ |
| | | 'button' => '<button type="button" class="toggle-cart row" title="Your Cart" data-action="toggle-cart" aria-label="Open Cart" aria-controls="checkout" aria-expanded="false"> |
| | | '.jvbIcon('cart').'<span class="abs"></span><span class="abs count"></span> |
| | | '.jvbIcon('shopping-cart').'<span class="abs"></span><span class="abs count"></span> |
| | | </button>', |
| | | 'content' => $form |
| | | ]; |
| | |
| | | */ |
| | | protected function handleTheSavePost(int $postID, \WP_Post $post, bool $update, array $settings): void |
| | | { |
| | | error_log('Queuing Sync to Square'); |
| | | // Queue the sync operation |
| | | $this->queueOperation('sync_to_square', [ |
| | | 'items' => [$postID], |
| | |
| | | return new WP_Error('post_not_found', "Post $postID not found"); |
| | | } |
| | | |
| | | $meta = new MetaManager($postID, 'post'); |
| | | $meta = Meta::forPost($postID); |
| | | $post_type = get_post_type($postID); |
| | | |
| | | // Get existing Square catalog ID if it exists |
| | |
| | | } |
| | | |
| | | // Add variations |
| | | $variations = $meta->getValue('product_variations'); |
| | | $variations = $meta->get('product_variations'); |
| | | if (empty($variations)) { |
| | | // Create default variation if none exist |
| | | $price = floatval($meta->getValue('price') ?: 0); |
| | | $price = floatval($meta->get('price') ?: 0); |
| | | $catalog_object['item_data']['variations'][] = [ |
| | | 'type' => 'ITEM_VARIATION', |
| | | 'id' => $existing_square_id ? null : '#'.BASE.'menu_item_' . $postID . '_var_default', |
| | |
| | | } |
| | | |
| | | // Add modifiers if they exist |
| | | $modifiers = $meta->getValue('modifiers'); |
| | | $modifiers = $meta->get('modifiers'); |
| | | if (!empty($modifiers)) { |
| | | $modifier_ids = []; |
| | | foreach ($modifiers as $modifier) { |
| | |
| | | } |
| | | |
| | | // Add tax settings |
| | | $tax_ids = $meta->getValue('tax_ids'); |
| | | $tax_ids = $meta->get('tax_ids'); |
| | | if (!empty($tax_ids)) { |
| | | $catalog_object['item_data']['tax_ids'] = $tax_ids; |
| | | } |
| | |
| | | |
| | | $message = sprintf( |
| | | "Welcome to %s!\n\n" . |
| | | "Your account has been created. Please click the link below to set your password:\n\n" . |
| | | "Your account has been created. Please click the button below to set your password:\n\n" . |
| | | "%s\n\n" . |
| | | "Once you've set your password, you can log in to:\n" . |
| | | "Or, copy and paste the link below:\n\n". |
| | | "%s\n\n" . |
| | | "Once you've set your password, you can:\n" . |
| | | "- View your order history\n" . |
| | | "- Save your favorite items\n" . |
| | | "- Speed up checkout with saved payment methods\n\n" . |
| | | "If you didn't create this account, please ignore this email.\n\n" . |
| | | "Thanks,\n%s", |
| | | "Thanks,\n", |
| | | $site_name, |
| | | $reset_url, |
| | | $site_name |
| | | JVB()->email()->button('Reset Password', $reset_url), |
| | | JVB()->email()->link($reset_url), |
| | | ); |
| | | |
| | | jvbMail( |
| | | JVB()->email()->sendEmail( |
| | | $user->user_email, |
| | | sprintf('[%s] Welcome! Set Your Password', $site_name), |
| | | $message |
| | |
| | | // Send notification |
| | | $user = get_user_by('ID', $user_id); |
| | | if ($user) { |
| | | wp_mail( |
| | | JVB()->email()->sendEmail( |
| | | $user->user_email, |
| | | '['.get_bloginfo('name').'] Security Code', |
| | | 'For your security, enter this code to continue accessing your account and saved payment methods.', |
| | | ['Content-Type: text/html; charset=UTF-8'] |
| | | ); |
| | | } |
| | | } |
| | |
| | | |
| | | if ($wp_order_id) { |
| | | // Update the post meta |
| | | $meta = new MetaManager($wp_order_id, 'post'); |
| | | $meta = Meta::forPost($wp_order_id); |
| | | $updates = [ |
| | | 'status' => $state, |
| | | 'updated_at' => current_time('mysql') |
| | |
| | | */ |
| | | private function mapSquareFieldsToWordPress(int $post_id, array $item): void |
| | | { |
| | | $meta = new MetaManager($post_id, 'post'); |
| | | $meta = Meta::forPost($post_id); |
| | | $field_map = $this->getFieldMapping(get_post_type($post_id)); |
| | | |
| | | $values_to_save = []; |
| | |
| | | update_user_meta($user->ID, BASE . '_square_customer_updated', current_time('mysql')); |
| | | |
| | | // Clear cached customer data |
| | | $this->cache->delete('square_customer_' . $user->ID); |
| | | $this->cache->forget('square_customer_' . $user->ID); |
| | | } |
| | | |
| | | return true; |
| | |
| | | |
| | | // Validate environment setting |
| | | if (isset($credentials['environment'])) { |
| | | error_log('Environment: '.print_r($credentials['environment'], true)); |
| | | $validEnvironments = ['sandbox', 'production']; |
| | | if (!in_array($credentials['environment'], $validEnvironments)) { |
| | | $this->logError('Invalid environment setting', [ |
| | |
| | | } |
| | | |
| | | // Save all order meta |
| | | $meta = new MetaManager($order_post_id, 'post'); |
| | | $meta = Meta::forPost($order_post_id); |
| | | $fields = $this->getSquarePostConfig('_sq_orders')['fields']; |
| | | unset($fields['post_title']); |
| | | $meta->setFieldConfig($fields); |
| | | |
| | | $meta->setAll([ |
| | | 'square_order_id' => $order_data['square_order_id'], |