feat(UI): Stock Items page added with getting, filtering, and saving data.
This commit is contained in:
24
README.md
24
README.md
@@ -14,3 +14,27 @@ python -m flask run
|
||||
|
||||
host for local network:
|
||||
python -m flask run --host=0.0.0.0
|
||||
|
||||
|
||||
files dedicated to each page:
|
||||
CSS
|
||||
page
|
||||
HTML
|
||||
page
|
||||
row
|
||||
JavaScript
|
||||
page
|
||||
api
|
||||
router
|
||||
MySQL
|
||||
get
|
||||
save
|
||||
table
|
||||
staging table
|
||||
audit table
|
||||
Python
|
||||
business object
|
||||
controller
|
||||
datastore
|
||||
form
|
||||
model
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
97
business_objects/address.py
Normal file
97
business_objects/address.py
Normal file
@@ -0,0 +1,97 @@
|
||||
"""
|
||||
Project: PARTS Website
|
||||
Author: Edward Middleton-Smith
|
||||
Precision And Research Technology Systems Limited
|
||||
|
||||
Technology: Business Objects
|
||||
Feature: Address Business Object
|
||||
|
||||
Description:
|
||||
Business object for address
|
||||
"""
|
||||
|
||||
# internal
|
||||
import lib.argument_validation as av
|
||||
from business_objects.base import Base
|
||||
from business_objects.region import Region
|
||||
from extensions import db
|
||||
# external
|
||||
from typing import ClassVar
|
||||
|
||||
|
||||
class Address(db.Model, Base):
|
||||
FLAG_ADDRESS_LINE_1: ClassVar[str] = 'address_line_1'
|
||||
FLAG_ADDRESS_LINE_2: ClassVar[str] = 'address_line_2'
|
||||
FLAG_CITY: ClassVar[str] = 'city'
|
||||
FLAG_COUNTY: ClassVar[str] = 'county'
|
||||
NAME_ATTR_OPTION_VALUE: ClassVar[str] = Base.ATTR_ID_ADDRESS
|
||||
NAME_ATTR_OPTION_TEXT: ClassVar[str] = Base.FLAG_POSTCODE
|
||||
__tablename__ = 'Shop_Address'
|
||||
id_address = db.Column(db.Integer, primary_key=True)
|
||||
id_region = db.Column(db.Integer)
|
||||
postcode = db.Column(db.String(20))
|
||||
address_line_1 = db.Column(db.String(256))
|
||||
address_line_2 = db.Column(db.String(256))
|
||||
city = db.Column(db.String(256))
|
||||
county = db.Column(db.String(256))
|
||||
active = db.Column(db.Boolean)
|
||||
|
||||
# region = None
|
||||
|
||||
def __init__(self):
|
||||
super().__init__()
|
||||
Base.__init__(self)
|
||||
self.region = None
|
||||
@classmethod
|
||||
def from_DB_storage_location(cls, query_row):
|
||||
address = cls()
|
||||
address.id_address = query_row[2]
|
||||
address.id_region = query_row[3]
|
||||
return address
|
||||
@classmethod
|
||||
def from_DB_plant(cls, query_row):
|
||||
address = cls()
|
||||
address.id_address = query_row[1]
|
||||
address.id_region = query_row[2]
|
||||
@classmethod
|
||||
def from_DB_stock_item(cls, query_row):
|
||||
address = cls()
|
||||
address.id_address = query_row[6]
|
||||
address.id_region = query_row[7]
|
||||
return address
|
||||
def __repr__(self):
|
||||
return f'''
|
||||
{self.ATTR_ID_ADDRESS}: {self.id_address}
|
||||
{self.FLAG_REGION}: {self.region}
|
||||
{self.FLAG_POSTCODE}: {self.postcode}
|
||||
{self.FLAG_ADDRESS_LINE_1}: {self.address_line_1}
|
||||
{self.FLAG_ADDRESS_LINE_2}: {self.address_line_2}
|
||||
{self.FLAG_CITY}: {self.city}
|
||||
{self.FLAG_COUNTY}: {self.county}
|
||||
{self.FLAG_ACTIVE}: {self.active}
|
||||
'''
|
||||
def to_json(self):
|
||||
return {
|
||||
**self.get_shared_json_attributes(self),
|
||||
self.ATTR_ID_ADDRESS: self.id_address,
|
||||
self.FLAG_REGION: self.region.to_json(),
|
||||
self.FLAG_POSTCODE: self.postcode,
|
||||
self.FLAG_ADDRESS_LINE_1: self.address_line_1,
|
||||
self.FLAG_ADDRESS_LINE_2: self.address_line_2,
|
||||
self.FLAG_CITY: self.city,
|
||||
self.FLAG_COUNTY: self.county,
|
||||
self.FLAG_ACTIVE: 1 if av.input_bool(self.active, self.FLAG_ACTIVE, f'{self.__class__.__name__}.to_json') else 0
|
||||
}
|
||||
@classmethod
|
||||
def from_json(cls, json):
|
||||
print(f'{cls.__name__}.from_json: {json}')
|
||||
address = cls()
|
||||
address.id_address = json[cls.ATTR_ID_ADDRESS],
|
||||
address.region = Region.from_json(json[cls.FLAG_REGION]),
|
||||
address.postcode = json[cls.FLAG_POSTCODE],
|
||||
address.address_line_1 = json[cls.FLAG_ADDRESS_LINE_1],
|
||||
address.address_line_2 = json.get(cls.FLAG_ADDRESS_LINE_2, ''),
|
||||
address.city = json[cls.FLAG_CITY],
|
||||
address.county = json[cls.FLAG_COUNTY],
|
||||
address.active = json[cls.FLAG_ACTIVE]
|
||||
return address
|
||||
@@ -19,15 +19,20 @@ from typing import ClassVar
|
||||
|
||||
class Base():
|
||||
ATTR_ID_ACCESS_LEVEL: ClassVar[str] = 'id_access_level'
|
||||
ATTR_ID_ADDRESS: ClassVar[str] = 'id_address'
|
||||
ATTR_ID_CURRENCY: ClassVar[str] = 'id_currency'
|
||||
ATTR_ID_DELIVERY_REGION: ClassVar[str] = 'id_delivery_region'
|
||||
ATTR_ID_REGION: ClassVar[str] = 'id_region'
|
||||
ATTR_ID_USER: ClassVar[str] = 'id_user'
|
||||
ATTR_ID_USER_MANAGER: ClassVar[str] = 'id_user_manager'
|
||||
FLAG_ACCESS_LEVEL_REQUIRED: ClassVar[str] = 'access_level_required'
|
||||
FLAG_ACTIVE: ClassVar[str] = 'active'
|
||||
FLAG_ADDRESS: ClassVar[str] = 'address'
|
||||
FLAG_CAN_ADMIN: ClassVar[str] = 'can_admin'
|
||||
FLAG_CAN_EDIT: ClassVar[str] = 'can_edit'
|
||||
FLAG_CAN_VIEW: ClassVar[str] = 'can_view'
|
||||
FLAG_CODE: ClassVar[str] = 'code'
|
||||
FLAG_CURRENCY: ClassVar[str] = 'currency'
|
||||
FLAG_CURRENCY_COST: ClassVar[str] = 'currency_cost'
|
||||
FLAG_DESCRIPTION: ClassVar[str] = 'description'
|
||||
FLAG_DISPLAY_ORDER: ClassVar[str] = 'display_order'
|
||||
FLAG_GUID: ClassVar[str] = 'guid'
|
||||
@@ -38,10 +43,14 @@ class Base():
|
||||
FLAG_NAME_ATTR_OPTION_VALUE: ClassVar[str] = 'NAME_ATTR_OPTION_VALUE'
|
||||
FLAG_NAME_SINGULAR: ClassVar[str] = 'name_singular'
|
||||
FLAG_NAME_PLURAL: ClassVar[str] = 'name_plural'
|
||||
FLAG_POSTCODE: ClassVar[str] = 'postcode'
|
||||
FLAG_PRIORITY: ClassVar[str] = 'priority'
|
||||
FLAG_REGION: ClassVar[str] = 'region'
|
||||
FLAG_ROWS: ClassVar[str] = 'rows'
|
||||
FLAG_SYMBOL: ClassVar[str] = 'symbol'
|
||||
FLAG_URL: ClassVar[str] = 'url'
|
||||
FLAG_VALUE_LOCAL_VAT_EXCL: ClassVar[str] = 'value_local_vat_excl'
|
||||
FLAG_VALUE_LOCAL_VAT_INCL: ClassVar[str] = 'value_local_vat_incl'
|
||||
NAME_ATTR_OPTION_TEXT: ClassVar[str] = 'name-attribute-option-text'
|
||||
NAME_ATTR_OPTION_VALUE: ClassVar[str] = 'name-attribute-option-value'
|
||||
|
||||
|
||||
@@ -81,6 +81,15 @@ class Currency(db.Model, Store_Base):
|
||||
v_arg_type = 'class attribute'
|
||||
currency = cls()
|
||||
return currency
|
||||
@classmethod
|
||||
def from_DB_stock_item(cls, query_row):
|
||||
_m = 'Currency.from_DB_get_many_stock_item'
|
||||
v_arg_type = 'class attribute'
|
||||
currency = cls()
|
||||
currency.id_currency = query_row[12]
|
||||
currency.code = query_row[13]
|
||||
currency.symbol = query_row[14]
|
||||
return currency
|
||||
def __repr__(self):
|
||||
return f'''
|
||||
id: {self.id_currency}
|
||||
@@ -30,11 +30,8 @@ class Get_Many_Parameters_Base(BaseModel, metaclass=ABCMeta):
|
||||
@abstractmethod
|
||||
def get_default(cls): # , id_user
|
||||
pass
|
||||
"""
|
||||
@abstractmethod
|
||||
def to_json(self):
|
||||
pass
|
||||
"""
|
||||
return self.dict()
|
||||
"""
|
||||
@classmethod
|
||||
@abstractmethod
|
||||
|
||||
82
business_objects/region.py
Normal file
82
business_objects/region.py
Normal file
@@ -0,0 +1,82 @@
|
||||
"""
|
||||
Project: PARTS Website
|
||||
Author: Edward Middleton-Smith
|
||||
Precision And Research Technology Systems Limited
|
||||
|
||||
Technology: Business Objects
|
||||
Feature: Address Region Business Object
|
||||
|
||||
Description:
|
||||
Business object for address region
|
||||
"""
|
||||
|
||||
# internal
|
||||
import lib.argument_validation as av
|
||||
from business_objects.base import Base
|
||||
from extensions import db
|
||||
# external
|
||||
from typing import ClassVar
|
||||
|
||||
|
||||
class Region(db.Model, Base):
|
||||
NAME_ATTR_OPTION_VALUE: ClassVar[str] = Base.ATTR_ID_REGION
|
||||
NAME_ATTR_OPTION_TEXT: ClassVar[str] = Base.FLAG_NAME
|
||||
__tablename__ = 'Shop_Region'
|
||||
id_region = db.Column(db.Integer, primary_key=True)
|
||||
code = db.Column(db.String(50))
|
||||
name = db.Column(db.String(200))
|
||||
active = db.Column(db.Boolean)
|
||||
|
||||
# region = None
|
||||
|
||||
def __init__(self):
|
||||
super().__init__()
|
||||
Base.__init__(self)
|
||||
self.region = None
|
||||
|
||||
@classmethod
|
||||
def from_DB_stock_item(cls, query_row):
|
||||
plant = cls()
|
||||
plant.id_region = query_row[7]
|
||||
return plant
|
||||
def __repr__(self):
|
||||
return f'''
|
||||
{self.ATTR_ID_REGION}: {self.id_region}
|
||||
{self.FLAG_CODE}: {self.code}
|
||||
{self.FLAG_NAME}: {self.name}
|
||||
{self.FLAG_ACTIVE}: {self.active}
|
||||
'''
|
||||
def to_json(self):
|
||||
return {
|
||||
**self.get_shared_json_attributes(self),
|
||||
self.ATTR_ID_REGION: self.id_region,
|
||||
self.FLAG_CODE: self.code,
|
||||
self.FLAG_NAME: self.name,
|
||||
self.FLAG_ACTIVE: 1 if av.input_bool(self.active, self.FLAG_ACTIVE, f'{self.__class__.__name__}.to_json') else 0
|
||||
}
|
||||
@classmethod
|
||||
def from_json(cls, json):
|
||||
print(f'{cls.__name__}.from_json: {json}')
|
||||
plant = cls()
|
||||
plant.id_region = json[cls.ATTR_ID_REGION]
|
||||
plant.code = json[cls.FLAG_CODE]
|
||||
plant.name = json[cls.FLAG_NAME]
|
||||
plant.active = json[cls.FLAG_ACTIVE]
|
||||
return plant
|
||||
@classmethod
|
||||
def from_DB_get_many_product_catalogue(cls, query_row):
|
||||
region = cls()
|
||||
region.id_region = query_row[0]
|
||||
region.name = query_row[1]
|
||||
region.code = query_row[2]
|
||||
# self.display_order = query_row[3]
|
||||
return region
|
||||
@classmethod
|
||||
def from_DB_region(cls, query_row):
|
||||
region = cls()
|
||||
region.id_region = query_row[0]
|
||||
region.code = query_row[1]
|
||||
region.name = query_row[2]
|
||||
region.active = av.input_bool(query_row[3], cls.FLAG_ACTIVE, f'{cls.__name__}.from_DB_region')
|
||||
region.display_order = query_row[4]
|
||||
return region
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -22,7 +22,7 @@ class Delivery_Option():
|
||||
delay_max: int
|
||||
quantity_min: float
|
||||
quantity_max: float
|
||||
regions: list # [Enum_Delivery_Region]
|
||||
regions: list # [Enum_Region]
|
||||
cost: float
|
||||
|
||||
def __new__(cls, name, delay_min, delay_max, quantity_min, quantity_max, regions, cost):
|
||||
@@ -33,7 +33,7 @@ class Delivery_Option():
|
||||
av.val_int(delay_max, 'delay_max', _m, 0, v_arg_type = v_arg_type)
|
||||
av.val_float(quantity_min, 'quantity_min', _m, 0, v_arg_type = v_arg_type)
|
||||
av.val_float(quantity_max, 'quantity_max', _m, 0, v_arg_type = v_arg_type)
|
||||
av.val_list_instances(regions, 'regions', _m, Enum_Delivery_Region, v_arg_type = v_arg_type)
|
||||
av.val_list_instances(regions, 'regions', _m, Enum_Region, v_arg_type = v_arg_type)
|
||||
av.val_float(cost, 'cost', _m, 0, v_arg_type = v_arg_type)
|
||||
return super(Delivery_Option, cls).__new__(cls)
|
||||
|
||||
|
||||
@@ -1,103 +0,0 @@
|
||||
"""
|
||||
Project: PARTS Website
|
||||
Author: Edward Middleton-Smith
|
||||
Precision And Research Technology Systems Limited
|
||||
|
||||
Technology: Business Objects
|
||||
Feature: Delivery Region Business Object
|
||||
|
||||
Description:
|
||||
Business object for delivery region
|
||||
"""
|
||||
|
||||
# internal
|
||||
from business_objects.store.store_base import Store_Base
|
||||
from extensions import db
|
||||
from lib import argument_validation as av
|
||||
# external
|
||||
from enum import Enum
|
||||
from typing import ClassVar
|
||||
|
||||
|
||||
class Enum_Delivery_Region(Enum):
|
||||
UK = 0
|
||||
|
||||
class Delivery_Region(db.Model, Store_Base):
|
||||
NAME_ATTR_OPTION_VALUE: ClassVar[str] = Store_Base.ATTR_ID_DELIVERY_REGION
|
||||
NAME_ATTR_OPTION_TEXT: ClassVar[str] = Store_Base.FLAG_NAME
|
||||
|
||||
id_region = db.Column(db.Integer, primary_key=True)
|
||||
"""
|
||||
id_category = db.Column(db.Integer)
|
||||
id_product = db.Column(db.Integer)
|
||||
id_discount = db.Column(db.Integer)
|
||||
"""
|
||||
code = db.Column(db.String(50))
|
||||
name = db.Column(db.String(200))
|
||||
active = db.Column(db.Boolean)
|
||||
display_order = db.Column(db.Integer)
|
||||
"""
|
||||
def __new__(cls, id, id_category, id_product, id_discount, code, name, display_order):
|
||||
_m = 'Delivery_Region.__new__'
|
||||
v_arg_type = 'class attribute'
|
||||
av.val_int(id, 'id', _m, 0, v_arg_type = v_arg_type)
|
||||
av.val_int(id_category, 'id_category', _m, 0, v_arg_type=v_arg_type)
|
||||
av.val_int(id_product, 'id_product', _m, 0, v_arg_type = v_arg_type)
|
||||
av.val_int(id_discount, 'id_discount', _m, v_arg_type = v_arg_type)
|
||||
av.val_str(code, 'code', _m, max_len = 50, v_arg_type = v_arg_type)
|
||||
av.val_str(name, 'name', _m, max_len = 100, v_arg_type = v_arg_type)
|
||||
av.val_int(display_order, 'display_order', _m, v_arg_type = v_arg_type)
|
||||
return super(Delivery_Region, cls).__new__(cls)
|
||||
|
||||
def __init__(self, id, id_category, id_product, id_discount, code, name, display_order):
|
||||
self.id_region = id
|
||||
self.id_category = id_category
|
||||
self.id_product = id_product
|
||||
self.id_discount = id_discount
|
||||
self.name = name
|
||||
self.code = code
|
||||
self.display_order = display_order
|
||||
"""
|
||||
@classmethod
|
||||
def from_DB_get_many_product_catalogue(cls, query_row):
|
||||
region = cls()
|
||||
region.id_region = query_row[0]
|
||||
region.name = query_row[1]
|
||||
region.code = query_row[2]
|
||||
# self.display_order = query_row[3]
|
||||
return region
|
||||
@classmethod
|
||||
def from_DB_region(cls, query_row):
|
||||
region = cls()
|
||||
region.id_region = query_row[0]
|
||||
region.code = query_row[1]
|
||||
region.name = query_row[2]
|
||||
region.active = av.input_bool(query_row[3], cls.FLAG_ACTIVE, f'{cls.__name__}.from_DB_region')
|
||||
region.display_order = query_row[4]
|
||||
return region
|
||||
def __repr__(self):
|
||||
return f'''
|
||||
id: {self.id_region}
|
||||
name: {self.name}
|
||||
code: {self.code}
|
||||
active: {self.active}
|
||||
display_order: {self.display_order}
|
||||
'''
|
||||
def to_json(self):
|
||||
return {
|
||||
**self.get_shared_json_attributes(self),
|
||||
self.ATTR_ID_REGION: self.id_region,
|
||||
self.FLAG_CODE: self.code,
|
||||
self.FLAG_NAME: self.name,
|
||||
self.FLAG_ACTIVE: self.active,
|
||||
self.FLAG_DISPLAY_ORDER: self.display_order
|
||||
}
|
||||
@staticmethod
|
||||
def from_json(json_region):
|
||||
region = Delivery_Region()
|
||||
region.id_region = json_region[Delivery_Region.ATTR_ID_REGION]
|
||||
region.code = json_region[Delivery_Region.FLAG_CODE]
|
||||
region.name = json_region[Delivery_Region.FLAG_NAME]
|
||||
region.active = json_region[Delivery_Region.FLAG_ACTIVE]
|
||||
region.display_order = json_region[Delivery_Region.FLAG_DISPLAY_ORDER]
|
||||
return region
|
||||
92
business_objects/store/plant.py
Normal file
92
business_objects/store/plant.py
Normal file
@@ -0,0 +1,92 @@
|
||||
"""
|
||||
Project: PARTS Website
|
||||
Author: Edward Middleton-Smith
|
||||
Precision And Research Technology Systems Limited
|
||||
|
||||
Technology: Business Objects
|
||||
Feature: Plant Business Object
|
||||
|
||||
Description:
|
||||
Business object for plant
|
||||
"""
|
||||
|
||||
# internal
|
||||
import lib.argument_validation as av
|
||||
from business_objects.address import Address
|
||||
from business_objects.store.store_base import Store_Base
|
||||
from extensions import db
|
||||
# external
|
||||
from typing import ClassVar
|
||||
|
||||
|
||||
class Plant(db.Model, Store_Base):
|
||||
NAME_ATTR_OPTION_VALUE: ClassVar[str] = Store_Base.ATTR_ID_PLANT
|
||||
NAME_ATTR_OPTION_TEXT: ClassVar[str] = Store_Base.FLAG_NAME
|
||||
__tablename__ = 'Shop_Plant'
|
||||
id_plant = db.Column(db.Integer, primary_key=True)
|
||||
code = db.Column(db.String(50))
|
||||
name = db.Column(db.String(255))
|
||||
id_address = db.Column(db.Integer)
|
||||
id_user_manager = db.Column(db.Integer)
|
||||
active = db.Column(db.Boolean)
|
||||
|
||||
# address = None
|
||||
|
||||
def __init__(self):
|
||||
super().__init__()
|
||||
Store_Base.__init__(self)
|
||||
self.address = None
|
||||
@classmethod
|
||||
def from_DB_storage_location(cls, query_row):
|
||||
plant = cls()
|
||||
plant.id_plant = query_row[1]
|
||||
plant.id_address = query_row[2]
|
||||
plant.address = Address.from_DB_storage_location(query_row)
|
||||
return plant
|
||||
@classmethod
|
||||
def from_DB_plant(cls, query_row):
|
||||
plant = cls()
|
||||
plant.id_plant = query_row[0]
|
||||
plant.id_address = query_row[1]
|
||||
plant.address = Address.from_DB_plant(query_row)
|
||||
plant.code = query_row[4]
|
||||
plant.name = query_row[5]
|
||||
plant.active = query_row[6]
|
||||
return plant
|
||||
@classmethod
|
||||
def from_DB_stock_item(cls, query_row):
|
||||
plant = cls()
|
||||
plant.id_plant = query_row[5]
|
||||
plant.code = query_row[10]
|
||||
plant.name = query_row[11]
|
||||
return plant
|
||||
def __repr__(self):
|
||||
return f'''
|
||||
{self.ATTR_ID_PLANT}: {self.id_plant}
|
||||
{self.FLAG_CODE}: {self.code}
|
||||
{self.FLAG_NAME}: {self.name}
|
||||
{self.FLAG_ADDRESS}: {self.address}
|
||||
{self.ATTR_ID_USER_MANAGER}: {self.id_user_manager}
|
||||
{self.FLAG_ACTIVE}: {self.active}
|
||||
'''
|
||||
def to_json(self):
|
||||
return {
|
||||
**self.get_shared_json_attributes(self),
|
||||
self.ATTR_ID_PLANT: self.id_plant,
|
||||
self.FLAG_CODE: self.code,
|
||||
self.FLAG_NAME: self.name,
|
||||
self.FLAG_ADDRESS: self.address.to_json(),
|
||||
self.ATTR_ID_USER_MANAGER: self.id_user_manager,
|
||||
self.FLAG_ACTIVE: 1 if av.input_bool(self.active, self.FLAG_ACTIVE, f'{self.__class__.__name__}.to_json') else 0
|
||||
}
|
||||
@classmethod
|
||||
def from_json(cls, json):
|
||||
print(f'{cls.__name__}.from_json: {json}')
|
||||
plant = cls()
|
||||
plant.id_plant = json[cls.ATTR_ID_PLANT],
|
||||
plant.code = json[cls.FLAG_CODE],
|
||||
plant.name = json[cls.FLAG_NAME],
|
||||
plant.address = Address.from_json(json[cls.FLAG_ADDRESS]),
|
||||
plant.id_user_manager = json[cls.ATTR_ID_USER_MANAGER],
|
||||
plant.active = json[cls.FLAG_ACTIVE]
|
||||
return plant
|
||||
@@ -175,7 +175,7 @@ class Product(SQLAlchemy_ABC, Store_Base):
|
||||
if self.variation_trees[index_tree].is_equal(variation_tree):
|
||||
found_variation_tree_match = True
|
||||
break
|
||||
if not found_variation_tree_match:
|
||||
if not found_variation_tree_match and variation_tree is not None:
|
||||
self.variation_trees.append(variation_tree)
|
||||
def from_DB_Stripe_product(query_row):
|
||||
permutation = Product_Permutation.from_DB_Stripe_product(query_row)
|
||||
@@ -374,6 +374,13 @@ class Product(SQLAlchemy_ABC, Store_Base):
|
||||
text_input += tree.get_text_input_types()
|
||||
return text_input
|
||||
"""
|
||||
def get_csv_ids_permutation(self):
|
||||
csv = ''
|
||||
for permutation in self.permutations:
|
||||
if csv != '':
|
||||
csv += ','
|
||||
csv += str(permutation.id_permutation)
|
||||
return csv
|
||||
|
||||
|
||||
class Parameters_Product(Get_Many_Parameters_Base):
|
||||
@@ -482,7 +489,7 @@ class Parameters_Product(Get_Many_Parameters_Base):
|
||||
@staticmethod
|
||||
def from_form_filters_product_permutation(form):
|
||||
# if not (form is Filters_Product_Permutation): raise ValueError(f'Invalid form type: {type(form)}')
|
||||
av.val_instance(form, 'form', 'Parameters_Product.from_form', Filters_Product_Permutation)
|
||||
# av.val_instance(form, 'form', 'Parameters_Product.from_form', Filters_Product_Permutation)
|
||||
has_category_filter = not (form.id_category.data == '0' or form.id_category.data == '')
|
||||
has_product_filter = not (form.id_product.data == '0' or form.id_product.data == '')
|
||||
get_permutations_stock_below_min = av.input_bool(form.is_out_of_stock.data, "is_out_of_stock", "Parameters_Product.from_form")
|
||||
@@ -491,11 +498,11 @@ class Parameters_Product(Get_Many_Parameters_Base):
|
||||
get_all_product_category = not has_category_filter,
|
||||
get_inactive_product_category = False,
|
||||
# get_first_product_category_only = False,
|
||||
ids_product_category = form.id_category.data,
|
||||
ids_product_category = form.id_category.data if form.id_category.data is not None else '',
|
||||
get_all_product = not has_product_filter,
|
||||
get_inactive_product = False,
|
||||
# get_first_product_only = False,
|
||||
ids_product = form.id_product.data,
|
||||
ids_product = form.id_product.data if form.id_product.data is not None else '',
|
||||
get_all_permutation = not get_permutations_stock_below_min,
|
||||
get_inactive_permutation = False,
|
||||
# get_first_permutation_only = False,
|
||||
@@ -601,6 +608,9 @@ class Parameters_Product(Get_Many_Parameters_Base):
|
||||
ids_image = '',
|
||||
get_products_quantity_stock_below_min = False
|
||||
)
|
||||
@classmethod
|
||||
def from_filters_stock_item(cls, filters_stock_item):
|
||||
return cls.from_form_filters_product_permutation(filters_stock_item)
|
||||
|
||||
"""
|
||||
class Parameters_Product(Get_Many_Parameters_Base):
|
||||
|
||||
@@ -242,6 +242,11 @@ class Product_Category(SQLAlchemy_ABC, Store_Base):
|
||||
'value': self.id_category,
|
||||
'text': self.name
|
||||
}
|
||||
def get_csv_ids_permutation(self):
|
||||
list_ids = []
|
||||
for product in self.products:
|
||||
list_ids += product.get_csv_ids_permutation()
|
||||
return list_ids
|
||||
"""
|
||||
class Filters_Product_Category(BaseModel, Store_Base):
|
||||
ids_product_category: str
|
||||
@@ -433,6 +438,11 @@ class Product_Category_Container(Store_Base):
|
||||
if column.name not in ['created_on', 'created_by']
|
||||
}
|
||||
return self.to_object_with_missing_attributes(excluded_attributes)
|
||||
def get_csv_ids_permutation(self):
|
||||
list_ids = []
|
||||
for category in self.categories:
|
||||
list_ids += category.get_csv_ids_permutation()
|
||||
return ','.join(list_ids)
|
||||
|
||||
|
||||
"""
|
||||
|
||||
@@ -14,7 +14,7 @@ Business object for product permutation
|
||||
import lib.argument_validation as av
|
||||
from lib import data_types
|
||||
from forms.forms import Form_Basket_Add, Form_Basket_Edit
|
||||
from business_objects.store.currency import Currency
|
||||
from business_objects.currency import Currency
|
||||
from business_objects.store.delivery_option import Delivery_Option
|
||||
from business_objects.store.discount import Discount
|
||||
from business_objects.store.image import Image
|
||||
@@ -309,6 +309,7 @@ class Product_Permutation(db.Model, Store_Base):
|
||||
'value': self.id_permutation,
|
||||
'text': self.get_name_variations()
|
||||
}
|
||||
|
||||
def get_name(self):
|
||||
return
|
||||
def get_name_variations(self):
|
||||
@@ -317,19 +318,14 @@ class Product_Permutation(db.Model, Store_Base):
|
||||
return len(self.prices) > 0
|
||||
def get_price(self):
|
||||
return self.prices[0]
|
||||
def get_price_local_VAT_incl(self):
|
||||
price = self.get_price()
|
||||
return price.value_local_VAT_incl
|
||||
def get_price_local_VAT_excl(self):
|
||||
price = self.get_price()
|
||||
return price.value_local_VAT_excl
|
||||
|
||||
def output_lead_time(self):
|
||||
return '1 day' if self.latency_manufacture_days == 1 else f'{self.latency_manufacture_days} days'
|
||||
|
||||
def output_delivery_date(self):
|
||||
return (datetime.now() + timedelta(days=self.latency_manufacture_days)).strftime('%A, %d %B %Y')
|
||||
|
||||
"""
|
||||
def output_lead_time(self):
|
||||
return '1 day' if self.latency_manufacture_days == 1 else f'{self.latency_manufacture_days} days'
|
||||
|
||||
def output_price(self, is_included_VAT):
|
||||
if self.is_unavailable_in_currency_or_region:
|
||||
return 'Not available in currency and region'
|
||||
@@ -341,33 +337,14 @@ class Product_Permutation(db.Model, Store_Base):
|
||||
return f'{price.symbol_currency} {locale.format_string("%d", price.value_local_VAT_incl, grouping=True)}'
|
||||
else:
|
||||
return f'{price.symbol_currency} {locale.format_string("%d", price.value_local_VAT_excl, grouping=True)}'
|
||||
def output_currency(self):
|
||||
if not self.is_available:
|
||||
return ''
|
||||
"""
|
||||
price = self.get_price()
|
||||
return price.code_currency
|
||||
"""
|
||||
return self.code_currency_cost if self.symbol_currency_cost == '' else self.symbol_currency_cost
|
||||
"""
|
||||
def output_variations(self):
|
||||
if not self.has_variations: return ''
|
||||
return '\n'.join([f'{variation.name_variation_type}: {variation.name_variation}' for variation in self.variations])
|
||||
def output_variations_jsonify(self):
|
||||
if not self.has_variations: return ''
|
||||
return ','.join([f'{variation.id_type}: {variation.id_variation}' for variation in self.variations])
|
||||
"""
|
||||
def output_price_VAT_incl(self):
|
||||
locale.setlocale(locale.LC_ALL, '')
|
||||
return locale.format_string("%d", self.price_GBP_VAT_incl, grouping=True)
|
||||
def output_price_VAT_excl(self):
|
||||
locale.setlocale(locale.LC_ALL, '')
|
||||
return locale.format_string("%d", self.price_GBP_VAT_excl, grouping=True)
|
||||
def add_form_basket_add(self):
|
||||
self.form_basket_add = None
|
||||
|
||||
def add_form_basket_edit(self):
|
||||
self.form_basket_edit = None
|
||||
"""
|
||||
def __repr__(self):
|
||||
return f'''Product_Permutation
|
||||
id_permutation: {self.id_permutation}
|
||||
|
||||
@@ -11,8 +11,8 @@ Business object for product price
|
||||
"""
|
||||
|
||||
# internal
|
||||
from business_objects.store.currency import Currency
|
||||
from business_objects.store.delivery_region import Delivery_Region
|
||||
from business_objects.currency import Currency
|
||||
from business_objects.region import Region
|
||||
from business_objects.store.store_base import Store_Base
|
||||
from extensions import db
|
||||
# external
|
||||
@@ -22,8 +22,6 @@ from typing import ClassVar
|
||||
class Product_Price(db.Model, Store_Base):
|
||||
NAME_ATTR_OPTION_VALUE: ClassVar[str] = Store_Base.ATTR_ID_PRODUCT_PRICE
|
||||
NAME_ATTR_OPTION_TEXT = Store_Base.FLAG_TEXT
|
||||
FLAG_VALUE_LOCAL_VAT_INCL: ClassVar[str] = 'value-local-vat-incl'
|
||||
FLAG_VALUE_LOCAL_VAT_EXCL: ClassVar[str] = 'value-local-vat-excl'
|
||||
|
||||
id_price = db.Column(db.Integer, primary_key=True)
|
||||
id_permutation = db.Column(db.Integer)
|
||||
@@ -87,7 +85,7 @@ class Product_Price(db.Model, Store_Base):
|
||||
self.ATTR_ID_PRODUCT: self.id_product,
|
||||
self.ATTR_ID_PRODUCT_CATEGORY: self.id_category,
|
||||
self.FLAG_CURRENCY: self.currency.to_json(),
|
||||
# Delivery_Region.ATTR_ID_DELIVERY_REGION: self.id_region,
|
||||
# Region.ATTR_ID_REGION_DELIVERY: self.id_region,
|
||||
self.FLAG_VALUE_LOCAL_VAT_INCL: self.value_local_VAT_incl,
|
||||
self.FLAG_VALUE_LOCAL_VAT_EXCL: self.value_local_VAT_excl,
|
||||
self.FLAG_DISPLAY_ORDER: self.display_order
|
||||
@@ -101,7 +99,7 @@ class Product_Price(db.Model, Store_Base):
|
||||
price.id_product = json[cls.ATTR_ID_PRODUCT]
|
||||
price.id_category = json[cls.ATTR_ID_PRODUCT_CATEGORY]
|
||||
price.currency = Currency.from_json(json)
|
||||
# price.id_region = json[Delivery_Region.ATTR_ID_DELIVERY_REGION]
|
||||
# price.id_region = json[Region.ATTR_ID_REGION_DELIVERY]
|
||||
price.value_local_VAT_incl = json[cls.FLAG_VALUE_LOCAL_VAT_INCL]
|
||||
price.value_local_VAT_excl = json[cls.FLAG_VALUE_LOCAL_VAT_EXCL]
|
||||
price.display_order = json[cls.FLAG_DISPLAY_ORDER]
|
||||
|
||||
@@ -82,6 +82,7 @@ class Product_Variation_Tree():
|
||||
@classmethod
|
||||
def from_json_str(cls, json_str):
|
||||
variations = []
|
||||
if json_str is None or json_str == '': return None
|
||||
for json_variation in json_str.split(','):
|
||||
parts = json_variation.split(':')
|
||||
if len(parts) != 2: continue
|
||||
|
||||
@@ -13,13 +13,15 @@ import lib.argument_validation as av
|
||||
from lib import data_types
|
||||
from forms.store.stock_item import Filters_Stock_Item
|
||||
from business_objects.db_base import Get_Many_Parameters_Base
|
||||
from business_objects.store.product_price import Product_Price
|
||||
from business_objects.currency import Currency
|
||||
# from business_objects.discount import Discount
|
||||
from business_objects.store.product_variation_tree import Product_Variation_Tree
|
||||
from business_objects.store.storage_location import Storage_Location
|
||||
from business_objects.store.store_base import Store_Base
|
||||
from extensions import db
|
||||
# external
|
||||
from dataclasses import dataclass
|
||||
from typing import ClassVar
|
||||
from typing import ClassVar, Optional
|
||||
from datetime import datetime
|
||||
|
||||
|
||||
@@ -34,21 +36,19 @@ class Stock_Item(db.Model, Store_Base):
|
||||
FLAG_DATE_UNSEALED: ClassVar[str] = 'date_unsealed'
|
||||
FLAG_IS_CONSUMED: ClassVar[str] = 'is_consumed'
|
||||
FLAG_IS_SEALED: ClassVar[str] = 'is_sealed'
|
||||
FLAG_VALUE_LOCAL_VAT_EXCL_COST: ClassVar[str] = f'{Product_Price.FLAG_VALUE_LOCAL_VAT_EXCL}_cost'
|
||||
FLAG_VALUE_LOCAL_VAT_INCL_COST: ClassVar[str] = f'{Product_Price.FLAG_VALUE_LOCAL_VAT_INCL}_cost'
|
||||
|
||||
id_stock = db.Column(db.Integer, primary_key=True)
|
||||
id_permutation = db.Column(db.Integer)
|
||||
id_product = db.Column(db.Integer)
|
||||
id_category = db.Column(db.Integer)
|
||||
# name_category = db.Column(db.String(255))
|
||||
# name_product = db.Column(db.String(255))
|
||||
id_location_storage = db.Column(db.Integer)
|
||||
id_plant = db.Column(db.Integer)
|
||||
id_region = db.Column(db.Integer)
|
||||
id_currency_cost = db.Column(db.Integer)
|
||||
cost_local_VAT_excl = db.Column(db.Float)
|
||||
cost_local_VAT_incl = db.Column(db.Float)
|
||||
date_purchased = db.Column(db.DateTime)
|
||||
date_received = db.Column(db.DateTime)
|
||||
id_location_storage = db.Column(db.Integer)
|
||||
id_currency_cost = db.Column(db.Integer)
|
||||
cost_local_VAT_incl = db.Column(db.Float)
|
||||
cost_local_VAT_excl = db.Column(db.Float)
|
||||
is_sealed = db.Column(db.Boolean)
|
||||
date_unsealed = db.Column(db.DateTime)
|
||||
date_expiration = db.Column(db.DateTime)
|
||||
@@ -60,10 +60,15 @@ class Stock_Item(db.Model, Store_Base):
|
||||
can_edit = db.Column(db.Boolean)
|
||||
can_admin = db.Column(db.Boolean)
|
||||
"""
|
||||
# variation_tree: Product_Variation_Tree = None
|
||||
|
||||
def __init__(self):
|
||||
super().__init__()
|
||||
Store_Base.__init__(self)
|
||||
self.currency_cost = None
|
||||
self.storage_location = None
|
||||
self.variation_tree = None
|
||||
self.has_variations = False
|
||||
|
||||
def from_DB_stock_item(query_row):
|
||||
_m = 'Product.from_DB_stock_item'
|
||||
@@ -73,21 +78,20 @@ class Stock_Item(db.Model, Store_Base):
|
||||
stock_item.id_permutation = query_row[1]
|
||||
stock_item.id_product = query_row[2]
|
||||
stock_item.id_category = query_row[3]
|
||||
# stock_item.name_category = query_row[4]
|
||||
# stock_item.name_product = query_row[5]
|
||||
stock_item.date_purchased = query_row[4]
|
||||
stock_item.date_received = query_row[5]
|
||||
stock_item.id_location_storage = query_row[6]
|
||||
# stock_item.name_location_storage = query_row[9]
|
||||
stock_item.id_currency_cost = query_row[7]
|
||||
stock_item.cost_local_VAT_incl = query_row[8]
|
||||
stock_item.cost_local_VAT_excl = query_row[9]
|
||||
stock_item.is_sealed = av.input_bool(query_row[10], "is_sealed", _m, v_arg_type=v_arg_type)
|
||||
stock_item.date_unsealed = query_row[11]
|
||||
stock_item.date_expiration = query_row[12]
|
||||
stock_item.is_consumed = av.input_bool(query_row[13], "is_consumed", _m, v_arg_type=v_arg_type)
|
||||
stock_item.date_consumed = query_row[14]
|
||||
stock_item.active = av.input_bool(query_row[15], "active", _m, v_arg_type=v_arg_type)
|
||||
stock_item.id_location_storage = query_row[4]
|
||||
stock_item.storage_location = Storage_Location.from_DB_stock_item(query_row)
|
||||
stock_item.id_currency_cost = query_row[12]
|
||||
stock_item.currency_cost = Currency.from_DB_stock_item(query_row)
|
||||
stock_item.cost_local_VAT_excl = query_row[15]
|
||||
stock_item.cost_local_VAT_incl = query_row[16]
|
||||
stock_item.date_purchased = query_row[17]
|
||||
stock_item.date_received = query_row[18]
|
||||
stock_item.is_sealed = av.input_bool(query_row[19], "is_sealed", _m, v_arg_type=v_arg_type)
|
||||
stock_item.date_unsealed = query_row[20]
|
||||
stock_item.date_expiration = query_row[21]
|
||||
stock_item.is_consumed = av.input_bool(query_row[22], "is_consumed", _m, v_arg_type=v_arg_type)
|
||||
stock_item.date_consumed = query_row[23]
|
||||
stock_item.active = av.input_bool(query_row[24], "active", _m, v_arg_type=v_arg_type)
|
||||
"""
|
||||
stock_item.can_view = av.input_bool(query_row[24], "can_view", _m, v_arg_type=v_arg_type)
|
||||
stock_item.can_edit = av.input_bool(query_row[25], "can_edit", _m, v_arg_type=v_arg_type)
|
||||
@@ -99,96 +103,55 @@ class Stock_Item(db.Model, Store_Base):
|
||||
def from_json(cls, json):
|
||||
stock_item = cls()
|
||||
stock_item.id_stock = json[cls.ATTR_ID_STOCK_ITEM]
|
||||
stock_item.id_permutation = json[cls.ATTR_ID_PRODUCT_PERMUTATION]
|
||||
stock_item.id_permutation = json.get(cls.ATTR_ID_PRODUCT_PERMUTATION, 0)
|
||||
stock_item.id_product = json[cls.ATTR_ID_PRODUCT]
|
||||
stock_item.id_category = json[cls.ATTR_ID_PRODUCT_CATEGORY]
|
||||
print(f'json: {json}\nhalf stock item: {stock_item}')
|
||||
stock_item.variation_tree = Product_Variation_Tree.from_json_str(json[cls.FLAG_PRODUCT_VARIATIONS])
|
||||
stock_item.date_purchased = json[cls.FLAG_DATE_PURCHASED]
|
||||
stock_item.date_received = json[cls.FLAG_DATE_RECEIVED]
|
||||
stock_item.id_location_storage = json[cls.ATTR_ID_LOCATION_STORAGE]
|
||||
stock_item.id_location_storage = json[cls.ATTR_ID_STORAGE_LOCATION]
|
||||
stock_item.id_currency_cost = json[cls.ATTR_ID_CURRENCY_COST]
|
||||
stock_item.cost_local_VAT_incl = json[cls.FLAG_VALUE_LOCAL_VAT_INCL_COST]
|
||||
stock_item.cost_local_VAT_excl = json[cls.FLAG_VALUE_LOCAL_VAT_EXCL_COST]
|
||||
stock_item.cost_local_VAT_excl = json[cls.FLAG_COST_LOCAL_VAT_EXCL]
|
||||
stock_item.cost_local_VAT_incl = json[cls.FLAG_COST_LOCAL_VAT_INCL]
|
||||
stock_item.is_sealed = json[cls.FLAG_IS_SEALED]
|
||||
stock_item.date_unsealed = json[cls.FLAG_DATE_UNSEALED]
|
||||
stock_item.date_expiration = json[cls.FLAG_DATE_EXPIRATION]
|
||||
stock_item.is_consumed = json[cls.FLAG_IS_CONSUMED]
|
||||
stock_item.date_consumed = json[cls.FLAG_DATE_CONSUMED]
|
||||
stock_item.active = json[cls.FLAG_ACTIVE]
|
||||
"""
|
||||
stock_item.can_view = json[cls.FLAG_CAN_VIEW]
|
||||
stock_item.can_edit = json[cls.FLAG_CAN_EDIT]
|
||||
stock_item.can_admin = json[cls.FLAG_CAN_ADMIN]
|
||||
"""
|
||||
return stock_item
|
||||
"""
|
||||
def from_json(json_basket_item, key_id_product, key_id_permutation):
|
||||
permutation = Product_Permutation.from_json(json_basket_item, key_id_product, key_id_permutation)
|
||||
product = Product.from_permutation(permutation)
|
||||
return product
|
||||
|
||||
def output_lead_time(self):
|
||||
return self.get_permutation_selected().output_lead_time()
|
||||
def output_delivery_date(self):
|
||||
return self.get_permutation_selected().output_delivery_date()
|
||||
def output_price(self, is_included_VAT):
|
||||
return self.get_permutation_selected().output_price(is_included_VAT)
|
||||
def output_price_VAT_incl(self):
|
||||
return self.get_permutation_selected().output_price(True)
|
||||
def output_price_VAT_excl(self):
|
||||
return self.get_permutation_selected().output_price(False)
|
||||
def get_price_local(self, is_included_VAT):
|
||||
if is_included_VAT:
|
||||
return self.get_price_local_VAT_incl()
|
||||
else:
|
||||
return self.get_price_local_VAT_excl()
|
||||
def get_price_local_VAT_incl(self):
|
||||
return self.get_permutation_selected().get_price_local_VAT_incl()
|
||||
def get_price_local_VAT_excl(self):
|
||||
return self.get_permutation_selected().get_price_local_VAT_excl()
|
||||
def get_quantity_min(self):
|
||||
return self.get_permutation_selected().quantity_min
|
||||
def get_id_permutation(self):
|
||||
return self.get_permutation_selected().id_permutation
|
||||
def get_image_from_index(self, index_image):
|
||||
return self.get_permutation_selected().images[index_image]
|
||||
def get_name(self):
|
||||
return self.get_permutation_selected().name
|
||||
def get_description(self):
|
||||
return self.get_permutation_selected().description
|
||||
def output_currency(self):
|
||||
return self.get_permutation_selected().get_price().symbol_currency
|
||||
def add_form_basket_add(self):
|
||||
self.form_basket_add = None
|
||||
|
||||
def add_form_basket_edit(self):
|
||||
self.form_basket_edit = None
|
||||
"""
|
||||
def __repr__(self):
|
||||
return f'''Product
|
||||
return f'''Stock Item
|
||||
id_stock: {self.id_stock}
|
||||
id_permutation: {self.id_permutation}
|
||||
id_product: {self.id_product}
|
||||
id_category: {self.id_category}
|
||||
name: {self.name}
|
||||
display_order: {self.display_order}
|
||||
can_view: {self.can_view}
|
||||
can_edit: {self.can_edit}
|
||||
can_admin: {self.can_admin}
|
||||
has_variations: {self.has_variations}
|
||||
permutations: {self.permutations}
|
||||
variation trees: {self.variation_trees}
|
||||
variations: {self.variation_tree.to_preview_str() if self.variation_tree is not None else 'None'}
|
||||
storage_location: {self.storage_location}
|
||||
currency: {self.currency_cost}
|
||||
cost_local_VAT_excl: {self.cost_local_VAT_excl}
|
||||
cost_local_VAT_incl: {self.cost_local_VAT_incl}
|
||||
date_purchased: {self.date_purchased}
|
||||
date_received: {self.date_received}
|
||||
is_sealed: {self.is_sealed}
|
||||
date_unsealed: {self.date_unsealed}
|
||||
date_expiration: {self.date_expiration}
|
||||
is_consumed: {self.is_consumed}
|
||||
date_consumed: {self.date_consumed}
|
||||
active: {self.active}
|
||||
'''
|
||||
def to_json(self):
|
||||
return {
|
||||
**self.get_shared_json_attributes(self),
|
||||
self.ATTR_ID_PRODUCT: {self.id_product},
|
||||
self.ATTR_ID_PRODUCT_CATEGORY: {self.id_category},
|
||||
self.FLAG_NAME: {self.name},
|
||||
self.FLAG_DISPLAY_ORDER: {self.display_order},
|
||||
self.FLAG_CAN_VIEW: {self.can_view},
|
||||
self.FLAG_CAN_EDIT: {self.can_edit},
|
||||
self.FLAG_CAN_ADMIN: {self.can_admin},
|
||||
self.FLAG_HAS_VARIATIONS: {self.has_variations},
|
||||
self.FLAG_PRODUCT_PERMUTATION: {self.permutations},
|
||||
self.FLAG_PRODUCT_VARIATION_TREES: {self.variation_trees},
|
||||
self.ATTR_ID_STOCK_ITEM: self.id_stock,
|
||||
self.ATTR_ID_PRODUCT_PERMUTATION: self.id_permutation,
|
||||
self.ATTR_ID_PRODUCT: self.id_product,
|
||||
self.ATTR_ID_PRODUCT_CATEGORY: self.id_category,
|
||||
self.FLAG_STORAGE_LOCATION: self.storage_location.to_json(),
|
||||
self.FLAG_CURRENCY_COST: self.currency_cost.to_json(),
|
||||
self.FLAG_COST_LOCAL_VAT_EXCL: self.cost_local_VAT_excl,
|
||||
self.FLAG_COST_LOCAL_VAT_INCL: self.cost_local_VAT_incl,
|
||||
}
|
||||
def has_permutations(self):
|
||||
return len(self.permutations) > 0
|
||||
@@ -224,12 +187,11 @@ class Parameters_Stock_Item(Get_Many_Parameters_Base):
|
||||
a_ids_region_storage: str
|
||||
a_get_all_plant_storage: bool
|
||||
a_get_inactive_plant_storage: bool
|
||||
a_get_first_plant_storage_only: bool
|
||||
a_ids_plant_storage: str
|
||||
a_get_all_location_storage: bool
|
||||
a_get_inactive_location_storage: bool
|
||||
a_ids_location_storage: str
|
||||
a_date_received_to: datetime
|
||||
a_date_received_to: Optional[datetime] = None
|
||||
a_get_sealed_stock_item_only: bool
|
||||
a_get_unsealed_stock_item_only: bool
|
||||
a_get_expired_stock_item_only: bool
|
||||
@@ -244,7 +206,7 @@ class Parameters_Stock_Item(Get_Many_Parameters_Base):
|
||||
def get_default(cls):
|
||||
return cls(
|
||||
# a_id_user = id_user,
|
||||
a_get_all_product_permutation = True,
|
||||
a_get_all_product_permutation = False,
|
||||
a_get_inactive_product_permutation = False,
|
||||
a_ids_product_permutation = '',
|
||||
a_get_all_stock_item = True,
|
||||
@@ -271,3 +233,70 @@ class Parameters_Stock_Item(Get_Many_Parameters_Base):
|
||||
@classmethod
|
||||
def from_form_stock_item(cls, form):
|
||||
return cls.get_default()
|
||||
|
||||
|
||||
class Stock_Item_Temp(db.Model, Store_Base):
|
||||
__tablename__: ClassVar[str] = 'Shop_Stock_Item_Temp'
|
||||
__table_args__ = { 'extend_existing': True }
|
||||
id_stock: int = db.Column(db.Integer, primary_key=True)
|
||||
# id_category: int = db.Column(db.Integer)
|
||||
id_product: int = db.Column(db.Integer)
|
||||
# has_variations: bool = db.Column(db.Boolean)
|
||||
id_permutation: int = db.Column(db.Integer)
|
||||
id_pairs_variations: str = db.Column(db.String(4000))
|
||||
date_purchased: datetime = db.Column(db.DateTime)
|
||||
date_received: datetime = db.Column(db.DateTime, nullable=True)
|
||||
id_location_storage: int = db.Column(db.Integer)
|
||||
id_currency_cost: int = db.Column(db.Integer)
|
||||
cost_local_VAT_excl: float = db.Column(db.Float)
|
||||
cost_local_VAT_incl: float = db.Column(db.Float)
|
||||
is_sealed: bool = db.Column(db.Boolean)
|
||||
date_unsealed: datetime = db.Column(db.DateTime, nullable=True)
|
||||
date_expiration: datetime = db.Column(db.DateTime, nullable=True)
|
||||
is_consumed: bool = db.Column(db.Boolean)
|
||||
date_consumed: datetime = db.Column(db.DateTime, nullable=True)
|
||||
active: bool = db.Column(db.Boolean)
|
||||
guid: str = db.Column(db.String(36))
|
||||
|
||||
@classmethod
|
||||
def from_stock_item(cls, stock_item):
|
||||
row = cls()
|
||||
row.id_stock = stock_item.id_stock
|
||||
# row.id_category = stock_item.id_category
|
||||
row.id_product = stock_item.id_product
|
||||
row.id_permutation = stock_item.id_permutation
|
||||
# row.has_variations = stock_item.has_variations
|
||||
row.id_pairs_variations = stock_item.variation_tree.to_json_str() if stock_item.variation_tree is not None else ''
|
||||
row.date_purchased = stock_item.date_purchased
|
||||
row.date_received = stock_item.date_received if stock_item.date_received else None
|
||||
row.id_location_storage = stock_item.id_location_storage
|
||||
row.id_currency_cost = stock_item.id_currency_cost
|
||||
row.cost_local_VAT_excl = stock_item.cost_local_VAT_excl
|
||||
row.cost_local_VAT_incl = stock_item.cost_local_VAT_incl
|
||||
row.is_sealed = 1 if stock_item.is_sealed else 0
|
||||
row.date_unsealed = stock_item.date_unsealed if stock_item.date_unsealed else None
|
||||
row.date_expiration = stock_item.date_expiration if stock_item.date_expiration else None
|
||||
row.is_consumed = 1 if stock_item.is_consumed else 0
|
||||
row.date_consumed = stock_item.date_consumed if stock_item.date_consumed else None
|
||||
row.active = 1 if stock_item.active else 0
|
||||
return row
|
||||
def __repr__(self):
|
||||
return f'''
|
||||
id_stock: {self.id_stock}
|
||||
id_product: {self.id_product}
|
||||
id_permutation: {self.id_permutation}
|
||||
id_pairs_variations: {self.id_pairs_variations}
|
||||
date_purchased: {self.date_purchased}
|
||||
date_received: {self.date_received}
|
||||
id_location_storage: {self.id_location_storage}
|
||||
id_currency_cost: {self.id_currency_cost}
|
||||
cost_local_VAT_excl: {self.cost_local_VAT_excl}
|
||||
cost_local_VAT_incl: {self.cost_local_VAT_incl}
|
||||
is_sealed: {self.is_sealed}
|
||||
date_unsealed: {self.date_unsealed}
|
||||
date_expiration: {self.date_expiration}
|
||||
is_consumed: {self.is_consumed}
|
||||
date_consumed: {self.date_consumed}
|
||||
active: {self.active}
|
||||
guid: {self.guid}
|
||||
'''
|
||||
@@ -12,6 +12,7 @@ Business object for product
|
||||
|
||||
# internal
|
||||
import lib.argument_validation as av
|
||||
from business_objects.store.plant import Plant
|
||||
from business_objects.store.store_base import Store_Base
|
||||
from extensions import db
|
||||
# external
|
||||
@@ -28,18 +29,32 @@ class Storage_Location(db.Model, Store_Base):
|
||||
name = db.Column(db.String(255))
|
||||
active = db.Column(db.Boolean)
|
||||
|
||||
# plant = None
|
||||
|
||||
def __init__(self):
|
||||
super().__init__()
|
||||
Store_Base.__init__(self)
|
||||
self.plant = None
|
||||
|
||||
@classmethod
|
||||
def from_DB_storage_location(cls, query_row):
|
||||
location = cls()
|
||||
location.id_location = query_row[0]
|
||||
location.id_plant = query_row[1]
|
||||
location.plant = Plant.from_DB_storage_location(query_row)
|
||||
location.code = query_row[2]
|
||||
location.name = query_row[3]
|
||||
location.active = query_row[4]
|
||||
return location
|
||||
@classmethod
|
||||
def from_DB_stock_item(cls, query_row):
|
||||
location = cls()
|
||||
location.id_location = query_row[4]
|
||||
location.id_plant = query_row[5]
|
||||
location.code = query_row[8]
|
||||
location.name = query_row[9]
|
||||
location.plant = Plant.from_DB_stock_item(query_row)
|
||||
return location
|
||||
def __repr__(self):
|
||||
return f'''
|
||||
{self.ATTR_ID_STORAGE_LOCATION}: {self.id_location}
|
||||
@@ -67,3 +82,6 @@ class Storage_Location(db.Model, Store_Base):
|
||||
location.name = json[cls.FLAG_NAME],
|
||||
location.active = json[cls.FLAG_ACTIVE]
|
||||
return location
|
||||
|
||||
def get_full_name(self):
|
||||
return f'{self.plant.name} - {self.name}'
|
||||
@@ -58,9 +58,9 @@ class I_Store_Base():
|
||||
|
||||
class Store_Base(Base):
|
||||
# ATTR_ID_CURRENCY_COST: ClassVar[str] = 'id_currency_cost'
|
||||
ATTR_ID_DELIVERY_OPTION: ClassVar[str] = 'id_delivery_option'
|
||||
ATTR_ID_DISCOUNT: ClassVar[str] = 'id_discount'
|
||||
ATTR_ID_IMAGE: ClassVar[str] = 'id_image'
|
||||
ATTR_ID_LOCATION_STORAGE: ClassVar[str] = 'id_location_storage'
|
||||
ATTR_ID_PLANT: ClassVar[str] = 'id_plant'
|
||||
ATTR_ID_PRODUCT: ClassVar[str] = 'id_product'
|
||||
ATTR_ID_PRODUCT_CATEGORY: ClassVar[str] = 'id_category'
|
||||
@@ -70,10 +70,15 @@ class Store_Base(Base):
|
||||
ATTR_ID_PRODUCT_VARIATION: ClassVar[str] = 'id_variation'
|
||||
ATTR_ID_PRODUCT_VARIATION_TYPE: ClassVar[str] = 'id_type'
|
||||
ATTR_ID_STOCK_ITEM: ClassVar[str] = 'id_stock_item'
|
||||
FLAG_CURRENCY: ClassVar[str] = 'currency'
|
||||
ATTR_ID_STORAGE_LOCATION: ClassVar[str] = 'id_location'
|
||||
FLAG_COST_LOCAL: ClassVar[str] = 'cost_local'
|
||||
FLAG_COST_LOCAL_VAT_EXCL: ClassVar[str] = FLAG_COST_LOCAL + '_vat_excl'
|
||||
FLAG_COST_LOCAL_VAT_INCL: ClassVar[str] = FLAG_COST_LOCAL + '_vat_incl'
|
||||
FLAG_DELIVERY_OPTION: ClassVar[str] = 'delivery_option'
|
||||
FLAG_HAS_VARIATIONS: ClassVar[str] = 'has_variations'
|
||||
FLAG_IS_OUT_OF_STOCK: ClassVar[str] = 'is_out_of_stock'
|
||||
FLAG_DISCOUNT: ClassVar[str] = 'discount'
|
||||
FLAG_PLANT: ClassVar[str] = 'plant'
|
||||
FLAG_PRODUCT: ClassVar[str] = 'product'
|
||||
FLAG_PRODUCT_CATEGORY: ClassVar[str] = 'product_category'
|
||||
FLAG_PRODUCT_IMAGE: ClassVar[str] = 'product_image'
|
||||
@@ -85,6 +90,7 @@ class Store_Base(Base):
|
||||
FLAG_QUANTITY_MIN: ClassVar[str] = 'quantity_min'
|
||||
FLAG_QUANTITY_MAX: ClassVar[str] = 'quantity_max'
|
||||
FLAG_STOCK_ITEM: ClassVar[str] = 'stock_item'
|
||||
FLAG_STORAGE_LOCATION: ClassVar[str] = 'storage_location'
|
||||
FLAG_TEXT: ClassVar[str] = 'text'
|
||||
FLAG_VALUE_TEXT: ClassVar[str] = 'value_text'
|
||||
|
||||
@@ -38,7 +38,9 @@ class User(db.Model, Base):
|
||||
# is_logged_in: bool
|
||||
|
||||
def __init__(self):
|
||||
self.id_user = 0
|
||||
self.is_logged_in = False
|
||||
super().__init__()
|
||||
|
||||
def from_DB_user(query_row):
|
||||
_m = 'User.from_DB_user'
|
||||
@@ -62,7 +64,7 @@ class User(db.Model, Base):
|
||||
_m = 'User.from_json'
|
||||
user = User()
|
||||
if json is None: return user
|
||||
print(f'json: {json}')
|
||||
print(f'{_m}\njson: {json}')
|
||||
user.id_user = json['id_user']
|
||||
user.id_user_auth0 = json['id_user_auth0']
|
||||
user.firstname = json['firstname']
|
||||
@@ -85,7 +87,7 @@ class User(db.Model, Base):
|
||||
_m = 'User.from_json_auth0'
|
||||
user = User()
|
||||
if json is None: return user
|
||||
print(f'json: {json}')
|
||||
print(f'{_m}\njson: {json}')
|
||||
user_info = json['userinfo']
|
||||
user.id_user = None
|
||||
user.id_user_auth0 = user_info['sub']
|
||||
@@ -136,11 +138,6 @@ class User(db.Model, Base):
|
||||
can_admin_user: {self.can_admin_user}
|
||||
'''
|
||||
|
||||
@staticmethod
|
||||
def get_default():
|
||||
user = User()
|
||||
user.id_user = None
|
||||
return user
|
||||
|
||||
|
||||
@dataclass
|
||||
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -88,6 +88,11 @@ def services():
|
||||
def admin_home():
|
||||
try:
|
||||
model = Model_View_Admin_Home()
|
||||
if not model.is_user_logged_in:
|
||||
# return redirect(url_for('routes_user.login', callback = Model_View_Admin_Home.HASH_PAGE_ADMIN_HOME))
|
||||
return redirect(url_for('routes_core.home'))
|
||||
if not (model.user.can_admin_store or model.user.can_admin_user):
|
||||
return redirect(url_for('routes_core.home'))
|
||||
html_body = render_template('pages/core/_admin_home.html', model = model)
|
||||
except Exception as e:
|
||||
return jsonify(error=str(e)), 403
|
||||
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -111,6 +111,9 @@ def products():
|
||||
form_filters = Filters_Product()
|
||||
print(f'form_filters={form_filters}')
|
||||
model = Model_View_Store_Product(form_filters)
|
||||
if not model.is_user_logged_in:
|
||||
# return redirect(url_for('routes_user.login', data = jsonify({ Model_View_Store_Product.KEY_CALLBACK: Model_View_Store_Product.HASH_PAGE_STORE_PRODUCTS })))
|
||||
return redirect(url_for('routes_core.home'))
|
||||
return render_template('pages/store/_products.html', model = model)
|
||||
|
||||
@routes_store_product.route(Model_View_Store_Product.HASH_GET_STORE_PRODUCT, methods=['POST'])
|
||||
@@ -124,6 +127,8 @@ def filter_product():
|
||||
Model_View_Store_Product.FLAG_MESSAGE: f'Form invalid.\n{form_filters.errors}'
|
||||
})
|
||||
model = Model_View_Store_Product(form_filters = form_filters)
|
||||
if not model.is_user_logged_in:
|
||||
raise Exception('User not logged in')
|
||||
return jsonify({
|
||||
Model_View_Store_Product.FLAG_STATUS: Model_View_Store_Product.FLAG_SUCCESS,
|
||||
Model_View_Store_Product.KEY_DATA: model.category_list.to_json()
|
||||
@@ -161,6 +166,8 @@ def save_product():
|
||||
save_errors = Model_View_Store_Product.save_products(data.get('comment', 'No comment'), objsProduct)
|
||||
|
||||
model_return = Model_View_Store_Product(form_filters=form_filters)
|
||||
if not model_return.is_user_logged_in:
|
||||
raise Exception('User not logged in')
|
||||
print('nips')
|
||||
return jsonify({
|
||||
Model_View_Store_Product.FLAG_STATUS: Model_View_Store_Product.FLAG_SUCCESS,
|
||||
|
||||
@@ -54,6 +54,9 @@ def categories():
|
||||
return redirect(url_for('routes_store_product_category.categories', **filters.to_json()))
|
||||
"""
|
||||
model = Model_View_Store_Product_Category(form_filters)
|
||||
if not model.is_user_logged_in:
|
||||
# return redirect(url_for('routes_user.login', data = jsonify({ Model_View_Store_Product_Category.KEY_CALLBACK: Model_View_Store_Product_Category.HASH_PAGE_STORE_PRODUCT_CATEGORIES })))
|
||||
return redirect(url_for('routes_core.home'))
|
||||
return render_template('pages/store/_product_categories.html', model = model)
|
||||
|
||||
@routes_store_product_category.route(Model_View_Store_Product_Category.HASH_GET_STORE_PRODUCT_CATEGORY, methods=['POST'])
|
||||
@@ -70,6 +73,8 @@ def filter_category():
|
||||
# ToDo: manually validate category, product
|
||||
# filters_form = Filters_Product_Category.from_form(form_filters)
|
||||
model = Model_View_Store_Product_Category(form_filters = form_filters)
|
||||
if not model.is_user_logged_in:
|
||||
raise Exception('User not logged in')
|
||||
return jsonify({
|
||||
Model_View_Store_Product_Category.FLAG_STATUS: Model_View_Store_Product_Category.FLAG_SUCCESS,
|
||||
Model_View_Store_Product_Category.KEY_DATA: model.category_list.to_json()
|
||||
@@ -106,7 +111,8 @@ def save_category():
|
||||
Model_View_Store_Product_Category.save_categories(data.get('comment', 'No comment'), objsCategory)
|
||||
|
||||
model_return = Model_View_Store_Product_Category(form_filters=form_filters)
|
||||
print('nips')
|
||||
if not model_return.is_user_logged_in:
|
||||
raise Exception('User not logged in')
|
||||
return jsonify({
|
||||
Model_View_Store_Product_Category.FLAG_STATUS: Model_View_Store_Product_Category.FLAG_SUCCESS,
|
||||
Model_View_Store_Product_Category.KEY_DATA: model_return.category_list.to_json()
|
||||
|
||||
@@ -96,6 +96,9 @@ def permutations():
|
||||
form_filters = Filters_Product_Permutation()
|
||||
print(f'form_filters={form_filters}')
|
||||
model = Model_View_Store_Product_Permutation(form_filters)
|
||||
if not model.is_user_logged_in:
|
||||
# return redirect(url_for('routes_user.login', data = jsonify({ Model_View_Store_Product_Permutation.KEY_CALLBACK: Model_View_Store_Product_Permutation.HASH_PAGE_STORE_PRODUCT_PERMUTATIONS })))
|
||||
return redirect(url_for('routes_core.home'))
|
||||
return render_template('pages/store/_product_permutations.html', model = model)
|
||||
|
||||
@routes_store_product_permutation.route(Model_View_Store_Product_Permutation.HASH_GET_STORE_PRODUCT_PERMUTATION, methods=['POST'])
|
||||
@@ -109,6 +112,8 @@ def filter_permutation():
|
||||
Model_View_Store_Product_Permutation.FLAG_MESSAGE: f'Form invalid.\n{form_filters.errors}'
|
||||
})
|
||||
model = Model_View_Store_Product_Permutation(form_filters = form_filters)
|
||||
if not model.is_user_logged_in:
|
||||
raise Exception('User not logged in')
|
||||
return jsonify({
|
||||
Model_View_Store_Product_Permutation.FLAG_STATUS: Model_View_Store_Product_Permutation.FLAG_SUCCESS,
|
||||
Model_View_Store_Product_Permutation.KEY_DATA: model.category_list.to_json()
|
||||
@@ -146,6 +151,8 @@ def save_permutation():
|
||||
Model_View_Store_Product_Permutation.save_permutations(data.get('comment', 'No comment'), objsPermutation)
|
||||
|
||||
model_return = Model_View_Store_Product_Permutation(form_filters=form_filters)
|
||||
if not model_return.is_user_logged_in:
|
||||
raise Exception('User not logged in')
|
||||
print('nips')
|
||||
return jsonify({
|
||||
Model_View_Store_Product_Permutation.FLAG_STATUS: Model_View_Store_Product_Permutation.FLAG_SUCCESS,
|
||||
|
||||
@@ -11,91 +11,26 @@ Initializes the Flask application, sets the configuration based on the environme
|
||||
"""
|
||||
|
||||
# internal
|
||||
from business_objects.store.product import Product, Parameters_Product, Product_Permutation
|
||||
from business_objects.store.stock_item import Stock_Item
|
||||
from forms.store.stock_item import Filters_Stock_Item
|
||||
from models.model_view_base import Model_View_Base
|
||||
from models.model_view_store import Model_View_Store
|
||||
from models.model_view_store_supplier import Model_View_Store_Supplier
|
||||
from models.model_view_store_product_category import Model_View_Store_Product_Category
|
||||
from models.model_view_store_product_permutation import Model_View_Store_Product_Permutation
|
||||
from models.model_view_store_stock_item import Model_View_Store_Stock_Item
|
||||
from helpers.helper_app import Helper_App
|
||||
import lib.argument_validation as av
|
||||
# external
|
||||
from datetime import datetime
|
||||
from flask import Flask, render_template, jsonify, request, render_template_string, send_from_directory, redirect, url_for, session, Blueprint, current_app
|
||||
from extensions import db, oauth
|
||||
from urllib.parse import quote_plus, urlencode
|
||||
from authlib.integrations.flask_client import OAuth
|
||||
from authlib.integrations.base_client import OAuthError
|
||||
from urllib.parse import quote, urlparse, parse_qs
|
||||
|
||||
import requests
|
||||
|
||||
routes_store_stock_item = Blueprint('routes_store_stock_item', __name__)
|
||||
|
||||
"""
|
||||
@routes_store_stock_item.route('/store/stock_items', methods=['GET'])
|
||||
def stock():
|
||||
filters = Filters_Stock_Item.get_default()
|
||||
model = Model_View_Store_Stock_Item(filters_stock_item=filters)
|
||||
return render_template('pages/store/_stock_items.html', model = model)
|
||||
|
||||
@routes_store_stock_item.route('/store/stock_item_filter', methods=['POST'])
|
||||
def stock_filter():
|
||||
data = Helper_App.get_request_data(request)
|
||||
form_filters = None
|
||||
try:
|
||||
form_filters = get_Filters_Stock_Items(data)
|
||||
if not form_filters.validate_on_submit():
|
||||
return jsonify({Model_View_Base.FLAG_STATUS: Model_View_Base.FLAG_FAILURE, Model_View_Base.FLAG_MESSAGE: f'Form invalid.\n{form_filters.errors}'})
|
||||
# ToDo: manually validate category, product
|
||||
filters_form = Filters_Stock_Item.from_form(form_filters)
|
||||
model = Model_View_Store_Stock_Item(filters_stock_item=filters_form)
|
||||
return jsonify({Model_View_Base.FLAG_STATUS: Model_View_Base.FLAG_SUCCESS, 'Success': True, Model_View_Base.KEY_DATA: model.category_list.to_permutation_row_list()})
|
||||
except Exception as e:
|
||||
return jsonify({Model_View_Base.FLAG_STATUS: Model_View_Base.FLAG_FAILURE, Model_View_Base.FLAG_MESSAGE: f'Bad data received by controller.\n{e}'})
|
||||
|
||||
def get_Filters_Stock_Items(data_request):
|
||||
data_form = data_request[Model_View_Store_Stock_Item.KEY_FORM]
|
||||
form_filters = Filters_Stock_Item(**data_form)
|
||||
form_filters.is_out_of_stock.data = av.input_bool(data_form['is_out_of_stock'], 'is_out_of_stock', 'permutations_post')
|
||||
return form_filters
|
||||
|
||||
@routes_store_stock_item.route('/store/stock_item_save', methods=['POST'])
|
||||
def stock_save():
|
||||
data = Helper_App.get_request_data(request)
|
||||
""
|
||||
form_filters = None
|
||||
try:
|
||||
form_filters = get_Filters_Stock_Items(data)
|
||||
if not form_filters.validate_on_submit():
|
||||
return jsonify({Model_View_Base.FLAG_STATUS: Model_View_Base.FLAG_FAILURE, Model_View_Base.FLAG_MESSAGE: f'Filters form invalid.\n{form_filters.errors}'})
|
||||
|
||||
stock_items = data[Model_View_Store_Stock.KEY_PERMUTATIONS]
|
||||
print(f'stock_items: {stock_items}')
|
||||
if len(stock_items) == 0:
|
||||
return jsonify({Model_View_Base.FLAG_STATUS: Model_View_Base.FLAG_FAILURE, Model_View_Base.FLAG_MESSAGE: f'No stock items.'})
|
||||
objsStockItem = []
|
||||
for stock_item in stock_items:
|
||||
objsStockItem.append(Product_Permutation.from_json(stock_item))
|
||||
print(f'objsStockItem: {objsStockItem}')
|
||||
|
||||
# ToDo: manually validate category, product
|
||||
filters_form = Stock_Filters.from_form(form_filters)
|
||||
model_save = Model_View_Store_Stock(filters_product=filters_form)
|
||||
model_save.save_stock_items(data.comment, objsPermutation)
|
||||
|
||||
model_return = Model_View_Store_Stock(filters_product=filters_form)
|
||||
return jsonify({Model_View_Base.FLAG_STATUS: Model_View_Base.FLAG_SUCCESS, 'Success': True, Model_View_Base.KEY_DATA: model_return.category_list.to_permutation_row_list()})
|
||||
except Exception as e:
|
||||
return jsonify({Model_View_Base.FLAG_STATUS: Model_View_Base.FLAG_FAILURE, Model_View_Base.FLAG_MESSAGE: f'Bad data received by controller.\n{e}'})
|
||||
""
|
||||
"""
|
||||
|
||||
|
||||
@routes_store_stock_item.route(Model_View_Store_Stock_Item.HASH_PAGE_STORE_STOCK_ITEMS, methods=['GET'])
|
||||
def permutations():
|
||||
print('permutations')
|
||||
def stock_items():
|
||||
print('stock_items')
|
||||
try:
|
||||
form_filters = Filters_Stock_Item.from_json(request.args)
|
||||
except Exception as e:
|
||||
@@ -103,19 +38,39 @@ def permutations():
|
||||
form_filters = Filters_Stock_Item()
|
||||
print(f'form_filters={form_filters}')
|
||||
model = Model_View_Store_Stock_Item(form_filters)
|
||||
return render_template('pages/store/_stock_items.html', model = model)
|
||||
if not model.is_user_logged_in:
|
||||
# return redirect(url_for('routes_user.login', data = jsonify({ Model_View_Store_Stock_Item.KEY_CALLBACK: Model_View_Store_Stock_Item.HASH_PAGE_STORE_STOCK_ITEMS })))
|
||||
# return requests.post(f"{current_app.config['URL_HOST']}{url_for('routes_user.login')}", json={ Model_View_Store_Stock_Item.KEY_CALLBACK: Model_View_Store_Stock_Item.HASH_PAGE_STORE_STOCK_ITEMS })
|
||||
return redirect(url_for('routes_core.home'))
|
||||
return render_template('pages/store/_stock_items.html', model = model, datetime = datetime)
|
||||
|
||||
@routes_store_stock_item.route(Model_View_Store_Stock_Item.HASH_GET_STORE_STOCK_ITEM, methods=['POST'])
|
||||
def filter_permutation():
|
||||
def filter_stock_item():
|
||||
data = Helper_App.get_request_data(request)
|
||||
try:
|
||||
form_filters = Filters_Stock_Item.from_json(data)
|
||||
if not form_filters.validate_on_submit():
|
||||
return jsonify({
|
||||
Model_View_Store_Stock_Item.FLAG_STATUS: Model_View_Store_Stock_Item.FLAG_FAILURE,
|
||||
Model_View_Store_Stock_Item.FLAG_MESSAGE: f'Form invalid.\n{form_filters.errors}'
|
||||
})
|
||||
model = Model_View_Store_Stock_Item(form_filters = form_filters)
|
||||
error_keys = list(form_filters.errors.keys())
|
||||
try:
|
||||
error_keys.remove(Stock_Item.ATTR_ID_PRODUCT_CATEGORY)
|
||||
"""
|
||||
if not av.val_int(form_filters.id_product_category.data):
|
||||
form_filters.errors[Stock_Item.ATTR_ID_PRODUCT_CATEGORY] = ['Invalid category.']
|
||||
"""
|
||||
except:
|
||||
pass
|
||||
try:
|
||||
error_keys.remove(Stock_Item.ATTR_ID_PRODUCT)
|
||||
except:
|
||||
pass
|
||||
if error_keys:
|
||||
return jsonify({
|
||||
Model_View_Store_Stock_Item.FLAG_STATUS: Model_View_Store_Stock_Item.FLAG_FAILURE,
|
||||
Model_View_Store_Stock_Item.FLAG_MESSAGE: f'Form invalid.\n{form_filters.errors}'
|
||||
})
|
||||
model = Model_View_Store_Stock_Item(filters_stock_item = form_filters)
|
||||
if not model.is_user_logged_in:
|
||||
raise Exception('User not logged in.')
|
||||
return jsonify({
|
||||
Model_View_Store_Stock_Item.FLAG_STATUS: Model_View_Store_Stock_Item.FLAG_SUCCESS,
|
||||
Model_View_Store_Stock_Item.KEY_DATA: model.category_list.to_json()
|
||||
@@ -127,33 +82,55 @@ def filter_permutation():
|
||||
})
|
||||
|
||||
@routes_store_stock_item.route(Model_View_Store_Stock_Item.HASH_SAVE_STORE_STOCK_ITEM, methods=['POST'])
|
||||
def save_permutation():
|
||||
def save_stock_item():
|
||||
data = Helper_App.get_request_data(request)
|
||||
try:
|
||||
form_filters = Filters_Stock_Item.from_json(data[Model_View_Store_Stock_Item.FLAG_FORM_FILTERS])
|
||||
"""
|
||||
if not form_filters.validate_on_submit():
|
||||
return jsonify({
|
||||
Model_View_Store_Stock_Item.FLAG_STATUS: Model_View_Store_Stock_Item.FLAG_FAILURE,
|
||||
Model_View_Store_Stock_Item.FLAG_MESSAGE: f'Filters form invalid.\n{form_filters.errors}'
|
||||
})
|
||||
error_keys = list(form_filters.errors.keys())
|
||||
try:
|
||||
error_keys.remove(Stock_Item.ATTR_ID_PRODUCT_CATEGORY)
|
||||
""
|
||||
if not av.val_int(form_filters.id_product_category.data):
|
||||
form_filters.errors[Stock_Item.ATTR_ID_PRODUCT_CATEGORY] = ['Invalid category.']
|
||||
""
|
||||
except:
|
||||
pass
|
||||
try:
|
||||
error_keys.remove(Stock_Item.ATTR_ID_PRODUCT)
|
||||
except:
|
||||
pass
|
||||
if error_keys:
|
||||
return jsonify({
|
||||
Model_View_Store_Stock_Item.FLAG_STATUS: Model_View_Store_Stock_Item.FLAG_FAILURE,
|
||||
Model_View_Store_Stock_Item.FLAG_MESSAGE: f'Form invalid.\n{form_filters.errors}'
|
||||
})
|
||||
"""
|
||||
# filters_form = Filters_Stock_Item.from_form(form_filters)
|
||||
print(f'form_filters: {form_filters}')
|
||||
|
||||
permutations = data[Model_View_Store_Stock_Item.FLAG_STOCK_ITEM]
|
||||
if len(permutations) == 0:
|
||||
stock_items = data[Model_View_Store_Stock_Item.FLAG_STOCK_ITEM]
|
||||
if len(stock_items) == 0:
|
||||
return jsonify({
|
||||
Model_View_Store_Stock_Item.FLAG_STATUS: Model_View_Store_Stock_Item.FLAG_FAILURE,
|
||||
Model_View_Store_Stock_Item.FLAG_MESSAGE: f'No permutations.'
|
||||
Model_View_Store_Stock_Item.FLAG_MESSAGE: f'No stock items.'
|
||||
})
|
||||
objsPermutation = []
|
||||
for permutation in permutations:
|
||||
objsPermutation.append(Stock_Item.from_json(permutation))
|
||||
print(f'stock_items={stock_items}')
|
||||
objs_stock_item = []
|
||||
for stock_item in stock_items:
|
||||
objs_stock_item.append(Stock_Item.from_json(stock_item))
|
||||
# model_save = Model_View_Store_Stock_Item() # filters_product=filters_form)
|
||||
print(f'objsPermutation={objsPermutation}')
|
||||
Model_View_Store_Stock_Item.save_permutations(data.get('comment', 'No comment'), objsPermutation)
|
||||
|
||||
model_return = Model_View_Store_Stock_Item(form_filters=form_filters)
|
||||
print('nips')
|
||||
print(f'objs_stock_item={objs_stock_item}')
|
||||
save_errors = Model_View_Store_Stock_Item.save_stock_items(data.get('comment', 'No comment'), objs_stock_item)
|
||||
if len(save_errors) > 0:
|
||||
return jsonify({
|
||||
Model_View_Store_Stock_Item.FLAG_STATUS: Model_View_Store_Stock_Item.FLAG_FAILURE,
|
||||
Model_View_Store_Stock_Item.FLAG_MESSAGE: f'Save errors: {save_errors}'
|
||||
})
|
||||
model_return = Model_View_Store_Stock_Item(filters_stock_item=form_filters)
|
||||
if not model_return.is_user_logged_in:
|
||||
raise Exception('User not logged in.')
|
||||
return jsonify({
|
||||
Model_View_Store_Stock_Item.FLAG_STATUS: Model_View_Store_Stock_Item.FLAG_SUCCESS,
|
||||
Model_View_Store_Stock_Item.KEY_DATA: model_return.category_list.to_json()
|
||||
|
||||
@@ -53,6 +53,9 @@ def supplier():
|
||||
# if not logged in:
|
||||
try:
|
||||
model = Model_View_Store_Supplier(form)
|
||||
if not model.is_user_logged_in:
|
||||
# return redirect(url_for('routes_user.login', data = jsonify({ Model_View_Store_Supplier.KEY_CALLBACK: Model_View_Store_Supplier.HASH_PAGE_STORE_SUPPLIERS })))
|
||||
return redirect(url_for('routes_core.home'))
|
||||
# print('importing basket')
|
||||
# model.import_JSON_basket(data)
|
||||
model.get_basket(data)
|
||||
|
||||
@@ -170,6 +170,9 @@ def logout_callback():
|
||||
def user():
|
||||
try:
|
||||
model = Model_View_User(current_app, db)
|
||||
if not model.is_user_logged_in:
|
||||
# return redirect(url_for('routes_user.login', data = jsonify({ Model_View_User.KEY_CALLBACK: Model_View_User.HASH_PAGE_USER_ACCOUNT })))
|
||||
return redirect(url_for('routes_core.home'))
|
||||
html_body = render_template('pages/user/_user.html', model = model)
|
||||
except Exception as e:
|
||||
return str(e)
|
||||
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -20,7 +20,7 @@ from business_objects.store.product_category import Product_Category_Container,
|
||||
from business_objects.store.currency import Currency
|
||||
from business_objects.store.image import Image
|
||||
from business_objects.store.delivery_option import Delivery_Option
|
||||
from business_objects.store.delivery_region import Delivery_Region
|
||||
from business_objects.store.delivery_region import Region
|
||||
from business_objects.store.discount import Discount
|
||||
from business_objects.store.order import Order
|
||||
from business_objects.store.product import Product, Product_Permutation, Product_Price, Parameters_Product # Permutation_Variation_Link
|
||||
@@ -145,7 +145,7 @@ class DataStore_Base(BaseModel):
|
||||
result_set_1 = cursor.fetchall()
|
||||
regions = []
|
||||
for row in result_set_1:
|
||||
region = Delivery_Region.make_from_DB_region(row)
|
||||
region = Region.make_from_DB_region(row)
|
||||
regions.append(region)
|
||||
print(f'regions: {regions}')
|
||||
DataStore_Base.db_cursor_clear(cursor)
|
||||
|
||||
@@ -14,10 +14,10 @@ Datastore for Store
|
||||
# from routes import bp_home
|
||||
from business_objects.store.basket import Basket, Basket_Item
|
||||
from business_objects.store.product_category import Product_Category_Container, Product_Category
|
||||
from business_objects.store.currency import Currency
|
||||
from business_objects.currency import Currency
|
||||
from business_objects.store.image import Image
|
||||
from business_objects.store.delivery_option import Delivery_Option
|
||||
from business_objects.store.delivery_region import Delivery_Region
|
||||
from business_objects.region import Region
|
||||
from business_objects.store.discount import Discount
|
||||
from business_objects.store.order import Order
|
||||
from business_objects.store.product import Product, Product_Permutation, Parameters_Product
|
||||
@@ -235,7 +235,7 @@ class DataStore_Store_Base(DataStore_Base):
|
||||
result_set_1 = cursor.fetchall()
|
||||
regions = []
|
||||
for row in result_set_1:
|
||||
region = Delivery_Region.from_DB_region(row)
|
||||
region = Region.from_DB_region(row)
|
||||
regions.append(region)
|
||||
print(f'regions: {regions}')
|
||||
DataStore_Store_Base.db_cursor_clear(cursor)
|
||||
|
||||
@@ -15,10 +15,10 @@ Datastore for Store Baskets
|
||||
import lib.argument_validation as av
|
||||
from business_objects.store.basket import Basket, Basket_Item
|
||||
from business_objects.store.product_category import Product_Category_Container, Product_Category
|
||||
from business_objects.store.currency import Currency
|
||||
from business_objects.currency import Currency
|
||||
from business_objects.store.image import Image
|
||||
from business_objects.store.delivery_option import Delivery_Option
|
||||
from business_objects.store.delivery_region import Delivery_Region
|
||||
from business_objects.region import Region
|
||||
from business_objects.store.discount import Discount
|
||||
from business_objects.store.order import Order
|
||||
from business_objects.store.product import Product, Product_Permutation, Product_Price, Parameters_Product
|
||||
|
||||
@@ -14,10 +14,10 @@ Datastore for Store Product Categories
|
||||
import lib.argument_validation as av
|
||||
from business_objects.store.basket import Basket, Basket_Item
|
||||
from business_objects.store.product_category import Product_Category_Container, Product_Category, Product_Category_Temp
|
||||
from business_objects.store.currency import Currency
|
||||
from business_objects.currency import Currency
|
||||
from business_objects.store.image import Image
|
||||
from business_objects.store.delivery_option import Delivery_Option
|
||||
from business_objects.store.delivery_region import Delivery_Region
|
||||
from business_objects.region import Region
|
||||
from business_objects.store.discount import Discount
|
||||
from business_objects.store.order import Order
|
||||
from business_objects.store.product import Product, Product_Permutation, Product_Price, Parameters_Product
|
||||
|
||||
@@ -15,10 +15,10 @@ Datastore for Store Product Variations
|
||||
import lib.argument_validation as av
|
||||
from business_objects.store.basket import Basket, Basket_Item
|
||||
from business_objects.store.product_category import Product_Category_Container, Product_Category
|
||||
from business_objects.store.currency import Currency
|
||||
from business_objects.currency import Currency
|
||||
from business_objects.store.image import Image
|
||||
from business_objects.store.delivery_option import Delivery_Option
|
||||
from business_objects.store.delivery_region import Delivery_Region
|
||||
from business_objects.region import Region
|
||||
from business_objects.store.discount import Discount
|
||||
from business_objects.store.order import Order
|
||||
from business_objects.store.product import Product, Product_Permutation, Product_Price, Parameters_Product
|
||||
|
||||
@@ -13,21 +13,10 @@ Datastore for Store Stock Items
|
||||
# internal
|
||||
# from routes import bp_home
|
||||
import lib.argument_validation as av
|
||||
from business_objects.store.basket import Basket, Basket_Item
|
||||
from business_objects.store.product_category import Product_Category_Container, Product_Category
|
||||
from business_objects.store.currency import Currency
|
||||
from business_objects.store.image import Image
|
||||
from business_objects.store.delivery_option import Delivery_Option
|
||||
from business_objects.store.delivery_region import Delivery_Region
|
||||
from business_objects.store.discount import Discount
|
||||
from business_objects.store.order import Order
|
||||
from business_objects.store.product import Product, Product_Permutation, Product_Price, Parameters_Product
|
||||
from business_objects.sql_error import SQL_Error
|
||||
from business_objects.store.stock_item import Stock_Item
|
||||
from business_objects.user import User, User_Filters, User_Permission_Evaluation
|
||||
from business_objects.store.product_variation import Product_Variation, Product_Variation_Filters, Product_Variation_Container
|
||||
from business_objects.store.stock_item import Stock_Item, Parameters_Stock_Item, Stock_Item_Temp
|
||||
from datastores.datastore_store_base import DataStore_Store_Base
|
||||
# from helpers.helper_db_mysql import Helper_DB_MySQL
|
||||
from helpers.helper_db_mysql import Helper_DB_MySQL
|
||||
# from models.model_view_store_checkout import Model_View_Store_Checkout # circular!
|
||||
from extensions import db
|
||||
# external
|
||||
@@ -52,11 +41,11 @@ class DataStore_Store_Stock_Item(DataStore_Store_Base):
|
||||
super().__init__()
|
||||
|
||||
# Stock Items
|
||||
def get_many_stock_item(self, Parameters_Stock_Item, category_list):
|
||||
def get_many_stock_item(self, parameters_stock_item, category_list):
|
||||
# redundant argument validation?
|
||||
_m = 'DataStore_Store_Stock_Item.get_many_stock_item'
|
||||
av.val_instance(Parameters_Stock_Item, 'Parameters_Stock_Item', _m, Parameters_Stock_Item)
|
||||
argument_dict = Parameters_Stock_Item.to_json()
|
||||
av.val_instance(parameters_stock_item, 'parameters_stock_item', _m, Parameters_Stock_Item)
|
||||
argument_dict = parameters_stock_item.to_json()
|
||||
user = self.get_user_session()
|
||||
"""
|
||||
argument_dict['a_id_user'] = user.id_user # 'auth0|6582b95c895d09a70ba10fef' # id_user
|
||||
@@ -67,6 +56,9 @@ class DataStore_Store_Stock_Item(DataStore_Store_Base):
|
||||
, **argument_dict
|
||||
, 'a_debug': 0
|
||||
}
|
||||
ids_permutation = category_list.get_csv_ids_permutation()
|
||||
print(f'ids_permutation: {ids_permutation}')
|
||||
argument_dict['a_ids_product_permutation'] = ids_permutation
|
||||
print(f'argument_dict: {argument_dict}')
|
||||
print('executing p_shop_get_many_stock_item')
|
||||
result = self.db_procedure_execute('p_shop_get_many_stock_item', argument_dict)
|
||||
@@ -85,7 +77,7 @@ class DataStore_Store_Stock_Item(DataStore_Store_Base):
|
||||
print(f'raw categories: {result_set_1}')
|
||||
for row in result_set_1:
|
||||
new_stock_item = Stock_Item.from_DB_stock_item(row)
|
||||
category_list.add_stock_item(new_stock_item, row)
|
||||
category_list.add_stock_item(new_stock_item) # , row)
|
||||
|
||||
# Errors
|
||||
cursor.nextset()
|
||||
@@ -112,5 +104,47 @@ class DataStore_Store_Stock_Item(DataStore_Store_Base):
|
||||
if 'region' in error.msg or 'currency' in error.msg:
|
||||
permutation.is_unavailable_in_currency_or_region = True
|
||||
"""
|
||||
DataStore_Store_Stock_Item.db_cursor_clear(cursor)
|
||||
return category_list, errors # categories, category_index
|
||||
|
||||
@classmethod
|
||||
def save_stock_items(cls, comment, stock_items):
|
||||
_m = 'DataStore_Store_Stock_Item.save_stock_items'
|
||||
av.val_str(comment, 'comment', _m)
|
||||
|
||||
guid = Helper_DB_MySQL.create_guid_str()
|
||||
now = datetime.now()
|
||||
user = cls.get_user_session()
|
||||
rows = []
|
||||
for stock_item in stock_items:
|
||||
# row = permutation.to_temporary_record()
|
||||
row = Stock_Item_Temp.from_stock_item(stock_item)
|
||||
row.guid = guid
|
||||
rows.append(row)
|
||||
|
||||
print(f'rows: {rows}')
|
||||
|
||||
DataStore_Store_Base.upload_bulk(Stock_Item_Temp.__tablename__, rows, 1000)
|
||||
print('bulk uploaded')
|
||||
|
||||
argument_dict_list = {
|
||||
'a_comment': comment,
|
||||
'a_guid': guid,
|
||||
'a_id_user': user.id_user,
|
||||
'a_debug': 0
|
||||
}
|
||||
result = cls.db_procedure_execute('p_shop_save_stock_item', argument_dict_list)
|
||||
print('saved product permutations')
|
||||
|
||||
# Errors
|
||||
cursor = result.cursor
|
||||
cursor.nextset()
|
||||
result_set_e = cursor.fetchall()
|
||||
print(f'raw errors: {result_set_e}')
|
||||
errors = []
|
||||
if len(result_set_e) > 0:
|
||||
errors = [SQL_Error.from_DB_record(row) for row in result_set_e] # (row[0], row[1])
|
||||
for error in errors:
|
||||
print(f"Error [{error.code}]: {error.msg}")
|
||||
DataStore_Store_Stock_Item.db_cursor_clear(cursor)
|
||||
return errors
|
||||
|
||||
@@ -15,10 +15,10 @@ Datastore for Store Stripe service
|
||||
import lib.argument_validation as av
|
||||
from business_objects.store.basket import Basket, Basket_Item
|
||||
from business_objects.store.product_category import Product_Category_Container, Product_Category
|
||||
from business_objects.store.currency import Currency
|
||||
from business_objects.currency import Currency
|
||||
from business_objects.store.image import Image
|
||||
from business_objects.store.delivery_option import Delivery_Option
|
||||
from business_objects.store.delivery_region import Delivery_Region
|
||||
from business_objects.region import Region
|
||||
from business_objects.store.discount import Discount
|
||||
from business_objects.store.order import Order
|
||||
from business_objects.store.product import Product, Product_Permutation, Product_Price, Parameters_Product
|
||||
|
||||
@@ -139,6 +139,76 @@ class DataStore_User(DataStore_Base):
|
||||
'a_id_user': user.id_user
|
||||
, 'a_id_user_auth0': user.id_user_auth0
|
||||
, **user_filters.to_json()
|
||||
, 'a_debug': 0
|
||||
|
||||
}
|
||||
# argument_dict_list['a_guid'] = guid
|
||||
result = self.db_procedure_execute('p_get_many_user', argument_dict_list)
|
||||
"""
|
||||
query = text(f"SELECT * FROM Shop_Calc_User_Temp UE_T WHERE UE_T.guid = '{guid}'")
|
||||
result = self.db.session.execute(query)
|
||||
"""
|
||||
cursor = result.cursor
|
||||
result_set = cursor.fetchall()
|
||||
print(f'raw users: {result_set}')
|
||||
print(f'type result set: {str(type(result_set))}')
|
||||
print(f'len result set: {len(result_set)}')
|
||||
"""
|
||||
user_permission_evals = []
|
||||
for row in result_set:
|
||||
user_permission_eval = User_Permission_Evaluation.from_DB_user_eval(row)
|
||||
user_permission_evals.append(user_permission_eval)
|
||||
print(f'user_permission_evals: {user_permission_evals}')
|
||||
"""
|
||||
users = []
|
||||
if len(result_set) > 0:
|
||||
for row in result_set:
|
||||
print(f'row: {row}')
|
||||
user = User.from_DB_user(row)
|
||||
users.append(user)
|
||||
print(f'user {str(type(user))}: {user}')
|
||||
print(f'type users: {str(type(users))}\n type user 0: {str(type(None if len(users) == 0 else users[0]))}')
|
||||
# error_list, cursor = self.get_error_list_from_cursor(cursor)
|
||||
errors = []
|
||||
cursor.nextset()
|
||||
result_set_e = cursor.fetchall()
|
||||
print(f'raw errors: {result_set_e}')
|
||||
if len(result_set_e) > 0:
|
||||
errors = [SQL_Error.from_DB_record(row) for row in result_set_e] # [SQL_Error(row[0], row[1]) for row in result_set_e]
|
||||
for error in errors:
|
||||
print(f"Error [{error.code}]: {error.msg}")
|
||||
|
||||
DataStore_User.db_cursor_clear(cursor)
|
||||
|
||||
return users, errors
|
||||
|
||||
def get_many_user(self, user_filters, user=None):
|
||||
_m = 'DataStore_User.get_many_user'
|
||||
print(_m)
|
||||
# av.val_str(user_filters, 'user_filters', _m)
|
||||
# av.val_list(permutations, 'list_permutations', _m, Product_Permutation, 1)
|
||||
av.val_instance(user_filters, 'user_filters', _m, User_Filters)
|
||||
|
||||
guid = Helper_DB_MySQL.create_guid()
|
||||
# now = datetime.now()
|
||||
# user = self.get_user_session()
|
||||
|
||||
"""
|
||||
argument_dict_list = {
|
||||
'a_id_user': id_user,
|
||||
'a_comment': comment,
|
||||
'a_guid': guid
|
||||
}
|
||||
"""
|
||||
if user is None:
|
||||
user = self.get_user_session()
|
||||
argument_dict_list = {
|
||||
# 'a_guid': guid
|
||||
'a_id_user': user.id_user
|
||||
, 'a_id_user_auth0': user.id_user_auth0
|
||||
, **user_filters.to_json()
|
||||
, 'a_debug': 0
|
||||
|
||||
}
|
||||
# argument_dict_list['a_guid'] = guid
|
||||
result = self.db_procedure_execute('p_get_many_user', argument_dict_list)
|
||||
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -23,7 +23,7 @@ from abc import ABCMeta, abstractmethod
|
||||
|
||||
|
||||
class Filters_Access_Level(Form_Base):
|
||||
active = BooleanField("Active only?")
|
||||
active = BooleanField("Active only?", default = True)
|
||||
def __repr__(self):
|
||||
return f'{self.__class__.__name__}(active={self.active.data})'
|
||||
@classmethod
|
||||
|
||||
@@ -122,7 +122,7 @@ class Form_Supplier(FlaskForm):
|
||||
fax = StringField('Fax number')
|
||||
website = StringField('Website')
|
||||
id_currency = SelectField('Currency ID')
|
||||
is_active = BooleanField('Active')
|
||||
is_active = BooleanField('Active', default = True)
|
||||
|
||||
# class Form_Supplier_Purchase_Order(FlaskForm):
|
||||
|
||||
@@ -130,5 +130,5 @@ class Form_Supplier(FlaskForm):
|
||||
|
||||
# User
|
||||
class Form_Filters_User(FlaskForm):
|
||||
active = BooleanField('Active only?')
|
||||
active = BooleanField('Active only?', default = True)
|
||||
id_user = SelectField('User ID', validators=[Optional()], choices=[])
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -24,7 +24,7 @@ from flask_wtf.recaptcha import RecaptchaField
|
||||
class Filters_Product(FlaskForm):
|
||||
id_category = SelectField('Category', validators=[Optional()], choices=[('', 'All')])
|
||||
is_not_empty = BooleanField('Not empty only?')
|
||||
active = BooleanField("Active only?")
|
||||
active = BooleanField("Active only?", default = True)
|
||||
@classmethod
|
||||
def from_filters_product(cls, filters_product):
|
||||
form = Filters_Product()
|
||||
|
||||
@@ -27,7 +27,7 @@ from abc import ABCMeta, abstractmethod
|
||||
|
||||
class Filters_Product_Category(Form_Base):
|
||||
is_not_empty = BooleanField('Not empty only?')
|
||||
active = BooleanField("Active only?")
|
||||
active = BooleanField("Active only?", default = True)
|
||||
"""
|
||||
@classmethod
|
||||
def from_filters(cls, filters):
|
||||
|
||||
@@ -25,8 +25,8 @@ from flask_wtf.recaptcha import RecaptchaField
|
||||
from abc import ABCMeta, abstractmethod
|
||||
|
||||
class Filters_Stock_Item(Form_Base):
|
||||
id_category = SelectField('Category', validators=[Optional()], choices=[])
|
||||
id_product = SelectField('Product', validators=[Optional()], choices=[])
|
||||
id_category = SelectField('Category', choices=[Form_Base.get_choice_all()], default='')
|
||||
id_product = SelectField('Product', choices=[Form_Base.get_choice_all()], default='')
|
||||
is_out_of_stock = BooleanField('Out of stock only?')
|
||||
quantity_min = FloatField('Min stock')
|
||||
quantity_max = FloatField('Max stock')
|
||||
@@ -45,9 +45,9 @@ class Filters_Stock_Item(Form_Base):
|
||||
@classmethod
|
||||
def from_json(cls, json):
|
||||
form = cls()
|
||||
form.id_category.choices = [(json[Store_Base.ATTR_ID_PRODUCT_CATEGORY], json[Store_Base.ATTR_ID_PRODUCT_CATEGORY])]
|
||||
# form.id_category.choices = [(json[Store_Base.ATTR_ID_PRODUCT_CATEGORY], json[Store_Base.ATTR_ID_PRODUCT_CATEGORY])]
|
||||
form.id_category.data = json[Store_Base.ATTR_ID_PRODUCT_CATEGORY]
|
||||
form.id_product.choices = [(json[Store_Base.ATTR_ID_PRODUCT], json[Store_Base.ATTR_ID_PRODUCT])]
|
||||
# form.id_product.choices = [(json[Store_Base.ATTR_ID_PRODUCT], json[Store_Base.ATTR_ID_PRODUCT])]
|
||||
form.id_product.data = json[Store_Base.ATTR_ID_PRODUCT]
|
||||
form.is_out_of_stock.data = av.input_bool(json[Store_Base.FLAG_IS_OUT_OF_STOCK], Store_Base.FLAG_IS_OUT_OF_STOCK, f'{cls.__name__}.from_json')
|
||||
form.quantity_min.data = json[Store_Base.FLAG_QUANTITY_MIN]
|
||||
@@ -66,3 +66,11 @@ class Filters_Stock_Item(Form_Base):
|
||||
filters = cls()
|
||||
filters.id_category.choices = cls.get_choices_blank()
|
||||
filters.id_product.choices = cls.get_choices_blank()
|
||||
"""
|
||||
def import_values(self, form_filters):
|
||||
self.id_category.data = form_filters.id_category.data
|
||||
self.id_product.data = form_filters.id_product.data
|
||||
self.is_out_of_stock.data = form_filters.is_out_of_stock.data
|
||||
self.quantity_min.data = form_filters.quantity_min.data
|
||||
self.quantity_max.data = form_filters.quantity_max.data
|
||||
"""
|
||||
@@ -23,7 +23,7 @@ from abc import ABCMeta, abstractmethod
|
||||
|
||||
|
||||
class Filters_Unit_Measurement(Form_Base):
|
||||
active = BooleanField("Active only?")
|
||||
active = BooleanField("Active only?", default = True)
|
||||
@classmethod
|
||||
def from_filters(cls, filters):
|
||||
form = Filters_Unit_Measurement()
|
||||
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user