Как добавить поля для выбора даты и времени в оформление заказа WooCommerce

Диагностика задачи: зачем нужны поля даты и времени в оформлении заказа WooCommerce

В интернет-магазинах на WooCommerce часто требуется добавить дополнительные поля для выбора даты и времени доставки, бронирования или услуги. Стандартный набор полей WooCommerce этого не предусматривает, поэтому задача — добавить эти поля в оформление заказа (checkout), сохранить данные и вывести их в админке и письмах.

Как добавить поле выбора даты в оформление заказа WooCommerce

Для добавления обычных полей использовать фильтр woocommerce_checkout_fields. Для даты и времени можно использовать HTML5-поля с типами date и time. Вот пример добавления двух полей:

add_filter('woocommerce_checkout_fields', 'add_date_time_checkout_fields');
function add_date_time_checkout_fields($fields) {
    $fields['billing']['billing_delivery_date'] = array(
        'type'        => 'date',
        'label'       => __('Дата доставки', 'woocommerce'),
        'required'    => true,
        'class'       => array('form-row-wide'),
        'priority'    => 120,
    );
    $fields['billing']['billing_delivery_time'] = array(
        'type'        => 'time',
        'label'       => __('Время доставки', 'woocommerce'),
        'required'    => true,
        'class'       => array('form-row-wide'),
        'priority'    => 130,
    );
    return $fields;
}

Сохранение данных полей в метаданные заказа

Чтобы данные полей сохранялись и были доступны в админке, нужно использовать хук woocommerce_checkout_update_order_meta:

add_action('woocommerce_checkout_update_order_meta', 'save_delivery_date_time_fields');
function save_delivery_date_time_fields($order_id) {
    if (!empty($_POST['billing_delivery_date'])) {
        update_post_meta($order_id, '_billing_delivery_date', sanitize_text_field($_POST['billing_delivery_date']));
    }
    if (!empty($_POST['billing_delivery_time'])) {
        update_post_meta($order_id, '_billing_delivery_time', sanitize_text_field($_POST['billing_delivery_time']));
    }
}

Отображение полей в админке WooCommerce и письмах

Чтобы видеть эти поля в админке заказа, добавим вывод с помощью хука woocommerce_admin_order_data_after_billing_address:

add_action('woocommerce_admin_order_data_after_billing_address', 'display_delivery_date_time_admin_order', 10, 1);
function display_delivery_date_time_admin_order($order){
    $date = get_post_meta($order->get_id(), '_billing_delivery_date', true);
    $time = get_post_meta($order->get_id(), '_billing_delivery_time', true);
    if ($date) {
        echo '<p><strong>Дата доставки:</strong> ' . esc_html($date) . '</p>';
    }
    if ($time) {
        echo '<p><strong>Время доставки:</strong> ' . esc_html($time) . '</p>';
    }
}

Для отображения в письмах нужно добавить к фильтру woocommerce_email_order_meta_fields:

add_filter('woocommerce_email_order_meta_fields', 'add_delivery_date_time_email_meta_fields', 10, 3);
function add_delivery_date_time_email_meta_fields($fields, $sent_to_admin, $order) {
    $fields['billing_delivery_date'] = array(
        'label' => __('Дата доставки'),
        'value' => get_post_meta($order->get_id(), '_billing_delivery_date', true),
    );
    $fields['billing_delivery_time'] = array(
        'label' => __('Время доставки'),
        'value' => get_post_meta($order->get_id(), '_billing_delivery_time', true),
    );
    return $fields;
}

Проверка результата после внедрения

  • Перейдите на страницу оформления заказа, убедитесь, что поля «Дата доставки» и «Время доставки» отображаются и обязательны к заполнению.
  • Оформите заказ, заполнив эти поля.
  • В админке WooCommerce откройте заказ и убедитесь, что данные отображаются корректно в блоке с данными покупателя.
  • Получите письмо с подтверждением заказа — проверьте наличие даты и времени доставки в метаданных.

Частые ошибки и как их исправить

  • Поля не отображаются на странице оформления заказа: Проверьте, что ваш фильтр woocommerce_checkout_fields возвращает массив полей. Также убедитесь, что приоритеты полей не конфликтуют с другими изменениями.
  • Данные не сохраняются в заказе: Убедитесь, что в функции сохранения используются правильные имена полей из $_POST и вызывается update_post_meta с правильным ID заказа.
  • Поля не видны в админке или письмах: Проверьте, что хук для вывода данных в админке подключён и что метаданные сохраняются с тем же ключом, который вы выводите.
  • Ошибка валидации или пустые поля: Если поля обязательны, убедитесь, что фронтенд-валидация срабатывает, или добавьте серверную проверку через woocommerce_checkout_process.

Практические советы по безопасности и производительности

  • Обязательно используйте sanitize_text_field для входящих данных, чтобы предотвратить XSS и сохранить данные корректно.
  • Добавьте серверную валидацию, чтобы пользователь не мог отправить пустые или некорректные даты:
add_action('woocommerce_checkout_process', 'validate_delivery_date_time_fields');
function validate_delivery_date_time_fields() {
    if (empty($_POST['billing_delivery_date'])) {
        wc_add_notice(__('Пожалуйста, выберите дату доставки.'), 'error');
    }
    if (empty($_POST['billing_delivery_time'])) {
        wc_add_notice(__('Пожалуйста, выберите время доставки.'), 'error');
    }
}
  • Для улучшения UX можно подключить JavaScript-библиотеки выбора даты и времени (например, jQuery UI Datepicker) — это особенно актуально для сложных форматов и ограничений.
  • Если сайта много трафика, старайтесь минимизировать хук woocommerce_checkout_fields и кэшировать данные при возможности.

Сравнение способов добавления даты и времени в оформление заказа WooCommerce

МетодПреимуществаНедостатки
HTML5 поля date и timeПростая реализация, без дополнительных библиотек, работает во всех современных браузерахОграниченные возможности кастомизации, разный UX в разных браузерах
Использование jQuery UI Datepicker (или других JS плагинов)Гибкий и удобный UI, можно задавать ограничения, форматированиеТребует подключения скриптов и стилей, чуть больше нагрузки
Плагины WooCommerce для бронирования (например, WooCommerce Bookings)Полноценное решение с управлением датами, временем и ограничениямиПлатное решение, сложнее кастомизировать под узкие задачи
⭐⭐⭐⭐⭐