Account done
This commit is contained in:
parent
2466efb208
commit
6765f0a93e
brewman
@ -1,17 +1,19 @@
|
||||
import traceback
|
||||
import uuid
|
||||
from typing import List
|
||||
from datetime import datetime
|
||||
|
||||
from fastapi import APIRouter, Depends, Security
|
||||
from pydantic import ValidationError
|
||||
from fastapi import APIRouter, HTTPException, status, Depends, Security
|
||||
from sqlalchemy import func
|
||||
from sqlalchemy.exc import SQLAlchemyError
|
||||
from sqlalchemy.orm import joinedload_all, Session
|
||||
|
||||
from ..core.security import User, get_current_active_user as get_user
|
||||
from ..db.session import SessionLocal
|
||||
from ..models.master import CostCentre, Account, AccountType, AccountBase
|
||||
from ..models.validation_exception import ValidationError
|
||||
from ..models.voucher import Voucher, Journal, VoucherType
|
||||
from ..schemas.master import Account as AccountSchema
|
||||
import brewman.schemas.master as schemas
|
||||
|
||||
router = APIRouter()
|
||||
|
||||
|
||||
@ -24,11 +26,14 @@ def get_db():
|
||||
db.close()
|
||||
|
||||
|
||||
@router.post("/")
|
||||
def save(data: AccountSchema, db: Session = Depends(get_db), user: User = Security(get_user, scopes=["accounts"])):
|
||||
@router.post("/", response_model=schemas.Account)
|
||||
def save(
|
||||
data: schemas.AccountSaveUpdate,
|
||||
db: Session = Depends(get_db),
|
||||
user: User = Security(get_user, scopes=["accounts"]),
|
||||
):
|
||||
try:
|
||||
item = Account(
|
||||
code=0,
|
||||
name=data.name,
|
||||
type=data.type,
|
||||
is_starred=data.is_starred,
|
||||
@ -38,56 +43,85 @@ def save(data: AccountSchema, db: Session = Depends(get_db), user: User = Securi
|
||||
).create(db)
|
||||
db.commit()
|
||||
return account_info(item.id, db)
|
||||
except:
|
||||
except SQLAlchemyError as e:
|
||||
db.rollback()
|
||||
finally:
|
||||
db.close()
|
||||
|
||||
|
||||
@router.put("/{id_}")
|
||||
def update(id_: uuid.UUID, db: Session = Depends(get_db), user: User = Security(get_user, scopes=["accounts"])):
|
||||
item = (
|
||||
db.query(Account)
|
||||
.filter(Account.id == id_)
|
||||
.first()
|
||||
)
|
||||
if item.is_fixture:
|
||||
raise ValidationError(
|
||||
"{0} is a fixture and cannot be edited or deleted.".format(item.name)
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=str(e),
|
||||
)
|
||||
except Exception:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=traceback.format_exc(),
|
||||
)
|
||||
new_type = int(request.json_body["type"])
|
||||
if not item.type == new_type:
|
||||
item.code = Account.get_code(new_type, request.dbsession)
|
||||
item.type = new_type
|
||||
item.name = request.json_body["name"]
|
||||
item.is_active = request.json_body["isActive"]
|
||||
item.is_reconcilable = request.json_body["isReconcilable"]
|
||||
item.is_starred = request.json_body["isStarred"]
|
||||
item.cost_centre_id = uuid.UUID(request.json_body["costCentre"]["id"])
|
||||
transaction.commit()
|
||||
return account_info(item.id, request.dbsession)
|
||||
|
||||
|
||||
@router.delete("/{id}") # "Accounts"
|
||||
def delete(id_: uuid.UUID, db: Session = Depends(get_db), user: User = Security(get_user, scopes=["accounts"])):
|
||||
account = (
|
||||
db.query(Account)
|
||||
.filter(Account.id == id_)
|
||||
.first()
|
||||
)
|
||||
can_delete, reason = account.can_delete(request.has_permission("Advanced Delete"))
|
||||
@router.put("/{id_}", response_model=schemas.Account)
|
||||
def update(
|
||||
id_: uuid.UUID,
|
||||
data: schemas.AccountSaveUpdate,
|
||||
db: Session = Depends(get_db),
|
||||
user: User = Security(get_user, scopes=["accounts"]),
|
||||
):
|
||||
try:
|
||||
item: Account = db.query(Account).filter(Account.id == id_).first()
|
||||
if item.is_fixture:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=f"{item.name} is a fixture and cannot be edited or deleted.",
|
||||
)
|
||||
if not item.type == data.type:
|
||||
item.code = Account.get_code(data.type, db)
|
||||
item.type = data.type
|
||||
item.name = data.name
|
||||
item.is_active = data.is_active
|
||||
item.is_reconcilable = data.is_reconcilable
|
||||
item.is_starred = data.is_starred
|
||||
item.cost_centre_id = data.cost_centre.id_
|
||||
db.commit()
|
||||
return account_info(item.id, db)
|
||||
except SQLAlchemyError as e:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR, detail=str(e),
|
||||
)
|
||||
except Exception:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=traceback.format_exc(),
|
||||
)
|
||||
|
||||
|
||||
@router.delete("/{id}")
|
||||
def delete(
|
||||
id_: uuid.UUID,
|
||||
db: Session = Depends(get_db),
|
||||
user: User = Security(get_user, scopes=["accounts"]),
|
||||
):
|
||||
account: Account = db.query(Account).filter(Account.id == id_).first()
|
||||
can_delete, reason = account.can_delete("Advanced Delete" in user.permissions)
|
||||
if can_delete:
|
||||
delete_with_data(account, db)
|
||||
transaction.commit()
|
||||
db.commit()
|
||||
return account_info(None, db)
|
||||
else:
|
||||
transaction.abort()
|
||||
response = Response("Cannot delete account because {0}".format(reason))
|
||||
response.status_int = 500
|
||||
return response
|
||||
db.abort()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=f"Cannot delete account because {reason}",
|
||||
)
|
||||
|
||||
|
||||
@router.get("/list") # "Authenticated"
|
||||
@router.get("/")
|
||||
def show_blank(
|
||||
db: Session = Depends(get_db), user: User = Security(get_user, scopes=["accounts"])
|
||||
):
|
||||
return account_info(None, db)
|
||||
|
||||
|
||||
@router.get("/list")
|
||||
async def show_list(db: Session = Depends(get_db), user: User = Depends(get_user)):
|
||||
list_ = (
|
||||
db.query(Account)
|
||||
@ -113,9 +147,16 @@ async def show_list(db: Session = Depends(get_db), user: User = Depends(get_user
|
||||
return accounts
|
||||
|
||||
|
||||
@router.get("/query") # "Authenticated"
|
||||
async def show_term(q: str, t: int = None, r: bool = None, a: bool = None, c: int = None,
|
||||
db: Session = Depends(get_db), current_user: User = Depends(get_user)):
|
||||
@router.get("/query")
|
||||
async def show_term(
|
||||
q: str,
|
||||
t: int = None,
|
||||
r: bool = None,
|
||||
a: bool = None,
|
||||
c: int = None,
|
||||
db: Session = Depends(get_db),
|
||||
current_user: User = Depends(get_user),
|
||||
):
|
||||
count = c
|
||||
|
||||
list_ = []
|
||||
@ -126,29 +167,32 @@ async def show_term(q: str, t: int = None, r: bool = None, a: bool = None, c: in
|
||||
return {"user": current_user.name, "list": list_}
|
||||
|
||||
|
||||
@router.get("/{id_}/balance") # "Authenticated"
|
||||
async def show_balance(id_: uuid.UUID, d: str = None, db: Session = Depends(get_db), user: User = Depends(get_user)):
|
||||
date = (
|
||||
None
|
||||
if d is None or d == ""
|
||||
else datetime.datetime.strptime(d, "%d-%b-%Y")
|
||||
)
|
||||
@router.get("/{id_}/balance")
|
||||
async def show_balance(
|
||||
id_: uuid.UUID,
|
||||
d: str = None,
|
||||
db: Session = Depends(get_db),
|
||||
user: User = Depends(get_user),
|
||||
):
|
||||
date = None if d is None or d == "" else datetime.datetime.strptime(d, "%d-%b-%Y")
|
||||
return {"date": balance(id_, date, db), "total": balance(id_, None, db)}
|
||||
|
||||
|
||||
@router.get("/{id_}") # "Accounts"
|
||||
def show_id(id_: uuid.UUID, db: Session = Depends(get_db), user: User = Security(get_user, scopes=["accounts"])):
|
||||
@router.get("/{id_}")
|
||||
def show_id(
|
||||
id_: uuid.UUID,
|
||||
db: Session = Depends(get_db),
|
||||
user: User = Security(get_user, scopes=["accounts"]),
|
||||
):
|
||||
return account_info(id_, db)
|
||||
|
||||
|
||||
def balance(id_: uuid.UUID, date, dbsession: Session):
|
||||
account = dbsession.query(AccountBase).filter(AccountBase.id == id_).first()
|
||||
def balance(id_: uuid.UUID, date, db: Session):
|
||||
account = db.query(AccountBase).filter(AccountBase.id == id_).first()
|
||||
if not account.type_object.balance_sheet:
|
||||
return 0
|
||||
|
||||
bal = dbsession.query(func.sum(Journal.amount * Journal.debit)).join(
|
||||
Journal.voucher
|
||||
)
|
||||
bal = db.query(func.sum(Journal.amount * Journal.debit)).join(Journal.voucher)
|
||||
if date is not None:
|
||||
bal = bal.filter(Voucher.date <= date)
|
||||
|
||||
@ -160,11 +204,6 @@ def balance(id_: uuid.UUID, date, dbsession: Session):
|
||||
return 0 if bal is None else bal
|
||||
|
||||
|
||||
@router.get("/") # "Accounts"
|
||||
def show_blank(db: Session = Depends(get_db), user: User = Security(get_user, scopes=["accounts"])):
|
||||
return account_info(None, db)
|
||||
|
||||
|
||||
def account_info(id_, db):
|
||||
if id_ is None:
|
||||
account = {
|
||||
@ -198,7 +237,7 @@ def delete_with_data(account, db):
|
||||
suspense_account = (
|
||||
db.query(Account).filter(Account.id == Account.suspense()).first()
|
||||
)
|
||||
query = (
|
||||
query: List[Voucher] = (
|
||||
db.query(Voucher)
|
||||
.options(joinedload_all(Voucher.journals, Journal.account, innerjoin=True))
|
||||
.filter(Voucher.journals.any(Journal.account_id == account.id))
|
||||
@ -219,8 +258,8 @@ def delete_with_data(account, db):
|
||||
else:
|
||||
if sus_jnl is None:
|
||||
acc_jnl.account = suspense_account
|
||||
voucher.narration += "\nSuspense \u20B9{0:,.2f} is {1}".format(
|
||||
acc_jnl.amount, account.name
|
||||
voucher.narration += (
|
||||
f"\nSuspense \u20B9{acc_jnl.amount:,.2f} is {account.name}"
|
||||
)
|
||||
else:
|
||||
amount = (sus_jnl.debit * sus_jnl.amount) + (
|
||||
@ -232,9 +271,7 @@ def delete_with_data(account, db):
|
||||
else:
|
||||
sus_jnl.amount = abs(amount)
|
||||
sus_jnl.debit = -1 if amount < 0 else 1
|
||||
voucher.narration += "\nDeleted \u20B9{0:,.2f} of {1}".format(
|
||||
acc_jnl.amount * acc_jnl.debit, account.name
|
||||
)
|
||||
voucher.narration += f"\nDeleted \u20B9{acc_jnl.amount * acc_jnl.debit:,.2f} of {account.name}"
|
||||
if voucher.type in (
|
||||
VoucherType.by_name("Payment").id,
|
||||
VoucherType.by_name("Receipt").id,
|
||||
|
@ -1,12 +1,14 @@
|
||||
from fastapi import APIRouter, Depends
|
||||
|
||||
from ..core.security import User, get_current_active_user as get_user
|
||||
from brewman.models.master import AccountType
|
||||
from fastapi import APIRouter
|
||||
|
||||
router = APIRouter()
|
||||
|
||||
|
||||
@router.get("/") # "Authenticated"
|
||||
def account_type_list(request):
|
||||
account_types = []
|
||||
for item in AccountType.list():
|
||||
account_types.append({"id": item.id, "name": item.name})
|
||||
return account_types
|
||||
@router.get("/")
|
||||
def account_type_list(user: User = Depends(get_user)):
|
||||
return [
|
||||
{"id": item.id, "name": item.name}
|
||||
for item in AccountType.list()
|
||||
]
|
||||
|
@ -1,19 +1,14 @@
|
||||
import traceback
|
||||
import uuid
|
||||
from typing import List, Optional
|
||||
|
||||
from sqlalchemy.exc import SQLAlchemyError
|
||||
|
||||
import brewman.schemas.master as schemas
|
||||
|
||||
from fastapi import APIRouter, HTTPException, status, Depends, Security
|
||||
from sqlalchemy.exc import SQLAlchemyError
|
||||
from sqlalchemy.orm import Session
|
||||
|
||||
import brewman.schemas.master as schemas
|
||||
from ..core.security import User, get_current_active_user as get_user
|
||||
from ..db.session import SessionLocal
|
||||
from ..models.master import CostCentre
|
||||
|
||||
|
||||
router = APIRouter()
|
||||
|
||||
|
||||
|
@ -62,15 +62,18 @@ class CostCentre(CostCentreSaveUpdate):
|
||||
is_fixture: bool = Field(alias="isFixture")
|
||||
|
||||
|
||||
class Account(BaseModel):
|
||||
id_: uuid.UUID
|
||||
code: int
|
||||
class AccountSaveUpdate(BaseModel):
|
||||
name: str
|
||||
type: int
|
||||
is_starred: bool
|
||||
is_active: bool
|
||||
is_reconcilable: bool
|
||||
cost_centre: CostCentre
|
||||
|
||||
|
||||
class Account(AccountSaveUpdate):
|
||||
id_: uuid.UUID = Field(alias="id")
|
||||
code: int
|
||||
is_fixture: bool
|
||||
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user