From ad8a2d2cc377ee130b1e7000fae805d8f59b0546 Mon Sep 17 00:00:00 2001 From: tanshu Date: Tue, 30 Jun 2020 11:32:09 +0530 Subject: [PATCH] Fix: Save account error was because in constructor type did not end in underscore Fix: Employee save as checking for in None instead of is None Feature: Checking the existing token for validity in constructor of auth service, this should prevent last login showing Feature: Moved the middleware secret key into the env file Chore: Replaced my own GUID() with postgres UUID() type --- .env | 3 + brewman/core/config.py | 1 + brewman/db/base.py | 4 +- brewman/main.py | 2 +- brewman/models/auth.py | 28 ++++----- brewman/models/guidtype.py | 58 ------------------- brewman/models/master.py | 32 +++++----- brewman/models/voucher.py | 54 ++++++++--------- brewman/routers/account.py | 2 +- brewman/routers/cost_centre.py | 3 +- brewman/routers/product.py | 8 +-- overlord/package.json | 2 +- overlord/src/app/auth/auth.service.ts | 20 ++++++- .../src/app/auth/login/login.component.ts | 2 +- overlord/src/app/core/jwt.interceptor.ts | 2 +- .../product-list/product-list.component.ts | 56 +++++++++--------- overlord/src/app/role/role.service.ts | 12 ++-- overlord/src/app/user/user.service.ts | 12 ++-- setup.py | 2 +- 19 files changed, 132 insertions(+), 171 deletions(-) delete mode 100644 brewman/models/guidtype.py diff --git a/.env b/.env index f7a05751..98cfa08a 100644 --- a/.env +++ b/.env @@ -10,7 +10,10 @@ POSTGRES_USER= POSTGRES_PASSWORD= POSTGRES_DB= +# openssl rand -hex 32 SECRET_KEY= +# openssl rand -hex 5 +MIDDLEWARE_SECRET_KEY= ALGORITHM=HS256 JWT_TOKEN_EXPIRE_MINUTES=30 diff --git a/brewman/core/config.py b/brewman/core/config.py index e7caa39b..0774b6d2 100644 --- a/brewman/core/config.py +++ b/brewman/core/config.py @@ -8,6 +8,7 @@ from pydantic import BaseSettings, PostgresDsn, validator class Settings(BaseSettings): # openssl rand -hex 32 SECRET_KEY: str = secrets.token_urlsafe(32) + MIDDLEWARE_SECRET_KEY: str = secrets.token_urlsafe(5) ALGORITHM: str = "HS256" JWT_TOKEN_EXPIRE_MINUTES: int = 30 HOST: str = "0.0.0.0" diff --git a/brewman/db/base.py b/brewman/db/base.py index 96390195..0550aa80 100644 --- a/brewman/db/base.py +++ b/brewman/db/base.py @@ -3,8 +3,8 @@ from brewman.db.base_class import Base # noqa from brewman.models import ( Client, - user_group, - role_group, + user_role, + role_permission, User, LoginHistory, Role, diff --git a/brewman/main.py b/brewman/main.py index 80de10c7..7ddf52fb 100644 --- a/brewman/main.py +++ b/brewman/main.py @@ -61,7 +61,7 @@ Base.metadata.create_all(bind=engine) app = FastAPI() -app.add_middleware(SessionMiddleware, secret_key="c982367648") +app.add_middleware(SessionMiddleware, secret_key=settings.MIDDLEWARE_SECRET_KEY) app.include_router(db_image.router, prefix="/db-image", tags=["db-image"]) app.include_router(login.router, tags=["login"]) app.include_router(account.router, prefix="/api/accounts", tags=["accounts"]) diff --git a/brewman/models/auth.py b/brewman/models/auth.py index f9180574..ea0f76de 100644 --- a/brewman/models/auth.py +++ b/brewman/models/auth.py @@ -8,7 +8,7 @@ from sqlalchemy.schema import ForeignKey, Table from sqlalchemy import Column, Boolean, Unicode, Integer, DateTime, UniqueConstraint from sqlalchemy.orm import synonym, relationship, Session -from brewman.models.guidtype import GUID +from sqlalchemy.dialects.postgresql import UUID from .meta import Base @@ -19,7 +19,7 @@ def encrypt(val): class Client(Base): __tablename__ = "auth_clients" - id = Column("client_id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("client_id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) code = Column("code", Integer, unique=True, nullable=False) name = Column("name", Unicode(255), unique=True, nullable=False) enabled = Column("enabled", Boolean, nullable=False) @@ -51,24 +51,24 @@ class Client(Base): user_role = Table( "user_roles", Base.metadata, - Column("id", GUID(), primary_key=True, default=uuid.uuid4), - Column("user_id", GUID(), ForeignKey("auth_users.id")), - Column("role_id", GUID(), ForeignKey("auth_roles.id")), + Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4), + Column("user_id", UUID(as_uuid=True), ForeignKey("auth_users.id")), + Column("role_id", UUID(as_uuid=True), ForeignKey("auth_roles.id")), ) role_permission = Table( "role_permissions", Base.metadata, - Column("id", GUID(), primary_key=True, default=uuid.uuid4), - Column("permission_id", GUID(), ForeignKey("auth_permissions.id")), - Column("role_id", GUID(), ForeignKey("auth_roles.id")), + Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4), + Column("permission_id", UUID(as_uuid=True), ForeignKey("auth_permissions.id")), + Column("role_id", UUID(as_uuid=True), ForeignKey("auth_roles.id")), ) class User(Base): __tablename__ = "auth_users" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) name = Column("username", Unicode(255), unique=True) _password = Column("password", Unicode(60)) locked_out = Column("disabled", Boolean) @@ -111,9 +111,9 @@ class User(Base): class LoginHistory(Base): __tablename__ = "auth_login_history" __table_args__ = (UniqueConstraint("user_id", "client_id", "date"),) - id = Column("login_history_id", GUID(), primary_key=True, default=uuid.uuid4) - user_id = Column("user_id", GUID(), ForeignKey("auth_users.id"), nullable=False) - client_id = Column("client_id", GUID(), ForeignKey("auth_clients.client_id"), nullable=False) + id = Column("login_history_id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) + user_id = Column("user_id", UUID(as_uuid=True), ForeignKey("auth_users.id"), nullable=False) + client_id = Column("client_id", UUID(as_uuid=True), ForeignKey("auth_clients.client_id"), nullable=False) date = Column("date", DateTime(timezone=True), nullable=False) def __init__(self, user_id=None, client_id=None, date=None, id_=None): @@ -126,7 +126,7 @@ class LoginHistory(Base): class Role(Base): __tablename__ = "auth_roles" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) name = Column("name", Unicode(255), unique=True) def __init__(self, name=None, id_=None): @@ -137,7 +137,7 @@ class Role(Base): class Permission(Base): __tablename__ = "auth_permissions" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) name = Column("name", Unicode(255), unique=True) roles = relationship("Role", secondary=role_permission, backref="permissions") diff --git a/brewman/models/guidtype.py b/brewman/models/guidtype.py deleted file mode 100644 index 44227001..00000000 --- a/brewman/models/guidtype.py +++ /dev/null @@ -1,58 +0,0 @@ -import uuid -from sqlalchemy.dialects.postgresql import UUID -from sqlalchemy.dialects.sqlite import BLOB -from sqlalchemy.types import TypeDecorator, CHAR, Binary - - -class GUID(TypeDecorator): - """Platform-independent GUID type. - - Uses Postgresql's UUID type, otherwise uses - CHAR(32), storing as stringified hex values. - - """ - - impl = Binary - - # if dialect.value == 'postgresql': - # impl = CHAR - # elif dialect.value == 'mysql': - # impl = MSBinary - # elif dialect.valie == 'sqlite': - # impl = Binary - # else: - # impl = Binary - - def load_dialect_impl(self, dialect): - if dialect.name == "postgresql": - return dialect.type_descriptor(UUID()) - elif dialect.name == "sqlite": - return dialect.type_descriptor(BLOB()) - else: - return dialect.type_descriptor(CHAR(32)) - - def process_bind_param(self, value, dialect): - if value is None: - return None - elif dialect.name == "postgresql": - return str(value) - elif not isinstance(value, uuid.UUID): - raise ValueError("value %s is not a valid uuid.UUID" % value) - else: - return value.bytes - # if not isinstance(value, uuid.UUID): - # return "%.32x" % uuid.UUID(value) - # else: - # # hexstring - # return "%.32x" % value - - def process_result_value(self, value, dialect=None): - if value is None: - return None - elif isinstance(value, bytes): - return uuid.UUID(bytes=value) - else: - return uuid.UUID(value) - - def is_mutable(self): - return False diff --git a/brewman/models/master.py b/brewman/models/master.py index dba4edde..ecd30f1a 100644 --- a/brewman/models/master.py +++ b/brewman/models/master.py @@ -15,7 +15,7 @@ from sqlalchemy import ( ) from sqlalchemy.orm import relationship, Session -from brewman.models.guidtype import GUID +from sqlalchemy.dialects.postgresql import UUID from .meta import Base @@ -23,15 +23,15 @@ class Product(Base): __tablename__ = "products" __table_args__ = (UniqueConstraint("name", "units"),) - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) code = Column("code", Integer, unique=True) name = Column("name", Unicode(255), nullable=False) units = Column("units", Unicode(255), nullable=False) fraction = Column("fraction", Numeric, nullable=False) fraction_units = Column("fraction_units", Unicode(255), nullable=False) product_yield = Column("product_yield", Numeric, nullable=False) - product_group_id = Column("product_group_id", GUID(), ForeignKey("product_groups.id"), nullable=False,) - account_id = Column("account_id", GUID(), ForeignKey("accounts.id"), nullable=False) + product_group_id = Column("product_group_id", UUID(as_uuid=True), ForeignKey("product_groups.id"), nullable=False,) + account_id = Column("account_id", UUID(as_uuid=True), ForeignKey("accounts.id"), nullable=False) price = Column("cost_price", Numeric, nullable=False) sale_price = Column("sale_price", Numeric, nullable=False) is_active = Column("is_active", Boolean, nullable=False) @@ -118,8 +118,8 @@ class Product(Base): class Recipe(Base): __tablename__ = "recipes" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) - product_id = Column("product_id", GUID(), ForeignKey("products.id"), nullable=False) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) + product_id = Column("product_id", UUID(as_uuid=True), ForeignKey("products.id"), nullable=False) quantity = Column("quantity", Numeric, nullable=False) cost_price = Column("cost_price", Numeric, nullable=False) @@ -162,9 +162,9 @@ class RecipeItem(Base): __tablename__ = "recipe_items" __table_args__ = (UniqueConstraint("recipe_id", "product_id"),) - id = Column("recipe_item_id", GUID(), primary_key=True, default=uuid.uuid4) - recipe_id = Column("recipe_id", GUID(), ForeignKey("recipes.id"), nullable=False) - product_id = Column("product_id", GUID(), ForeignKey("products.id"), nullable=False) + id = Column("recipe_item_id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) + recipe_id = Column("recipe_id", UUID(as_uuid=True), ForeignKey("recipes.id"), nullable=False) + product_id = Column("product_id", UUID(as_uuid=True), ForeignKey("products.id"), nullable=False) quantity = Column("quantity", Integer, nullable=False) price = Column("price", Integer, nullable=False) @@ -181,7 +181,7 @@ class RecipeItem(Base): class ProductGroup(Base): __tablename__ = "product_groups" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) name = Column("name", Unicode(255), unique=True) is_fixture = Column("is_fixture", Boolean, nullable=False) @@ -204,7 +204,7 @@ class ProductGroup(Base): class CostCentre(Base): __tablename__ = "cost_centres" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) name = Column("name", Unicode(255), unique=True) is_fixture = Column("is_fixture", Boolean, nullable=False) @@ -243,7 +243,7 @@ class CostCentre(Base): class AccountBase(Base): __tablename__ = "accounts" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) code = Column("code", Integer, nullable=False) name = Column("name", Unicode(255), unique=True, nullable=False) type = Column("type", Integer, nullable=False) @@ -251,7 +251,7 @@ class AccountBase(Base): is_starred = Column("is_starred", Boolean, nullable=False) is_active = Column("is_active", Boolean, nullable=False) is_reconcilable = Column("is_reconcilable", Boolean, nullable=False) - cost_centre_id = Column("cost_centre_id", GUID(), ForeignKey("cost_centres.id"), nullable=False) + cost_centre_id = Column("cost_centre_id", UUID(as_uuid=True), ForeignKey("cost_centres.id"), nullable=False) is_fixture = Column("is_fixture", Boolean, nullable=False) __mapper_args__ = {"polymorphic_on": account_type} @@ -369,7 +369,7 @@ class Employee(AccountBase): __tablename__ = "employees" __mapper_args__ = {"polymorphic_identity": "employees"} - id = Column("id", GUID(), ForeignKey(AccountBase.id), primary_key=True) + id = Column("id", UUID(as_uuid=True), ForeignKey(AccountBase.id), primary_key=True) designation = Column("designation", Unicode(255), nullable=False) salary = Column("salary", Integer, nullable=False) points = Column("points", Numeric(precision=5, scale=2), nullable=False) @@ -409,7 +409,7 @@ class Employee(AccountBase): def create(self, db: Session): code = db.query(func.max(AccountBase.code)).filter(AccountBase.type == self.type).one()[0] - self.code = 1 if code in None else code + 1 + self.code = 1 if code is None else code + 1 self.name += f" ({str(self.code)})" db.add(self) return self @@ -508,7 +508,7 @@ class AccountType: class DbSetting(Base): __tablename__ = "settings" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) name = Column("name", Unicode(255), unique=True, nullable=False) data = Column("data", PickleType) diff --git a/brewman/models/voucher.py b/brewman/models/voucher.py index 0214e8e5..bc8add6f 100644 --- a/brewman/models/voucher.py +++ b/brewman/models/voucher.py @@ -16,7 +16,7 @@ from sqlalchemy.dialects.postgresql import BYTEA from sqlalchemy.ext.hybrid import hybrid_property from sqlalchemy.orm import relationship, synonym, backref, Session -from brewman.models.guidtype import GUID +from sqlalchemy.dialects.postgresql import UUID from brewman.models.master import Product from .meta import Base @@ -63,7 +63,7 @@ class VoucherType: class Voucher(Base): __tablename__ = "vouchers" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) date = Column("date", Date, nullable=False, index=True) narration = Column("narration", Unicode(1000), nullable=False) is_reconciled = Column("is_reconciled", Boolean, nullable=False) @@ -72,9 +72,9 @@ class Voucher(Base): creation_date = Column("creation_date", DateTime(timezone=True), nullable=False) last_edit_date = Column("last_edit_date", DateTime(timezone=True), nullable=False) _type = Column("voucher_type", Integer, nullable=False) - user_id = Column("user_id", GUID(), ForeignKey("auth_users.id"), nullable=False) + user_id = Column("user_id", UUID(as_uuid=True), ForeignKey("auth_users.id"), nullable=False) posted = Column("is_posted", Boolean, nullable=False) - poster_id = Column("poster_id", GUID(), ForeignKey("auth_users.id")) + poster_id = Column("poster_id", UUID(as_uuid=True), ForeignKey("auth_users.id")) user = relationship("User", primaryjoin="User.id==Voucher.user_id", cascade=None) poster = relationship("User", primaryjoin="User.id==Voucher.poster_id", cascade=None) @@ -136,12 +136,12 @@ class Voucher(Base): class Journal(Base): __tablename__ = "journals" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) debit = Column("debit", Integer) amount = Column("amount", Numeric) - voucher_id = Column("voucher_id", GUID(), ForeignKey("vouchers.id"), nullable=False, index=True) - account_id = Column("account_id", GUID(), ForeignKey("accounts.id"), nullable=False) - cost_centre_id = Column("cost_centre_id", GUID(), ForeignKey("cost_centres.id"), nullable=False) + voucher_id = Column("voucher_id", UUID(as_uuid=True), ForeignKey("vouchers.id"), nullable=False, index=True) + account_id = Column("account_id", UUID(as_uuid=True), ForeignKey("accounts.id"), nullable=False) + cost_centre_id = Column("cost_centre_id", UUID(as_uuid=True), ForeignKey("cost_centres.id"), nullable=False) voucher = relationship("Voucher", back_populates="journals") account = relationship("AccountBase", back_populates="journals") @@ -167,9 +167,9 @@ class Journal(Base): class EmployeeBenefit(Base): __tablename__ = "employee_benefit" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) - voucher_id = Column("voucher_id", GUID(), ForeignKey("vouchers.id"), nullable=False) - journal_id = Column("journal_id", GUID(), ForeignKey("journals.id"), nullable=False) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) + voucher_id = Column("voucher_id", UUID(as_uuid=True), ForeignKey("vouchers.id"), nullable=False) + journal_id = Column("journal_id", UUID(as_uuid=True), ForeignKey("journals.id"), nullable=False) gross_salary = Column("gross_salary", Integer) days_worked = Column("days_worked", Integer) esi_ee = Column("esi_employee", Integer) @@ -210,9 +210,9 @@ class EmployeeBenefit(Base): class Incentive(Base): __tablename__ = "incentives" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) - voucher_id = Column("voucher_id", GUID(), ForeignKey("vouchers.id"), nullable=False) - journal_id = Column("journal_id", GUID(), ForeignKey("journals.id"), nullable=False) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) + voucher_id = Column("voucher_id", UUID(as_uuid=True), ForeignKey("vouchers.id"), nullable=False) + journal_id = Column("journal_id", UUID(as_uuid=True), ForeignKey("journals.id"), nullable=False) days_worked = Column("days_worked", Numeric(precision=5, scale=1), nullable=False) points = Column("points", Numeric(precision=5, scale=2), nullable=False) @@ -234,10 +234,10 @@ class Incentive(Base): class Inventory(Base): __tablename__ = "inventories" __table_args__ = (UniqueConstraint("voucher_id", "batch_id"),) - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) - voucher_id = Column("voucher_id", GUID(), ForeignKey("vouchers.id"), nullable=False, index=True) - product_id = Column("product_id", GUID(), ForeignKey("products.id"), nullable=False) - batch_id = Column("batch_id", GUID(), ForeignKey("batches.id"), nullable=False) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) + voucher_id = Column("voucher_id", UUID(as_uuid=True), ForeignKey("vouchers.id"), nullable=False, index=True) + product_id = Column("product_id", UUID(as_uuid=True), ForeignKey("products.id"), nullable=False) + batch_id = Column("batch_id", UUID(as_uuid=True), ForeignKey("batches.id"), nullable=False) quantity = Column("quantity", Numeric) rate = Column("rate", Numeric) tax = Column("tax", Numeric) @@ -281,9 +281,9 @@ class Inventory(Base): class Batch(Base): __tablename__ = "batches" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) name = Column("name", Date, nullable=False) - product_id = Column("product_id", GUID(), ForeignKey("products.id"), nullable=False) + product_id = Column("product_id", UUID(as_uuid=True), ForeignKey("products.id"), nullable=False) quantity_remaining = Column("quantity_remaining", Numeric) rate = Column("rate", Numeric) tax = Column("tax", Numeric) @@ -327,13 +327,13 @@ class Batch(Base): class Attendance(Base): __tablename__ = "attendances" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) - employee_id = Column("employee_id", GUID(), ForeignKey("employees.id")) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) + employee_id = Column("employee_id", UUID(as_uuid=True), ForeignKey("employees.id")) date = Column("date", Date, nullable=False) attendance_type = Column("attendance_type", Integer) amount = Column("amount", Numeric) creation_date = Column("creation_date", DateTime(timezone=True)) - user_id = Column("user_id", GUID(), ForeignKey("auth_users.id")) + user_id = Column("user_id", UUID(as_uuid=True), ForeignKey("auth_users.id")) is_valid = Column("is_valid", Boolean) user = relationship("User", primaryjoin="User.id==Attendance.user_id") @@ -375,8 +375,8 @@ class Attendance(Base): class Fingerprint(Base): __tablename__ = "fingerprints" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) - employee_id = Column("employee_id", GUID(), ForeignKey("employees.id")) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) + employee_id = Column("employee_id", UUID(as_uuid=True), ForeignKey("employees.id")) date = Column("date", DateTime) def __init__(self, id_=None, employee_id=None, date=None): @@ -389,8 +389,8 @@ class Fingerprint(Base): class DbImage(Base): __tablename__ = "images" - id = Column("id", GUID(), primary_key=True, default=uuid.uuid4) - resource_id = Column("resource_id", GUID(), nullable=False) + id = Column("id", UUID(as_uuid=True), primary_key=True, default=uuid.uuid4) + resource_id = Column("resource_id", UUID(as_uuid=True), nullable=False) resource_type = Column("resource_type", Unicode(255), nullable=False) image = Column("image", BYTEA, nullable=False) thumbnail = Column("thumbnail", BYTEA, nullable=False) diff --git a/brewman/routers/account.py b/brewman/routers/account.py index 26aa8eb4..0b2b464d 100644 --- a/brewman/routers/account.py +++ b/brewman/routers/account.py @@ -33,7 +33,7 @@ def save( try: item = Account( name=data.name, - type=data.type, + type_=data.type, is_starred=data.is_starred, is_active=data.is_active, is_reconcilable=data.is_reconcilable, diff --git a/brewman/routers/cost_centre.py b/brewman/routers/cost_centre.py index 5d4a32ab..81fcff7a 100644 --- a/brewman/routers/cost_centre.py +++ b/brewman/routers/cost_centre.py @@ -70,13 +70,12 @@ def update( raise - @router.delete("/{id_}") def delete( id_: uuid.UUID, db: Session = Depends(get_db), user: UserToken = Security(get_user, scopes=["cost-centres"]), ): try: - item = db.query(CostCentre).filter(CostCentre.id == id_).first() + item: CostCentre = db.query(CostCentre).filter(CostCentre.id == id_).first() if item is None: raise HTTPException( diff --git a/brewman/routers/product.py b/brewman/routers/product.py index df9063ac..46ca9e34 100644 --- a/brewman/routers/product.py +++ b/brewman/routers/product.py @@ -97,11 +97,11 @@ def update( def delete( id_: uuid.UUID, db: Session = Depends(get_db), user: UserToken = Security(get_user, scopes=["products"]), ): - product: Product = db.query(Product).filter(Product.id == id_).first() - can_delete, reason = product.can_delete("advanced-delete" in user.permissions) + item: Product = db.query(Product).filter(Product.id == id_).first() + can_delete, reason = item.can_delete("advanced-delete" in user.permissions) if can_delete: - delete_with_data(product, db) + delete_with_data(item, db) db.commit() return product_info(None, db) else: @@ -111,7 +111,7 @@ def delete( ) -@router.get("/") # "Products" +@router.get("/") def show_blank( db: Session = Depends(get_db), user: UserToken = Security(get_user, scopes=["products"]), ): diff --git a/overlord/package.json b/overlord/package.json index b5523b4d..b6e1fe29 100644 --- a/overlord/package.json +++ b/overlord/package.json @@ -1,6 +1,6 @@ { "name": "overlord", - "version": "7.0.2", + "version": "7.0.3", "scripts": { "ng": "ng", "start": "ng serve", diff --git a/overlord/src/app/auth/auth.service.ts b/overlord/src/app/auth/auth.service.ts index e0f6e7d9..268cf7f6 100644 --- a/overlord/src/app/auth/auth.service.ts +++ b/overlord/src/app/auth/auth.service.ts @@ -16,12 +16,28 @@ export class AuthService { public currentUser: Observable; constructor(private http: HttpClient) { - this.currentUserSubject = new BehaviorSubject(JSON.parse(localStorage.getItem(JWT_USER))); + const existingToken: User = JSON.parse(localStorage.getItem(JWT_USER)); + if (existingToken === null || Date.now() > existingToken.exp * 1000) { + localStorage.removeItem(JWT_USER); + this.currentUserSubject = new BehaviorSubject(null); + } else { + this.currentUserSubject = new BehaviorSubject(existingToken); + } this.currentUser = this.currentUserSubject.asObservable(); } public get user(): User { - return this.currentUserSubject.value; + const val = this.currentUserSubject.value; + if (val == null) { + return val; + } + const expired = Date.now() > val.exp * 1000; + if (expired) { + this.logout(); + return null; + } else { + return this.currentUserSubject.value; + } } login(username: string, password: string, otp: string) { diff --git a/overlord/src/app/auth/login/login.component.ts b/overlord/src/app/auth/login/login.component.ts index 6d2c52cc..98495883 100644 --- a/overlord/src/app/auth/login/login.component.ts +++ b/overlord/src/app/auth/login/login.component.ts @@ -60,7 +60,7 @@ export class LoginComponent implements OnInit, AfterViewInit { this.router.navigate([this.returnUrl]); }, (error) => { - if (error.status === 401 && 'Client is not registered' == error.error.detail) { + if (error.status === 401 && 'Client is not registered' === error.error.detail) { this.showOtp = true; this.clientId = this.cs.getCookie('client_id'); } diff --git a/overlord/src/app/core/jwt.interceptor.ts b/overlord/src/app/core/jwt.interceptor.ts index 4c4bfef2..1031b411 100644 --- a/overlord/src/app/core/jwt.interceptor.ts +++ b/overlord/src/app/core/jwt.interceptor.ts @@ -18,7 +18,7 @@ export class JwtInterceptor implements HttpInterceptor { // console.log("intercepting:\nisRefreshing: ", this.isRefreshing, "\n user: ", this.authService.user,"\n needsRefreshing: ", this.authService.needsRefreshing()); if (!this.isRefreshing && this.authService.user && this.authService.needsRefreshing()) { this.isRefreshing = true; - this.authService.refreshToken().subscribe( x=> this.isRefreshing = false); + this.authService.refreshToken().subscribe( x => this.isRefreshing = false); } const currentUser = this.authService.user; if (currentUser?.access_token) { diff --git a/overlord/src/app/product/product-list/product-list.component.ts b/overlord/src/app/product/product-list/product-list.component.ts index 13b83d5c..db7d2618 100644 --- a/overlord/src/app/product/product-list/product-list.component.ts +++ b/overlord/src/app/product/product-list/product-list.component.ts @@ -1,13 +1,13 @@ -import {AfterViewInit, Component, ElementRef, OnInit, ViewChild} from '@angular/core'; +import { AfterViewInit, Component, ElementRef, OnInit, ViewChild } from '@angular/core'; import { MatPaginator } from '@angular/material/paginator'; import { MatSort } from '@angular/material/sort'; -import {ProductListDataSource} from './product-list-datasource'; -import {Product} from '../../core/product'; -import {ActivatedRoute} from '@angular/router'; -import {debounceTime, distinctUntilChanged, startWith} from 'rxjs/operators'; -import {FormBuilder, FormGroup} from '@angular/forms'; -import {Observable} from 'rxjs'; -import {ToCsvService} from "../../shared/to-csv.service"; +import { ProductListDataSource } from './product-list-datasource'; +import { Product } from '../../core/product'; +import { ActivatedRoute } from '@angular/router'; +import { debounceTime, distinctUntilChanged, startWith } from 'rxjs/operators'; +import { FormBuilder, FormGroup } from '@angular/forms'; +import { Observable } from 'rxjs'; +import { ToCsvService } from '../../shared/to-csv.service'; @Component({ selector: 'app-product-list', @@ -15,6 +15,25 @@ import {ToCsvService} from "../../shared/to-csv.service"; styleUrls: ['./product-list.component.css'] }) export class ProductListComponent implements OnInit, AfterViewInit { + + constructor(private route: ActivatedRoute, private fb: FormBuilder, private toCsv: ToCsvService) { + this.showExtended = false; + this.createForm(); + this.filter = this.listenToFilterChange(); + } + + get showExtended(): boolean { + return this._showExtended; + } + + set showExtended(value: boolean) { + this._showExtended = value; + if (value) { + this.displayedColumns = ['name', 'costPrice', 'productYield', 'productGroup', 'info']; + } else { + this.displayedColumns = ['name', 'costPrice', 'productGroup', 'info']; + } + } @ViewChild('filterElement', { static: true }) filterElement: ElementRef; @ViewChild(MatPaginator, { static: true }) paginator: MatPaginator; @ViewChild(MatSort, { static: true }) sort: MatSort; @@ -25,11 +44,7 @@ export class ProductListComponent implements OnInit, AfterViewInit { /** Columns displayed in the table. Columns IDs can be added, removed, or reordered. */ displayedColumns: string[]; - constructor(private route: ActivatedRoute, private fb: FormBuilder, private toCsv: ToCsvService) { - this.showExtended = false; - this.createForm(); - this.filter = this.listenToFilterChange(); - } + private _showExtended: boolean; createForm() { this.form = this.fb.group({ @@ -60,21 +75,6 @@ export class ProductListComponent implements OnInit, AfterViewInit { }, 0); } - private _showExtended: boolean; - - get showExtended(): boolean { - return this._showExtended; - } - - set showExtended(value: boolean) { - this._showExtended = value; - if (value) { - this.displayedColumns = ['name', 'costPrice', 'productYield', 'productGroup', 'info']; - } else { - this.displayedColumns = ['name', 'costPrice', 'productGroup', 'info']; - } - } - exportCsv() { const headers = { Code: 'code', diff --git a/overlord/src/app/role/role.service.ts b/overlord/src/app/role/role.service.ts index 0bf91846..b5b1232a 100644 --- a/overlord/src/app/role/role.service.ts +++ b/overlord/src/app/role/role.service.ts @@ -1,9 +1,9 @@ -import {Injectable} from '@angular/core'; -import {HttpClient, HttpHeaders, HttpParams} from '@angular/common/http'; -import {ErrorLoggerService} from '../core/error-logger.service'; -import {catchError} from 'rxjs/operators'; -import {Observable} from 'rxjs/internal/Observable'; -import {Role} from './role'; +import { Injectable } from '@angular/core'; +import { HttpClient, HttpHeaders } from '@angular/common/http'; +import { ErrorLoggerService } from '../core/error-logger.service'; +import { catchError } from 'rxjs/operators'; +import { Observable } from 'rxjs/internal/Observable'; +import { Role } from './role'; const httpOptions = { headers: new HttpHeaders({'Content-Type': 'application/json'}) diff --git a/overlord/src/app/user/user.service.ts b/overlord/src/app/user/user.service.ts index ca7f5941..9c7e8cc2 100644 --- a/overlord/src/app/user/user.service.ts +++ b/overlord/src/app/user/user.service.ts @@ -1,9 +1,9 @@ -import {Injectable} from '@angular/core'; -import {HttpClient, HttpHeaders, HttpParams} from '@angular/common/http'; -import {ErrorLoggerService} from '../core/error-logger.service'; -import {catchError} from 'rxjs/operators'; -import {Observable} from 'rxjs/internal/Observable'; -import {User} from '../core/user'; +import { Injectable } from '@angular/core'; +import { HttpClient, HttpHeaders } from '@angular/common/http'; +import { ErrorLoggerService } from '../core/error-logger.service'; +import { catchError } from 'rxjs/operators'; +import { Observable } from 'rxjs/internal/Observable'; +import { User } from '../core/user'; const httpOptions = { headers: new HttpHeaders({'Content-Type': 'application/json'}) diff --git a/setup.py b/setup.py index f28b0be7..edfdcf5d 100644 --- a/setup.py +++ b/setup.py @@ -11,7 +11,7 @@ with open(os.path.join(here, 'requirements.txt'), "r") as r: requires = r.read().splitlines() setup(name='brewman', - version='7.0.2', + version='7.0.3', description='brewman', long_description=README + '\n\n' + CHANGES, classifiers=[