Modifier Category table added as a parent of modifiers

They are also linked to products / menu categroies as to which products they can be used on
The linking to menu categories is done in the frontend, database is linked directly to products
Treeview for menu categories yet to be done in modifier category detail form
This commit is contained in:
Amritanshu
2019-06-20 17:45:28 +05:30
parent 05f8058a15
commit e1c42d4470
34 changed files with 972 additions and 59 deletions

View File

@ -27,7 +27,7 @@ from .master import (
PrintLocation,
Product,
MenuCategory,
MenuCategoryModifier,
ModifierCategory,
SaleCategory,
SettleOption,
Tax

View File

@ -57,15 +57,17 @@ class Client(Base):
user_roles = Table(
'user_roles', Base.metadata,
Column('id', GUID(), primary_key=True, default=uuid.uuid4),
Column('user_id', GUID(), ForeignKey('users.id')),
Column('role_id', GUID(), ForeignKey('roles.id'))
Column('user_id', GUID(), ForeignKey('users.id'), nullable=False),
Column('role_id', GUID(), ForeignKey('roles.id'), nullable=False),
UniqueConstraint('user_id', 'role_id')
)
role_permissions = Table(
'role_permissions', Base.metadata,
Column('id', GUID(), primary_key=True, default=uuid.uuid4),
Column('permission_id', GUID(), ForeignKey('permissions.id')),
Column('role_id', GUID(), ForeignKey('roles.id'))
Column('permission_id', GUID(), ForeignKey('permissions.id'), nullable=False),
Column('role_id', GUID(), ForeignKey('roles.id'), nullable=False),
UniqueConstraint('permission_id', 'role_id')
)

View File

@ -10,7 +10,7 @@ from sqlalchemy import (
Integer,
case,
JSON,
)
Table)
from sqlalchemy.ext.hybrid import hybrid_property
from sqlalchemy.orm import relationship
from .meta import Base
@ -200,6 +200,34 @@ class Product(Base):
return True, ""
modifier_categories_products = Table(
'modifier_categories_products', Base.metadata,
Column('id', GUID(), primary_key=True, default=uuid.uuid4),
Column('product_id', GUID(), ForeignKey('products.id'), nullable=False),
Column('modifier_categories_id', GUID(), ForeignKey('modifier_categories.id'), nullable=False),
UniqueConstraint('product_id', 'modifier_categories_id')
)
class ModifierCategory(Base):
__tablename__ = "modifier_categories"
id = Column("id", GUID(), primary_key=True, default=uuid.uuid4)
name = Column("name", Unicode(255), nullable=False, unique=True)
minimum = Column("minimum", Integer, nullable=False)
maximum = Column("maximum", Integer, nullable=True)
sort_order = Column("sort_order", Numeric, nullable=False)
products = relationship("Product", secondary=modifier_categories_products, backref="modifier_categories")
def __init__(self, name=None, minimum=None, maximum=None, sort_order=0, id=None):
self.id = id
self.name = name
self.minimum = minimum
self.maximum = maximum
self.sort_order = sort_order
class Modifier(Base):
__tablename__ = "modifiers"
@ -207,38 +235,20 @@ class Modifier(Base):
name = Column("name", Unicode(255), nullable=False, unique=True)
show_in_bill = Column("show_in_bill", Boolean, nullable=False)
price = Column("price", Numeric, nullable=False)
modifier_category_id = Column(
"modifier_category_id", GUID(), ForeignKey("modifier_categories.id"), nullable=False
)
def __init__(self, name=None, show_in_bill=None, price=None, id=None):
modifier_category = relationship("ModifierCategory", backref="modifiers")
def __init__(self, name=None, show_in_bill=None, price=None, modifier_category_id=None, id=None):
self.id = id
self.name = name
self.show_in_bill = show_in_bill
self.modifier_category_id = modifier_category_id
self.price = price
class MenuCategoryModifier(Base):
__tablename__ = "menu_category_modifiers"
id = Column("id", GUID(), primary_key=True, default=uuid.uuid4)
menu_category_id = Column(
"menu_cateory_id", GUID(), ForeignKey("menu_categories.id")
)
modifier_id = Column(
"modifier_id", GUID(), ForeignKey("modifiers.id"), nullable=False
)
show_automatically = Column("show_automatically", Boolean, nullable=False)
menu_category = relationship("MenuCategory", backref="modifiers")
modifier = relationship("Modifier", backref="menu_categories")
def __init__(
self, menu_category_id=None, modifier_id=None, show_automatically=None, id=None
):
self.id = id
self.menu_category_id = menu_category_id
self.modifier_id = modifier_id
self.show_automatically = show_automatically
class DbSetting(Base):
__tablename__ = "settings"

View File

@ -63,6 +63,14 @@ def includeme(config):
config.add_route("v1_sale_categories_list", "/v1/sale-categories")
config.add_route("v1_sale_category_types_list", "/v1/sale-category-types")
config.add_route("modifier_categories_new", "/modifier-categories/new")
config.add_route("modifier_categories_id", "/modifier-categories/{id}")
config.add_route("modifier_categories_list", "/modifier-categories")
config.add_route("v1_modifier_categories_new", "/v1/modifier-categories/new")
config.add_route("v1_modifier_categories_id", "/v1/modifier-categories/{id}")
config.add_route("v1_modifier_categories_list", "/v1/modifier-categories")
config.add_route("v1_modifier_category_types_list", "/v1/modifier-category-types")
config.add_route("v1_bills_new", "/v1/bills/new")
config.add_route("v1_bills_id", "/v1/bills/{id}")

View File

@ -32,7 +32,8 @@ from barker.models import (
Printer,
Product,
MenuCategory,
MenuCategoryModifier,
ModifierCategory,
SaleCategory,
Reprint,
Role,
role_permissions,

View File

@ -5,10 +5,10 @@ import transaction
from pyramid.view import view_config
from sqlalchemy import or_
from barker.models import Modifier, MenuCategoryModifier
from barker.models import Modifier, ModifierCategory
@view_config(request_method='PUT', route_name='modifier', renderer='json', permission='Modifiers', trans=True)
@view_config(request_method='POST', route_name='modifier', renderer='json', permission='Modifiers', trans=True)
def save(request):
json = request.json_body
item = Modifier(json['Name'], json['ShowInBill'], json['Price'])
@ -19,7 +19,7 @@ def save(request):
return modifier_info(item)
@view_config(request_method='POST', route_name='modifier_id', renderer='json', permission='Modifiers', trans=True)
@view_config(request_method='PUT', route_name='modifier_id', renderer='json', permission='Modifiers', trans=True)
def update(request):
json = request.json_body
item = request.dbsession.query(Modifier).filter(Modifier.id == uuid.UUID(request.matchdict['id'])).first()

View File

@ -0,0 +1,260 @@
import uuid
import transaction
from pyramid.view import view_config
from sqlalchemy import or_
from sqlalchemy.orm import joinedload, Load
from barker.models import ModifierCategory, Product
from barker.models.validation_exception import ValidationError
from barker.views import product
@view_config(
request_method="POST",
route_name="v1_modifier_categories_new",
renderer="json",
permission="Modifiers",
trans=True,
)
def save(request):
json = request.json_body
name = json.get("name", "").strip()
if name == "":
raise ValidationError("Name cannot be blank")
try:
minimum = int(json.get("minimum", 0))
if minimum < 0:
raise ValidationError("Minimum must be an integer >= 0")
except ValueError:
raise ValidationError("Minimum must be an integer >= 0")
try:
maximum = json.get("maximum", None)
if maximum is not None:
maximum = int(maximum)
if maximum < 0:
raise ValidationError(
"Maximum must be an integer and cannot be less than zero"
)
elif maximum == 0:
maximum = None
except ValueError:
raise ValidationError("Maximum must be an integer and cannot be less than zero")
item = ModifierCategory(name, minimum, maximum)
request.dbsession.add(item)
add_products(item, json["menuCategories"], request.dbsession)
transaction.commit()
return modifier_category_info(item.id, request.dbsession)
@view_config(
request_method="PUT",
route_name="v1_modifier_categories_id",
renderer="json",
permission="Modifiers",
trans=True,
)
def update(request):
item = (
request.dbsession.query(ModifierCategory)
.filter(ModifierCategory.id == uuid.UUID(request.matchdict["id"]))
.first()
)
json = request.json_body
item.name = json["name"].strip()
if item.name == "":
raise ValidationError("Name cannot be blank")
try:
item.minimum = int(json.get("minimum", 0))
if item.minimum < 0:
raise ValidationError("Minimum must be an integer >= 0")
except ValueError:
raise ValidationError("Minimum must be an integer >= 0")
try:
item.maximum = json.get("maximum", None)
if item.maximum is not None:
item.maximum = int(item.maximum)
if item.maximum < 0:
raise ValidationError(
"Maximum must be an integer and cannot be less than zero"
)
elif item.maximum == 0:
item.maximum = None
except ValueError:
raise ValidationError("Maximum must be an integer and cannot be less than zero")
add_products(item, json["menuCategories"], request.dbsession)
transaction.commit()
return modifier_category_info(item.id, request.dbsession)
@view_config(
request_method="DELETE",
route_name="v1_modifier_categories_id",
renderer="json",
permission="Modifiers",
trans=True,
)
def delete(request):
item = (
request.dbsession.query(ModifierCategory)
.filter(ModifierCategory.id == uuid.UUID(request.matchdict["id"]))
.first()
)
request.dbsession.delete(item)
transaction.commit()
return {None, request.dbsession}
@view_config(
request_method="GET",
route_name="v1_modifier_categories_id",
renderer="json",
permission="Authenticated",
)
def show_id(request):
id_ = uuid.UUID(request.matchdict["id"])
return modifier_category_info(id_, request.dbsession)
@view_config(
request_method="GET",
route_name="v1_modifier_categories_new",
renderer="json",
permission="Authenticated",
)
def show_blank(request):
return modifier_category_info(None, request.dbsession)
@view_config(
request_method="GET",
route_name="v1_modifier_categories_list",
renderer="json",
permission="Authenticated",
)
def show_list(request):
list_ = (
request.dbsession.query(ModifierCategory)
.order_by(ModifierCategory.sort_order)
.order_by(ModifierCategory.name)
.all()
)
modifier_categories = []
for item in list_:
modifier_categories.append(
{
"id": item.id,
"name": item.name,
"minimum": item.minimum,
"maximum": item.maximum,
"products": [p.name for p in item.products],
}
)
return modifier_categories
@view_config(
request_method="GET",
route_name="v1_modifier_categories_list",
renderer="json",
request_param="pg",
permission="Authenticated",
)
def show_for_pg(request):
menu_category_id = uuid.UUID(request.GET["pg"])
pgm_list = (
request.dbsession.query(MenuCategoryModifier)
.filter(
or_(
MenuCategoryModifier.menu_category == None,
MenuCategoryModifier.menu_category_id == menu_category_id,
)
)
.all()
)
pg_modifiers = []
for item in pgm_list:
pg_modifiers.append(
{
"ModifierID": item.modifier_id,
"Name": item.modifier.name,
"ShowInBill": item.modifier.show_in_bill,
"Price": item.modifier.price,
}
)
return pg_modifiers
def modifier_category_info(item, dbsession):
from barker.models import MenuCategory
menu_categories = (
dbsession.query(MenuCategory)
.options(joinedload(MenuCategory.products, innerjoin=True))
.filter(Product.is_active == True)
.order_by(MenuCategory.sort_order, Product.sort_order, Product.name)
.all()
)
if item is None:
return {
"name": "",
"minimum": 0,
"maximum": 0,
"menuCategories": [
{
"id": mc.id,
"name": mc.name,
"enabled": False,
"products": [
{"id": p.id, "name": p.name, "enabled": False}
for p in mc.products
],
}
for mc in menu_categories
],
}
if type(item) is uuid.UUID:
item = (
dbsession.query(ModifierCategory)
.filter(ModifierCategory.id == item)
.first()
)
return {
"id": item.id,
"name": item.name,
"minimum": item.minimum,
"maximum": item.maximum,
"menuCategories": [
{
"id": mc.id,
"name": mc.name,
"enabled": False,
"products": [
{
"id": p.id,
"name": p.name,
"enabled": True if p in item.products else False,
}
for p in mc.products
],
}
for mc in menu_categories
],
}
def add_products(modifier_category, menu_categories, dbsession):
for mc in menu_categories:
for p in mc['products']:
id_ = uuid.UUID(p["id"])
old = [p for p in modifier_category.products if p.id == id_]
old = None if len(old) == 0 else old[0]
if p["enabled"] and old is None:
product_object = (
dbsession.query(Product).filter(Product.id == id_).one()
)
modifier_category.products.append(product_object)
elif not p["enabled"] and old:
modifier_category.products.remove(old)

View File

@ -13,9 +13,7 @@ def save(request):
request.dbsession.add(item)
add_permissions(item, request.json_body['permissions'], request.dbsession)
transaction.commit()
item = request.dbsession.query(Role).filter(Role.id == item.id).first()
permissions = request.dbsession.query(Permission).order_by(Permission.name).all()
return role_info(item, permissions)
return role_info(item.id, request.dbsession)
@view_config(request_method='PUT', route_name='v1_roles_id', renderer='json', permission='Users', trans=True)
@ -25,9 +23,7 @@ def update(request):
item.name = request.json_body['name']
add_permissions(item, request.json_body['permissions'], request.dbsession)
transaction.commit()
item = request.dbsession.query(Role).filter(Role.id == item.id).first()
permissions = request.dbsession.query(Permission).order_by(Permission.name).all()
return role_info(item, permissions)
return role_info(item.id, request.dbsession)
def add_permissions(role, permissions, dbsession):
@ -58,15 +54,12 @@ def delete(request):
@view_config(request_method='GET', route_name='v1_roles_id', renderer='json', permission='Authenticated')
def show_id(request):
id_ = uuid.UUID(request.matchdict['id'])
item = request.dbsession.query(Role).filter(Role.id == id_).first()
permissions = request.dbsession.query(Permission).order_by(Permission.name).all()
return role_info(item, permissions)
return role_info(id_, request.dbsession)
@view_config(request_method='GET', route_name='v1_roles_new', renderer='json', permission='Authenticated')
def show_blank(request):
permissions = request.dbsession.query(Permission).order_by(Permission.name).all()
return role_info(None, permissions)
return role_info(None, request.dbsession)
@view_config(request_method='GET', route_name='v1_roles_list', renderer='json', permission='Authenticated')
@ -77,16 +70,18 @@ def show_list(request):
]
def role_info(item, permissions):
if item is not None:
return {
'id': item.id,
'name': item.name,
'permissions': [{'id': p.id, 'name': p.name, 'enabled': True if p in item.permissions else False}
for p in permissions]
}
else:
def role_info(item, dbsession):
permissions = dbsession.query(Permission).order_by(Permission.name).all()
if item is None:
return {
'name': '',
'permissions': [{'id': p.id, 'name': p.name, 'enabled': False} for p in permissions]
}
if type(item) is uuid.UUID:
item = dbsession.query(Role).filter(Role.id == item).first()
return {
'id': item.id,
'name': item.name,
'permissions': [{'id': p.id, 'name': p.name, 'enabled': True if p in item.permissions else False}
for p in permissions]
}