fix: bugs in sales estimates.

This commit is contained in:
Ahmed Bouhuolia
2020-10-25 20:13:12 +02:00
parent ca6acf6517
commit d0dc322963
2 changed files with 40 additions and 10 deletions

View File

@@ -230,37 +230,47 @@ export default class SalesEstimatesController extends BaseController {
if (error instanceof ServiceError) { if (error instanceof ServiceError) {
if (error.errorType === 'ITEMS_NOT_FOUND') { if (error.errorType === 'ITEMS_NOT_FOUND') {
return res.boom.badRequest(null, { return res.boom.badRequest(null, {
errors: [{ type: 'ITEMS.IDS.NOT.EXISTS', code: 400 }], errors: [{ type: 'ITEMS.IDS.NOT.EXISTS', code: 100 }],
}); });
} }
if (error.errorType === 'ENTRIES_IDS_NOT_FOUND') { if (error.errorType === 'ENTRIES_IDS_NOT_FOUND') {
return res.boom.badRequest(null, { return res.boom.badRequest(null, {
errors: [{ type: 'ENTRIES.IDS.NOT.EXISTS', code: 300 }], errors: [{ type: 'ENTRIES.IDS.NOT.EXISTS', code: 200 }],
}); });
} }
if (error.errorType === 'ITEMS_IDS_NOT_EXISTS') { if (error.errorType === 'ITEMS_IDS_NOT_EXISTS') {
return res.boom.badRequest(null, { return res.boom.badRequest(null, {
errors: [{ type: 'ITEMS.IDS.NOT.EXISTS', code: 200 }], errors: [{ type: 'ITEMS.IDS.NOT.EXISTS', code: 300 }],
}); });
} }
if (error.errorType === 'NOT_PURCHASE_ABLE_ITEMS') { if (error.errorType === 'NOT_PURCHASE_ABLE_ITEMS') {
return res.boom.badRequest(null, { return res.boom.badRequest(null, {
errors: [{ type: 'NOT_PURCHASABLE_ITEMS', code: 200 }], errors: [{ type: 'NOT_PURCHASABLE_ITEMS', code: 400 }],
}); });
} }
if (error.errorType === 'SALE_ESTIMATE_NOT_FOUND') { if (error.errorType === 'SALE_ESTIMATE_NOT_FOUND') {
return res.boom.badRequest(null, { return res.boom.badRequest(null, {
errors: [{ type: 'SALE_ESTIMATE_NOT_FOUND', code: 200 }], errors: [{ type: 'SALE_ESTIMATE_NOT_FOUND', code: 500 }],
}); });
} }
if (error.errorType === 'CUSTOMER_NOT_FOUND') { if (error.errorType === 'CUSTOMER_NOT_FOUND') {
return res.boom.badRequest(null, { return res.boom.badRequest(null, {
errors: [{ type: 'CUSTOMER_NOT_FOUND', code: 200 }], errors: [{ type: 'CUSTOMER_NOT_FOUND', code: 600 }],
}); });
} }
if (error.errorType === 'SALE_ESTIMATE_NUMBER_EXISTANCE') { if (error.errorType === 'SALE_ESTIMATE_NUMBER_EXISTANCE') {
return res.boom.badRequest(null, { return res.boom.badRequest(null, {
errors: [{ type: 'ESTIMATE.NUMBER.IS.NOT.UNQIUE', code: 300 }], errors: [{ type: 'ESTIMATE.NUMBER.IS.NOT.UNQIUE', code: 700 }],
});
}
if (error.errorType === 'NOT_SELL_ABLE_ITEMS') {
return res.boom.badRequest(null, {
errors: [{ type: 'NOT_SELL_ABLE_ITEMS', code: 800 }],
});
}
if (error.errorType === 'contact_not_found') {
return res.boom.badRequest(null, {
errors: [{ type: 'CUSTOMER_NOT_FOUND', code: 900 }],
}); });
} }
} }

View File

@@ -19,7 +19,7 @@ const ERRORS = {
CUSTOMER_NOT_FOUND: 'CUSTOMER_NOT_FOUND', CUSTOMER_NOT_FOUND: 'CUSTOMER_NOT_FOUND',
SALE_ESTIMATE_NUMBER_EXISTANCE: 'SALE_ESTIMATE_NUMBER_EXISTANCE', SALE_ESTIMATE_NUMBER_EXISTANCE: 'SALE_ESTIMATE_NUMBER_EXISTANCE',
ITEMS_IDS_NOT_EXISTS: 'ITEMS_IDS_NOT_EXISTS', ITEMS_IDS_NOT_EXISTS: 'ITEMS_IDS_NOT_EXISTS',
} };
/** /**
* Sale estimate service. * Sale estimate service.
* @Service * @Service
@@ -97,14 +97,21 @@ export default class SaleEstimateService {
amount, amount,
...formatDateFields(estimateDTO, ['estimate_date', 'expiration_date']), ...formatDateFields(estimateDTO, ['estimate_date', 'expiration_date']),
}; };
// Validate estimate number uniquiness on the storage.
await this.validateEstimateNumberExistance(tenantId, estimateDTO.estimateNumber); await this.validateEstimateNumberExistance(tenantId, estimateDTO.estimateNumber);
// Retrieve the given customer or throw not found service error.
await this.customersService.getCustomer(tenantId, estimateDTO.customerId); await this.customersService.getCustomer(tenantId, estimateDTO.customerId);
// Validate items IDs existance on the storage.
await this.itemsEntriesService.validateItemsIdsExistance(tenantId, estimateDTO.entries); await this.itemsEntriesService.validateItemsIdsExistance(tenantId, estimateDTO.entries);
// Validate non-sellable items.
await this.itemsEntriesService.validateNonSellableEntriesItems(tenantId, estimateDTO.entries); await this.itemsEntriesService.validateNonSellableEntriesItems(tenantId, estimateDTO.entries);
const saleEstimate = await SaleEstimate.query() const saleEstimate = await SaleEstimate.query()
.upsertGraph({ .upsertGraphAndFetch({
...omit(estimateObj, ['entries']), ...omit(estimateObj, ['entries']),
entries: estimateObj.entries.map((entry) => ({ entries: estimateObj.entries.map((entry) => ({
reference_type: 'SaleEstimate', reference_type: 'SaleEstimate',
@@ -135,19 +142,29 @@ export default class SaleEstimateService {
amount, amount,
...formatDateFields(estimateDTO, ['estimate_date', 'expiration_date']), ...formatDateFields(estimateDTO, ['estimate_date', 'expiration_date']),
}; };
// Validate estimate number uniquiness on the storage.
await this.validateEstimateNumberExistance(tenantId, estimateDTO.estimateNumber, estimateId); await this.validateEstimateNumberExistance(tenantId, estimateDTO.estimateNumber, estimateId);
// Retrieve the given customer or throw not found service error.
await this.customersService.getCustomer(tenantId, estimateDTO.customerId); await this.customersService.getCustomer(tenantId, estimateDTO.customerId);
// Validate sale estimate entries existance.
await this.itemsEntriesService.validateEntriesIdsExistance(tenantId, estimateId, 'SaleEstiamte', estimateDTO.entries); await this.itemsEntriesService.validateEntriesIdsExistance(tenantId, estimateId, 'SaleEstiamte', estimateDTO.entries);
// Validate items IDs existance on the storage.
await this.itemsEntriesService.validateItemsIdsExistance(tenantId, estimateDTO.entries); await this.itemsEntriesService.validateItemsIdsExistance(tenantId, estimateDTO.entries);
// Validate non-sellable items.
await this.itemsEntriesService.validateNonSellableEntriesItems(tenantId, estimateDTO.entries); await this.itemsEntriesService.validateNonSellableEntriesItems(tenantId, estimateDTO.entries);
this.logger.info('[sale_estimate] editing sale estimate on the storage.'); this.logger.info('[sale_estimate] editing sale estimate on the storage.');
const saleEstimate = await SaleEstimate.query() const saleEstimate = await SaleEstimate.query()
.upsertGraph({ .upsertGraphAndFetch({
id: estimateId, id: estimateId,
...omit(estimateObj, ['entries']), ...omit(estimateObj, ['entries']),
entries: estimateObj.entries.map((entry) => ({ entries: estimateObj.entries.map((entry) => ({
reference_type: 'SaleEstimate',
...omit(entry, ['total', 'amount']), ...omit(entry, ['total', 'amount']),
})), })),
}); });
@@ -155,6 +172,8 @@ export default class SaleEstimateService {
await this.eventDispatcher.dispatch(events.saleEstimates.onEdited, { await this.eventDispatcher.dispatch(events.saleEstimates.onEdited, {
tenantId, estimateId, saleEstimate, oldSaleEstimate, tenantId, estimateId, saleEstimate, oldSaleEstimate,
}); });
this.logger.info('[sale_estiamte] edited successfully', { tenantId, estimateId });
return saleEstimate; return saleEstimate;
} }
@@ -168,6 +187,7 @@ export default class SaleEstimateService {
public async deleteEstimate(tenantId: number, estimateId: number): Promise<void> { public async deleteEstimate(tenantId: number, estimateId: number): Promise<void> {
const { SaleEstimate, ItemEntry } = this.tenancy.models(tenantId); const { SaleEstimate, ItemEntry } = this.tenancy.models(tenantId);
// Retrieve sale estimate or throw not found service error.
const oldSaleEstimate = await this.getSaleEstimateOrThrowError(tenantId, estimateId); const oldSaleEstimate = await this.getSaleEstimateOrThrowError(tenantId, estimateId);
this.logger.info('[sale_estimate] delete sale estimate and associated entries from the storage.'); this.logger.info('[sale_estimate] delete sale estimate and associated entries from the storage.');