fix(): Cart workflow price calculation for different items but same variant (#13511)

RESOLVES CORE-1204

**What**
- Fix wrong price tier when multiple items are targetting the same variant
- fix type import from the wrong package

**Notes**
If you are struggling navigating the changes, you can focus on the following files:
```
integration-tests/http/__tests__/cart/store/cart.spec.ts
integration-tests/modules/__tests__/cart/store/cart.workflows.spec.ts
packages/core/core-flows/src/cart/steps/get-promotion-codes-to-apply.ts
packages/core/core-flows/src/cart/steps/get-variant-price-sets.ts
packages/core/core-flows/src/cart/workflows/add-to-cart.ts
packages/core/core-flows/src/cart/workflows/create-carts.ts
packages/core/core-flows/src/cart/workflows/get-variants-and-items-with-prices.ts
packages/core/core-flows/src/cart/workflows/refresh-cart-items.ts
packages/core/core-flows/src/order/workflows/add-line-items.ts
packages/core/core-flows/src/order/workflows/create-order.ts
```
This commit is contained in:
Adrien de Peretti
2025-09-26 07:19:46 +00:00
committed by GitHub
parent 3960c80e9f
commit 5ea32aaa44
281 changed files with 1864 additions and 1466 deletions
+5
View File
@@ -0,0 +1,5 @@
---
"@medusajs/core-flows": patch
---
fix(): Cart workflow price calculation for different items but same variant
@@ -285,6 +285,156 @@ medusaIntegrationTestRunner({
) )
}) })
it("should successfully create a cart with a line items for the same variant with different quantities and calculate prices based on the correct quantity", async () => {
const productData = {
title: "Medusa T-Shirt based quantity",
handle: "t-shirt-with-quantity-prices",
status: ProductStatus.PUBLISHED,
options: [
{
title: "Size",
values: ["S"],
},
],
variants: [
{
title: "S",
sku: "SHIRT-S-BLACK-w-quantity-prices",
options: {
Size: "S",
},
manage_inventory: false,
prices: [
{
amount: 1500,
currency_code: "usd",
min_quantity: 1,
max_quantity: 4,
},
{
amount: 1000,
currency_code: "usd",
min_quantity: 5,
max_quantity: 10,
},
],
},
],
}
const newProduct = await api.post(
`/admin/products`,
productData,
adminHeaders
)
const variantId = newProduct.data.product.variants[0].id
const newCart = (
await api.post(
`/store/carts`,
{
currency_code: "usd",
sales_channel_id: salesChannel.id,
region_id: region.id,
shipping_address: shippingAddressData,
items: [{ variant_id: variantId, quantity: 6 }],
},
storeHeaders
)
).data.cart
expect(newCart).toEqual(
expect.objectContaining({
item_subtotal: 5714.285714285715,
item_tax_total: 285.7142857142857,
item_total: 6000,
items: [
expect.objectContaining({
quantity: 6,
title: "Medusa T-Shirt based quantity",
unit_price: 1000,
updated_at: expect.any(String),
variant_barcode: null,
variant_id: expect.any(String),
variant_sku: "SHIRT-S-BLACK-w-quantity-prices",
variant_title: "S",
}),
],
original_item_subtotal: 5714.285714285715,
original_item_tax_total: 285.7142857142857,
original_item_total: 6000,
original_shipping_subtotal: 0,
original_shipping_tax_total: 0,
original_shipping_total: 0,
original_tax_total: 285.7142857142857,
original_total: 6000,
shipping_subtotal: 0,
shipping_tax_total: 0,
shipping_total: 0,
subtotal: 5714.285714285715,
tax_total: 285.7142857142857,
total: 6000,
})
)
const updatedCart = (
await api.post(
`/store/carts/${newCart.id}/line-items`,
{
variant_id: variantId,
quantity: 1,
metadata: { custom: true },
},
storeHeaders
)
).data.cart
expect(updatedCart).toEqual(
expect.objectContaining({
item_subtotal: 7142.857142857143,
item_tax_total: 357.14285714285717,
item_total: 7500,
items: expect.arrayContaining([
expect.objectContaining({
quantity: 6,
title: "Medusa T-Shirt based quantity",
unit_price: 1000,
updated_at: expect.any(String),
variant_barcode: null,
variant_id: expect.any(String),
variant_sku: "SHIRT-S-BLACK-w-quantity-prices",
variant_title: "S",
}),
expect.objectContaining({
quantity: 1,
title: "Medusa T-Shirt based quantity",
unit_price: 1500,
updated_at: expect.any(String),
variant_barcode: null,
variant_id: expect.any(String),
variant_sku: "SHIRT-S-BLACK-w-quantity-prices",
variant_title: "S",
}),
]),
original_item_subtotal: 7142.857142857143,
original_item_tax_total: 357.14285714285717,
original_item_total: 7500,
original_shipping_subtotal: 0,
original_shipping_tax_total: 0,
original_shipping_total: 0,
original_tax_total: 357.14285714285717,
original_total: 7500,
shipping_subtotal: 0,
shipping_tax_total: 0,
shipping_total: 0,
subtotal: 7142.857142857143,
tax_total: 357.14285714285717,
total: 7500,
})
)
})
describe("with sale price lists", () => { describe("with sale price lists", () => {
let priceList let priceList
@@ -1881,7 +1881,7 @@ medusaIntegrationTestRunner({
expect(errors).toEqual([ expect(errors).toEqual([
{ {
action: "get-variant-price-sets", action: "get-variant-items-with-prices-workflow-as-step",
handlerType: "invoke", handlerType: "invoke",
error: expect.objectContaining({ error: expect.objectContaining({
message: expect.stringContaining( message: expect.stringContaining(
@@ -4307,18 +4307,20 @@ medusaIntegrationTestRunner({
}) })
} }
const { result: result1 } = await listShippingOptionsForCartWorkflow( const { result: result1 } =
appContainer await listShippingOptionsForCartWorkflow(appContainer).run({
).run({ input: { cart_id: cart.id } }) input: { cart_id: cart.id },
})
expect(result1).toHaveLength(1) expect(result1).toHaveLength(1)
expect(result1[0].name).toEqual(shippingOption.name) expect(result1[0].name).toEqual(shippingOption.name)
setShippingOptionsContextHook = undefined setShippingOptionsContextHook = undefined
const { result: result2 } = await listShippingOptionsForCartWorkflow( const { result: result2 } =
appContainer await listShippingOptionsForCartWorkflow(appContainer).run({
).run({ input: { cart_id: cart.id } }) input: { cart_id: cart.id },
})
expect(result2).toHaveLength(0) expect(result2).toHaveLength(0)
}) })
@@ -1,4 +1,4 @@
import { IApiKeyModuleService } from "@medusajs/framework/types" import type { IApiKeyModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,4 @@
import { LinkWorkflowInput } from "@medusajs/framework/types" import type { LinkWorkflowInput } from "@medusajs/framework/types"
import { import {
ContainerRegistrationKeys, ContainerRegistrationKeys,
Modules, Modules,
@@ -8,7 +8,7 @@ import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
/** /**
* The data to manage the sales channels of a publishable API key. * The data to manage the sales channels of a publishable API key.
* *
* @property id - The ID of the publishable API key. * @property id - The ID of the publishable API key.
* @property add - The sales channel IDs to add to the publishable API key. * @property add - The sales channel IDs to add to the publishable API key.
* @property remove - The sales channel IDs to remove from the publishable API key. * @property remove - The sales channel IDs to remove from the publishable API key.
@@ -18,7 +18,7 @@ export type LinkSalesChannelsToApiKeyStepInput = LinkWorkflowInput
export const linkSalesChannelsToApiKeyStepId = "link-sales-channels-to-api-key" export const linkSalesChannelsToApiKeyStepId = "link-sales-channels-to-api-key"
/** /**
* This step manages the sales channels of a publishable API key. * This step manages the sales channels of a publishable API key.
* *
* @example * @example
* const data = linkSalesChannelsToApiKeyStep({ * const data = linkSalesChannelsToApiKeyStep({
* id: "apk_123", * id: "apk_123",
@@ -1,4 +1,4 @@
import { ISalesChannelModuleService } from "@medusajs/framework/types" import type { ISalesChannelModuleService } from "@medusajs/framework/types"
import { import {
MedusaError, MedusaError,
Modules, Modules,
@@ -1,4 +1,4 @@
import { ApiKeyDTO, CreateApiKeyDTO } from "@medusajs/framework/types" import type { ApiKeyDTO, CreateApiKeyDTO } from "@medusajs/framework/types"
import { import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
@@ -1,4 +1,4 @@
import { LinkWorkflowInput } from "@medusajs/framework/types" import type { LinkWorkflowInput } from "@medusajs/framework/types"
import { WorkflowData, createWorkflow } from "@medusajs/framework/workflows-sdk" import { WorkflowData, createWorkflow } from "@medusajs/framework/workflows-sdk"
import { import {
linkSalesChannelsToApiKeyStep, linkSalesChannelsToApiKeyStep,
@@ -7,7 +7,7 @@ import {
/** /**
* The data to manage the sales channels of a publishable API key. * The data to manage the sales channels of a publishable API key.
* *
* @property id - The ID of the publishable API key. * @property id - The ID of the publishable API key.
* @property add - The sales channel IDs to add to the publishable API key. * @property add - The sales channel IDs to add to the publishable API key.
* @property remove - The sales channel IDs to remove from the publishable API key. * @property remove - The sales channel IDs to remove from the publishable API key.
@@ -19,10 +19,10 @@ export const linkSalesChannelsToApiKeyWorkflowId =
/** /**
* This workflow manages the sales channels of a publishable API key. It's used by the * This workflow manages the sales channels of a publishable API key. It's used by the
* [Manage Sales Channels API Route](https://docs.medusajs.com/api/admin#api-keys_postapikeysidsaleschannels). * [Manage Sales Channels API Route](https://docs.medusajs.com/api/admin#api-keys_postapikeysidsaleschannels).
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to * You can use this workflow within your customizations or your own custom workflows, allowing you to
* manage the sales channels of a publishable API key within your custom flows. * manage the sales channels of a publishable API key within your custom flows.
* *
* @example * @example
* const { result } = await linkSalesChannelsToApiKeyWorkflow(container) * const { result } = await linkSalesChannelsToApiKeyWorkflow(container)
* .run({ * .run({
@@ -32,7 +32,7 @@ export const linkSalesChannelsToApiKeyWorkflowId =
* remove: ["sc_321"] * remove: ["sc_321"]
* } * }
* }) * })
* *
* @summary * @summary
* Manage the sales channels of a publishable API key. * Manage the sales channels of a publishable API key.
*/ */
@@ -1,6 +1,6 @@
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { IAuthModuleService } from "@medusajs/framework/types" import type { IAuthModuleService } from "@medusajs/framework/types"
import { isDefined, Modules } from "@medusajs/framework/utils" import { isDefined, Modules } from "@medusajs/framework/utils"
export type SetAuthAppMetadataStepInput = { export type SetAuthAppMetadataStepInput = {
@@ -14,16 +14,16 @@ export const setAuthAppMetadataStepId = "set-auth-app-metadata"
* This step sets the `app_metadata` property of an auth identity. This is useful to * This step sets the `app_metadata` property of an auth identity. This is useful to
* associate a user (whether it's an admin user or customer) with an auth identity * associate a user (whether it's an admin user or customer) with an auth identity
* that allows them to authenticate into Medusa. * that allows them to authenticate into Medusa.
* *
* You can learn more about auth identites in * You can learn more about auth identites in
* [this documentation](https://docs.medusajs.com/resources/commerce-modules/auth/auth-identity-and-actor-types). * [this documentation](https://docs.medusajs.com/resources/commerce-modules/auth/auth-identity-and-actor-types).
* *
* To use this for a custom actor type, check out [this guide](https://docs.medusajs.com/resources/commerce-modules/auth/create-actor-type) * To use this for a custom actor type, check out [this guide](https://docs.medusajs.com/resources/commerce-modules/auth/create-actor-type)
* that explains how to create a custom `manager` actor type and manage its users. * that explains how to create a custom `manager` actor type and manage its users.
* *
* @example * @example
* To associate an auth identity with an actor type (user, customer, or other actor types): * To associate an auth identity with an actor type (user, customer, or other actor types):
* *
* ```ts * ```ts
* const data = setAuthAppMetadataStep({ * const data = setAuthAppMetadataStep({
* authIdentityId: "au_1234", * authIdentityId: "au_1234",
@@ -31,9 +31,9 @@ export const setAuthAppMetadataStepId = "set-auth-app-metadata"
* value: "user_123" * value: "user_123"
* }) * })
* ``` * ```
* *
* To remove the association with an actor type, such as when deleting the user: * To remove the association with an actor type, such as when deleting the user:
* *
* ```ts * ```ts
* const data = setAuthAppMetadataStep({ * const data = setAuthAppMetadataStep({
* authIdentityId: "au_1234", * authIdentityId: "au_1234",
@@ -9,7 +9,7 @@ import {
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { emitEventStep, useRemoteQueryStep } from "../../common" import { emitEventStep, useRemoteQueryStep } from "../../common"
import { ProjectConfigOptions } from "@medusajs/framework/types" import type { ProjectConfigOptions } from "@medusajs/framework/types"
/** /**
* This workflow generates a reset password token for a user. It's used by the * This workflow generates a reset password token for a user. It's used by the
@@ -1,4 +1,4 @@
import { Logger } from "@medusajs/framework/types" import type { Logger } from "@medusajs/framework/types"
import { ContainerRegistrationKeys } from "@medusajs/framework/utils" import { ContainerRegistrationKeys } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { refundPaymentAndRecreatePaymentSessionWorkflow } from "../workflows/refund-payment-recreate-payment-session" import { refundPaymentAndRecreatePaymentSessionWorkflow } from "../workflows/refund-payment-recreate-payment-session"
@@ -1,4 +1,7 @@
import { BigNumberInput, IInventoryService } from "@medusajs/framework/types" import type {
BigNumberInput,
IInventoryService,
} from "@medusajs/framework/types"
import { import {
MathBN, MathBN,
MedusaError, MedusaError,
@@ -1,4 +1,7 @@
import { CreateCartDTO, ICartModuleService } from "@medusajs/framework/types" import type {
CreateCartDTO,
ICartModuleService,
} from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,7 @@
import { CustomerDTO, ICustomerModuleService } from "@medusajs/framework/types" import type {
CustomerDTO,
ICustomerModuleService,
} from "@medusajs/framework/types"
import { isDefined, Modules, validateEmail } from "@medusajs/framework/utils" import { isDefined, Modules, validateEmail } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,7 @@
import { CartDTO, IPromotionModuleService } from "@medusajs/framework/types" import type {
CartDTO,
IPromotionModuleService,
} from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,4 @@
import { IPromotionModuleService } from "@medusajs/framework/types" import type { IPromotionModuleService } from "@medusajs/framework/types"
import { import {
MedusaError, MedusaError,
Modules, Modules,
@@ -79,7 +79,7 @@ export const getPromotionCodesToApply = createStep(
const adjustmentCodes: string[] = [] const adjustmentCodes: string[] = []
items.concat(shipping_methods).forEach((object) => { items.concat(shipping_methods).forEach((object) => {
object.adjustments?.forEach((adjustment) => { object.adjustments?.forEach((adjustment) => {
if (adjustment.code && !adjustmentCodes.includes(adjustment.code)) { if (adjustment.code) {
adjustmentCodes.push(adjustment.code) adjustmentCodes.push(adjustment.code)
} }
}) })
@@ -34,6 +34,10 @@ export interface GetVariantPriceSetsStepBulkInput {
* The variants to get price sets for. * The variants to get price sets for.
*/ */
data: { data: {
/**
* The ID of the item.
*/
id?: string
/** /**
* The ID of the variant to get the price set for. * The ID of the variant to get the price set for.
*/ */
@@ -51,6 +55,10 @@ interface VariantPriceSetData {
} }
interface PriceCalculationItem { interface PriceCalculationItem {
/**
* The ID of the item. In case of variants we wont have an item id
*/
id?: string
variantId: string variantId: string
priceSetId: string priceSetId: string
context?: Record<string, unknown> context?: Record<string, unknown>
@@ -124,7 +132,7 @@ async function processVariantPriceSets(
for (const item of groupItems) { for (const item of groupItems) {
const calculatedPriceSet = priceSetMap.get(item.priceSetId) const calculatedPriceSet = priceSetMap.get(item.priceSetId)
if (calculatedPriceSet) { if (calculatedPriceSet) {
result[item.variantId] = calculatedPriceSet result[item.id ?? item.variantId] = calculatedPriceSet
} }
} }
} }
@@ -196,6 +204,7 @@ function createCalculationItemsFromBulkData(
const priceSetId = variantToPriceSetId.get(item.variantId) const priceSetId = variantToPriceSetId.get(item.variantId)
if (priceSetId) { if (priceSetId) {
calculationItems.push({ calculationItems.push({
id: item.id,
variantId: item.variantId, variantId: item.variantId,
priceSetId, priceSetId,
context: item.context, context: item.context,
@@ -1,4 +1,4 @@
import { ICartModuleService } from "@medusajs/framework/types" import type { ICartModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,4 @@
import { ICartModuleService } from "@medusajs/framework/types" import type { ICartModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,4 @@
import { ICartModuleService } from "@medusajs/framework/types" import type { ICartModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -16,7 +16,10 @@ export interface RemoveShippingMethodFromCartStepInput {
* The shipping methods removed from the cart, along with IDs of related records * The shipping methods removed from the cart, along with IDs of related records
* that were removed. * that were removed.
*/ */
export type RemoveShippingMethodFromCartStepOutput = Record<string, string[]> | void export type RemoveShippingMethodFromCartStepOutput = Record<
string,
string[]
> | void
export const removeShippingMethodFromCartStepId = export const removeShippingMethodFromCartStepId =
"remove-shipping-method-to-cart-step" "remove-shipping-method-to-cart-step"
@@ -37,7 +40,7 @@ export const removeShippingMethodFromCartStep = createStep(
) )
return new StepResponse( return new StepResponse(
methods as RemoveShippingMethodFromCartStepOutput, methods as RemoveShippingMethodFromCartStepOutput,
data.shipping_method_ids data.shipping_method_ids
) )
}, },
@@ -1,6 +1,6 @@
import { MathBN, Modules } from "@medusajs/framework/utils" import { MathBN, Modules } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { BigNumberInput } from "@medusajs/types" import type { BigNumberInput } from "@medusajs/framework/types"
/** /**
* The details of the items and their quantity to reserve. * The details of the items and their quantity to reserve.
@@ -1,4 +1,4 @@
import { IPromotionModuleService } from "@medusajs/framework/types" import type { IPromotionModuleService } from "@medusajs/framework/types"
import { import {
ContainerRegistrationKeys, ContainerRegistrationKeys,
Modules, Modules,
@@ -1,4 +1,4 @@
import { CartWorkflowDTO } from "@medusajs/framework/types" import type { CartWorkflowDTO } from "@medusajs/framework/types"
import { import {
isPresent, isPresent,
MathBN, MathBN,
@@ -1,5 +1,12 @@
import { CartDTO, IFulfillmentModuleService } from "@medusajs/framework/types" import type {
import { arrayDifference, MedusaError, Modules, } from "@medusajs/framework/utils" CartDTO,
IFulfillmentModuleService,
} from "@medusajs/framework/types"
import {
arrayDifference,
MedusaError,
Modules,
} from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
/** /**
@@ -39,7 +46,7 @@ export const validateCartShippingOptionsStepId =
/** /**
* This step validates shipping options to ensure they can be applied on a cart. * This step validates shipping options to ensure they can be applied on a cart.
* If not valid, the step throws an error. * If not valid, the step throws an error.
* *
* @example * @example
* const data = validateCartShippingOptionsStep({ * const data = validateCartShippingOptionsStep({
* // retrieve the details of the cart from another workflow * // retrieve the details of the cart from another workflow
@@ -52,7 +59,12 @@ export const validateCartShippingOptionsStepId =
export const validateCartShippingOptionsStep = createStep( export const validateCartShippingOptionsStep = createStep(
validateCartShippingOptionsStepId, validateCartShippingOptionsStepId,
async (data: ValidateCartShippingOptionsStepInput, { container }) => { async (data: ValidateCartShippingOptionsStepInput, { container }) => {
const { option_ids: optionIds = [], cart, shippingOptionsContext, prefetched_shipping_options: prefetchedShippingOptions } = data const {
option_ids: optionIds = [],
cart,
shippingOptionsContext,
prefetched_shipping_options: prefetchedShippingOptions,
} = data
if (!optionIds.length) { if (!optionIds.length) {
return new StepResponse(void 0) return new StepResponse(void 0)
@@ -1,4 +1,4 @@
import { CartDTO, CartWorkflowDTO } from "@medusajs/framework/types" import type { CartDTO, CartWorkflowDTO } from "@medusajs/framework/types"
import { MedusaError } from "@medusajs/framework/utils" import { MedusaError } from "@medusajs/framework/utils"
import { createStep } from "@medusajs/framework/workflows-sdk" import { createStep } from "@medusajs/framework/workflows-sdk"
@@ -16,13 +16,13 @@ export const validateCartStepId = "validate-cart"
/** /**
* This step validates a cart to ensure it exists and is not completed. * This step validates a cart to ensure it exists and is not completed.
* If not valid, the step throws an error. * If not valid, the step throws an error.
* *
* :::tip * :::tip
* *
* You can use the {@link retrieveCartStep} to retrieve a cart's details. * You can use the {@link retrieveCartStep} to retrieve a cart's details.
* *
* ::: * :::
* *
* @example * @example
* const data = validateCartStep({ * const data = validateCartStep({
* // retrieve the details of the cart from another workflow * // retrieve the details of the cart from another workflow
@@ -1,7 +1,7 @@
import { MedusaError } from "@medusajs/framework/utils" import { MedusaError } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { SalesChannelDTO } from "@medusajs/types" import type { SalesChannelDTO } from "@medusajs/framework/types"
export const validateSalesChannelStep = createStep( export const validateSalesChannelStep = createStep(
"validate-sales-channel", "validate-sales-channel",
@@ -2,7 +2,7 @@ import { Modules, promiseAll } from "@medusajs/framework/utils"
import { import {
IFulfillmentModuleService, IFulfillmentModuleService,
ValidateFulfillmentDataContext, ValidateFulfillmentDataContext,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { createStep, StepResponse } from "@medusajs/workflows-sdk" import { createStep, StepResponse } from "@medusajs/workflows-sdk"
/** /**
@@ -19,7 +19,7 @@ export type ValidateShippingMethodsDataInput = {
*/ */
provider_id: string provider_id: string
/** /**
* The `data` property of the shipping option that the shipping method was * The `data` property of the shipping option that the shipping method was
* created from. * created from.
*/ */
option_data: Record<string, unknown> option_data: Record<string, unknown>
@@ -36,16 +36,18 @@ export type ValidateShippingMethodsDataInput = {
/** /**
* The validated data of the shipping methods. * The validated data of the shipping methods.
*/ */
export type ValidateShippingMethodsDataOutput = void | { export type ValidateShippingMethodsDataOutput =
[x: string]: Record<string, unknown>; | void
}[] | {
[x: string]: Record<string, unknown>
}[]
export const validateAndReturnShippingMethodsDataStepId = export const validateAndReturnShippingMethodsDataStepId =
"validate-and-return-shipping-methods-data" "validate-and-return-shipping-methods-data"
/** /**
* This step validates shipping options to ensure they can be applied on a cart. * This step validates shipping options to ensure they can be applied on a cart.
* The step either returns the validated data or void. * The step either returns the validated data or void.
* *
* @example * @example
* const data = validateAndReturnShippingMethodsDataStep({ * const data = validateAndReturnShippingMethodsDataStep({
* id: "sm_123", * id: "sm_123",
@@ -4,7 +4,7 @@ import {
CartWorkflowDTO, CartWorkflowDTO,
ProductVariantDTO, ProductVariantDTO,
ShippingOptionDTO, ShippingOptionDTO,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { createStep, StepResponse } from "@medusajs/workflows-sdk" import { createStep, StepResponse } from "@medusajs/workflows-sdk"
/** /**
@@ -1,4 +1,4 @@
import { BigNumberInput } from "@medusajs/framework/types" import type { BigNumberInput } from "@medusajs/framework/types"
import { MedusaError, isPresent } from "@medusajs/framework/utils" import { MedusaError, isPresent } from "@medusajs/framework/utils"
import { createStep } from "@medusajs/framework/workflows-sdk" import { createStep } from "@medusajs/framework/workflows-sdk"
@@ -30,7 +30,7 @@ export const validateVariantPricesStepId = "validate-variant-prices"
/** /**
* This step validates the specified variant objects to ensure they have prices. * This step validates the specified variant objects to ensure they have prices.
* If not valid, the step throws an error. * If not valid, the step throws an error.
* *
* @example * @example
* const data = validateVariantPricesStep({ * const data = validateVariantPricesStep({
* variants: [ * variants: [
@@ -1,4 +1,4 @@
import { ConfirmVariantInventoryWorkflowInputDTO } from "@medusajs/framework/types" import type { ConfirmVariantInventoryWorkflowInputDTO } from "@medusajs/framework/types"
import { MedusaError } from "@medusajs/framework/utils" import { MedusaError } from "@medusajs/framework/utils"
import { prepareConfirmInventoryInput } from "../prepare-confirm-inventory-input" import { prepareConfirmInventoryInput } from "../prepare-confirm-inventory-input"
@@ -2,12 +2,11 @@ import {
AdditionalData, AdditionalData,
AddToCartWorkflowInputDTO, AddToCartWorkflowInputDTO,
ConfirmVariantInventoryWorkflowInputDTO, ConfirmVariantInventoryWorkflowInputDTO,
WithCalculatedPrice, CreateLineItemForCartDTO,
} from "@medusajs/framework/types" } from "@medusajs/framework/types"
import { import {
CartWorkflowEvents, CartWorkflowEvents,
deduplicate, deduplicate,
filterObjectByKeys,
isDefined, isDefined,
} from "@medusajs/framework/utils" } from "@medusajs/framework/utils"
import { import {
@@ -16,7 +15,6 @@ import {
parallelize, parallelize,
transform, transform,
when, when,
WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { useQueryGraphStep } from "../../common" import { useQueryGraphStep } from "../../common"
@@ -25,12 +23,10 @@ import { acquireLockStep, releaseLockStep } from "../../locking"
import { import {
createLineItemsStep, createLineItemsStep,
getLineItemActionsStep, getLineItemActionsStep,
getVariantPriceSetsStep,
updateLineItemsStep, updateLineItemsStep,
} from "../steps" } from "../steps"
import { validateCartStep } from "../steps/validate-cart" import { validateCartStep } from "../steps/validate-cart"
import { validateLineItemPricesStep } from "../steps/validate-line-item-prices" import { validateLineItemPricesStep } from "../steps/validate-line-item-prices"
import { validateVariantPricesStep } from "../steps/validate-variant-prices"
import { import {
cartFieldsForPricingContext, cartFieldsForPricingContext,
productVariantsFields, productVariantsFields,
@@ -43,6 +39,7 @@ import {
} from "../utils/prepare-line-item-data" } from "../utils/prepare-line-item-data"
import { pricingContextResult } from "../utils/schemas" import { pricingContextResult } from "../utils/schemas"
import { confirmVariantInventoryWorkflow } from "./confirm-variant-inventory" import { confirmVariantInventoryWorkflow } from "./confirm-variant-inventory"
import { getVariantsAndItemsWithPrices } from "./get-variants-and-items-with-prices"
import { refreshCartItemsWorkflow } from "./refresh-cart-items" import { refreshCartItemsWorkflow } from "./refresh-cart-items"
const cartFields = ["completed_at"].concat(cartFieldsForPricingContext) const cartFields = ["completed_at"].concat(cartFieldsForPricingContext)
@@ -119,32 +116,30 @@ export const addToCartWorkflow = createWorkflow(
name: addToCartWorkflowId, name: addToCartWorkflowId,
idempotent: false, idempotent: false,
}, },
(input: WorkflowData<AddToCartWorkflowInputDTO & AdditionalData>) => { (input: AddToCartWorkflowInputDTO & AdditionalData) => {
acquireLockStep({ acquireLockStep({
key: input.cart_id, key: input.cart_id,
timeout: 2, timeout: 2,
ttl: 10, ttl: 10,
}) })
const cartQuery = useQueryGraphStep({ const { data: cart } = useQueryGraphStep({
entity: "cart", entity: "cart",
filters: { id: input.cart_id }, filters: { id: input.cart_id },
fields: cartFields, fields: cartFields,
options: { throwIfKeyNotFound: true }, options: { throwIfKeyNotFound: true, isList: false },
}).config({ name: "get-cart" }) }).config({ name: "get-cart" })
const cart = transform({ cartQuery }, ({ cartQuery }) => {
return cartQuery.data[0]
})
validateCartStep({ cart }) validateCartStep({ cart })
const validate = createHook("validate", { const validate = createHook("validate", {
input, input,
cart, cart,
}) })
const variantIds = transform({ input }, (data) => { const variantIds = transform({ input }, (data): string[] => {
return (data.input.items ?? []).map((i) => i.variant_id).filter(Boolean) return (data.input.items ?? [])
.map((i) => i.variant_id)
.filter((v): v is string => !!v)
}) })
const setPricingContext = createHook( const setPricingContext = createHook(
@@ -162,43 +157,46 @@ export const addToCartWorkflow = createWorkflow(
const setPricingContextResult = setPricingContext.getResult() const setPricingContextResult = setPricingContext.getResult()
const variants = when( const { variants: variantsData, lineItems: lineItemsData } = when(
"should-calculate-prices", "should-calculate-prices",
{ variantIds }, { variantIds },
({ variantIds }) => { ({ variantIds }) => {
return !!variantIds.length return !!variantIds.length
} }
).then(() => { ).then(() => {
const pricingContext = transform( const { variants: variantsData, lineItems: items } =
{ cart, items: input.items, setPricingContextResult }, getVariantsAndItemsWithPrices.runAsStep({
(data): { variantId: string; context: Record<string, unknown> }[] => { input: {
const baseContext = { cart,
...filterObjectByKeys(data.cart, cartFieldsForPricingContext), items: input.items,
...(data.setPricingContextResult setPricingContextResult: setPricingContextResult!,
? data.setPricingContextResult variants: {
: {}), id: variantIds,
currency_code: data.cart.currency_code, fields: deduplicate([
region_id: data.cart.region_id, ...productVariantsFields,
region: data.cart.region, ...requiredVariantFieldsForInventoryConfirmation,
customer_id: data.cart.customer_id, ]),
customer: data.cart.customer, },
} },
})
return data.items const lineItems = transform({ items }, ({ items }) => {
.filter((i) => i.variant_id) return items.map((item) => {
.map((item) => { return item.data as CreateLineItemForCartDTO
return { })
variantId: item.variant_id!, })
context: {
...baseContext,
quantity: item.quantity,
},
}
})
}
)
const { data: variantsData } = useQueryGraphStep({ return { variants: variantsData, lineItems }
})
const fetchedVariants = when(
"fetch-variants",
{ variantsData, variantIds },
({ variantsData, variantIds }) => {
return !variantsData?.length && !!variantIds.length
}
).then(() => {
return useQueryGraphStep({
entity: "variants", entity: "variants",
fields: deduplicate([ fields: deduplicate([
...productVariantsFields, ...productVariantsFields,
@@ -207,55 +205,50 @@ export const addToCartWorkflow = createWorkflow(
filters: { filters: {
id: variantIds, id: variantIds,
}, },
}) }).config({ name: "fetch-variants" })
const calculatedPriceSets = getVariantPriceSetsStep({
data: pricingContext,
})
const variants = transform(
{ variantsData, calculatedPriceSets },
({ variantsData, calculatedPriceSets }) => {
return variantsData.map((variant) => {
variant.calculated_price = calculatedPriceSets[variant.id]
return variant
})
}
)
validateVariantPricesStep({ variants })
return variants as (PrepareVariantLineItemInput &
ConfirmVariantInventoryWorkflowInputDTO["variants"][number] &
WithCalculatedPrice)[]
}) })
const lineItems = transform({ input, variants }, (data) => { const variants = transform(
const items = (data.input.items ?? []).map((item) => { { variantsData, fetchedVariants },
const variant = (data.variants ?? []).find( ({ variantsData, fetchedVariants }) => {
(v) => v.id === item.variant_id return (variantsData ??
)! fetchedVariants) as unknown as PrepareVariantLineItemInput[]
}
)
const input: PrepareLineItemDataInput = { const lineItems = transform(
item, { cart_id: input.cart_id, items: input.items, lineItemsData, variants },
variant: variant, ({ cart_id, items: items_, lineItemsData, variants }) => {
cartId: data.input.cart_id, if (lineItemsData?.length) {
unitPrice: item.unit_price, return lineItemsData
isTaxInclusive:
item.is_tax_inclusive ??
variant?.calculated_price?.is_calculated_price_tax_inclusive,
isCustomPrice: isDefined(item?.unit_price),
} }
if (variant && !isDefined(input.unitPrice)) { const items = (items_ ?? []).map((item) => {
input.unitPrice = variant.calculated_price?.calculated_amount const variant = (variants ?? []).find(
} (v) => v.id === item.variant_id
)!
return prepareLineItemData(input) const input: PrepareLineItemDataInput = {
}) item,
variant: variant,
cartId: cart_id,
unitPrice: item.unit_price,
isTaxInclusive:
item.is_tax_inclusive ??
variant?.calculated_price?.is_calculated_price_tax_inclusive,
isCustomPrice: isDefined(item?.unit_price),
}
return items if (variant && !isDefined(input.unitPrice)) {
}) input.unitPrice = variant.calculated_price?.calculated_amount
}
return prepareLineItemData(input)
})
return items
}
)
validateLineItemPricesStep({ items: lineItems }) validateLineItemPricesStep({ items: lineItems })
@@ -287,7 +280,8 @@ export const addToCartWorkflow = createWorkflow(
confirmVariantInventoryWorkflow.runAsStep({ confirmVariantInventoryWorkflow.runAsStep({
input: { input: {
sales_channel_id: cart.sales_channel_id, sales_channel_id: cart.sales_channel_id,
variants, variants:
variants as unknown as ConfirmVariantInventoryWorkflowInputDTO["variants"],
items: input.items, items: input.items,
itemsToUpdate: itemsToConfirmInventory, itemsToUpdate: itemsToConfirmInventory,
}, },
@@ -1,11 +1,11 @@
import { ConfirmVariantInventoryWorkflowInputDTO } from "@medusajs/framework/types" import type { ConfirmVariantInventoryWorkflowInputDTO } from "@medusajs/framework/types"
import { import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
createWorkflow, createWorkflow,
transform, transform,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { BigNumberInput } from "@medusajs/types" import type { BigNumberInput } from "@medusajs/framework/types"
import { confirmInventoryStep } from "../steps" import { confirmInventoryStep } from "../steps"
import { prepareConfirmInventoryInput } from "../utils/prepare-confirm-inventory-input" import { prepareConfirmInventoryInput } from "../utils/prepare-confirm-inventory-input"
@@ -1,11 +1,12 @@
import { import {
AdditionalData, AdditionalData,
ConfirmVariantInventoryWorkflowInputDTO,
CreateCartDTO,
CreateCartWorkflowInputDTO, CreateCartWorkflowInputDTO,
} from "@medusajs/framework/types" } from "@medusajs/framework/types"
import { import {
CartWorkflowEvents, CartWorkflowEvents,
deduplicate, deduplicate,
isDefined,
MedusaError, MedusaError,
} from "@medusajs/framework/utils" } from "@medusajs/framework/utils"
import { import {
@@ -13,30 +14,22 @@ import {
createWorkflow, createWorkflow,
parallelize, parallelize,
transform, transform,
when,
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { useQueryGraphStep } from "../../common"
import { emitEventStep } from "../../common/steps/emit-event" import { emitEventStep } from "../../common/steps/emit-event"
import { import {
createCartsStep, createCartsStep,
findOneOrAnyRegionStep, findOneOrAnyRegionStep,
findOrCreateCustomerStep, findOrCreateCustomerStep,
findSalesChannelStep, findSalesChannelStep,
getVariantPriceSetsStep,
} from "../steps" } from "../steps"
import { validateLineItemPricesStep } from "../steps/validate-line-item-prices"
import { validateSalesChannelStep } from "../steps/validate-sales-channel" import { validateSalesChannelStep } from "../steps/validate-sales-channel"
import { validateVariantPricesStep } from "../steps/validate-variant-prices"
import { productVariantsFields } from "../utils/fields" import { productVariantsFields } from "../utils/fields"
import { requiredVariantFieldsForInventoryConfirmation } from "../utils/prepare-confirm-inventory-input" import { requiredVariantFieldsForInventoryConfirmation } from "../utils/prepare-confirm-inventory-input"
import {
prepareLineItemData,
PrepareLineItemDataInput,
} from "../utils/prepare-line-item-data"
import { pricingContextResult } from "../utils/schemas" import { pricingContextResult } from "../utils/schemas"
import { confirmVariantInventoryWorkflow } from "./confirm-variant-inventory" import { confirmVariantInventoryWorkflow } from "./confirm-variant-inventory"
import { getVariantsAndItemsWithPrices } from "./get-variants-and-items-with-prices"
import { refreshPaymentCollectionForCartWorkflow } from "./refresh-payment-collection" import { refreshPaymentCollectionForCartWorkflow } from "./refresh-payment-collection"
import { updateCartPromotionsWorkflow } from "./update-cart-promotions" import { updateCartPromotionsWorkflow } from "./update-cart-promotions"
import { updateTaxLinesWorkflow } from "./update-tax-lines" import { updateTaxLinesWorkflow } from "./update-tax-lines"
@@ -119,7 +112,9 @@ export const createCartWorkflow = createWorkflow(
createCartWorkflowId, createCartWorkflowId,
(input: WorkflowData<CreateCartWorkflowInput>) => { (input: WorkflowData<CreateCartWorkflowInput>) => {
const variantIds = transform({ input }, (data) => { const variantIds = transform({ input }, (data) => {
return (data.input.items ?? []).map((i) => i.variant_id).filter(Boolean) return (data.input.items ?? [])
.map((i) => i.variant_id)
.filter((v): v is string => !!v)
}) })
const [salesChannel, region, customerData] = parallelize( const [salesChannel, region, customerData] = parallelize(
@@ -151,79 +146,31 @@ export const createCartWorkflow = createWorkflow(
) )
const setPricingContextResult = setPricingContext.getResult() const setPricingContextResult = setPricingContext.getResult()
// TODO: This is on par with the context used in v1.*, but we can be more flexible. const { variants, lineItems } = getVariantsAndItemsWithPrices.runAsStep({
const pricingContext = transform( input: {
{ input, region, customerData, setPricingContextResult }, cart: {
(data) => { currency_code: input.currency_code,
if (!data.region) { region,
throw new MedusaError(MedusaError.Types.NOT_FOUND, "No regions found") region_id: region.id,
} customer_id: customerData.customer?.id,
return {
...(data.setPricingContextResult ? data.setPricingContextResult : {}),
currency_code: data.input.currency_code ?? data.region.currency_code,
region_id: data.region.id,
customer_id: data.customerData.customer?.id,
}
}
)
const variants = when("has-variants", { variantIds }, ({ variantIds }) => {
return !!variantIds.length
}).then(() => {
const { data: variantsData } = useQueryGraphStep({
entity: "variants",
fields: deduplicate([
...productVariantsFields,
...requiredVariantFieldsForInventoryConfirmation,
]),
filters: {
id: variantIds,
}, },
}) items: input.items,
setPricingContextResult: setPricingContextResult!,
const calculatedPriceContext = transform( variants: {
{ pricingContext, items: input.items }, id: variantIds,
(data): { variantId: string; context: Record<string, unknown> }[] => { fields: deduplicate([
const baseContext = data.pricingContext ...productVariantsFields,
...requiredVariantFieldsForInventoryConfirmation,
return (data.items ?? []) ]),
.filter((i) => i.variant_id) },
.map((item) => { },
return {
variantId: item.variant_id!,
context: {
...baseContext,
quantity: item.quantity,
},
}
})
}
)
const calculatedPriceSets = getVariantPriceSetsStep({
data: calculatedPriceContext,
})
const variants = transform(
{ variantsData, calculatedPriceSets },
({ variantsData, calculatedPriceSets }) => {
return variantsData.map((variant) => {
variant.calculated_price = calculatedPriceSets[variant.id]
return variant
})
}
)
validateVariantPricesStep({ variants })
return variants
}) })
confirmVariantInventoryWorkflow.runAsStep({ confirmVariantInventoryWorkflow.runAsStep({
input: { input: {
sales_channel_id: salesChannel.id, sales_channel_id: salesChannel.id,
variants: variants!, variants:
variants as unknown as ConfirmVariantInventoryWorkflowInputDTO["variants"],
items: input.items!, items: input.items!,
}, },
}) })
@@ -262,39 +209,11 @@ export const createCartWorkflow = createWorkflow(
} }
) )
const lineItems = transform({ input, variants }, (data) => {
const items = (data.input.items ?? []).map((item) => {
const variant = (data.variants ?? []).find(
(v) => v.id === item.variant_id
)!
const input: PrepareLineItemDataInput = {
item,
variant: variant,
unitPrice: item.unit_price,
isTaxInclusive:
item.is_tax_inclusive ??
variant?.calculated_price?.is_calculated_price_tax_inclusive,
isCustomPrice: isDefined(item?.unit_price),
}
if (variant && !input.unitPrice) {
input.unitPrice = variant.calculated_price?.calculated_amount
}
return prepareLineItemData(input)
})
return items
})
validateLineItemPricesStep({ items: lineItems })
const cartToCreate = transform({ lineItems, cartInput }, (data) => { const cartToCreate = transform({ lineItems, cartInput }, (data) => {
return { return {
...data.cartInput, ...data.cartInput,
items: data.lineItems, items: data.lineItems.map((i) => i.data),
} } as unknown as CreateCartDTO
}) })
const validate = createHook("validate", { const validate = createHook("validate", {
@@ -0,0 +1,226 @@
import {
BigNumberInput,
CartDTO,
CartLineItemDTO,
CreateCartCreateLineItemDTO,
CustomerDTO,
OrderWorkflow,
RegionDTO,
UpdateLineItemDTO,
UpdateLineItemWithSelectorDTO,
} from "@medusajs/framework/types"
import {
filterObjectByKeys,
isDefined,
MedusaError,
simpleHash,
} from "@medusajs/framework/utils"
import {
createWorkflow,
transform,
WorkflowData,
WorkflowResponse,
} from "@medusajs/framework/workflows-sdk"
import { useQueryGraphStep } from "../../common"
import { getVariantPriceSetsStep } from "../steps"
import {
cartFieldsForPricingContext,
productVariantsFields,
} from "../utils/fields"
import {
prepareLineItemData,
PrepareLineItemDataInput,
} from "../utils/prepare-line-item-data"
interface GetVariantsAndItemsWithPricesWorkflowInput {
cart: Partial<CartDTO> & {
region?: Partial<RegionDTO>
region_id?: string
customer?: Partial<CustomerDTO>
customer_id?: string
}
items?: Partial<
| CreateCartCreateLineItemDTO
| CartLineItemDTO
| OrderWorkflow.OrderAddLineItemWorkflowInput["items"][number]
>[]
setPricingContextResult: object
variants?: {
id?: string[]
fields?: string[]
}
}
type GetVariantsAndItemsWithPricesWorkflowOutput = {
// The variant can depend on the requested fields and therefore the caller will know better
variants: (object & {
calculated_price: {
calculated_price: {
price_list_type: string
}
is_calculated_price_tax_inclusive: boolean
original_amount: BigNumberInput
calculated_amount: BigNumberInput
}
})[]
lineItems: UpdateLineItemWithSelectorDTO[]
}
export const getVariantsAndItemsWithPricesId =
"get-variant-items-with-prices-workflow"
export const getVariantsAndItemsWithPrices = createWorkflow(
getVariantsAndItemsWithPricesId,
(
input: WorkflowData<GetVariantsAndItemsWithPricesWorkflowInput>
): WorkflowResponse<GetVariantsAndItemsWithPricesWorkflowOutput> => {
const variantIds = transform(
{ cart: input.cart, items: input.items, variantIds: input.variants?.id },
(data): string[] => {
if (data.variantIds) {
return data.variantIds
}
return Array.from(
new Set(
(data.cart.items ?? data.items ?? []).map((i) => i.variant_id)
)
).filter((v): v is string => !!v)
}
)
const cartPricingContext = transform(
{
cart: input.cart,
items: input.items,
setPricingContextResult: input.setPricingContextResult,
},
(
data
): {
id: string
variantId: string
context: Record<string, unknown>
}[] => {
const cart = data.cart
const baseContext = {
...filterObjectByKeys(cart, cartFieldsForPricingContext),
...(data.setPricingContextResult ? data.setPricingContextResult : {}),
currency_code: cart.currency_code ?? cart.region?.currency_code,
region_id: cart.region_id,
region: cart.region,
customer_id: cart.customer_id,
customer: cart.customer,
}
return (data.items ?? cart.items ?? [])
.filter((i) => i.variant_id)
.map((item) => {
const idLike =
(item as CartLineItemDTO).id ?? simpleHash(JSON.stringify(item))
return {
id: idLike,
variantId: item.variant_id!,
context: {
...baseContext,
quantity: item.quantity,
},
}
})
}
)
const variantQueryFields = transform(
{ variants: input.variants },
(data) => {
return data.variants?.fields ?? productVariantsFields
}
)
const { data: variantsData } = useQueryGraphStep({
entity: "variants",
fields: variantQueryFields,
filters: {
id: variantIds,
},
}).config({ name: "fetch-variants" })
const calculatedPriceSets = getVariantPriceSetsStep({
data: cartPricingContext,
})
const variantsItemsWithPrices = transform(
{
cart: input.cart,
items: input.items,
variantsData,
calculatedPriceSets,
},
({
cart,
items: inputItems,
variantsData,
calculatedPriceSets,
}): GetVariantsAndItemsWithPricesWorkflowOutput => {
const priceNotFound: string[] = []
const items = (inputItems ?? cart.items ?? []).map((item) => {
const item_ = item as any
const idLike =
(item as CartLineItemDTO).id ?? simpleHash(JSON.stringify(item))
let calculatedPriceSet = calculatedPriceSets[idLike]
if (!calculatedPriceSet) {
calculatedPriceSet = calculatedPriceSets[item_.variant_id!]
}
if (!calculatedPriceSet && item_.variant_id) {
priceNotFound.push(item_.variant_id)
}
const variant = variantsData.find((v) => v.id === item.variant_id)
if (variant) {
variant.calculated_price = calculatedPriceSet
}
const isCustomPrice =
item_.is_custom_price ?? isDefined(item?.unit_price)
const input: PrepareLineItemDataInput = {
item: item_,
variant: variant,
cartId: cart.id,
unitPrice: item_.unit_price,
isTaxInclusive:
item_.is_tax_inclusive ??
calculatedPriceSet?.is_calculated_price_tax_inclusive,
isCustomPrice: isCustomPrice,
}
if (variant && !isCustomPrice) {
input.unitPrice = calculatedPriceSet.calculated_amount
input.isTaxInclusive =
calculatedPriceSet.is_calculated_price_tax_inclusive
}
const preparedItem = prepareLineItemData(input)
return {
selector: { id: (item_ as CartLineItemDTO).id },
data: preparedItem as Partial<UpdateLineItemDTO>,
}
})
if (priceNotFound.length > 0) {
throw new MedusaError(
MedusaError.Types.INVALID_DATA,
`Variants with IDs ${priceNotFound.join(", ")} do not have a price`
)
}
return { variants: variantsData, lineItems: items }
}
)
return new WorkflowResponse(variantsItemsWithPrices)
}
)
@@ -11,7 +11,7 @@ import {
AdditionalData, AdditionalData,
CalculateShippingOptionPriceDTO, CalculateShippingOptionPriceDTO,
ListShippingOptionsForCartWithPricingWorkflowInput, ListShippingOptionsForCartWithPricingWorkflowInput,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { useQueryGraphStep, validatePresenceOfStep } from "../../common" import { useQueryGraphStep, validatePresenceOfStep } from "../../common"
import { useRemoteQueryStep } from "../../common/steps/use-remote-query" import { useRemoteQueryStep } from "../../common/steps/use-remote-query"
@@ -14,9 +14,16 @@ import { cartFieldsForPricingContext } from "../utils/fields"
import { import {
AdditionalData, AdditionalData,
ListShippingOptionsForCartWorkflowInput, ListShippingOptionsForCartWorkflowInput,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { deduplicate, filterObjectByKeys, isDefined } from "@medusajs/framework/utils" import {
import { pricingContextResult, shippingOptionsContextResult } from "../utils/schemas" deduplicate,
filterObjectByKeys,
isDefined,
} from "@medusajs/framework/utils"
import {
pricingContextResult,
shippingOptionsContextResult,
} from "../utils/schemas"
export const listShippingOptionsForCartWorkflowId = export const listShippingOptionsForCartWorkflowId =
"list-shipping-options-for-cart" "list-shipping-options-for-cart"
@@ -81,26 +88,26 @@ export const listShippingOptionsForCartWorkflowId =
* Learn more about prices calculation context in the [Prices Calculation](https://docs.medusajs.com/resources/commerce-modules/pricing/price-calculation) documentation. * Learn more about prices calculation context in the [Prices Calculation](https://docs.medusajs.com/resources/commerce-modules/pricing/price-calculation) documentation.
* *
* ::: * :::
* *
* @property hooks.setShippingOptionsContext - This hook is executed after the cart is retrieved and before the shipping options are queried. You can consume this hook to return any custom context useful for the shipping options retrieval. * @property hooks.setShippingOptionsContext - This hook is executed after the cart is retrieved and before the shipping options are queried. You can consume this hook to return any custom context useful for the shipping options retrieval.
* *
* For example, you can consume the hook to add the customer Id to the context: * For example, you can consume the hook to add the customer Id to the context:
* *
* ```ts * ```ts
* import { listShippingOptionsForCartWithPricingWorkflow } from "@medusajs/medusa/core-flows" * import { listShippingOptionsForCartWithPricingWorkflow } from "@medusajs/medusa/core-flows"
* import { StepResponse } from "@medusajs/workflows-sdk" * import { StepResponse } from "@medusajs/workflows-sdk"
* *
* listShippingOptionsForCartWithPricingWorkflow.hooks.setShippingOptionsContext( * listShippingOptionsForCartWithPricingWorkflow.hooks.setShippingOptionsContext(
* async ({ cart }, { container }) => { * async ({ cart }, { container }) => {
* *
* if (cart.customer_id) { * if (cart.customer_id) {
* return new StepResponse({ * return new StepResponse({
* customer_id: cart.customer_id, * customer_id: cart.customer_id,
* }) * })
* } * }
* *
* const query = container.resolve("query") * const query = container.resolve("query")
* *
* const { data: carts } = await query.graph({ * const { data: carts } = await query.graph({
* entity: "cart", * entity: "cart",
* filters: { * filters: {
@@ -108,20 +115,20 @@ export const listShippingOptionsForCartWorkflowId =
* }, * },
* fields: ["customer_id"], * fields: ["customer_id"],
* }) * })
* *
* return new StepResponse({ * return new StepResponse({
* customer_id: carts[0].customer_id, * customer_id: carts[0].customer_id,
* }) * })
* } * }
* ) * )
* ``` * ```
* *
* The `customer_id` property will be added to the context along with other properties such as `is_return` and `enabled_in_store`. * The `customer_id` property will be added to the context along with other properties such as `is_return` and `enabled_in_store`.
* *
* :::note * :::note
* *
* You should also consume the `setShippingOptionsContext` hook in the {@link listShippingOptionsForCartWithPricingWorkflow} workflow to ensure that the context is consistent when listing shipping options across workflows. * You should also consume the `setShippingOptionsContext` hook in the {@link listShippingOptionsForCartWithPricingWorkflow} workflow to ensure that the context is consistent when listing shipping options across workflows.
* *
* ::: * :::
*/ */
export const listShippingOptionsForCartWorkflow = createWorkflow( export const listShippingOptionsForCartWorkflow = createWorkflow(
@@ -209,16 +216,31 @@ export const listShippingOptionsForCartWorkflow = createWorkflow(
resultValidator: shippingOptionsContextResult, resultValidator: shippingOptionsContextResult,
} }
) )
const setShippingOptionsContextResult = setShippingOptionsContext.getResult() const setShippingOptionsContextResult =
setShippingOptionsContext.getResult()
const queryVariables = transform( const queryVariables = transform(
{ input, fulfillmentSetIds, cart, setPricingContextResult, setShippingOptionsContextResult }, {
({ input, fulfillmentSetIds, cart, setPricingContextResult, setShippingOptionsContextResult }) => { input,
fulfillmentSetIds,
cart,
setPricingContextResult,
setShippingOptionsContextResult,
},
({
input,
fulfillmentSetIds,
cart,
setPricingContextResult,
setShippingOptionsContextResult,
}) => {
return { return {
id: input.option_ids, id: input.option_ids,
context: { context: {
...(setShippingOptionsContextResult ? setShippingOptionsContextResult : {}), ...(setShippingOptionsContextResult
? setShippingOptionsContextResult
: {}),
is_return: input.is_return ? "true" : "false", is_return: input.is_return ? "true" : "false",
enabled_in_store: !isDefined(input.enabled_in_store) enabled_in_store: !isDefined(input.enabled_in_store)
? "true" ? "true"
@@ -1,8 +1,5 @@
import { import type { AdditionalData } from "@medusajs/framework/types"
filterObjectByKeys, import { isDefined, PromotionActions } from "@medusajs/framework/utils"
isDefined,
PromotionActions,
} from "@medusajs/framework/utils"
import { import {
createHook, createHook,
createWorkflow, createWorkflow,
@@ -11,22 +8,13 @@ import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { AdditionalData, CartDTO } from "@medusajs/types"
import { useQueryGraphStep } from "../../common" import { useQueryGraphStep } from "../../common"
import { useRemoteQueryStep } from "../../common/steps/use-remote-query" import { useRemoteQueryStep } from "../../common/steps/use-remote-query"
import { acquireLockStep, releaseLockStep } from "../../locking" import { acquireLockStep, releaseLockStep } from "../../locking"
import { getVariantPriceSetsStep, updateLineItemsStep } from "../steps" import { updateLineItemsStep } from "../steps"
import { validateVariantPricesStep } from "../steps/validate-variant-prices" import { cartFieldsForRefreshSteps } from "../utils/fields"
import {
cartFieldsForPricingContext,
cartFieldsForRefreshSteps,
productVariantsFields,
} from "../utils/fields"
import {
prepareLineItemData,
PrepareLineItemDataInput,
} from "../utils/prepare-line-item-data"
import { pricingContextResult } from "../utils/schemas" import { pricingContextResult } from "../utils/schemas"
import { getVariantsAndItemsWithPrices } from "./get-variants-and-items-with-prices"
import { refreshCartShippingMethodsWorkflow } from "./refresh-cart-shipping-methods" import { refreshCartShippingMethodsWorkflow } from "./refresh-cart-shipping-methods"
import { refreshPaymentCollectionForCartWorkflow } from "./refresh-payment-collection" import { refreshPaymentCollectionForCartWorkflow } from "./refresh-payment-collection"
import { updateCartPromotionsWorkflow } from "./update-cart-promotions" import { updateCartPromotionsWorkflow } from "./update-cart-promotions"
@@ -168,93 +156,11 @@ export const refreshCartItemsWorkflow = createWorkflow(
}, },
}) })
const variantIds = transform({ cart }, (data: { cart: CartDTO }) => { const { lineItems } = getVariantsAndItemsWithPrices.runAsStep({
return (data.cart.items ?? []).map((i) => i.variant_id).filter(Boolean) input: {
}) cart,
setPricingContextResult: setPricingContextResult!,
const cartPricingContext = transform(
{ cart, setPricingContextResult },
(data): { variantId: string; context: Record<string, unknown> }[] => {
const cart = data.cart
const baseContext = {
...filterObjectByKeys(cart, cartFieldsForPricingContext),
...(data.setPricingContextResult
? data.setPricingContextResult
: {}),
currency_code: cart.currency_code,
region_id: cart.region_id,
region: cart.region,
customer_id: cart.customer_id,
customer: cart.customer,
}
return cart.items
.filter((i) => i.variant_id)
.map((item) => {
return {
variantId: item.variant_id,
context: {
...baseContext,
quantity: item.quantity,
},
}
})
}
)
const { data: variantsData } = useQueryGraphStep({
entity: "variants",
fields: productVariantsFields,
filters: {
id: variantIds,
}, },
}).config({ name: "fetch-variants" })
const calculatedPriceSets = getVariantPriceSetsStep({
data: cartPricingContext,
})
const variants = transform(
{ variantsData, calculatedPriceSets },
({ variantsData, calculatedPriceSets }) => {
return variantsData.map((variant) => {
variant.calculated_price = calculatedPriceSets[variant.id]
return variant
})
}
)
validateVariantPricesStep({ variants })
const lineItems = transform({ cart, variants }, ({ cart, variants }) => {
const items = cart.items.map((item) => {
const variant = (variants ?? []).find(
(v) => v.id === item.variant_id
)!
const input: PrepareLineItemDataInput = {
item,
variant: variant,
cartId: cart.id,
unitPrice: item.unit_price,
isTaxInclusive: item.is_tax_inclusive,
}
if (variant && !item.is_custom_price) {
input.unitPrice = variant.calculated_price?.calculated_amount
input.isTaxInclusive =
variant.calculated_price?.is_calculated_price_tax_inclusive
}
const preparedItem = prepareLineItemData(input)
return {
selector: { id: item.id },
data: preparedItem,
}
})
return items
}) })
updateLineItemsStep({ updateLineItemsStep({
@@ -1,4 +1,7 @@
import { BigNumberInput, PaymentSessionDTO } from "@medusajs/framework/types" import type {
BigNumberInput,
PaymentSessionDTO,
} from "@medusajs/framework/types"
import { import {
createWorkflow, createWorkflow,
WorkflowData, WorkflowData,
@@ -1,5 +1,5 @@
import { Link } from "@medusajs/framework/modules-sdk" import { Link } from "@medusajs/framework/modules-sdk"
import { LinkDefinition } from "@medusajs/framework/types" import type { LinkDefinition } from "@medusajs/framework/types"
import { ContainerRegistrationKeys } from "@medusajs/framework/utils" import { ContainerRegistrationKeys } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
@@ -1,5 +1,5 @@
import { Link } from "@medusajs/framework/modules-sdk" import { Link } from "@medusajs/framework/modules-sdk"
import { LinkDefinition } from "@medusajs/framework/types" import type { LinkDefinition } from "@medusajs/framework/types"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { ContainerRegistrationKeys } from "@medusajs/framework/utils" import { ContainerRegistrationKeys } from "@medusajs/framework/utils"
@@ -1,5 +1,5 @@
import { Link } from "@medusajs/framework/modules-sdk" import { Link } from "@medusajs/framework/modules-sdk"
import { LinkDefinition } from "@medusajs/framework/types" import type { LinkDefinition } from "@medusajs/framework/types"
import { import {
ContainerRegistrationKeys, ContainerRegistrationKeys,
MedusaError, MedusaError,
@@ -1,4 +1,7 @@
import { BatchWorkflowInput, LinkDefinition } from "@medusajs/framework/types" import type {
BatchWorkflowInput,
LinkDefinition,
} from "@medusajs/framework/types"
import { import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
@@ -12,12 +15,12 @@ import { updateRemoteLinksStep } from "../steps/update-remote-links"
export const batchLinksWorkflowId = "batch-links" export const batchLinksWorkflowId = "batch-links"
/** /**
* This workflow manages one or more links to create, update, or dismiss them. * This workflow manages one or more links to create, update, or dismiss them.
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to * You can use this workflow within your customizations or your own custom workflows, allowing you to
* manage links within your custom flows. * manage links within your custom flows.
* *
* Learn more about links in [this documentation](https://docs.medusajs.com/learn/fundamentals/module-links/link). * Learn more about links in [this documentation](https://docs.medusajs.com/learn/fundamentals/module-links/link).
* *
* @example * @example
* const { result } = await batchLinksWorkflow(container) * const { result } = await batchLinksWorkflow(container)
* .run({ * .run({
@@ -59,9 +62,9 @@ export const batchLinksWorkflowId = "batch-links"
* ] * ]
* } * }
* }) * })
* *
* @summary * @summary
* *
* Manage links between two records of linked data models. * Manage links between two records of linked data models.
*/ */
export const batchLinksWorkflow = createWorkflow( export const batchLinksWorkflow = createWorkflow(
@@ -1,4 +1,4 @@
import { LinkDefinition } from "@medusajs/framework/types" import type { LinkDefinition } from "@medusajs/framework/types"
import { import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
@@ -9,12 +9,12 @@ import { createRemoteLinkStep } from "../steps/create-remote-links"
export const createLinksWorkflowId = "create-link" export const createLinksWorkflowId = "create-link"
/** /**
* This workflow creates one or more links between records. * This workflow creates one or more links between records.
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to * You can use this workflow within your customizations or your own custom workflows, allowing you to
* create links within your custom flows. * create links within your custom flows.
* *
* Learn more about links in [this documentation](https://docs.medusajs.com/learn/fundamentals/module-links/link). * Learn more about links in [this documentation](https://docs.medusajs.com/learn/fundamentals/module-links/link).
* *
* @example * @example
* const { result } = await createLinksWorkflow(container) * const { result } = await createLinksWorkflow(container)
* .run({ * .run({
@@ -30,9 +30,9 @@ export const createLinksWorkflowId = "create-link"
* } * }
* ] * ]
* }) * })
* *
* @summary * @summary
* *
* Create links between two records of linked data models. * Create links between two records of linked data models.
*/ */
export const createLinksWorkflow = createWorkflow( export const createLinksWorkflow = createWorkflow(
@@ -1,4 +1,4 @@
import { LinkDefinition } from "@medusajs/framework/types" import type { LinkDefinition } from "@medusajs/framework/types"
import { import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
@@ -9,12 +9,12 @@ import { dismissRemoteLinkStep } from "../steps/dismiss-remote-links"
export const dismissLinksWorkflowId = "dismiss-link" export const dismissLinksWorkflowId = "dismiss-link"
/** /**
* This workflow dismisses one or more links between records. * This workflow dismisses one or more links between records.
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to * You can use this workflow within your customizations or your own custom workflows, allowing you to
* dismiss links within your custom flows. * dismiss links within your custom flows.
* *
* Learn more about links in [this documentation](https://docs.medusajs.com/learn/fundamentals/module-links/link). * Learn more about links in [this documentation](https://docs.medusajs.com/learn/fundamentals/module-links/link).
* *
* @example * @example
* const { result } = await dismissLinksWorkflow(container) * const { result } = await dismissLinksWorkflow(container)
* .run({ * .run({
@@ -30,9 +30,9 @@ export const dismissLinksWorkflowId = "dismiss-link"
* } * }
* ] * ]
* }) * })
* *
* @summary * @summary
* *
* Dismiss links between two records of linked data models. * Dismiss links between two records of linked data models.
*/ */
export const dismissLinksWorkflow = createWorkflow( export const dismissLinksWorkflow = createWorkflow(
@@ -1,4 +1,4 @@
import { LinkDefinition } from "@medusajs/framework/types" import type { LinkDefinition } from "@medusajs/framework/types"
import { import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
@@ -9,12 +9,12 @@ import { updateRemoteLinksStep } from "../steps/update-remote-links"
export const updateLinksWorkflowId = "update-link" export const updateLinksWorkflowId = "update-link"
/** /**
* This workflow updates one or more links between records. * This workflow updates one or more links between records.
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to * You can use this workflow within your customizations or your own custom workflows, allowing you to
* update links within your custom flows. * update links within your custom flows.
* *
* Learn more about links in [this documentation](https://docs.medusajs.com/learn/fundamentals/module-links/link). * Learn more about links in [this documentation](https://docs.medusajs.com/learn/fundamentals/module-links/link).
* *
* @example * @example
* const { result } = await updateLinksWorkflow(container) * const { result } = await updateLinksWorkflow(container)
* .run({ * .run({
@@ -35,9 +35,9 @@ export const updateLinksWorkflowId = "update-link"
* } * }
* ] * ]
* }) * })
* *
* @summary * @summary
* *
* Update links between two records of linked data models. * Update links between two records of linked data models.
*/ */
export const updateLinksWorkflow = createWorkflow( export const updateLinksWorkflow = createWorkflow(
@@ -1,4 +1,4 @@
import { ICustomerModuleService } from "@medusajs/framework/types" import type { ICustomerModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
@@ -1,10 +1,10 @@
import { LinkWorkflowInput } from "@medusajs/framework/types" import type { LinkWorkflowInput } from "@medusajs/framework/types"
import { WorkflowData, createWorkflow } from "@medusajs/framework/workflows-sdk" import { WorkflowData, createWorkflow } from "@medusajs/framework/workflows-sdk"
import { linkCustomerGroupsToCustomerStep } from "../steps" import { linkCustomerGroupsToCustomerStep } from "../steps"
/** /**
* The data to manage the customer groups of a customer. * The data to manage the customer groups of a customer.
* *
* @property id - The ID of the customer to manage its groups. * @property id - The ID of the customer to manage its groups.
* @property add - The IDs of the customer groups to add the customer to. * @property add - The IDs of the customer groups to add the customer to.
* @property remove - The IDs of the customer groups to remove the customer from. * @property remove - The IDs of the customer groups to remove the customer from.
@@ -14,12 +14,12 @@ export type LinkCustomerGroupsToCustomerWorkflowInput = LinkWorkflowInput
export const linkCustomerGroupsToCustomerWorkflowId = export const linkCustomerGroupsToCustomerWorkflowId =
"link-customer-groups-to-customer" "link-customer-groups-to-customer"
/** /**
* This workflow manages the customer groups a customer is in. It's used by the * This workflow manages the customer groups a customer is in. It's used by the
* [Manage Groups of Customer Admin API Route](https://docs.medusajs.com/api/admin#customers_postcustomersidcustomergroups). * [Manage Groups of Customer Admin API Route](https://docs.medusajs.com/api/admin#customers_postcustomersidcustomergroups).
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to * You can use this workflow within your customizations or your own custom workflows, allowing you to
* manage the customer groups of a customer in your custom flow. * manage the customer groups of a customer in your custom flow.
* *
* @example * @example
* const { result } = await linkCustomerGroupsToCustomerWorkflow(container) * const { result } = await linkCustomerGroupsToCustomerWorkflow(container)
* .run({ * .run({
@@ -29,14 +29,16 @@ export const linkCustomerGroupsToCustomerWorkflowId =
* remove: ["cusgrp_456"] * remove: ["cusgrp_456"]
* } * }
* }) * })
* *
* @summary * @summary
* *
* Manage groups of a customer. * Manage groups of a customer.
*/ */
export const linkCustomerGroupsToCustomerWorkflow = createWorkflow( export const linkCustomerGroupsToCustomerWorkflow = createWorkflow(
linkCustomerGroupsToCustomerWorkflowId, linkCustomerGroupsToCustomerWorkflowId,
(input: WorkflowData<LinkCustomerGroupsToCustomerWorkflowInput>): WorkflowData<void> => { (
input: WorkflowData<LinkCustomerGroupsToCustomerWorkflowInput>
): WorkflowData<void> => {
return linkCustomerGroupsToCustomerStep(input) return linkCustomerGroupsToCustomerStep(input)
} }
) )
@@ -1,10 +1,10 @@
import { LinkWorkflowInput } from "@medusajs/framework/types" import type { LinkWorkflowInput } from "@medusajs/framework/types"
import { WorkflowData, createWorkflow } from "@medusajs/framework/workflows-sdk" import { WorkflowData, createWorkflow } from "@medusajs/framework/workflows-sdk"
import { linkCustomersToCustomerGroupStep } from "../steps" import { linkCustomersToCustomerGroupStep } from "../steps"
/** /**
* The data to manage the customers of a group. * The data to manage the customers of a group.
* *
* @property id - The ID of the customer group to manage its customers. * @property id - The ID of the customer group to manage its customers.
* @property add - The IDs of the customers to add to the customer group. * @property add - The IDs of the customers to add to the customer group.
* @property remove - The IDs of the customers to remove from the customer group. * @property remove - The IDs of the customers to remove from the customer group.
@@ -14,12 +14,12 @@ export type LinkCustomersToCustomerGroupWorkflow = LinkWorkflowInput
export const linkCustomersToCustomerGroupWorkflowId = export const linkCustomersToCustomerGroupWorkflowId =
"link-customers-to-customer-group" "link-customers-to-customer-group"
/** /**
* This workflow manages the customers of a customer group. It's used by the * This workflow manages the customers of a customer group. It's used by the
* [Manage Customers of Group Admin API Route](https://docs.medusajs.com/api/admin#customer-groups_postcustomergroupsidcustomers). * [Manage Customers of Group Admin API Route](https://docs.medusajs.com/api/admin#customer-groups_postcustomergroupsidcustomers).
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to * You can use this workflow within your customizations or your own custom workflows, allowing you to
* manage the customers of a customer group within your custom flows. * manage the customers of a customer group within your custom flows.
* *
* @example * @example
* const { result } = await linkCustomersToCustomerGroupWorkflow(container) * const { result } = await linkCustomersToCustomerGroupWorkflow(container)
* .run({ * .run({
@@ -29,14 +29,16 @@ export const linkCustomersToCustomerGroupWorkflowId =
* remove: ["cus_456"] * remove: ["cus_456"]
* } * }
* }) * })
* *
* @summary * @summary
* *
* Manage the customers of a customer group. * Manage the customers of a customer group.
*/ */
export const linkCustomersToCustomerGroupWorkflow = createWorkflow( export const linkCustomersToCustomerGroupWorkflow = createWorkflow(
linkCustomersToCustomerGroupWorkflowId, linkCustomersToCustomerGroupWorkflowId,
(input: WorkflowData<LinkCustomersToCustomerGroupWorkflow>): WorkflowData<void> => { (
input: WorkflowData<LinkCustomersToCustomerGroupWorkflow>
): WorkflowData<void> => {
return linkCustomersToCustomerGroupStep(input) return linkCustomersToCustomerGroupStep(input)
} }
) )
@@ -1,4 +1,4 @@
import { ICustomerModuleService } from "@medusajs/framework/types" import type { ICustomerModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,4 @@
import { ICustomerModuleService } from "@medusajs/framework/types" import type { ICustomerModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,4 @@
import { CreateCustomerDTO, CustomerDTO } from "@medusajs/framework/types" import type { CreateCustomerDTO, CustomerDTO } from "@medusajs/framework/types"
import { import {
createWorkflow, createWorkflow,
transform, transform,
@@ -27,13 +27,13 @@ export const createCustomerAccountWorkflowId = "create-customer-account"
/** /**
* This workflow creates a customer and attaches it to an auth identity. It's used by the * This workflow creates a customer and attaches it to an auth identity. It's used by the
* [Register Customer Store API Route](https://docs.medusajs.com/api/store#customers_postcustomers). * [Register Customer Store API Route](https://docs.medusajs.com/api/store#customers_postcustomers).
* *
* You can create an auth identity first using the [Retrieve Registration JWT Token API Route](https://docs.medusajs.com/api/store#auth_postactor_typeauth_provider_register). * You can create an auth identity first using the [Retrieve Registration JWT Token API Route](https://docs.medusajs.com/api/store#auth_postactor_typeauth_provider_register).
* Learn more about basic authentication flows in [this documentation](https://docs.medusajs.com/resources/commerce-modules/auth/authentication-route). * Learn more about basic authentication flows in [this documentation](https://docs.medusajs.com/resources/commerce-modules/auth/authentication-route).
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to * You can use this workflow within your customizations or your own custom workflows, allowing you to
* register or create customer accounts within your custom flows. * register or create customer accounts within your custom flows.
* *
* @example * @example
* const { result } = await createCustomerAccountWorkflow(container) * const { result } = await createCustomerAccountWorkflow(container)
* .run({ * .run({
@@ -46,9 +46,9 @@ export const createCustomerAccountWorkflowId = "create-customer-account"
* } * }
* } * }
* }) * })
* *
* @summary * @summary
* *
* Create or register a customer account. * Create or register a customer account.
*/ */
export const createCustomerAccountWorkflow = createWorkflow( export const createCustomerAccountWorkflow = createWorkflow(
@@ -1,4 +1,7 @@
import { AdditionalData, CreateCustomerDTO } from "@medusajs/framework/types" import type {
AdditionalData,
CreateCustomerDTO,
} from "@medusajs/framework/types"
import { CustomerWorkflowEvents } from "@medusajs/framework/utils" import { CustomerWorkflowEvents } from "@medusajs/framework/utils"
import { import {
WorkflowData, WorkflowData,
@@ -23,11 +26,11 @@ export type CreateCustomersWorkflowInput = {
export const createCustomersWorkflowId = "create-customers" export const createCustomersWorkflowId = "create-customers"
/** /**
* This workflow creates one or more customers. It's used by the [Create Customer Admin API Route](https://docs.medusajs.com/api/admin#customers_postcustomers). * This workflow creates one or more customers. It's used by the [Create Customer Admin API Route](https://docs.medusajs.com/api/admin#customers_postcustomers).
* *
* This workflow has a hook that allows you to perform custom actions on the created customer. You can see an example in [this guide](https://docs.medusajs.com/resources/commerce-modules/customer/extend). * This workflow has a hook that allows you to perform custom actions on the created customer. You can see an example in [this guide](https://docs.medusajs.com/resources/commerce-modules/customer/extend).
* *
* You can also use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around creating customers. * You can also use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around creating customers.
* *
* @example * @example
* const { result } = await createCustomersWorkflow(container) * const { result } = await createCustomersWorkflow(container)
* .run({ * .run({
@@ -44,11 +47,11 @@ export const createCustomersWorkflowId = "create-customers"
* } * }
* } * }
* }) * })
* *
* @summary * @summary
* *
* Create one or more customers. * Create one or more customers.
* *
* @property hooks.customersCreated - This hook is executed after the customers are created. You can consume this hook to perform custom actions on the created customers. * @property hooks.customersCreated - This hook is executed after the customers are created. You can consume this hook to perform custom actions on the created customers.
*/ */
export const createCustomersWorkflow = createWorkflow( export const createCustomersWorkflow = createWorkflow(
@@ -3,7 +3,7 @@ import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { import {
CreateLineItemAdjustmentDTO, CreateLineItemAdjustmentDTO,
IOrderModuleService, IOrderModuleService,
} from "@medusajs/types" } from "@medusajs/framework/types"
export const createDraftOrderLineItemAdjustmentsStepId = export const createDraftOrderLineItemAdjustmentsStepId =
"create-draft-order-line-item-adjustments" "create-draft-order-line-item-adjustments"
@@ -24,7 +24,7 @@ export interface CreateDraftOrderLineItemAdjustmentsStepInput {
/** /**
* This step creates line item adjustments for a draft order. * This step creates line item adjustments for a draft order.
* *
* @example * @example
* const data = createDraftOrderLineItemAdjustmentsStep({ * const data = createDraftOrderLineItemAdjustmentsStep({
* order_id: "order_123", * order_id: "order_123",
@@ -3,7 +3,7 @@ import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { import {
CreateShippingMethodAdjustmentDTO, CreateShippingMethodAdjustmentDTO,
IOrderModuleService, IOrderModuleService,
} from "@medusajs/types" } from "@medusajs/framework/types"
export const createDraftOrderShippingMethodAdjustmentsStepId = export const createDraftOrderShippingMethodAdjustmentsStepId =
"create-draft-order-shipping-method-adjustments" "create-draft-order-shipping-method-adjustments"
@@ -20,7 +20,7 @@ export interface CreateDraftOrderShippingMethodAdjustmentsStepInput {
/** /**
* This step creates shipping method adjustments for a draft order. * This step creates shipping method adjustments for a draft order.
* *
* @example * @example
* const data = createDraftOrderShippingMethodAdjustmentsStep({ * const data = createDraftOrderShippingMethodAdjustmentsStep({
* shippingMethodAdjustmentsToCreate: [ * shippingMethodAdjustmentsToCreate: [
@@ -1,4 +1,4 @@
import { IOrderModuleService } from "@medusajs/framework/types" import type { IOrderModuleService } from "@medusajs/framework/types"
import { createStep } from "@medusajs/framework/workflows-sdk" import { createStep } from "@medusajs/framework/workflows-sdk"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
@@ -1,6 +1,6 @@
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { IOrderModuleService, OrderDTO } from "@medusajs/types" import type { IOrderModuleService, OrderDTO } from "@medusajs/framework/types"
/** /**
* The details of the draft order to get the promotion context for. * The details of the draft order to get the promotion context for.
@@ -14,14 +14,14 @@ export interface GetDraftOrderPromotionContextStepInput {
/** /**
* This step gets the promotion context for a draft order. * This step gets the promotion context for a draft order.
* *
* :::note * :::note
* *
* You can retrieve a draft order's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query), * You can retrieve a draft order's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query),
* or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep). * or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep).
* *
* ::: * :::
* *
* @example * @example
* const data = getDraftOrderPromotionContextStep({ * const data = getDraftOrderPromotionContextStep({
* order: { * order: {
@@ -1,6 +1,6 @@
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { IOrderModuleService } from "@medusajs/types" import type { IOrderModuleService } from "@medusajs/framework/types"
export const removeDraftOrderLineItemAdjustmentsStepId = export const removeDraftOrderLineItemAdjustmentsStepId =
"remove-draft-order-line-item-adjustments" "remove-draft-order-line-item-adjustments"
@@ -16,7 +16,7 @@ export interface RemoveDraftOrderLineItemAdjustmentsStepInput {
/** /**
* This step removes line item adjustments from a draft order. * This step removes line item adjustments from a draft order.
* *
* @example * @example
* const data = removeDraftOrderLineItemAdjustmentsStep({ * const data = removeDraftOrderLineItemAdjustmentsStep({
* lineItemAdjustmentIdsToRemove: ["adj_123", "adj_456"], * lineItemAdjustmentIdsToRemove: ["adj_123", "adj_456"],
@@ -1,6 +1,6 @@
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
import { IOrderModuleService } from "@medusajs/types" import type { IOrderModuleService } from "@medusajs/framework/types"
export const removeDraftOrderShippingMethodAdjustmentsStepId = export const removeDraftOrderShippingMethodAdjustmentsStepId =
"remove-draft-order-shipping-method-adjustments" "remove-draft-order-shipping-method-adjustments"
@@ -17,7 +17,7 @@ export interface RemoveDraftOrderShippingMethodAdjustmentsStepInput {
/** /**
* This step removes shipping method adjustments from a draft order. * This step removes shipping method adjustments from a draft order.
* *
* @example * @example
* const data = removeDraftOrderShippingMethodAdjustmentsStep({ * const data = removeDraftOrderShippingMethodAdjustmentsStep({
* shippingMethodAdjustmentIdsToRemove: ["adj_123", "adj_456"], * shippingMethodAdjustmentIdsToRemove: ["adj_123", "adj_456"],
@@ -1,6 +1,9 @@
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { BigNumberInput, IOrderModuleService } from "@medusajs/types" import type {
BigNumberInput,
IOrderModuleService,
} from "@medusajs/framework/types"
export const restoreDraftOrderShippingMethodsStepId = export const restoreDraftOrderShippingMethodsStepId =
"restore-draft-order-shipping-methods" "restore-draft-order-shipping-methods"
@@ -49,20 +52,20 @@ export interface RestoreDraftOrderShippingMethodsStepInput {
/** /**
* This step restores the shipping methods of a draft order. * This step restores the shipping methods of a draft order.
* It's useful when you need to revert changes made by a canceled draft order edit. * It's useful when you need to revert changes made by a canceled draft order edit.
* *
* @example * @example
* const data = restoreDraftOrderShippingMethodsStep({ * const data = restoreDraftOrderShippingMethodsStep({
* shippingMethods: [ * shippingMethods: [
* { * {
* id: "shipping_method_123", * id: "shipping_method_123",
* before: { * before: {
* shipping_option_id: "shipping_option_123", * shipping_option_id: "shipping_option_123",
* amount: 10 * amount: 10
* }, * },
* after: { * after: {
* shipping_option_id: "shipping_option_123", * shipping_option_id: "shipping_option_123",
* amount: 10 * amount: 10
* } * }
* }, * },
* ], * ],
* }) * })
@@ -4,7 +4,7 @@ import {
PromotionActions, PromotionActions,
} from "@medusajs/framework/utils" } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { IPromotionModuleService } from "@medusajs/types" import type { IPromotionModuleService } from "@medusajs/framework/types"
export const updateDraftOrderPromotionsStepId = "update-draft-order-promotions" export const updateDraftOrderPromotionsStepId = "update-draft-order-promotions"
@@ -22,7 +22,7 @@ export interface UpdateDraftOrderPromotionsStepInput {
promo_codes: string[] promo_codes: string[]
/** /**
* The action to perform on the promotions. You can either: * The action to perform on the promotions. You can either:
* *
* - Add the promotions to the draft order. * - Add the promotions to the draft order.
* - Replace the existing promotions with the new ones. * - Replace the existing promotions with the new ones.
* - Remove the promotions from the draft order. * - Remove the promotions from the draft order.
@@ -32,7 +32,7 @@ export interface UpdateDraftOrderPromotionsStepInput {
/** /**
* This step updates the promotions of a draft order. * This step updates the promotions of a draft order.
* *
* @example * @example
* const data = updateDraftOrderPromotionsStep({ * const data = updateDraftOrderPromotionsStep({
* id: "order_123", * id: "order_123",
@@ -1,6 +1,9 @@
import { MedusaError, Modules } from "@medusajs/framework/utils" import { MedusaError, Modules } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { BigNumberInput, IOrderModuleService } from "@medusajs/types" import type {
BigNumberInput,
IOrderModuleService,
} from "@medusajs/framework/types"
export const updateDraftOrderShippingMethodStepId = export const updateDraftOrderShippingMethodStepId =
"update-draft-order-shipping-method" "update-draft-order-shipping-method"
@@ -33,7 +36,7 @@ export interface UpdateDraftOrderShippingMethodStepInput {
/** /**
* This step updates the shipping method of a draft order. * This step updates the shipping method of a draft order.
* *
* @example * @example
* const data = updateDraftOrderShippingMethodStep({ * const data = updateDraftOrderShippingMethodStep({
* order_id: "order_123", * order_id: "order_123",
@@ -1,5 +1,5 @@
import { createStep } from "@medusajs/framework/workflows-sdk" import { createStep } from "@medusajs/framework/workflows-sdk"
import { OrderChangeDTO, OrderDTO } from "@medusajs/types" import type { OrderChangeDTO, OrderDTO } from "@medusajs/framework/types"
import { throwIfOrderChangeIsNotActive } from "../../order/utils/order-validation" import { throwIfOrderChangeIsNotActive } from "../../order/utils/order-validation"
import { throwIfNotDraftOrder } from "../utils/validation" import { throwIfNotDraftOrder } from "../utils/validation"
@@ -22,14 +22,14 @@ export const validateDraftOrderChangeStepId = "validate-draft-order-change"
/** /**
* This step validates that a draft order and its change are valid. It throws an error if the * This step validates that a draft order and its change are valid. It throws an error if the
* order is not a draft order or the order change is not active. * order is not a draft order or the order change is not active.
* *
* :::note * :::note
* *
* You can retrieve a draft order and its change's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query), * You can retrieve a draft order and its change's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query),
* or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep). * or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep).
* *
* ::: * :::
* *
* @example * @example
* const data = validateDraftOrderChangeStep({ * const data = validateDraftOrderChangeStep({
* order: { * order: {
@@ -1,8 +1,8 @@
import { OrderChangeActionDTO } from "@medusajs/types" import type { OrderChangeActionDTO } from "@medusajs/framework/types"
import { ChangeActionType, MedusaError } from "@medusajs/framework/utils" import { ChangeActionType, MedusaError } from "@medusajs/framework/utils"
import { createStep } from "@medusajs/framework/workflows-sdk" import { createStep } from "@medusajs/framework/workflows-sdk"
import { OrderChangeDTO, OrderWorkflow } from "@medusajs/types" import type { OrderChangeDTO, OrderWorkflow } from "@medusajs/framework/types"
/** /**
* The details of the draft order and its change to validate. * The details of the draft order and its change to validate.
@@ -21,14 +21,14 @@ export interface ValidateDraftOrderUpdateActionItemStepInput {
/** /**
* This step validates that an item change can be removed from a draft order edit. It throws an error if the * This step validates that an item change can be removed from a draft order edit. It throws an error if the
* item change is not in the draft order edit, or if the item change is not adding or updating an item. * item change is not in the draft order edit, or if the item change is not adding or updating an item.
* *
* :::note * :::note
* *
* You can retrieve a draft order change's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query), * You can retrieve a draft order change's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query),
* or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep). * or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep).
* *
* ::: * :::
* *
* @example * @example
* const data = validateDraftOrderRemoveActionItemStep({ * const data = validateDraftOrderRemoveActionItemStep({
* input: { * input: {
@@ -4,7 +4,7 @@ import {
OrderChangeActionDTO, OrderChangeActionDTO,
OrderChangeDTO, OrderChangeDTO,
OrderWorkflow, OrderWorkflow,
} from "@medusajs/types" } from "@medusajs/framework/types"
/** /**
* The details of the draft order and its change to validate. * The details of the draft order and its change to validate.
@@ -23,14 +23,14 @@ export interface ValidateDraftOrderShippingMethodActionStepInput {
/** /**
* This step validates that a shipping method change can be removed from a draft order edit. It throws an error if the * This step validates that a shipping method change can be removed from a draft order edit. It throws an error if the
* shipping method change is not in the draft order edit, or if the shipping method change is not adding a shipping method. * shipping method change is not in the draft order edit, or if the shipping method change is not adding a shipping method.
* *
* :::note * :::note
* *
* You can retrieve a draft order change's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query), * You can retrieve a draft order change's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query),
* or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep). * or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep).
* *
* ::: * :::
* *
* @example * @example
* const data = validateDraftOrderShippingMethodActionStep({ * const data = validateDraftOrderShippingMethodActionStep({
* input: { * input: {
@@ -1,8 +1,8 @@
import { OrderChangeActionDTO } from "@medusajs/types" import type { OrderChangeActionDTO } from "@medusajs/framework/types"
import { ChangeActionType, MedusaError } from "@medusajs/framework/utils" import { ChangeActionType, MedusaError } from "@medusajs/framework/utils"
import { createStep } from "@medusajs/framework/workflows-sdk" import { createStep } from "@medusajs/framework/workflows-sdk"
import { OrderChangeDTO, OrderWorkflow } from "@medusajs/types" import type { OrderChangeDTO, OrderWorkflow } from "@medusajs/framework/types"
/** /**
* The details of the draft order and its change to validate. * The details of the draft order and its change to validate.
@@ -21,14 +21,14 @@ export interface ValidateDraftOrderUpdateActionItemStepInput {
/** /**
* This step validates that a new item can be updated in a draft order edit. It throws an error if the * This step validates that a new item can be updated in a draft order edit. It throws an error if the
* item change is not in the draft order edit, or if the item change is not adding an item. * item change is not in the draft order edit, or if the item change is not adding an item.
* *
* :::note * :::note
* *
* You can retrieve a draft order change's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query), * You can retrieve a draft order change's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query),
* or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep). * or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep).
* *
* ::: * :::
* *
* @example * @example
* const data = validateDraftOrderUpdateActionItemStep({ * const data = validateDraftOrderUpdateActionItemStep({
* input: { * input: {
@@ -1,6 +1,6 @@
import { MedusaError, OrderStatus } from "@medusajs/framework/utils" import { MedusaError, OrderStatus } from "@medusajs/framework/utils"
import { createStep } from "@medusajs/framework/workflows-sdk" import { createStep } from "@medusajs/framework/workflows-sdk"
import { OrderDTO } from "@medusajs/types" import type { OrderDTO } from "@medusajs/framework/types"
/** /**
* The details of the draft order to validate. * The details of the draft order to validate.
@@ -14,14 +14,14 @@ export interface ValidateDraftOrderStepInput {
/** /**
* This step validates that an order is a draft order. It throws an error otherwise. * This step validates that an order is a draft order. It throws an error otherwise.
* *
* :::note * :::note
* *
* You can retrieve a draft order's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query), * You can retrieve a draft order's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query),
* or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep). * or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep).
* *
* ::: * :::
* *
* @example * @example
* const data = validateDraftOrderStep({ * const data = validateDraftOrderStep({
* order: { * order: {
@@ -1,5 +1,5 @@
import { createStep } from "@medusajs/framework/workflows-sdk" import { createStep } from "@medusajs/framework/workflows-sdk"
import { PromotionDTO } from "@medusajs/types" import type { PromotionDTO } from "@medusajs/framework/types"
import { import {
throwIfCodesAreInactive, throwIfCodesAreInactive,
throwIfCodesAreMissing, throwIfCodesAreMissing,
@@ -24,23 +24,23 @@ export interface ValidatePromoCodesToAddStepInput {
/** /**
* This step validates that the promo codes to add to a draft order are valid. It throws an error if the * This step validates that the promo codes to add to a draft order are valid. It throws an error if the
* promo codes don't exist or are inactive. * promo codes don't exist or are inactive.
* *
* :::note * :::note
* *
* You can retrieve a promotion's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query), * You can retrieve a promotion's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query),
* or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep). * or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep).
* *
* ::: * :::
* *
* @example * @example
* const data = validatePromoCodesToAddStep({ * const data = validatePromoCodesToAddStep({
* promo_codes: ["PROMO_123", "PROMO_456"], * promo_codes: ["PROMO_123", "PROMO_456"],
* promotions: [{ * promotions: [{
* id: "promo_123", * id: "promo_123",
* code: "PROMO_123" * code: "PROMO_123"
* }, { * }, {
* id: "promo_456", * id: "promo_456",
* code: "PROMO_456" * code: "PROMO_456"
* }], * }],
* }) * })
*/ */
@@ -1,5 +1,5 @@
import { createStep } from "@medusajs/framework/workflows-sdk" import { createStep } from "@medusajs/framework/workflows-sdk"
import { PromotionDTO } from "@medusajs/types" import type { PromotionDTO } from "@medusajs/framework/types"
import { throwIfCodesAreMissing } from "../utils/validation" import { throwIfCodesAreMissing } from "../utils/validation"
export const validatePromoCodesToRemoveId = "validate-promo-codes-to-remove" export const validatePromoCodesToRemoveId = "validate-promo-codes-to-remove"
@@ -21,23 +21,23 @@ export interface ValidatePromoCodesToRemoveStepInput {
/** /**
* This step validates that the promo codes can be removed from a draft order. It throws an error if the promo * This step validates that the promo codes can be removed from a draft order. It throws an error if the promo
* codes don't exist. * codes don't exist.
* *
* :::note * :::note
* *
* You can retrieve a promotion's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query), * You can retrieve a promotion's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query),
* or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep). * or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep).
* *
* ::: * :::
* *
* @example * @example
* const data = validatePromoCodesToRemoveStep({ * const data = validatePromoCodesToRemoveStep({
* promo_codes: ["PROMO_123", "PROMO_456"], * promo_codes: ["PROMO_123", "PROMO_456"],
* promotions: [{ * promotions: [{
* id: "promo_123", * id: "promo_123",
* code: "PROMO_123" * code: "PROMO_123"
* }, { * }, {
* id: "promo_456", * id: "promo_456",
* code: "PROMO_456" * code: "PROMO_456"
* }], * }],
* }) * })
*/ */
@@ -3,7 +3,7 @@ import {
OrderStatus, OrderStatus,
PromotionStatus, PromotionStatus,
} from "@medusajs/framework/utils" } from "@medusajs/framework/utils"
import { OrderDTO, PromotionDTO } from "@medusajs/types" import type { OrderDTO, PromotionDTO } from "@medusajs/framework/types"
interface ThrowIfNotDraftOrderInput { interface ThrowIfNotDraftOrderInput {
order: OrderDTO order: OrderDTO
@@ -10,7 +10,11 @@ import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { OrderChangeDTO, OrderDTO, OrderWorkflow } from "@medusajs/types" import {
OrderChangeDTO,
OrderDTO,
OrderWorkflow,
} from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
addOrderLineItemsWorkflow, addOrderLineItemsWorkflow,
@@ -9,7 +9,11 @@ import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { OrderChangeDTO, OrderDTO, PromotionDTO } from "@medusajs/types" import {
OrderChangeDTO,
OrderDTO,
PromotionDTO,
} from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
createOrderChangeActionsWorkflow, createOrderChangeActionsWorkflow,
@@ -39,10 +43,10 @@ export interface AddDraftOrderPromotionWorkflowInput {
/** /**
* This workflow adds promotions to a draft order. It's used by the * This workflow adds promotions to a draft order. It's used by the
* [Add Promotion to Draft Order Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersideditpromotions). * [Add Promotion to Draft Order Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersideditpromotions).
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around adding promotions to * You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around adding promotions to
* a draft order. * a draft order.
* *
* @example * @example
* const { result } = await addDraftOrderPromotionWorkflow(container) * const { result } = await addDraftOrderPromotionWorkflow(container)
* .run({ * .run({
@@ -51,9 +55,9 @@ export interface AddDraftOrderPromotionWorkflowInput {
* promo_codes: ["PROMO_CODE_1", "PROMO_CODE_2"] * promo_codes: ["PROMO_CODE_1", "PROMO_CODE_2"]
* } * }
* }) * })
* *
* @summary * @summary
* *
* Add promotions to a draft order. * Add promotions to a draft order.
*/ */
export const addDraftOrderPromotionWorkflow = createWorkflow( export const addDraftOrderPromotionWorkflow = createWorkflow(
@@ -19,7 +19,7 @@ import {
OrderChangeDTO, OrderChangeDTO,
OrderDTO, OrderDTO,
ShippingOptionDTO, ShippingOptionDTO,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
createOrderChangeActionsWorkflow, createOrderChangeActionsWorkflow,
@@ -4,7 +4,7 @@ import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { OrderDTO, OrderWorkflow } from "@medusajs/types" import type { OrderDTO, OrderWorkflow } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { createOrderChangeStep, previewOrderChangeStep } from "../../order" import { createOrderChangeStep, previewOrderChangeStep } from "../../order"
import { validateDraftOrderStep } from "../steps" import { validateDraftOrderStep } from "../steps"
@@ -14,12 +14,12 @@ export const beginDraftOrderEditWorkflowId = "begin-draft-order-edit"
/** /**
* This workflow begins a draft order edit. It's used by the * This workflow begins a draft order edit. It's used by the
* [Create Draft Order Edit Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersidedit). * [Create Draft Order Edit Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersidedit).
* *
* The draft order edit can later be requested using {@link requestDraftOrderEditWorkflow} or confirmed using {@link confirmDraftOrderEditWorkflow}. * The draft order edit can later be requested using {@link requestDraftOrderEditWorkflow} or confirmed using {@link confirmDraftOrderEditWorkflow}.
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around * You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around
* creating a draft order edit request. * creating a draft order edit request.
* *
* @example * @example
* const { result } = await beginDraftOrderEditWorkflow(container) * const { result } = await beginDraftOrderEditWorkflow(container)
* .run({ * .run({
@@ -27,9 +27,9 @@ export const beginDraftOrderEditWorkflowId = "begin-draft-order-edit"
* order_id: "order_123", * order_id: "order_123",
* } * }
* }) * })
* *
* @summary * @summary
* *
* Create a draft order edit request. * Create a draft order edit request.
*/ */
export const beginDraftOrderEditWorkflow = createWorkflow( export const beginDraftOrderEditWorkflow = createWorkflow(
@@ -10,7 +10,7 @@ import {
when, when,
WorkflowData, WorkflowData,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { OrderChangeDTO, OrderDTO } from "@medusajs/types" import type { OrderChangeDTO, OrderDTO } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { deleteOrderChangesStep, deleteOrderShippingMethods } from "../../order" import { deleteOrderChangesStep, deleteOrderShippingMethods } from "../../order"
import { restoreDraftOrderShippingMethodsStep } from "../steps/restore-draft-order-shipping-methods" import { restoreDraftOrderShippingMethodsStep } from "../steps/restore-draft-order-shipping-methods"
@@ -8,7 +8,11 @@ import {
transform, transform,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { BigNumberInput, OrderChangeDTO, OrderDTO } from "@medusajs/types" import {
BigNumberInput,
OrderChangeDTO,
OrderDTO,
} from "@medusajs/framework/types"
import { reserveInventoryStep } from "../../cart" import { reserveInventoryStep } from "../../cart"
import { import {
prepareConfirmInventoryInput, prepareConfirmInventoryInput,
@@ -10,7 +10,7 @@ import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { IOrderModuleService, OrderDTO } from "@medusajs/types" import type { IOrderModuleService, OrderDTO } from "@medusajs/framework/types"
import { emitEventStep, useRemoteQueryStep } from "../../common" import { emitEventStep, useRemoteQueryStep } from "../../common"
import { validateDraftOrderStep } from "../steps/validate-draft-order" import { validateDraftOrderStep } from "../steps/validate-draft-order"
@@ -78,10 +78,10 @@ export const convertDraftOrderStep = createStep(
/** /**
* This workflow converts a draft order to a pending order. It's used by the * This workflow converts a draft order to a pending order. It's used by the
* [Convert Draft Order to Order Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersidconverttoorder). * [Convert Draft Order to Order Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersidconverttoorder).
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around * You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around
* converting a draft order to a pending order. * converting a draft order to a pending order.
* *
* @example * @example
* const { result } = await convertDraftOrderWorkflow(container) * const { result } = await convertDraftOrderWorkflow(container)
* .run({ * .run({
@@ -89,9 +89,9 @@ export const convertDraftOrderStep = createStep(
* id: "order_123", * id: "order_123",
* } * }
* }) * })
* *
* @summary * @summary
* *
* Convert a draft order to a pending order. * Convert a draft order to a pending order.
*/ */
export const convertDraftOrderWorkflow = createWorkflow( export const convertDraftOrderWorkflow = createWorkflow(
@@ -5,7 +5,7 @@ import {
createWorkflow, createWorkflow,
transform, transform,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { OrderDTO } from "@medusajs/framework/types" import type { OrderDTO } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { removeRemoteLinkStep, useQueryGraphStep } from "../../common" import { removeRemoteLinkStep, useQueryGraphStep } from "../../common"
@@ -5,7 +5,7 @@ import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { OrderDTO } from "@medusajs/types" import type { OrderDTO } from "@medusajs/framework/types"
import { import {
getActionsToComputeFromPromotionsStep, getActionsToComputeFromPromotionsStep,
getPromotionCodesToApply, getPromotionCodesToApply,
@@ -11,7 +11,7 @@ import {
OrderDTO, OrderDTO,
OrderPreviewDTO, OrderPreviewDTO,
OrderWorkflow, OrderWorkflow,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
deleteOrderChangeActionsStep, deleteOrderChangeActionsStep,
@@ -13,7 +13,7 @@ import {
OrderDTO, OrderDTO,
OrderPreviewDTO, OrderPreviewDTO,
OrderWorkflow, OrderWorkflow,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
deleteOrderChangeActionsStep, deleteOrderChangeActionsStep,
@@ -9,7 +9,11 @@ import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { OrderChangeDTO, OrderDTO, PromotionDTO } from "@medusajs/types" import {
OrderChangeDTO,
OrderDTO,
PromotionDTO,
} from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
createOrderChangeActionsWorkflow, createOrderChangeActionsWorkflow,
@@ -40,10 +44,10 @@ export interface RemoveDraftOrderPromotionsWorkflowInput {
/** /**
* This workflow removes promotions from a draft order edit. It's used by the * This workflow removes promotions from a draft order edit. It's used by the
* [Remove Promotions from Draft Order Edit Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_deletedraftordersideditpromotions). * [Remove Promotions from Draft Order Edit Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_deletedraftordersideditpromotions).
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around * You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around
* removing promotions from a draft order edit. * removing promotions from a draft order edit.
* *
* @example * @example
* const { result } = await removeDraftOrderPromotionsWorkflow(container) * const { result } = await removeDraftOrderPromotionsWorkflow(container)
* .run({ * .run({
@@ -52,9 +56,9 @@ export interface RemoveDraftOrderPromotionsWorkflowInput {
* promo_codes: ["PROMO_CODE_1", "PROMO_CODE_2"], * promo_codes: ["PROMO_CODE_1", "PROMO_CODE_2"],
* } * }
* }) * })
* *
* @summary * @summary
* *
* Remove promotions from a draft order edit. * Remove promotions from a draft order edit.
*/ */
export const removeDraftOrderPromotionsWorkflow = createWorkflow( export const removeDraftOrderPromotionsWorkflow = createWorkflow(
@@ -10,7 +10,7 @@ import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { OrderChangeDTO, OrderDTO } from "@medusajs/types" import type { OrderChangeDTO, OrderDTO } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
createOrderChangeActionsWorkflow, createOrderChangeActionsWorkflow,
@@ -4,7 +4,7 @@ import {
transform, transform,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { OrderChangeDTO, OrderDTO } from "@medusajs/types" import type { OrderChangeDTO, OrderDTO } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
createOrUpdateOrderPaymentCollectionWorkflow, createOrUpdateOrderPaymentCollectionWorkflow,
@@ -51,10 +51,10 @@ export type RequestDraftOrderEditWorkflowInput = {
/** /**
* This workflow requests a draft order edit. It's used by the * This workflow requests a draft order edit. It's used by the
* [Request Draft Order Edit Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersideditrequest). * [Request Draft Order Edit Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersideditrequest).
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around * You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around
* requesting a draft order edit. * requesting a draft order edit.
* *
* @example * @example
* const { result } = await requestDraftOrderEditWorkflow(container) * const { result } = await requestDraftOrderEditWorkflow(container)
* .run({ * .run({
@@ -63,9 +63,9 @@ export type RequestDraftOrderEditWorkflowInput = {
* requested_by: "user_123", * requested_by: "user_123",
* } * }
* }) * })
* *
* @summary * @summary
* *
* Request a draft order edit. * Request a draft order edit.
*/ */
export const requestDraftOrderEditWorkflow = createWorkflow( export const requestDraftOrderEditWorkflow = createWorkflow(
@@ -11,7 +11,7 @@ import {
OrderChangeDTO, OrderChangeDTO,
OrderDTO, OrderDTO,
OrderWorkflow, OrderWorkflow,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
previewOrderChangeStep, previewOrderChangeStep,
@@ -13,7 +13,7 @@ import {
OrderDTO, OrderDTO,
OrderPreviewDTO, OrderPreviewDTO,
OrderWorkflow, OrderWorkflow,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
previewOrderChangeStep, previewOrderChangeStep,
@@ -17,7 +17,7 @@ import {
OrderDTO, OrderDTO,
OrderPreviewDTO, OrderPreviewDTO,
OrderWorkflow, OrderWorkflow,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
createOrderChangeActionsWorkflow, createOrderChangeActionsWorkflow,
@@ -10,7 +10,11 @@ import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
} from "@medusajs/framework/workflows-sdk" } from "@medusajs/framework/workflows-sdk"
import { BigNumberInput, OrderChangeDTO, OrderDTO } from "@medusajs/types" import {
BigNumberInput,
OrderChangeDTO,
OrderDTO,
} from "@medusajs/framework/types"
import { useRemoteQueryStep } from "../../common" import { useRemoteQueryStep } from "../../common"
import { import {
createOrderChangeActionsWorkflow, createOrderChangeActionsWorkflow,
@@ -13,7 +13,7 @@ import {
RegisterOrderChangeDTO, RegisterOrderChangeDTO,
UpdateOrderDTO, UpdateOrderDTO,
UpsertOrderAddressDTO, UpsertOrderAddressDTO,
} from "@medusajs/types" } from "@medusajs/framework/types"
import { emitEventStep, useRemoteQueryStep } from "../../common" import { emitEventStep, useRemoteQueryStep } from "../../common"
import { previewOrderChangeStep, registerOrderChangesStep } from "../../order" import { previewOrderChangeStep, registerOrderChangesStep } from "../../order"
import { validateDraftOrderStep } from "../steps/validate-draft-order" import { validateDraftOrderStep } from "../steps/validate-draft-order"
@@ -74,14 +74,14 @@ export interface UpdateDraftOrderStepInput {
/** /**
* This step updates a draft order's details. * This step updates a draft order's details.
* *
* :::note * :::note
* *
* You can retrieve a draft order's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query), * You can retrieve a draft order's details using [Query](https://docs.medusajs.com/learn/fundamentals/module-links/query),
* or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep). * or [useQueryGraphStep](https://docs.medusajs.com/resources/references/medusa-workflows/steps/useQueryGraphStep).
* *
* ::: * :::
* *
* @example * @example
* const data = updateDraftOrderStep({ * const data = updateDraftOrderStep({
* order: { * order: {
@@ -123,15 +123,15 @@ export const updateDraftOrderStep = createStep(
/** /**
* This workflow updates a draft order's details. It's used by the * This workflow updates a draft order's details. It's used by the
* [Update Draft Order Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersid). * [Update Draft Order Admin API Route](https://docs.medusajs.com/api/admin#draft-orders_postdraftordersid).
* *
* This workflow doesn't update the draft order's items, shipping methods, or promotions. Instead, you have to * This workflow doesn't update the draft order's items, shipping methods, or promotions. Instead, you have to
* create a draft order edit using {@link beginDraftOrderEditWorkflow} and make updates in the draft order edit. * create a draft order edit using {@link beginDraftOrderEditWorkflow} and make updates in the draft order edit.
* Then, you can confirm the draft order edit using {@link confirmDraftOrderEditWorkflow} or request a draft order edit * Then, you can confirm the draft order edit using {@link confirmDraftOrderEditWorkflow} or request a draft order edit
* using {@link requestDraftOrderEditWorkflow}. * using {@link requestDraftOrderEditWorkflow}.
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around * You can use this workflow within your customizations or your own custom workflows, allowing you to wrap custom logic around
* updating a draft order. * updating a draft order.
* *
* @example * @example
* const { result } = await updateDraftOrderWorkflow(container) * const { result } = await updateDraftOrderWorkflow(container)
* .run({ * .run({
@@ -141,9 +141,9 @@ export const updateDraftOrderStep = createStep(
* customer_id: "cus_123", * customer_id: "cus_123",
* } * }
* }) * })
* *
* @summary * @summary
* *
* Update a draft order's details. * Update a draft order's details.
*/ */
export const updateDraftOrderWorkflow = createWorkflow( export const updateDraftOrderWorkflow = createWorkflow(
@@ -1,4 +1,4 @@
import { IFileModuleService } from "@medusajs/framework/types" import type { IFileModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -12,7 +12,7 @@ export const deleteFilesStepId = "delete-files"
* This step deletes one or more files using the installed * This step deletes one or more files using the installed
* [File Module Provider](https://docs.medusajs.com/resources/infrastructure-modules/file). The files * [File Module Provider](https://docs.medusajs.com/resources/infrastructure-modules/file). The files
* will be removed from the database and the storage. * will be removed from the database and the storage.
* *
* @example * @example
* const data = deleteFilesStep([ * const data = deleteFilesStep([
* "id_123" * "id_123"
@@ -1,4 +1,4 @@
import { IFileModuleService } from "@medusajs/framework/types" import type { IFileModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -16,13 +16,13 @@ export type UploadFilesStepInput = {
filename: string filename: string
/** /**
* The MIME type of the file. * The MIME type of the file.
* *
* @example * @example
* img/jpg * img/jpg
*/ */
mimeType: string mimeType: string
/** /**
* The content of the file. For images, for example, * The content of the file. For images, for example,
* use binary string. For CSV files, use the CSV content. * use binary string. For CSV files, use the CSV content.
*/ */
content: string content: string
@@ -41,7 +41,7 @@ export const uploadFilesStepId = "upload-files"
/** /**
* This step uploads one or more files using the installed * This step uploads one or more files using the installed
* [File Module Provider](https://docs.medusajs.com/resources/infrastructure-modules/file). * [File Module Provider](https://docs.medusajs.com/resources/infrastructure-modules/file).
* *
* @example * @example
* const data = uploadFilesStep({ * const data = uploadFilesStep({
* files: [ * files: [
@@ -1,4 +1,4 @@
import { FileDTO } from "@medusajs/framework/types" import type { FileDTO } from "@medusajs/framework/types"
import { import {
WorkflowData, WorkflowData,
WorkflowResponse, WorkflowResponse,
@@ -20,13 +20,13 @@ export type UploadFilesWorkflowInput = {
filename: string filename: string
/** /**
* The MIME type of the file. * The MIME type of the file.
* *
* @example * @example
* img/jpg * img/jpg
*/ */
mimeType: string mimeType: string
/** /**
* The content of the file. For images, for example, * The content of the file. For images, for example,
* use binary string. For CSV files, use the CSV content. * use binary string. For CSV files, use the CSV content.
*/ */
content: string content: string
@@ -34,7 +34,7 @@ export type UploadFilesWorkflowInput = {
* The access level of the file. Use `public` for the file that * The access level of the file. Use `public` for the file that
* can be accessed by anyone. For example, for images that are displayed * can be accessed by anyone. For example, for images that are displayed
* on the storefront. Use `private` for files that are only accessible * on the storefront. Use `private` for files that are only accessible
* by authenticated users. For example, for CSV files used to * by authenticated users. For example, for CSV files used to
* import data. * import data.
*/ */
access: "public" | "private" access: "public" | "private"
@@ -43,13 +43,13 @@ export type UploadFilesWorkflowInput = {
export const uploadFilesWorkflowId = "upload-files" export const uploadFilesWorkflowId = "upload-files"
/** /**
* This workflow uploads one or more files using the installed * This workflow uploads one or more files using the installed
* [File Module Provider](https://docs.medusajs.com/resources/infrastructure-modules/file). The workflow is used by the * [File Module Provider](https://docs.medusajs.com/resources/infrastructure-modules/file). The workflow is used by the
* [Upload Files Admin API Route](https://docs.medusajs.com/api/admin#uploads_postuploads). * [Upload Files Admin API Route](https://docs.medusajs.com/api/admin#uploads_postuploads).
* *
* You can use this workflow within your customizations or your own custom workflows, allowing you to * You can use this workflow within your customizations or your own custom workflows, allowing you to
* upload files within your custom flows. * upload files within your custom flows.
* *
* @example * @example
* const { result } = await uploadFilesWorkflow(container) * const { result } = await uploadFilesWorkflow(container)
* .run({ * .run({
@@ -64,9 +64,9 @@ export const uploadFilesWorkflowId = "upload-files"
* ] * ]
* } * }
* }) * })
* *
* @summary * @summary
* *
* Upload files using the installed File Module Provider. * Upload files using the installed File Module Provider.
*/ */
export const uploadFilesWorkflow = createWorkflow( export const uploadFilesWorkflow = createWorkflow(
@@ -1,4 +1,4 @@
import { IFulfillmentModuleService } from "@medusajs/framework/types" import type { IFulfillmentModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,4 @@
import { IFulfillmentModuleService } from "@medusajs/framework/types" import type { IFulfillmentModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
@@ -1,4 +1,4 @@
import { IFulfillmentModuleService } from "@medusajs/framework/types" import type { IFulfillmentModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -1,5 +1,5 @@
import { DeleteEntityInput } from "@medusajs/framework/modules-sdk" import { DeleteEntityInput } from "@medusajs/framework/modules-sdk"
import { IFulfillmentModuleService } from "@medusajs/framework/types" import type { IFulfillmentModuleService } from "@medusajs/framework/types"
import { Modules } from "@medusajs/framework/utils" import { Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -1,5 +1,5 @@
import { Link } from "@medusajs/framework/modules-sdk" import { Link } from "@medusajs/framework/modules-sdk"
import { RemoteQueryFunction } from "@medusajs/framework/types" import type { RemoteQueryFunction } from "@medusajs/framework/types"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { import {
ContainerRegistrationKeys, ContainerRegistrationKeys,
@@ -1,4 +1,7 @@
import { ServiceZoneDTO, ShippingOptionDTO } from "@medusajs/framework/types" import type {
ServiceZoneDTO,
ShippingOptionDTO,
} from "@medusajs/framework/types"
import { import {
ContainerRegistrationKeys, ContainerRegistrationKeys,
MedusaError, MedusaError,
@@ -1,4 +1,4 @@
import { IFulfillmentModuleService } from "@medusajs/framework/types" import type { IFulfillmentModuleService } from "@medusajs/framework/types"
import { MedusaError, Modules } from "@medusajs/framework/utils" import { MedusaError, Modules } from "@medusajs/framework/utils"
import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk" import { StepResponse, createStep } from "@medusajs/framework/workflows-sdk"
@@ -1,7 +1,11 @@
import { FulfillmentWorkflow } from "@medusajs/framework/types" import type { FulfillmentWorkflow } from "@medusajs/framework/types"
import { MedusaError, Modules, ShippingOptionPriceType, } from "@medusajs/framework/utils" import {
MedusaError,
Modules,
ShippingOptionPriceType,
} from "@medusajs/framework/utils"
import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk" import { createStep, StepResponse } from "@medusajs/framework/workflows-sdk"
import { CreateShippingOptionDTO } from "@medusajs/types" import type { CreateShippingOptionDTO } from "@medusajs/framework/types"
/** /**
* The data to validate shipping option prices. * The data to validate shipping option prices.
@@ -1,4 +1,4 @@
import { FulfillmentWorkflow } from "@medusajs/framework/types" import type { FulfillmentWorkflow } from "@medusajs/framework/types"
import { import {
createWorkflow, createWorkflow,
transform, transform,
@@ -14,17 +14,17 @@ export const calculateShippingOptionsPricesWorkflowId =
/** /**
* This workflow calculates the prices for one or more shipping options in a cart. It's used by the * This workflow calculates the prices for one or more shipping options in a cart. It's used by the
* [Calculate Shipping Option Price Store API Route](https://docs.medusajs.com/api/store#shipping-options_postshippingoptionsidcalculate). * [Calculate Shipping Option Price Store API Route](https://docs.medusajs.com/api/store#shipping-options_postshippingoptionsidcalculate).
* *
* :::note * :::note
* *
* Calculating shipping option prices may require sending requests to third-party fulfillment services. * Calculating shipping option prices may require sending requests to third-party fulfillment services.
* This depends on the implementation of the fulfillment provider associated with the shipping option. * This depends on the implementation of the fulfillment provider associated with the shipping option.
* *
* ::: * :::
* *
* You can use this workflow within your own customizations or custom workflows, allowing you to * You can use this workflow within your own customizations or custom workflows, allowing you to
* calculate the prices of shipping options within your custom flows. * calculate the prices of shipping options within your custom flows.
* *
* @example * @example
* const { result } = await calculateShippingOptionsPricesWorkflow(container) * const { result } = await calculateShippingOptionsPricesWorkflow(container)
* .run({ * .run({
@@ -41,9 +41,9 @@ export const calculateShippingOptionsPricesWorkflowId =
* ] * ]
* } * }
* }) * })
* *
* @summary * @summary
* *
* Calculate shipping option prices in a cart. * Calculate shipping option prices in a cart.
*/ */
export const calculateShippingOptionsPricesWorkflow = createWorkflow( export const calculateShippingOptionsPricesWorkflow = createWorkflow(

Some files were not shown because too many files have changed in this diff Show More