|
|
@@ -40,6 +40,7 @@ import { unique } from '@vendure/common/lib/unique';
|
|
|
import { FindOptionsUtils } from 'typeorm/find-options/FindOptionsUtils';
|
|
|
|
|
|
import { RequestContext } from '../../api/common/request-context';
|
|
|
+import { RequestContextCacheService } from '../../cache/request-context-cache.service';
|
|
|
import { ErrorResultUnion, isGraphQlErrorResult } from '../../common/error/error-result';
|
|
|
import { EntityNotFoundError, InternalServerError, UserInputError } from '../../common/error/errors';
|
|
|
import {
|
|
|
@@ -154,6 +155,7 @@ export class OrderService {
|
|
|
private channelService: ChannelService,
|
|
|
private orderModifier: OrderModifier,
|
|
|
private customFieldRelationService: CustomFieldRelationService,
|
|
|
+ private requestCache: RequestContextCacheService,
|
|
|
) {}
|
|
|
|
|
|
/**
|
|
|
@@ -459,7 +461,7 @@ export class OrderService {
|
|
|
await this.orderModifier.updateOrderLineQuantity(ctx, orderLine, correctedQuantity, order);
|
|
|
}
|
|
|
const quantityWasAdjustedDown = correctedQuantity < quantity;
|
|
|
- const updatedOrder = await this.applyPriceAdjustments(ctx, order, orderLine);
|
|
|
+ const updatedOrder = await this.applyPriceAdjustments(ctx, order, [orderLine]);
|
|
|
if (quantityWasAdjustedDown) {
|
|
|
return new InsufficientStockError(correctedQuantity, updatedOrder);
|
|
|
} else {
|
|
|
@@ -509,7 +511,7 @@ export class OrderService {
|
|
|
await this.orderModifier.updateOrderLineQuantity(ctx, orderLine, correctedQuantity, order);
|
|
|
}
|
|
|
const quantityWasAdjustedDown = correctedQuantity < quantity;
|
|
|
- const updatedOrder = await this.applyPriceAdjustments(ctx, order, orderLine);
|
|
|
+ const updatedOrder = await this.applyPriceAdjustments(ctx, order, [orderLine]);
|
|
|
if (quantityWasAdjustedDown) {
|
|
|
return new InsufficientStockError(correctedQuantity, updatedOrder);
|
|
|
} else {
|
|
|
@@ -691,7 +693,12 @@ export class OrderService {
|
|
|
const order = await this.getOrderOrThrow(ctx, orderId);
|
|
|
const country = await this.countryService.findOneByCode(ctx, input.countryCode);
|
|
|
order.shippingAddress = { ...input, countryCode: input.countryCode, country: country.name };
|
|
|
- return this.connection.getRepository(ctx, Order).save(order);
|
|
|
+ await this.connection.getRepository(ctx, Order).save(order);
|
|
|
+ // Since a changed ShippingAddress could alter the activeTaxZone,
|
|
|
+ // we will remove any cached activeTaxZone so it can be re-calculated
|
|
|
+ // as needed.
|
|
|
+ this.requestCache.set(ctx, 'activeTaxZone', undefined);
|
|
|
+ return this.applyPriceAdjustments(ctx, order, order.lines);
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
@@ -702,7 +709,12 @@ export class OrderService {
|
|
|
const order = await this.getOrderOrThrow(ctx, orderId);
|
|
|
const country = await this.countryService.findOneByCode(ctx, input.countryCode);
|
|
|
order.billingAddress = { ...input, countryCode: input.countryCode, country: country.name };
|
|
|
- return this.connection.getRepository(ctx, Order).save(order);
|
|
|
+ await this.connection.getRepository(ctx, Order).save(order);
|
|
|
+ // Since a changed ShippingAddress could alter the activeTaxZone,
|
|
|
+ // we will remove any cached activeTaxZone so it can be re-calculated
|
|
|
+ // as needed.
|
|
|
+ this.requestCache.set(ctx, 'activeTaxZone', undefined);
|
|
|
+ return this.applyPriceAdjustments(ctx, order, order.lines);
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
@@ -1530,32 +1542,39 @@ export class OrderService {
|
|
|
private async applyPriceAdjustments(
|
|
|
ctx: RequestContext,
|
|
|
order: Order,
|
|
|
- updatedOrderLine?: OrderLine,
|
|
|
+ updatedOrderLines?: OrderLine[],
|
|
|
): Promise<Order> {
|
|
|
- if (updatedOrderLine) {
|
|
|
+ if (updatedOrderLines?.length) {
|
|
|
const { orderItemPriceCalculationStrategy, changedPriceHandlingStrategy } =
|
|
|
this.configService.orderOptions;
|
|
|
- let priceResult = await orderItemPriceCalculationStrategy.calculateUnitPrice(
|
|
|
- ctx,
|
|
|
- updatedOrderLine.productVariant,
|
|
|
- updatedOrderLine.customFields || {},
|
|
|
- );
|
|
|
- const initialListPrice =
|
|
|
- updatedOrderLine.items.find(i => i.initialListPrice != null)?.initialListPrice ??
|
|
|
- priceResult.price;
|
|
|
- if (initialListPrice !== priceResult.price) {
|
|
|
- priceResult = await changedPriceHandlingStrategy.handlePriceChange(
|
|
|
+ for (const updatedOrderLine of updatedOrderLines) {
|
|
|
+ const variant = await this.productVariantService.applyChannelPriceAndTax(
|
|
|
+ updatedOrderLine.productVariant,
|
|
|
ctx,
|
|
|
- priceResult,
|
|
|
- updatedOrderLine.items,
|
|
|
+ order,
|
|
|
);
|
|
|
- }
|
|
|
- for (const item of updatedOrderLine.items) {
|
|
|
- if (item.initialListPrice == null) {
|
|
|
- item.initialListPrice = initialListPrice;
|
|
|
+ let priceResult = await orderItemPriceCalculationStrategy.calculateUnitPrice(
|
|
|
+ ctx,
|
|
|
+ variant,
|
|
|
+ updatedOrderLine.customFields || {},
|
|
|
+ );
|
|
|
+ const initialListPrice =
|
|
|
+ updatedOrderLine.items.find(i => i.initialListPrice != null)?.initialListPrice ??
|
|
|
+ priceResult.price;
|
|
|
+ if (initialListPrice !== priceResult.price) {
|
|
|
+ priceResult = await changedPriceHandlingStrategy.handlePriceChange(
|
|
|
+ ctx,
|
|
|
+ priceResult,
|
|
|
+ updatedOrderLine.items,
|
|
|
+ );
|
|
|
+ }
|
|
|
+ for (const item of updatedOrderLine.items) {
|
|
|
+ if (item.initialListPrice == null) {
|
|
|
+ item.initialListPrice = initialListPrice;
|
|
|
+ }
|
|
|
+ item.listPrice = priceResult.price;
|
|
|
+ item.listPriceIncludesTax = priceResult.priceIncludesTax;
|
|
|
}
|
|
|
- item.listPrice = priceResult.price;
|
|
|
- item.listPriceIncludesTax = priceResult.priceIncludesTax;
|
|
|
}
|
|
|
}
|
|
|
const { items: promotions } = await this.promotionService.findAll(ctx, {
|
|
|
@@ -1566,7 +1585,7 @@ export class OrderService {
|
|
|
ctx,
|
|
|
order,
|
|
|
promotions,
|
|
|
- updatedOrderLine ? [updatedOrderLine] : [],
|
|
|
+ updatedOrderLines ?? [],
|
|
|
);
|
|
|
const updateFields: Array<keyof OrderItem> = [
|
|
|
'initialListPrice',
|