Compare commits

..
3 Commits
Author SHA1 Message Date
tanshu 5536bcae41 Version Bump v12.1.0 2024-12-17 08:47:13 +05:30
tanshu 55d5017254 Product sale report can now be section wise 2024-12-17 08:46:29 +05:30
tanshu bbb7be8070 Sale report now can be section wise 2024-12-17 08:23:18 +05:30
24 changed files with 187 additions and 146 deletions
+1 -1
View File
@@ -1 +1 @@
__version__ = "12.0.1"
__version__ = "12.1.0"
@@ -1,15 +1,16 @@
import uuid
from datetime import date, datetime, time, timedelta
from typing import Any
from typing import Annotated, Any
from fastapi import APIRouter, Cookie, Depends, Security
from fastapi import APIRouter, Cookie, Depends, Query, Security
from sqlalchemy import func, or_, select
from sqlalchemy.orm import Session
from ...core.config import settings
from ...core.security import get_current_active_user as get_user
from ...db.session import SessionFuture
from ...models.food_table import FoodTable
from ...models.inventory import Inventory
from ...models.kot import Kot
from ...models.menu_category import MenuCategory
@@ -31,6 +32,7 @@ router = APIRouter()
def product_sale_report_view(
start_date: date = Depends(report_start_date),
finish_date: date = Depends(report_finish_date),
section: Annotated[uuid.UUID | None, Query()] = None,
user: UserToken = Security(get_user, scopes=["product-sale-report"]),
):
check_audit_permission(start_date, user.permissions)
@@ -38,11 +40,12 @@ def product_sale_report_view(
return {
"startDate": start_date.strftime("%d-%b-%Y"),
"finishDate": finish_date.strftime("%d-%b-%Y"),
"amounts": product_sale_report(start_date, finish_date, db),
"sectionId": str(section) if section is not None else None,
"amounts": product_sale_report(start_date, finish_date, section, db),
}
def product_sale_report(s: date, f: date, db: Session):
def product_sale_report(s: date, f: date, id_: uuid.UUID, db: Session):
start_date = datetime.combine(s, time()) + timedelta(
minutes=settings.NEW_DAY_OFFSET_MINUTES - settings.TIMEZONE_OFFSET_MINUTES
)
@@ -51,7 +54,7 @@ def product_sale_report(s: date, f: date, db: Session):
)
day = func.date_trunc("day", Voucher.date - timedelta(minutes=settings.NEW_DAY_OFFSET_MINUTES)).label("day")
list_ = db.execute(
query = (
select(
ProductVersion.id,
ProductVersion.full_name,
@@ -65,6 +68,7 @@ def product_sale_report(s: date, f: date, db: Session):
.join(Product.versions)
.join(ProductVersion.sale_category)
.join(ProductVersion.menu_category)
.join(Voucher.food_table)
.where(
Voucher.date >= start_date,
Voucher.date <= finish_date,
@@ -77,16 +81,18 @@ def product_sale_report(s: date, f: date, db: Session):
ProductVersion.valid_till >= day,
),
)
.group_by(
SaleCategory.name,
MenuCategory.name,
ProductVersion.id,
ProductVersion.full_name,
Voucher.voucher_type,
Inventory.is_happy_hour,
)
.order_by(SaleCategory.name, MenuCategory.name, ProductVersion.full_name)
).all()
)
if id_:
query = query.where(FoodTable.section_id == id_)
query = query.group_by(
SaleCategory.name,
MenuCategory.name,
ProductVersion.id,
ProductVersion.full_name,
Voucher.voucher_type,
Inventory.is_happy_hour,
).order_by(SaleCategory.name, MenuCategory.name, ProductVersion.full_name)
list_ = db.execute(query).all()
info: list[Any] = []
for id_, name, v_type, hh, quantity in list_:
type_ = to_camel(VoucherType(v_type).name)
@@ -111,6 +117,7 @@ def product_sale_report(s: date, f: date, db: Session):
def print_report(
start_date: date = Depends(report_start_date),
finish_date: date = Depends(report_finish_date),
section: Annotated[uuid.UUID | None, Query()] = None,
device_id: uuid.UUID = Cookie(None),
user: UserToken = Security(get_user, scopes=["product-sale-report"]),
) -> bool:
@@ -120,6 +127,7 @@ def print_report(
"userName": user.name,
"startDate": start_date.strftime("%d-%b-%Y"),
"finishDate": finish_date.strftime("%d-%b-%Y"),
"sectionId": str(section) if section is not None else None,
"amounts": product_sale_report(start_date, finish_date, db),
}
print_product_sale_report(report, device_id, db)
+17 -8
View File
@@ -2,14 +2,16 @@ import uuid
from datetime import date, datetime, time, timedelta
from decimal import Decimal
from typing import Annotated
from fastapi import APIRouter, Cookie, Depends, Security
from fastapi import APIRouter, Cookie, Depends, Query, Security
from sqlalchemy import func, or_, select
from sqlalchemy.orm import Session
from ...core.config import settings
from ...core.security import get_current_active_user as get_user
from ...db.session import SessionFuture
from ...models.food_table import FoodTable
from ...models.inventory import Inventory
from ...models.kot import Kot
from ...models.product import Product
@@ -34,6 +36,7 @@ router = APIRouter()
def get_sale_report(
start_date: date = Depends(report_start_date),
finish_date: date = Depends(report_finish_date),
section: Annotated[uuid.UUID | None, Query()] = None,
user: UserToken = Security(get_user, scopes=["sale-report"]),
) -> SaleReport:
check_audit_permission(start_date, user.permissions)
@@ -41,8 +44,9 @@ def get_sale_report(
return SaleReport(
start_date=start_date,
finish_date=finish_date,
section_id=section,
amounts=(
get_sale(start_date, finish_date, db)
get_sale(start_date, finish_date, section, db)
+ [SaleReportItem(name="--", amount=Decimal(0))]
+ get_settlements(start_date, finish_date, db)
+ [SaleReportItem(name="--", amount=Decimal(0))]
@@ -52,7 +56,7 @@ def get_sale_report(
)
def get_sale(s: date, f: date, db: Session) -> list[SaleReportItem]:
def get_sale(s: date, f: date, id_: uuid.UUID | None, db: Session) -> list[SaleReportItem]:
start_date = datetime.combine(s, time()) + timedelta(
minutes=settings.NEW_DAY_OFFSET_MINUTES - settings.TIMEZONE_OFFSET_MINUTES
)
@@ -61,13 +65,14 @@ def get_sale(s: date, f: date, db: Session) -> list[SaleReportItem]:
)
day = func.date_trunc("day", Voucher.date - timedelta(minutes=settings.NEW_DAY_OFFSET_MINUTES)).label("day")
list_ = db.execute(
query = (
select(SaleCategory.name, func.sum(Inventory.net))
.join(Inventory.kot)
.join(Kot.voucher)
.join(Inventory.product)
.join(Product.versions)
.join(ProductVersion.sale_category)
.join(Voucher.food_table)
.where(
Voucher.date >= start_date,
Voucher.date <= finish_date,
@@ -82,9 +87,11 @@ def get_sale(s: date, f: date, db: Session) -> list[SaleReportItem]:
ProductVersion.valid_till >= day,
),
)
.group_by(SaleCategory.name)
.order_by(SaleCategory.name)
).all()
)
if id_:
query = query.where(FoodTable.section_id == id_)
query = query.group_by(SaleCategory.name).order_by(SaleCategory.name)
list_ = db.execute(query).all()
total = Decimal(0)
info = []
for gt, am in list_:
@@ -121,6 +128,7 @@ def get_settlements(s: date, f: date, db: Session) -> list[SaleReportItem]:
def print_report(
start_date: date = Depends(report_start_date),
finish_date: date = Depends(report_finish_date),
section: Annotated[uuid.UUID | None, Query()] = None,
device_id: uuid.UUID = Cookie(None),
user: UserToken = Security(get_user, scopes=["sale-report"]),
) -> bool:
@@ -129,8 +137,9 @@ def print_report(
report = SaleReport(
start_date=start_date,
finish_date=finish_date,
section_id=section,
amounts=(
get_sale(start_date, finish_date, db)
get_sale(start_date, finish_date, section, db)
+ [SaleReportItem(name="--", amount=Decimal(0))]
+ get_settlements(start_date, finish_date, db)
+ [SaleReportItem(name="--", amount=Decimal(0))]
+3
View File
@@ -1,3 +1,5 @@
import uuid
from datetime import date, datetime
from pydantic import BaseModel, ConfigDict, field_serializer, field_validator
@@ -15,6 +17,7 @@ class SaleReportItem(BaseModel):
class SaleReport(BaseModel):
start_date: date
finish_date: date
section_id: uuid.UUID | None
amounts: list[SaleReportItem]
user: UserLink
model_config = ConfigDict(str_strip_whitespace=True, alias_generator=to_camel, populate_by_name=True)
+1 -1
View File
@@ -1,6 +1,6 @@
[tool.poetry]
name = "barker"
version = "12.0.1"
version = "12.1.0"
description = "Point of Sale for a restaurant"
authors = ["tanshu <git@tanshu.com>"]
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "bookie",
"version": "12.0.1",
"version": "12.1.0",
"scripts": {
"ng": "ng",
"start": "ng serve",
+1 -1
View File
@@ -1,7 +1,7 @@
export const environment = {
production: true,
ACCESS_TOKEN_REFRESH_MINUTES: 10, // refresh token 10 minutes before expiry
version: '12.0.1',
version: '12.1.0',
};
export const dateFormat = {
@@ -14,7 +14,7 @@
<mat-card-content>
<form [formGroup]="form" class="flex flex-col">
<div class="flex flex-row justify-around content-start items-start sm:max-lg:flex-col">
<mat-form-field class="flex-auto basis-2/5 mr-5">
<mat-form-field class="flex-auto basis-1/3 mr-5">
<mat-label>Start Date</mat-label>
<input
matInput
@@ -26,7 +26,7 @@
<mat-datepicker-toggle matSuffix [for]="startDate"></mat-datepicker-toggle>
<mat-datepicker #startDate></mat-datepicker>
</mat-form-field>
<mat-form-field class="flex-auto basis-2/5 mr-5">
<mat-form-field class="flex-auto basis-1/3 mr-5">
<mat-label>Finish Date</mat-label>
<input
matInput
@@ -38,7 +38,18 @@
<mat-datepicker-toggle matSuffix [for]="finishDate"></mat-datepicker-toggle>
<mat-datepicker #finishDate></mat-datepicker>
</mat-form-field>
<button mat-raised-button class="flex-auto basis-1/5" color="primary" (click)="show()">Show</button>
<mat-form-field class="flex-auto basis-1/6 mr-5">
<mat-label>Section</mat-label>
<mat-select formControlName="section" name="section">
<mat-option>-- All --</mat-option>
@for (p of sections; track p.id) {
<mat-option [value]="p.id">
{{ p.name }}
</mat-option>
}
</mat-select>
</mat-form-field>
<button mat-raised-button class="flex-auto basis-1/6" color="primary" (click)="show()">Show</button>
</div>
</form>
<mat-table #table [dataSource]="dataSource" aria-label="Elements">
@@ -1,27 +1,18 @@
import { DecimalPipe } from '@angular/common';
import { Component, OnInit } from '@angular/core';
import { FormControl, FormGroup, ReactiveFormsModule } from '@angular/forms';
import { MatIconButton, MatButton } from '@angular/material/button';
import { MatCard, MatCardHeader, MatCardTitleGroup, MatCardTitle, MatCardContent } from '@angular/material/card';
import { MatDatepickerInput, MatDatepickerToggle, MatDatepicker } from '@angular/material/datepicker';
import { MatFormField, MatLabel, MatSuffix } from '@angular/material/form-field';
import { MatIcon } from '@angular/material/icon';
import { MatInput } from '@angular/material/input';
import {
MatTable,
MatColumnDef,
MatHeaderCellDef,
MatHeaderCell,
MatCellDef,
MatCell,
MatHeaderRowDef,
MatHeaderRow,
MatRowDef,
MatRow,
} from '@angular/material/table';
import { MatButtonModule } from '@angular/material/button';
import { MatCardModule } from '@angular/material/card';
import { MatDatepickerModule } from '@angular/material/datepicker';
import { MatFormFieldModule } from '@angular/material/form-field';
import { MatIconModule } from '@angular/material/icon';
import { MatInputModule } from '@angular/material/input';
import { MatSelectModule } from '@angular/material/select';
import { MatTableModule } from '@angular/material/table';
import { ActivatedRoute, Router } from '@angular/router';
import moment from 'moment';
import { Section } from '../core/section';
import { ToasterService } from '../core/toaster.service';
import { ToCsvService } from '../shared/to-csv.service';
@@ -34,41 +25,26 @@ import { ProductSaleReportService } from './product-sale-report.service';
templateUrl: './product-sale-report.component.html',
styleUrls: ['./product-sale-report.component.css'],
imports: [
MatCard,
MatCardHeader,
MatCardTitleGroup,
MatCardTitle,
MatIconButton,
MatIcon,
MatCardContent,
MatCardModule,
MatButtonModule,
ReactiveFormsModule,
MatFormField,
MatLabel,
MatInput,
MatDatepickerInput,
MatDatepickerToggle,
MatSuffix,
MatDatepicker,
MatButton,
MatTable,
MatColumnDef,
MatHeaderCellDef,
MatHeaderCell,
MatCellDef,
MatCell,
MatHeaderRowDef,
MatHeaderRow,
MatRowDef,
MatRow,
MatFormFieldModule,
MatInputModule,
MatIconModule,
MatDatepickerModule,
MatTableModule,
MatSelectModule,
DecimalPipe,
],
})
export class ProductSaleReportComponent implements OnInit {
sections: Section[] = [];
info: ProductSaleReport = new ProductSaleReport();
dataSource: ProductSaleReportDataSource = new ProductSaleReportDataSource(this.info.amounts);
form: FormGroup<{
startDate: FormControl<Date>;
finishDate: FormControl<Date>;
section: FormControl<string | null>;
}>;
/** Columns displayed in the table. Columns IDs can be added, removed, or reordered. */
@@ -85,16 +61,19 @@ export class ProductSaleReportComponent implements OnInit {
this.form = new FormGroup({
startDate: new FormControl(new Date(), { nonNullable: true }),
finishDate: new FormControl(new Date(), { nonNullable: true }),
section: new FormControl<string | null>(null),
});
}
ngOnInit() {
this.route.data.subscribe((value) => {
const data = value as { info: ProductSaleReport };
const data = value as { sections: Section[]; info: ProductSaleReport };
this.sections = data.sections;
this.info = data.info;
this.form.setValue({
startDate: moment(this.info.startDate, 'DD-MMM-YYYY').toDate(),
finishDate: moment(this.info.finishDate, 'DD-MMM-YYYY').toDate(),
section: this.info.sectionId || null,
});
this.dataSource = new ProductSaleReportDataSource(this.info.amounts);
});
@@ -102,25 +81,33 @@ export class ProductSaleReportComponent implements OnInit {
show() {
const info = this.getInfo();
const params = {
startDate: info.startDate,
finishDate: info.finishDate,
} as { startDate: string; finishDate: string; section?: string };
if (info.sectionId) {
params['section'] = info.sectionId;
}
this.router.navigate(['product-sale-report'], {
queryParams: {
startDate: info.startDate,
finishDate: info.finishDate,
},
queryParams: params,
});
}
getInfo(): ProductSaleReport {
const formModel = this.form.value;
return new ProductSaleReport({
const data = new ProductSaleReport({
startDate: moment(formModel.startDate).format('DD-MMM-YYYY'),
finishDate: moment(formModel.finishDate).format('DD-MMM-YYYY'),
});
if (formModel.section) {
data.sectionId = formModel.section;
}
return data;
}
print() {
this.ser.print(this.info.startDate, this.info.finishDate).subscribe({
this.ser.print(this.info.startDate, this.info.finishDate, this.info.sectionId).subscribe({
next: () => {
this.toaster.show('', 'Successfully Printed');
},
@@ -7,5 +7,6 @@ import { ProductSaleReportService } from './product-sale-report.service';
export const productSaleReportResolver: ResolveFn<ProductSaleReport> = (route) => {
const startDate = route.queryParamMap.get('startDate') ?? null;
const finishDate = route.queryParamMap.get('finishDate') ?? null;
return inject(ProductSaleReportService).get(startDate, finishDate);
const section = route.queryParamMap.get('section') ?? null;
return inject(ProductSaleReportService).get(startDate, finishDate, section);
};
@@ -1,6 +1,7 @@
import { Routes } from '@angular/router';
import { authGuard } from '../auth/auth-guard.service';
import { sectionListResolver } from '../sections/section-list.resolver';
import { ProductSaleReportComponent } from './product-sale-report.component';
import { productSaleReportResolver } from './product-sale-report.resolver';
@@ -14,6 +15,7 @@ export const routes: Routes = [
permission: 'Product Sale Report',
},
resolve: {
sections: sectionListResolver,
info: productSaleReportResolver,
},
runGuardsAndResolvers: 'always',
@@ -19,7 +19,7 @@ export class ProductSaleReportService {
private log: ErrorLoggerService,
) {}
get(startDate: string | null, finishDate: string | null): Observable<ProductSaleReport> {
get(startDate: string | null, finishDate: string | null, section: string | null): Observable<ProductSaleReport> {
const options = { params: new HttpParams() };
if (startDate !== null) {
options.params = options.params.set('s', startDate);
@@ -27,12 +27,15 @@ export class ProductSaleReportService {
if (finishDate !== null) {
options.params = options.params.set('f', finishDate);
}
if (section !== null) {
options.params = options.params.set('section', section);
}
return this.http
.get<ProductSaleReport>(url, options)
.pipe(catchError(this.log.handleError(serviceName, 'get'))) as Observable<ProductSaleReport>;
}
print(startDate: string | null, finishDate: string | null): Observable<boolean> {
print(startDate: string | null, finishDate: string | null, section: string | null): Observable<boolean> {
const printUrl = `${url}/print`;
const options = { params: new HttpParams() };
if (startDate !== null) {
@@ -41,6 +44,9 @@ export class ProductSaleReportService {
if (finishDate !== null) {
options.params = options.params.set('f', finishDate);
}
if (section !== null) {
options.params = options.params.set('section', section);
}
return this.http
.get<boolean>(printUrl, options)
.pipe(catchError(this.log.handleError(serviceName, 'print'))) as Observable<boolean>;
@@ -3,11 +3,13 @@ import { ProductSaleReportItem } from './product-sale-report-item';
export class ProductSaleReport {
startDate: string;
finishDate: string;
sectionId: string | null;
amounts: ProductSaleReportItem[];
public constructor(init?: Partial<ProductSaleReport>) {
this.startDate = '';
this.finishDate = '';
this.sectionId = null;
this.amounts = [];
Object.assign(this, init);
}
@@ -14,7 +14,7 @@
<mat-card-content>
<form [formGroup]="form" class="flex flex-col">
<div class="flex flex-row justify-around content-start items-start sm:max-lg:flex-col">
<mat-form-field class="flex-auto basis-2/5 mr-5">
<mat-form-field class="flex-auto basis-1/3 mr-5">
<mat-label>Start Date</mat-label>
<input
matInput
@@ -26,7 +26,7 @@
<mat-datepicker-toggle matSuffix [for]="startDate"></mat-datepicker-toggle>
<mat-datepicker #startDate></mat-datepicker>
</mat-form-field>
<mat-form-field class="flex-auto basis-2/5 mr-5">
<mat-form-field class="flex-auto basis-1/3 mr-5">
<mat-label>Finish Date</mat-label>
<input
matInput
@@ -38,7 +38,18 @@
<mat-datepicker-toggle matSuffix [for]="finishDate"></mat-datepicker-toggle>
<mat-datepicker #finishDate></mat-datepicker>
</mat-form-field>
<button mat-raised-button class="flex-auto basis-1/5" color="primary" (click)="show()">Show</button>
<mat-form-field class="flex-auto basis-1/6 mr-5">
<mat-label>Section</mat-label>
<mat-select formControlName="section" name="section">
<mat-option>-- All --</mat-option>
@for (p of sections; track p.id) {
<mat-option [value]="p.id">
{{ p.name }}
</mat-option>
}
</mat-select>
</mat-form-field>
<button mat-raised-button class="flex-auto basis-1/6" color="primary" (click)="show()">Show</button>
</div>
</form>
<mat-table #table [dataSource]="dataSource" aria-label="Elements">
@@ -1,27 +1,19 @@
import { CurrencyPipe } from '@angular/common';
import { Component, OnInit } from '@angular/core';
import { FormControl, FormGroup, ReactiveFormsModule } from '@angular/forms';
import { MatIconButton, MatButton } from '@angular/material/button';
import { MatCard, MatCardHeader, MatCardTitleGroup, MatCardTitle, MatCardContent } from '@angular/material/card';
import { MatDatepickerInput, MatDatepickerToggle, MatDatepicker } from '@angular/material/datepicker';
import { MatFormField, MatLabel, MatSuffix } from '@angular/material/form-field';
import { MatIcon } from '@angular/material/icon';
import { MatInput } from '@angular/material/input';
import {
MatTable,
MatColumnDef,
MatHeaderCellDef,
MatHeaderCell,
MatCellDef,
MatCell,
MatHeaderRowDef,
MatHeaderRow,
MatRowDef,
MatRow,
} from '@angular/material/table';
import { MatButtonModule } from '@angular/material/button';
import { MatCardModule } from '@angular/material/card';
import { MatOptionModule } from '@angular/material/core';
import { MatDatepickerModule } from '@angular/material/datepicker';
import { MatFormFieldModule } from '@angular/material/form-field';
import { MatIconModule } from '@angular/material/icon';
import { MatInputModule } from '@angular/material/input';
import { MatSelectModule } from '@angular/material/select';
import { MatTableModule } from '@angular/material/table';
import { ActivatedRoute, Router } from '@angular/router';
import moment from 'moment';
import { Section } from '../core/section';
import { ToasterService } from '../core/toaster.service';
import { ToCsvService } from '../shared/to-csv.service';
@@ -34,41 +26,27 @@ import { SaleReportService } from './sale-report.service';
templateUrl: './sale-report.component.html',
styleUrls: ['./sale-report.component.css'],
imports: [
MatCard,
MatCardHeader,
MatCardTitleGroup,
MatCardTitle,
MatIconButton,
MatIcon,
MatCardContent,
MatCardModule,
MatButtonModule,
ReactiveFormsModule,
MatFormField,
MatLabel,
MatInput,
MatDatepickerInput,
MatDatepickerToggle,
MatSuffix,
MatDatepicker,
MatButton,
MatTable,
MatColumnDef,
MatHeaderCellDef,
MatHeaderCell,
MatCellDef,
MatCell,
MatHeaderRowDef,
MatHeaderRow,
MatRowDef,
MatRow,
MatFormFieldModule,
MatIconModule,
MatInputModule,
MatDatepickerModule,
MatTableModule,
MatOptionModule,
MatSelectModule,
CurrencyPipe,
],
})
export class SaleReportComponent implements OnInit {
sections: Section[] = [];
info: SaleReport = new SaleReport();
dataSource: SaleReportDatasource = new SaleReportDatasource(this.info.amounts);
form: FormGroup<{
startDate: FormControl<Date>;
finishDate: FormControl<Date>;
section: FormControl<string | null>;
}>;
/** Columns displayed in the table. Columns IDs can be added, removed, or reordered. */
@@ -85,16 +63,19 @@ export class SaleReportComponent implements OnInit {
this.form = new FormGroup({
startDate: new FormControl(new Date(), { nonNullable: true }),
finishDate: new FormControl(new Date(), { nonNullable: true }),
section: new FormControl<string | null>(null),
});
}
ngOnInit() {
this.route.data.subscribe((value) => {
const data = value as { info: SaleReport };
const data = value as { sections: Section[]; info: SaleReport };
this.sections = data.sections;
this.info = data.info;
this.form.setValue({
startDate: moment(this.info.startDate, 'DD-MMM-YYYY').toDate(),
finishDate: moment(this.info.finishDate, 'DD-MMM-YYYY').toDate(),
section: this.info.sectionId || null,
});
this.dataSource = new SaleReportDatasource(this.info.amounts);
});
@@ -102,25 +83,32 @@ export class SaleReportComponent implements OnInit {
show() {
const info = this.getInfo();
const params = {
startDate: info.startDate,
finishDate: info.finishDate,
} as { startDate: string; finishDate: string; section?: string };
if (info.sectionId) {
params['section'] = info.sectionId;
}
this.router.navigate(['sale-report'], {
queryParams: {
startDate: info.startDate,
finishDate: info.finishDate,
},
queryParams: params,
});
}
getInfo(): SaleReport {
const formModel = this.form.value;
return new SaleReport({
const data = new SaleReport({
startDate: moment(formModel.startDate).format('DD-MMM-YYYY'),
finishDate: moment(formModel.finishDate).format('DD-MMM-YYYY'),
});
if (formModel.section) {
data.sectionId = formModel.section;
}
return data;
}
print() {
this.ser.print(this.info.startDate, this.info.finishDate).subscribe({
this.ser.print(this.info.startDate, this.info.finishDate, this.info.sectionId).subscribe({
next: () => {
this.toaster.show('', 'Successfully Printed');
},
@@ -7,5 +7,6 @@ import { SaleReportService } from './sale-report.service';
export const saleReportResolver: ResolveFn<SaleReport> = (route) => {
const startDate = route.queryParamMap.get('startDate') ?? null;
const finishDate = route.queryParamMap.get('finishDate') ?? null;
return inject(SaleReportService).get(startDate, finishDate);
const section = route.queryParamMap.get('section') ?? null;
return inject(SaleReportService).get(startDate, finishDate, section);
};
@@ -1,6 +1,7 @@
import { Routes } from '@angular/router';
import { authGuard } from '../auth/auth-guard.service';
import { sectionListResolver } from '../sections/section-list.resolver';
import { SaleReportComponent } from './sale-report.component';
import { saleReportResolver } from './sale-report.resolver';
@@ -14,6 +15,7 @@ export const routes: Routes = [
permission: 'Sale Report',
},
resolve: {
sections: sectionListResolver,
info: saleReportResolver,
},
runGuardsAndResolvers: 'always',
@@ -19,7 +19,7 @@ export class SaleReportService {
private log: ErrorLoggerService,
) {}
get(startDate: string | null, finishDate: string | null): Observable<SaleReport> {
get(startDate: string | null, finishDate: string | null, section: string | null): Observable<SaleReport> {
const options = { params: new HttpParams() };
if (startDate !== null) {
options.params = options.params.set('s', startDate);
@@ -27,12 +27,15 @@ export class SaleReportService {
if (finishDate !== null) {
options.params = options.params.set('f', finishDate);
}
if (section !== null) {
options.params = options.params.set('section', section);
}
return this.http
.get<SaleReport>(url, options)
.pipe(catchError(this.log.handleError(serviceName, 'get'))) as Observable<SaleReport>;
}
print(startDate: string | null, finishDate: string | null): Observable<boolean> {
print(startDate: string | null, finishDate: string | null, section: string | null): Observable<boolean> {
const printUrl = `${url}/print`;
const options = { params: new HttpParams() };
if (startDate !== null) {
@@ -41,6 +44,9 @@ export class SaleReportService {
if (finishDate !== null) {
options.params = options.params.set('f', finishDate);
}
if (section !== null) {
options.params = options.params.set('section', section);
}
return this.http
.get<boolean>(printUrl, options)
.pipe(catchError(this.log.handleError(serviceName, 'print'))) as Observable<boolean>;
@@ -3,11 +3,13 @@ import { SaleReportItem } from './sale-report-item';
export class SaleReport {
startDate: string;
finishDate: string;
sectionId: string | null;
amounts: SaleReportItem[];
public constructor(init?: Partial<SaleReport>) {
this.startDate = '';
this.finishDate = '';
this.sectionId = null;
this.amounts = [];
Object.assign(this, init);
}
@@ -92,7 +92,6 @@ export class DiscountComponent {
this.data.subscribe((list: DiscountItem[]) => {
this.list = list;
console.log(list);
this.form.controls.discounts.clear();
this.list.forEach((x) => {
@@ -1,7 +1,12 @@
<h2 mat-dialog-title>Receive Payment</h2>
<mat-dialog-content>
<form [formGroup]="form" class="flex flex-col">
<mat-table #table [dataSource]="dataSource" formArrayName="amounts" [style.visibility]="this.displayTable ? 'visible': 'hidden'">
<mat-table
#table
[dataSource]="dataSource"
formArrayName="amounts"
[style.visibility]="this.displayTable ? 'visible' : 'hidden'"
>
<!-- Name Column -->
<ng-container matColumnDef="name">
<mat-header-cell *matHeaderCellDef class="bold">Amount</mat-header-cell>
@@ -24,7 +29,7 @@
<mat-row *matRowDef="let row; columns: displayedColumns"></mat-row>
<mat-footer-row *matFooterRowDef="displayedColumns"></mat-footer-row>
</mat-table>
<mat-form-field class="flex-auto" [style.visibility]="this.displayReason ? 'visible': 'hidden'">
<mat-form-field class="flex-auto" [style.visibility]="this.displayReason ? 'visible' : 'hidden'">
<mat-label>Reason</mat-label>
<input
type="text"
@@ -138,7 +138,6 @@ export class ReceivePaymentComponent {
}),
),
);
console.log('re', this.displayReason)
});
this.form.valueChanges.subscribe((x) => this.listenToAmountChange(x.amounts));
}
@@ -103,7 +103,6 @@ export class UserDetailComponent implements OnInit, AfterViewInit {
this.ser.saveOrUpdate(this.getItem()).subscribe({
next: () => {
this.toaster.show('Success', '');
console.log(this.item.id);
if ((this.item.id as string) === 'me') {
this.router.navigateByUrl('/');
} else {
+1 -1
View File
@@ -1,6 +1,6 @@
[tool.poetry]
name = "frank"
version = "12.0.1"
version = "12.1.0"
description = "Point of Sale for a restaurant"
authors = ["tanshu <git@tanshu.com>"]