Розробка кошика на Vue.js для 1С-Бітрікс
Кошик — найбільш чутливий до UX компонент магазину. Стандартний bitrix:sale.basket.basket виконує повне перезавантаження при кожній зміні кількості або видаленні товару. Vue-кошик з optimistic updates усуває це: візуально все відбувається миттєво, а синхронізація з сервером іде у фоні.
Битрікс API для роботи з кошиком
Основні методи модуля sale:
// Додати до кошика
\Bitrix\Sale\Basket::create(SITE_ID);
$basketItem = $basket->createItem('catalog', $productId);
$basketItem->setFields(['QUANTITY' => 1, 'CURRENCY' => 'RUB']);
$basket->save();
// AJAX-контролер для Vue:
// POST /basket/add { productId, quantity, props }
// POST /basket/update { itemId, quantity }
// POST /basket/remove { itemId }
// GET /basket — поточний стан
Або через REST API: sale.basketitem.add, sale.basketitem.update, sale.basketitem.delete.
Структура Vue-кошика
CartApp.vue — кореневий, зчитує cartStore
├── CartDrawer.vue — бічна панель (slide-over)
├── CartIcon.vue — іконка з лічильником у шапці
├── CartItem.vue — рядок товару (фото, назва, кількість, ціна)
├── CartSummary.vue — підсумок, промокод, кнопка оформлення
└── EmptyCart.vue — заглушка порожнього кошика
Pinia store кошика
export const useCartStore = defineStore('cart', {
state: () => ({
items: [],
totalPrice: 0,
discounts: [],
isLoading: false,
}),
getters: {
itemCount: (state) => state.items.reduce((sum, i) => sum + i.quantity, 0),
},
actions: {
async addItem(productId, quantity = 1) {
// Optimistic update: додаємо локально одразу
this.items.push({ productId, quantity, pending: true });
try {
const result = await cartApi.add(productId, quantity);
// Оновлюємо з даними від сервера (реальний ID, ціна)
this.syncFromServer(result.basket);
} catch {
// Відкат при помилці
this.items = this.items.filter(i => !i.pending);
}
}
}
});
Синхронізація між вкладками
Користувач відкрив магазин у двох вкладках. Товар додано в одній — кошик в іншій застарів. Рішення:
// Слухаємо localStorage-подію (BroadcastChannel — сучасний варіант)
const channel = new BroadcastChannel('cart-sync');
channel.onmessage = (e) => {
if (e.data.type === 'CART_UPDATED') cartStore.fetchCart();
};
// При зміні кошика:
channel.postMessage({ type: 'CART_UPDATED' });
Приклад із практики
Магазин електроніки: кошик стандартний Бітрікс з AJAX. Проблема: при додаванні товару через кнопку на картці (sale.basket.basket.ajax) сторінка «моргала» — повністю перемальовувався блок кошика в шапці. На мобільних пристроях це сприймалося як підвисання. Vue-кошик з CartIcon (лічильник оновлюється миттєво через Pinia) та CartDrawer (відкривається sliding panel без перезавантаження) — додавання товару візуально миттєве, запит до сервера іде асинхронно.
Терміни виконання
| Варіант | Термін |
|---|---|
| Кошик-drawer з базовими операціями | від 4 до 6 робочих днів |
| З промокодами, знижками, збереженими списками | від 8 до 12 робочих днів |
| Інтеграція з Vue-каталогом і оформленням замовлення | від 3 до 5 робочих днів додатково |







