mirror of
https://github.com/bigcapitalhq/bigcapital.git
synced 2026-02-19 06:10:31 +00:00
refactor: dynamic list to nestjs
This commit is contained in:
@@ -8,7 +8,14 @@ import { CloseSaleReceipt } from './commands/CloseSaleReceipt.service';
|
||||
import { DeleteSaleReceipt } from './commands/DeleteSaleReceipt.service';
|
||||
import { GetSaleReceipt } from './queries/GetSaleReceipt.service';
|
||||
import { EditSaleReceipt } from './commands/EditSaleReceipt.service';
|
||||
import { ISaleReceiptDTO, ISaleReceiptState } from './types/SaleReceipts.types';
|
||||
import {
|
||||
ISaleReceiptDTO,
|
||||
ISaleReceiptState,
|
||||
ISalesReceiptsFilter,
|
||||
} from './types/SaleReceipts.types';
|
||||
import { GetSaleReceiptsService } from './queries/GetSaleReceipts.service';
|
||||
import { SaleReceipt } from './models/SaleReceipt';
|
||||
import { IPaginationMeta } from '@/interfaces/Model';
|
||||
|
||||
@Injectable()
|
||||
export class SaleReceiptApplication {
|
||||
@@ -17,7 +24,7 @@ export class SaleReceiptApplication {
|
||||
private editSaleReceiptService: EditSaleReceipt,
|
||||
private getSaleReceiptService: GetSaleReceipt,
|
||||
private deleteSaleReceiptService: DeleteSaleReceipt,
|
||||
// private getSaleReceiptsService: GetSaleReceipts,
|
||||
private getSaleReceiptsService: GetSaleReceiptsService,
|
||||
private closeSaleReceiptService: CloseSaleReceipt,
|
||||
private getSaleReceiptPdfService: SaleReceiptsPdfService,
|
||||
// private saleReceiptNotifyBySmsService: SaleReceiptNotifyBySms,
|
||||
@@ -74,20 +81,16 @@ export class SaleReceiptApplication {
|
||||
|
||||
/**
|
||||
* Retrieve sales receipts paginated and filterable list.
|
||||
* @param {number} tenantId
|
||||
* @param {ISalesReceiptsFilter} filterDTO
|
||||
* @returns
|
||||
*/
|
||||
// public async getSaleReceipts(
|
||||
// tenantId: number,
|
||||
// filterDTO: ISalesReceiptsFilter,
|
||||
// ): Promise<{
|
||||
// data: ISaleReceipt[];
|
||||
// pagination: IPaginationMeta;
|
||||
// filterMeta: IFilterMeta;
|
||||
// }> {
|
||||
// return this.getSaleReceiptsService.getSaleReceipts(tenantId, filterDTO);
|
||||
// }
|
||||
public async getSaleReceipts(filterDTO: ISalesReceiptsFilter): Promise<{
|
||||
data: SaleReceipt[];
|
||||
pagination: IPaginationMeta;
|
||||
filterMeta: IFilterMeta;
|
||||
}> {
|
||||
return this.getSaleReceiptsService.getSaleReceipts(filterDTO);
|
||||
}
|
||||
|
||||
/**
|
||||
* Closes the given sale receipt.
|
||||
@@ -106,9 +109,7 @@ export class SaleReceiptApplication {
|
||||
* @returns
|
||||
*/
|
||||
public getSaleReceiptPdf(tenantId: number, saleReceiptId: number) {
|
||||
return this.getSaleReceiptPdfService.saleReceiptPdf(
|
||||
saleReceiptId,
|
||||
);
|
||||
return this.getSaleReceiptPdfService.saleReceiptPdf(saleReceiptId);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -24,6 +24,8 @@ import { SaleReceiptGLEntriesSubscriber } from './subscribers/SaleReceiptGLEntri
|
||||
import { SaleReceiptGLEntries } from './ledger/SaleReceiptGLEntries';
|
||||
import { LedgerModule } from '../Ledger/Ledger.module';
|
||||
import { AccountsModule } from '../Accounts/Accounts.module';
|
||||
import { SaleReceiptInventoryTransactionsSubscriber } from './inventory/SaleReceiptWriteInventoryTransactions';
|
||||
import { GetSaleReceiptsService } from './queries/GetSaleReceipts.service';
|
||||
|
||||
@Module({
|
||||
controllers: [SaleReceiptsController],
|
||||
@@ -53,7 +55,9 @@ import { AccountsModule } from '../Accounts/Accounts.module';
|
||||
SaleReceiptBrandingTemplate,
|
||||
SaleReceiptIncrement,
|
||||
SaleReceiptGLEntries,
|
||||
SaleReceiptGLEntriesSubscriber
|
||||
SaleReceiptGLEntriesSubscriber,
|
||||
SaleReceiptInventoryTransactionsSubscriber,
|
||||
GetSaleReceiptsService
|
||||
],
|
||||
})
|
||||
export class SaleReceiptsModule {}
|
||||
|
||||
@@ -0,0 +1,66 @@
|
||||
import { Injectable } from '@nestjs/common';
|
||||
import { Knex } from 'knex';
|
||||
import { InventoryService } from '@/modules/InventoryCost/Inventory';
|
||||
import { ItemsEntriesService } from '@/modules/Items/ItemsEntries.service';
|
||||
import { SaleReceipt } from '../models/SaleReceipt';
|
||||
|
||||
@Injectable()
|
||||
export class SaleReceiptInventoryTransactions {
|
||||
constructor(
|
||||
private readonly itemsEntriesService: ItemsEntriesService,
|
||||
private readonly inventoryService: InventoryService,
|
||||
) {}
|
||||
|
||||
/**
|
||||
* Records the inventory transactions from the given bill input.
|
||||
* @param {Bill} bill - Bill model object.
|
||||
* @param {number} billId - Bill id.
|
||||
* @return {Promise<void>}
|
||||
*/
|
||||
public async recordInventoryTransactions(
|
||||
saleReceipt: SaleReceipt,
|
||||
override?: boolean,
|
||||
trx?: Knex.Transaction,
|
||||
): Promise<void> {
|
||||
// Loads the inventory items entries of the given sale invoice.
|
||||
const inventoryEntries =
|
||||
await this.itemsEntriesService.filterInventoryEntries(
|
||||
saleReceipt.entries,
|
||||
);
|
||||
const transaction = {
|
||||
transactionId: saleReceipt.id,
|
||||
transactionType: 'SaleReceipt',
|
||||
transactionNumber: saleReceipt.receiptNumber,
|
||||
exchangeRate: saleReceipt.exchangeRate,
|
||||
|
||||
date: saleReceipt.receiptDate,
|
||||
direction: 'OUT',
|
||||
entries: inventoryEntries,
|
||||
createdAt: saleReceipt.createdAt,
|
||||
|
||||
warehouseId: saleReceipt.warehouseId,
|
||||
};
|
||||
return this.inventoryService.recordInventoryTransactionsFromItemsEntries(
|
||||
transaction,
|
||||
override,
|
||||
trx,
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverts the inventory transactions of the given bill id.
|
||||
* @param {number} tenantId - Tenant id.
|
||||
* @param {number} billId - Bill id.
|
||||
* @return {Promise<void>}
|
||||
*/
|
||||
public async revertInventoryTransactions(
|
||||
receiptId: number,
|
||||
trx?: Knex.Transaction,
|
||||
) {
|
||||
return this.inventoryService.deleteInventoryTransactions(
|
||||
receiptId,
|
||||
'SaleReceipt',
|
||||
trx,
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,69 @@
|
||||
import { OnEvent } from '@nestjs/event-emitter';
|
||||
import {
|
||||
ISaleReceiptCreatedPayload,
|
||||
ISaleReceiptEditedPayload,
|
||||
ISaleReceiptEventDeletedPayload,
|
||||
} from '../types/SaleReceipts.types';
|
||||
import { Injectable } from '@nestjs/common';
|
||||
import { events } from '@/common/events/events';
|
||||
import { SaleReceiptInventoryTransactions } from './SaleReceiptInventoryTransactions';
|
||||
|
||||
@Injectable()
|
||||
export class SaleReceiptInventoryTransactionsSubscriber {
|
||||
constructor(
|
||||
private readonly saleReceiptInventory: SaleReceiptInventoryTransactions
|
||||
) {}
|
||||
|
||||
/**
|
||||
* Handles the writing inventory transactions once the receipt created.
|
||||
* @param {ISaleReceiptCreatedPayload} payload -
|
||||
*/
|
||||
@OnEvent(events.saleReceipt.onCreated)
|
||||
public async handleWritingInventoryTransactions({
|
||||
saleReceipt,
|
||||
trx,
|
||||
}: ISaleReceiptCreatedPayload) {
|
||||
// Can't continue if the sale receipt is not closed yet.
|
||||
if (!saleReceipt.closedAt) return null;
|
||||
|
||||
await this.saleReceiptInventory.recordInventoryTransactions(
|
||||
saleReceipt,
|
||||
false,
|
||||
trx
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
* Rewriting the inventory transactions once the sale invoice be edited.
|
||||
* @param {ISaleReceiptEditedPayload} payload -
|
||||
*/
|
||||
@OnEvent(events.saleReceipt.onEdited)
|
||||
public async handleRewritingInventoryTransactions({
|
||||
saleReceipt,
|
||||
trx,
|
||||
}: ISaleReceiptEditedPayload) {
|
||||
// Can't continue if the sale receipt is not closed yet.
|
||||
if (!saleReceipt.closedAt) return null;
|
||||
|
||||
await this.saleReceiptInventory.recordInventoryTransactions(
|
||||
saleReceipt,
|
||||
true,
|
||||
trx
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
* Handles deleting the inventory transactions once the receipt deleted.
|
||||
* @param {ISaleReceiptEventDeletedPayload} payload -
|
||||
*/
|
||||
@OnEvent(events.saleReceipt.onDeleted)
|
||||
public async handleDeletingInventoryTransactions({
|
||||
saleReceiptId,
|
||||
trx,
|
||||
}: ISaleReceiptEventDeletedPayload) {
|
||||
await this.saleReceiptInventory.revertInventoryTransactions(
|
||||
saleReceiptId,
|
||||
trx
|
||||
);
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,73 @@
|
||||
import * as R from 'ramda';
|
||||
import { SaleReceiptTransformer } from './SaleReceiptTransformer';
|
||||
import { Inject, Injectable } from '@nestjs/common';
|
||||
import { TransformerInjectable } from '@/modules/Transformer/TransformerInjectable.service';
|
||||
import { DynamicListService } from '@/modules/DynamicListing/DynamicList.service';
|
||||
import { ISalesReceiptsFilter } from '../types/SaleReceipts.types';
|
||||
import { SaleReceipt } from '../models/SaleReceipt';
|
||||
import { IPaginationMeta } from '@/interfaces/Model';
|
||||
|
||||
interface GetSaleReceiptsSettings {
|
||||
fetchEntriesGraph?: boolean;
|
||||
}
|
||||
@Injectable()
|
||||
export class GetSaleReceiptsService {
|
||||
constructor(
|
||||
private readonly transformer: TransformerInjectable,
|
||||
private readonly dynamicListService: DynamicListService,
|
||||
|
||||
@Inject(SaleReceipt.name)
|
||||
private readonly saleReceiptModel: typeof SaleReceipt,
|
||||
) {}
|
||||
|
||||
/**
|
||||
* Retrieve sales receipts paginated and filterable list.
|
||||
* @param {number} tenantId
|
||||
* @param {ISaleReceiptFilter} salesReceiptsFilter
|
||||
*/
|
||||
public async getSaleReceipts(filterDTO: ISalesReceiptsFilter): Promise<{
|
||||
data: SaleReceipt[];
|
||||
pagination: IPaginationMeta;
|
||||
filterMeta: IFilterMeta;
|
||||
}> {
|
||||
// Parses the stringified filter roles.
|
||||
const filter = this.parseListFilterDTO(filterDTO);
|
||||
|
||||
// Dynamic list service.
|
||||
const dynamicFilter = await this.dynamicListService.dynamicList(
|
||||
SaleReceipt,
|
||||
filter,
|
||||
);
|
||||
const { results, pagination } = await this.saleReceiptModel
|
||||
.query()
|
||||
.onBuild((builder) => {
|
||||
builder.withGraphFetched('depositAccount');
|
||||
builder.withGraphFetched('customer');
|
||||
builder.withGraphFetched('entries.item');
|
||||
|
||||
dynamicFilter.buildQuery()(builder);
|
||||
filterDTO?.filterQuery && filterDTO?.filterQuery(builder);
|
||||
})
|
||||
.pagination(filter.page - 1, filter.pageSize);
|
||||
|
||||
// Transformes the estimates models to POJO.
|
||||
const salesEstimates = await this.transformer.transform(
|
||||
results,
|
||||
new SaleReceiptTransformer(),
|
||||
);
|
||||
return {
|
||||
data: salesEstimates,
|
||||
pagination,
|
||||
filterMeta: dynamicFilter.getResponseMeta(),
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses the sale invoice list filter DTO.
|
||||
* @param filterDTO
|
||||
* @returns
|
||||
*/
|
||||
private parseListFilterDTO(filterDTO) {
|
||||
return R.compose(this.dynamicListService.parseStringifiedFilter)(filterDTO);
|
||||
}
|
||||
}
|
||||
@@ -1,84 +0,0 @@
|
||||
// import * as R from 'ramda';
|
||||
// import {
|
||||
// IFilterMeta,
|
||||
// IPaginationMeta,
|
||||
// ISaleReceipt,
|
||||
// ISalesReceiptsFilter,
|
||||
// } from '@/interfaces';
|
||||
// import HasTenancyService from '@/services/Tenancy/TenancyService';
|
||||
// import { Inject, Service } from 'typedi';
|
||||
// import { SaleReceiptTransformer } from './SaleReceiptTransformer';
|
||||
// import { TransformerInjectable } from '@/lib/Transformer/TransformerInjectable';
|
||||
// import DynamicListingService from '@/services/DynamicListing/DynamicListService';
|
||||
|
||||
// interface GetSaleReceiptsSettings {
|
||||
// fetchEntriesGraph?: boolean;
|
||||
// }
|
||||
// @Service()
|
||||
// export class GetSaleReceipts {
|
||||
// @Inject()
|
||||
// private tenancy: HasTenancyService;
|
||||
|
||||
// @Inject()
|
||||
// private transformer: TransformerInjectable;
|
||||
|
||||
// @Inject()
|
||||
// private dynamicListService: DynamicListingService;
|
||||
|
||||
// /**
|
||||
// * Retrieve sales receipts paginated and filterable list.
|
||||
// * @param {number} tenantId
|
||||
// * @param {ISaleReceiptFilter} salesReceiptsFilter
|
||||
// */
|
||||
// public async getSaleReceipts(
|
||||
// tenantId: number,
|
||||
// filterDTO: ISalesReceiptsFilter
|
||||
// ): Promise<{
|
||||
// data: ISaleReceipt[];
|
||||
// pagination: IPaginationMeta;
|
||||
// filterMeta: IFilterMeta;
|
||||
// }> {
|
||||
// const { SaleReceipt } = this.tenancy.models(tenantId);
|
||||
|
||||
// // Parses the stringified filter roles.
|
||||
// const filter = this.parseListFilterDTO(filterDTO);
|
||||
|
||||
// // Dynamic list service.
|
||||
// const dynamicFilter = await this.dynamicListService.dynamicList(
|
||||
// tenantId,
|
||||
// SaleReceipt,
|
||||
// filter
|
||||
// );
|
||||
// const { results, pagination } = await SaleReceipt.query()
|
||||
// .onBuild((builder) => {
|
||||
// builder.withGraphFetched('depositAccount');
|
||||
// builder.withGraphFetched('customer');
|
||||
// builder.withGraphFetched('entries.item');
|
||||
|
||||
// dynamicFilter.buildQuery()(builder);
|
||||
// filterDTO?.filterQuery && filterDTO?.filterQuery(builder);
|
||||
// })
|
||||
// .pagination(filter.page - 1, filter.pageSize);
|
||||
|
||||
// // Transformes the estimates models to POJO.
|
||||
// const salesEstimates = await this.transformer.transform(
|
||||
// tenantId,
|
||||
// results,
|
||||
// new SaleReceiptTransformer()
|
||||
// );
|
||||
// return {
|
||||
// data: salesEstimates,
|
||||
// pagination,
|
||||
// filterMeta: dynamicFilter.getResponseMeta(),
|
||||
// };
|
||||
// }
|
||||
|
||||
// /**
|
||||
// * Parses the sale invoice list filter DTO.
|
||||
// * @param filterDTO
|
||||
// * @returns
|
||||
// */
|
||||
// private parseListFilterDTO(filterDTO) {
|
||||
// return R.compose(this.dynamicListService.parseStringifiedFilter)(filterDTO);
|
||||
// }
|
||||
// }
|
||||
Reference in New Issue
Block a user