Реализован выбор склада для POS: добавлена логика выбора склада по умолчанию из сессии, эндпоинт смены склада, модалка выбора и отображение текущего склада
This commit is contained in:
@@ -14,6 +14,38 @@ from inventory.models import Showcase, Reservation, Warehouse
|
||||
from inventory.services import ShowcaseManager
|
||||
|
||||
|
||||
def get_pos_warehouse(request):
|
||||
"""
|
||||
Получить текущий склад для POS из сессии или выбрать дефолтный.
|
||||
Логика выбора:
|
||||
1. Если в сессии есть pos_warehouse_id - используем его
|
||||
2. Иначе берем склад с is_default=True
|
||||
3. Если нет is_default - берем первый активный
|
||||
4. Если нет активных складов - None
|
||||
"""
|
||||
warehouse_id = request.session.get('pos_warehouse_id')
|
||||
|
||||
if warehouse_id:
|
||||
try:
|
||||
return Warehouse.objects.get(id=warehouse_id, is_active=True)
|
||||
except Warehouse.DoesNotExist:
|
||||
# Склад был удален или деактивирован - сбрасываем сессию
|
||||
request.session.pop('pos_warehouse_id', None)
|
||||
|
||||
# Ищем склад по умолчанию
|
||||
warehouse = Warehouse.objects.filter(is_active=True, is_default=True).first()
|
||||
|
||||
if not warehouse:
|
||||
# Берем любой первый активный
|
||||
warehouse = Warehouse.objects.filter(is_active=True).first()
|
||||
|
||||
# Сохраняем в сессию для следующих запросов
|
||||
if warehouse:
|
||||
request.session['pos_warehouse_id'] = warehouse.id
|
||||
|
||||
return warehouse
|
||||
|
||||
|
||||
def get_showcase_kits_for_pos():
|
||||
"""
|
||||
Получает витринные комплекты для отображения в POS.
|
||||
@@ -124,9 +156,27 @@ def pos_terminal(request):
|
||||
Tablet-friendly POS screen prototype.
|
||||
Shows categories and all items (products + kits) for quick tap-to-add.
|
||||
Оптимизировано: убрана стартовая загрузка витрин, только thumbnail фото.
|
||||
Работает только с одним выбранным складом.
|
||||
"""
|
||||
from products.models import ProductPhoto, ProductKitPhoto
|
||||
|
||||
# Получаем текущий склад для POS
|
||||
current_warehouse = get_pos_warehouse(request)
|
||||
|
||||
if not current_warehouse:
|
||||
# Нет активных складов - показываем ошибку
|
||||
from django.contrib import messages
|
||||
messages.error(request, 'Нет активных складов. Обратитесь к администратору.')
|
||||
context = {
|
||||
'categories_json': json.dumps([]),
|
||||
'items_json': json.dumps([]),
|
||||
'showcase_kits_json': json.dumps([]),
|
||||
'current_warehouse': None,
|
||||
'warehouses': [],
|
||||
'title': 'POS Terminal',
|
||||
}
|
||||
return render(request, 'pos/terminal.html', context)
|
||||
|
||||
categories_qs = ProductCategory.objects.filter(is_active=True)
|
||||
|
||||
# Prefetch для первого фото товаров
|
||||
@@ -195,16 +245,52 @@ def pos_terminal(request):
|
||||
|
||||
# Объединяем все позиции
|
||||
all_items = products + kits
|
||||
|
||||
# Список всех активных складов для модалки выбора
|
||||
warehouses = Warehouse.objects.filter(is_active=True).order_by('-is_default', 'name')
|
||||
warehouses_list = [{
|
||||
'id': w.id,
|
||||
'name': w.name,
|
||||
'is_default': w.is_default
|
||||
} for w in warehouses]
|
||||
|
||||
context = {
|
||||
'categories_json': json.dumps(categories),
|
||||
'items_json': json.dumps(all_items),
|
||||
'showcase_kits_json': json.dumps([]), # Пустой массив - загрузка по API
|
||||
'current_warehouse': {
|
||||
'id': current_warehouse.id,
|
||||
'name': current_warehouse.name
|
||||
},
|
||||
'warehouses': warehouses_list,
|
||||
'title': 'POS Terminal',
|
||||
}
|
||||
return render(request, 'pos/terminal.html', context)
|
||||
|
||||
|
||||
@login_required
|
||||
@require_http_methods(["POST"])
|
||||
def set_warehouse(request, warehouse_id):
|
||||
"""
|
||||
Установить текущий склад для POS.
|
||||
Сохраняет выбор в сессию.
|
||||
"""
|
||||
try:
|
||||
warehouse = Warehouse.objects.get(id=warehouse_id, is_active=True)
|
||||
request.session['pos_warehouse_id'] = warehouse.id
|
||||
|
||||
return JsonResponse({
|
||||
'success': True,
|
||||
'warehouse_id': warehouse.id,
|
||||
'warehouse_name': warehouse.name
|
||||
})
|
||||
except Warehouse.DoesNotExist:
|
||||
return JsonResponse({
|
||||
'success': False,
|
||||
'error': 'Склад не найден или неактивен'
|
||||
}, status=404)
|
||||
|
||||
|
||||
@login_required
|
||||
@require_http_methods(["GET"])
|
||||
def showcase_items_api(request):
|
||||
|
||||
Reference in New Issue
Block a user