mirror of
https://github.com/bigcapitalhq/bigcapital.git
synced 2026-02-18 05:40:31 +00:00
add server to monorepo.
This commit is contained in:
197
packages/server/src/subscribers/Inventory/Inventory.ts
Normal file
197
packages/server/src/subscribers/Inventory/Inventory.ts
Normal file
@@ -0,0 +1,197 @@
|
||||
import { Inject, Service } from 'typedi';
|
||||
import { map, head } from 'lodash';
|
||||
|
||||
import events from '@/subscribers/events';
|
||||
import TenancyService from '@/services/Tenancy/TenancyService';
|
||||
import SaleInvoicesCost from '@/services/Sales/SalesInvoicesCost';
|
||||
import InventoryItemsQuantitySync from '@/services/Inventory/InventoryItemsQuantitySync';
|
||||
import InventoryService from '@/services/Inventory/Inventory';
|
||||
import {
|
||||
IComputeItemCostJobCompletedPayload,
|
||||
IInventoryTransactionsCreatedPayload,
|
||||
IInventoryTransactionsDeletedPayload,
|
||||
} from '@/interfaces';
|
||||
import { runAfterTransaction } from '@/services/UnitOfWork/TransactionsHooks';
|
||||
|
||||
@Service()
|
||||
export default class InventorySubscriber {
|
||||
@Inject()
|
||||
saleInvoicesCost: SaleInvoicesCost;
|
||||
|
||||
@Inject()
|
||||
tenancy: TenancyService;
|
||||
|
||||
@Inject()
|
||||
itemsQuantitySync: InventoryItemsQuantitySync;
|
||||
|
||||
@Inject()
|
||||
inventoryService: InventoryService;
|
||||
|
||||
@Inject('agenda')
|
||||
agenda: any;
|
||||
|
||||
/**
|
||||
* Attaches events with handlers.
|
||||
*/
|
||||
public attach(bus) {
|
||||
bus.subscribe(
|
||||
events.inventory.onInventoryTransactionsCreated,
|
||||
this.handleScheduleItemsCostOnInventoryTransactionsCreated
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventory.onInventoryTransactionsCreated,
|
||||
this.syncItemsQuantityOnceInventoryTransactionsCreated
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventory.onComputeItemCostJobScheduled,
|
||||
this.markGlobalSettingsComputeItems
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventory.onInventoryCostEntriesWritten,
|
||||
this.markGlobalSettingsComputeItemsCompeted
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventory.onComputeItemCostJobCompleted,
|
||||
this.onComputeItemCostJobFinished
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventory.onInventoryTransactionsDeleted,
|
||||
this.handleScheduleItemsCostOnInventoryTransactionsDeleted
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventory.onInventoryTransactionsDeleted,
|
||||
this.syncItemsQuantityOnceInventoryTransactionsDeleted
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Sync inventory items quantity once inventory transactions created.
|
||||
* @param {IInventoryTransactionsCreatedPayload} payload -
|
||||
*/
|
||||
private syncItemsQuantityOnceInventoryTransactionsCreated = async ({
|
||||
tenantId,
|
||||
inventoryTransactions,
|
||||
trx,
|
||||
}: IInventoryTransactionsCreatedPayload) => {
|
||||
const itemsQuantityChanges = this.itemsQuantitySync.getItemsQuantityChanges(
|
||||
inventoryTransactions
|
||||
);
|
||||
|
||||
await this.itemsQuantitySync.changeItemsQuantity(
|
||||
tenantId,
|
||||
itemsQuantityChanges,
|
||||
trx
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
* Handles schedule compute inventory items cost once inventory transactions created.
|
||||
* @param {IInventoryTransactionsCreatedPayload} payload -
|
||||
*/
|
||||
private handleScheduleItemsCostOnInventoryTransactionsCreated = async ({
|
||||
tenantId,
|
||||
inventoryTransactions,
|
||||
trx
|
||||
}: IInventoryTransactionsCreatedPayload) => {
|
||||
const inventoryItemsIds = map(inventoryTransactions, 'itemId');
|
||||
|
||||
runAfterTransaction(trx, async () => {
|
||||
try {
|
||||
await this.saleInvoicesCost.computeItemsCostByInventoryTransactions(
|
||||
tenantId,
|
||||
inventoryTransactions
|
||||
);
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* Marks items cost compute running state.
|
||||
*/
|
||||
private markGlobalSettingsComputeItems = async ({ tenantId }) => {
|
||||
await this.inventoryService.markItemsCostComputeRunning(tenantId, true);
|
||||
};
|
||||
|
||||
/**
|
||||
* Marks items cost compute as completed.
|
||||
*/
|
||||
private markGlobalSettingsComputeItemsCompeted = async ({ tenantId }) => {
|
||||
await this.inventoryService.markItemsCostComputeRunning(tenantId, false);
|
||||
};
|
||||
|
||||
/**
|
||||
* Handle run writing the journal entries once the compute items jobs completed.
|
||||
*/
|
||||
private onComputeItemCostJobFinished = async ({
|
||||
itemId,
|
||||
tenantId,
|
||||
startingDate,
|
||||
}: IComputeItemCostJobCompletedPayload) => {
|
||||
const dependsComputeJobs = await this.agenda.jobs({
|
||||
name: 'compute-item-cost',
|
||||
nextRunAt: { $ne: null },
|
||||
'data.tenantId': tenantId,
|
||||
});
|
||||
// There is no scheduled compute jobs waiting.
|
||||
if (dependsComputeJobs.length === 0) {
|
||||
await this.saleInvoicesCost.scheduleWriteJournalEntries(
|
||||
tenantId,
|
||||
startingDate
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Sync inventory items quantity once inventory transactions deleted.
|
||||
*/
|
||||
private syncItemsQuantityOnceInventoryTransactionsDeleted = async ({
|
||||
tenantId,
|
||||
oldInventoryTransactions,
|
||||
trx,
|
||||
}: IInventoryTransactionsDeletedPayload) => {
|
||||
const itemsQuantityChanges =
|
||||
this.itemsQuantitySync.getReverseItemsQuantityChanges(
|
||||
oldInventoryTransactions
|
||||
);
|
||||
await this.itemsQuantitySync.changeItemsQuantity(
|
||||
tenantId,
|
||||
itemsQuantityChanges,
|
||||
trx
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
* Schedules compute items cost once the inventory transactions deleted.
|
||||
*/
|
||||
private handleScheduleItemsCostOnInventoryTransactionsDeleted = async ({
|
||||
tenantId,
|
||||
transactionType,
|
||||
transactionId,
|
||||
oldInventoryTransactions,
|
||||
trx,
|
||||
}: IInventoryTransactionsDeletedPayload) => {
|
||||
// Ignore compute item cost with theses transaction types.
|
||||
const ignoreWithTransactionTypes = ['OpeningItem'];
|
||||
|
||||
if (ignoreWithTransactionTypes.indexOf(transactionType) !== -1) {
|
||||
return;
|
||||
}
|
||||
const inventoryItemsIds = map(oldInventoryTransactions, 'itemId');
|
||||
const startingDates = map(oldInventoryTransactions, 'date');
|
||||
const startingDate: Date = head(startingDates);
|
||||
|
||||
runAfterTransaction(trx, async () => {
|
||||
try {
|
||||
await this.saleInvoicesCost.scheduleComputeCostByItemsIds(
|
||||
tenantId,
|
||||
inventoryItemsIds,
|
||||
startingDate
|
||||
);
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
}
|
||||
});
|
||||
};
|
||||
}
|
||||
134
packages/server/src/subscribers/Inventory/InventoryAdjustment.ts
Normal file
134
packages/server/src/subscribers/Inventory/InventoryAdjustment.ts
Normal file
@@ -0,0 +1,134 @@
|
||||
import { Inject, Service } from 'typedi';
|
||||
import events from '@/subscribers/events';
|
||||
import InventoryAdjustmentService from '@/services/Inventory/InventoryAdjustmentService';
|
||||
import InventoryAdjustmentsGL from '@/services/Inventory/InventoryAdjustmentGL';
|
||||
import {
|
||||
IInventoryAdjustmentEventCreatedPayload,
|
||||
IInventoryAdjustmentEventDeletedPayload,
|
||||
IInventoryAdjustmentEventPublishedPayload,
|
||||
} from '@/interfaces';
|
||||
|
||||
@Service()
|
||||
export default class InventoryAdjustmentsSubscriber {
|
||||
@Inject()
|
||||
private inventoryAdjustment: InventoryAdjustmentService;
|
||||
|
||||
@Inject()
|
||||
private inventoryAdjustmentGL: InventoryAdjustmentsGL;
|
||||
|
||||
/**
|
||||
* Attaches events with handles.
|
||||
* @param bus
|
||||
*/
|
||||
public attach(bus) {
|
||||
bus.subscribe(
|
||||
events.inventoryAdjustment.onQuickCreated,
|
||||
this.handleWriteInventoryTransactionsOncePublished
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventoryAdjustment.onQuickCreated,
|
||||
this.handleGLEntriesOnceIncrementAdjustmentCreated
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventoryAdjustment.onPublished,
|
||||
this.handleGLEntriesOnceIncrementAdjustmentCreated
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventoryAdjustment.onPublished,
|
||||
this.handleWriteInventoryTransactionsOncePublished
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventoryAdjustment.onDeleted,
|
||||
this.handleRevertInventoryTransactionsOnceDeleted
|
||||
);
|
||||
bus.subscribe(
|
||||
events.inventoryAdjustment.onDeleted,
|
||||
this.revertAdjustmentGLEntriesOnceDeleted
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles writing increment inventory adjustment GL entries.
|
||||
*/
|
||||
private handleGLEntriesOnceIncrementAdjustmentCreated = async ({
|
||||
tenantId,
|
||||
inventoryAdjustmentId,
|
||||
inventoryAdjustment,
|
||||
trx,
|
||||
}: IInventoryAdjustmentEventCreatedPayload) => {
|
||||
// Can't continue if the inventory adjustment is not published.
|
||||
if (!inventoryAdjustment.isPublished) {
|
||||
return;
|
||||
}
|
||||
// Can't continue if the inventory adjustment direction is not `IN`.
|
||||
if (inventoryAdjustment.type !== 'increment') {
|
||||
return;
|
||||
}
|
||||
await this.inventoryAdjustmentGL.writeAdjustmentGLEntries(
|
||||
tenantId,
|
||||
inventoryAdjustmentId,
|
||||
trx
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
* Handles writing inventory transactions once the quick adjustment created.
|
||||
* @param {IInventoryAdjustmentEventPublishedPayload} payload
|
||||
* @param {IInventoryAdjustmentEventCreatedPayload} payload -
|
||||
*/
|
||||
private handleWriteInventoryTransactionsOncePublished = async ({
|
||||
tenantId,
|
||||
inventoryAdjustment,
|
||||
trx,
|
||||
}:
|
||||
| IInventoryAdjustmentEventPublishedPayload
|
||||
| IInventoryAdjustmentEventCreatedPayload) => {
|
||||
await this.inventoryAdjustment.writeInventoryTransactions(
|
||||
tenantId,
|
||||
inventoryAdjustment,
|
||||
false,
|
||||
trx
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
* Handles reverting invetory transactions once the inventory adjustment deleted.
|
||||
* @param {IInventoryAdjustmentEventDeletedPayload} payload -
|
||||
*/
|
||||
private handleRevertInventoryTransactionsOnceDeleted = async ({
|
||||
tenantId,
|
||||
inventoryAdjustmentId,
|
||||
oldInventoryAdjustment,
|
||||
trx,
|
||||
}: IInventoryAdjustmentEventDeletedPayload) => {
|
||||
// Can't continue if the inventory adjustment is not published.
|
||||
if (!oldInventoryAdjustment.isPublished) {
|
||||
return;
|
||||
}
|
||||
// Reverts the inventory transactions of adjustment transaction.
|
||||
await this.inventoryAdjustment.revertInventoryTransactions(
|
||||
tenantId,
|
||||
inventoryAdjustmentId,
|
||||
trx
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
* Reverts the inventory adjustment GL entries once the transaction deleted.
|
||||
* @param {IInventoryAdjustmentEventDeletedPayload} payload -
|
||||
*/
|
||||
private revertAdjustmentGLEntriesOnceDeleted = async ({
|
||||
tenantId,
|
||||
inventoryAdjustmentId,
|
||||
oldInventoryAdjustment,
|
||||
}: IInventoryAdjustmentEventDeletedPayload) => {
|
||||
// Can't continue if the inventory adjustment is not published.
|
||||
if (!oldInventoryAdjustment.isPublished) {
|
||||
return;
|
||||
}
|
||||
await this.inventoryAdjustmentGL.revertAdjustmentGLEntries(
|
||||
tenantId,
|
||||
inventoryAdjustmentId
|
||||
);
|
||||
};
|
||||
}
|
||||
Reference in New Issue
Block a user