-
-
Notifications
You must be signed in to change notification settings - Fork 2.9k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: Add HTTP endpoints and workflows for price preference management (
#7960) REF CORE-2376 Remaining pieces are adding UI to manage the flag, showing the flag in price editor, plugging it in cart calculations, and #7827
- Loading branch information
Showing
27 changed files
with
702 additions
and
10 deletions.
There are no files selected for viewing
221 changes: 221 additions & 0 deletions
221
integration-tests/http/__tests__/price-preference/admin/price-preference.spec.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,221 @@ | ||
import { medusaIntegrationTestRunner } from "medusa-test-utils" | ||
import { | ||
createAdminUser, | ||
adminHeaders, | ||
} from "../../../../helpers/create-admin-user" | ||
|
||
jest.setTimeout(30000) | ||
|
||
medusaIntegrationTestRunner({ | ||
env: {}, | ||
testSuite: ({ dbConnection, getContainer, api }) => { | ||
let pricePreference1 | ||
let pricePreference2 | ||
|
||
beforeEach(async () => { | ||
const container = getContainer() | ||
await createAdminUser(dbConnection, adminHeaders, container) | ||
|
||
pricePreference1 = ( | ||
await api.post( | ||
"/admin/price-preferences", | ||
{ | ||
attribute: "region_id", | ||
value: "region-1", | ||
is_tax_inclusive: true, | ||
}, | ||
adminHeaders | ||
) | ||
).data.price_preference | ||
|
||
pricePreference2 = ( | ||
await api.post( | ||
"/admin/price-preferences", | ||
{ | ||
attribute: "currency_code", | ||
value: "EUR", | ||
is_tax_inclusive: true, | ||
}, | ||
adminHeaders | ||
) | ||
).data.price_preference | ||
}) | ||
|
||
describe("/admin/price-preferences", () => { | ||
describe("POST /admin/price-preferences", () => { | ||
it("creates a price preference", async () => { | ||
const newPricePreference = ( | ||
await api.post( | ||
"/admin/price-preferences", | ||
{ | ||
attribute: "region_id", | ||
value: "region-2", | ||
is_tax_inclusive: true, | ||
}, | ||
adminHeaders | ||
) | ||
).data.price_preference | ||
|
||
expect(newPricePreference).toEqual( | ||
expect.objectContaining({ | ||
attribute: "region_id", | ||
value: "region-2", | ||
is_tax_inclusive: true, | ||
}) | ||
) | ||
}) | ||
|
||
it("creates a price preference with false tax inclusivity by default", async () => { | ||
const newPricePreference = ( | ||
await api.post( | ||
"/admin/price-preferences", | ||
{ | ||
attribute: "region_id", | ||
value: "region-2", | ||
}, | ||
adminHeaders | ||
) | ||
).data.price_preference | ||
|
||
expect(newPricePreference).toEqual( | ||
expect.objectContaining({ | ||
attribute: "region_id", | ||
value: "region-2", | ||
is_tax_inclusive: false, | ||
}) | ||
) | ||
}) | ||
}) | ||
|
||
describe("GET /admin/price-preferences", () => { | ||
it("returns a list of price preferences", async () => { | ||
const response = ( | ||
await api.get("/admin/price-preferences", adminHeaders) | ||
).data.price_preferences | ||
|
||
expect(response).toEqual( | ||
expect.arrayContaining([ | ||
expect.objectContaining({ | ||
attribute: "region_id", | ||
value: "region-1", | ||
is_tax_inclusive: true, | ||
}), | ||
expect.objectContaining({ | ||
attribute: "currency_code", | ||
value: "EUR", | ||
is_tax_inclusive: true, | ||
}), | ||
]) | ||
) | ||
}) | ||
it("filters price preferences by attribute", async () => { | ||
const response = ( | ||
await api.get( | ||
"/admin/price-preferences?attribute=region_id", | ||
adminHeaders | ||
) | ||
).data.price_preferences | ||
|
||
expect(response).toEqual([ | ||
expect.objectContaining({ | ||
attribute: "region_id", | ||
value: "region-1", | ||
is_tax_inclusive: true, | ||
}), | ||
]) | ||
}) | ||
}) | ||
|
||
describe("GET /admin/price-preferences/:id", () => { | ||
it("returns a price preference by :id", async () => { | ||
const response = ( | ||
await api.get( | ||
`/admin/price-preferences/${pricePreference1.id}`, | ||
adminHeaders | ||
) | ||
).data.price_preference | ||
|
||
expect(response).toEqual( | ||
expect.objectContaining({ | ||
attribute: "region_id", | ||
value: "region-1", | ||
is_tax_inclusive: true, | ||
}) | ||
) | ||
}) | ||
}) | ||
|
||
describe("POST /admin/price-preferences/:id", () => { | ||
it("updates a price preference", async () => { | ||
const response = ( | ||
await api.post( | ||
`/admin/price-preferences/${pricePreference1.id}`, | ||
{ | ||
attribute: "region_id", | ||
value: "region-2", | ||
is_tax_inclusive: false, | ||
}, | ||
adminHeaders | ||
) | ||
).data.price_preference | ||
|
||
expect(response).toEqual( | ||
expect.objectContaining({ | ||
attribute: "region_id", | ||
value: "region-2", | ||
is_tax_inclusive: false, | ||
}) | ||
) | ||
}) | ||
it("updates the tax inclusivity in the price preference", async () => { | ||
const response = ( | ||
await api.post( | ||
`/admin/price-preferences/${pricePreference1.id}`, | ||
{ | ||
is_tax_inclusive: false, | ||
}, | ||
adminHeaders | ||
) | ||
).data.price_preference | ||
|
||
expect(response).toEqual( | ||
expect.objectContaining({ | ||
attribute: "region_id", | ||
value: "region-1", | ||
is_tax_inclusive: false, | ||
}) | ||
) | ||
}) | ||
}) | ||
|
||
describe("DELETE /admin/price-preferences/:id", () => { | ||
it("Deletes a price preference", async () => { | ||
const deleteResponse = await api.delete( | ||
`/admin/price-preferences/${pricePreference1.id}`, | ||
adminHeaders | ||
) | ||
|
||
const remainingPricePreferences = ( | ||
await api.get("/admin/price-preferences", adminHeaders) | ||
).data.price_preferences | ||
|
||
expect(deleteResponse.data).toEqual( | ||
expect.objectContaining({ | ||
id: pricePreference1.id, | ||
object: "price_preference", | ||
deleted: true, | ||
}) | ||
) | ||
|
||
expect(remainingPricePreferences).toEqual([ | ||
expect.objectContaining({ | ||
attribute: "currency_code", | ||
value: "EUR", | ||
is_tax_inclusive: true, | ||
}), | ||
]) | ||
}) | ||
}) | ||
}) | ||
}, | ||
}) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1 +1,2 @@ | ||
export * from "./steps" | ||
export * from "./workflows" |
34 changes: 34 additions & 0 deletions
34
packages/core/core-flows/src/pricing/steps/create-price-preferences.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,34 @@ | ||
import { IPricingModuleService } from "@medusajs/types" | ||
import { PricingWorkflow } from "@medusajs/types/dist/workflow" | ||
import { ModuleRegistrationName } from "@medusajs/utils" | ||
import { StepResponse, createStep } from "@medusajs/workflows-sdk" | ||
|
||
type StepInput = PricingWorkflow.CreatePricePreferencesWorkflowInput[] | ||
|
||
export const createPricePreferencesStepId = "create-price-preferences" | ||
export const createPricePreferencesStep = createStep( | ||
createPricePreferencesStepId, | ||
async (data: StepInput, { container }) => { | ||
const pricingModule = container.resolve<IPricingModuleService>( | ||
ModuleRegistrationName.PRICING | ||
) | ||
|
||
const pricePreferences = await pricingModule.createPricePreferences(data) | ||
|
||
return new StepResponse( | ||
pricePreferences, | ||
pricePreferences.map((pricePreference) => pricePreference.id) | ||
) | ||
}, | ||
async (pricePreferences, { container }) => { | ||
if (!pricePreferences?.length) { | ||
return | ||
} | ||
|
||
const pricingModule = container.resolve<IPricingModuleService>( | ||
ModuleRegistrationName.PRICING | ||
) | ||
|
||
await pricingModule.deletePricePreferences(pricePreferences) | ||
} | ||
) |
28 changes: 28 additions & 0 deletions
28
packages/core/core-flows/src/pricing/steps/delete-price-preferences.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
import { IPricingModuleService } from "@medusajs/types" | ||
import { ModuleRegistrationName } from "@medusajs/utils" | ||
import { StepResponse, createStep } from "@medusajs/workflows-sdk" | ||
|
||
export const deletePricePreferencesStepId = "delete-price-preferences" | ||
export const deletePricePreferencesStep = createStep( | ||
deletePricePreferencesStepId, | ||
async (ids: string[], { container }) => { | ||
const service = container.resolve<IPricingModuleService>( | ||
ModuleRegistrationName.PRICING | ||
) | ||
|
||
await service.softDeletePricePreferences(ids) | ||
|
||
return new StepResponse(void 0, ids) | ||
}, | ||
async (prevIds, { container }) => { | ||
if (!prevIds?.length) { | ||
return | ||
} | ||
|
||
const service = container.resolve<IPricingModuleService>( | ||
ModuleRegistrationName.PRICING | ||
) | ||
|
||
await service.restorePricePreferences(prevIds) | ||
} | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,5 @@ | ||
export * from "./create-price-sets" | ||
export * from "./update-price-sets" | ||
export * from "./create-price-preferences" | ||
export * from "./update-price-preferences" | ||
export * from "./delete-price-preferences" |
45 changes: 45 additions & 0 deletions
45
packages/core/core-flows/src/pricing/steps/update-price-preferences.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,45 @@ | ||
import { PricingWorkflow, IPricingModuleService } from "@medusajs/types" | ||
import { | ||
ModuleRegistrationName, | ||
getSelectsAndRelationsFromObjectArray, | ||
} from "@medusajs/utils" | ||
import { StepResponse, createStep } from "@medusajs/workflows-sdk" | ||
|
||
type StepInput = PricingWorkflow.UpdatePricePreferencesWorkflowInput | ||
|
||
export const updatePricePreferencesStepId = "update-price-preferences" | ||
export const updatePricePreferencesStep = createStep( | ||
updatePricePreferencesStepId, | ||
async (input: StepInput, { container }) => { | ||
const service = container.resolve<IPricingModuleService>( | ||
ModuleRegistrationName.PRICING | ||
) | ||
|
||
const { selects, relations } = getSelectsAndRelationsFromObjectArray([ | ||
input.update, | ||
]) | ||
|
||
const prevData = await service.listPricePreferences(input.selector, { | ||
select: selects, | ||
relations, | ||
}) | ||
|
||
const updatedPricePreferences = await service.updatePricePreferences( | ||
input.selector, | ||
input.update | ||
) | ||
|
||
return new StepResponse(updatedPricePreferences, prevData) | ||
}, | ||
async (prevData, { container }) => { | ||
if (!prevData?.length) { | ||
return | ||
} | ||
|
||
const service = container.resolve<IPricingModuleService>( | ||
ModuleRegistrationName.PRICING | ||
) | ||
|
||
await service.upsertPricePreferences(prevData) | ||
} | ||
) |
13 changes: 13 additions & 0 deletions
13
packages/core/core-flows/src/pricing/workflows/create-price-preferences.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
import { PricingWorkflow } from "@medusajs/types" | ||
import { WorkflowData, createWorkflow } from "@medusajs/workflows-sdk" | ||
import { createPricePreferencesStep } from "../steps" | ||
|
||
type WorkflowInputData = PricingWorkflow.CreatePricePreferencesWorkflowInput[] | ||
|
||
export const createPricePreferencesWorkflowId = "create-price-preferences" | ||
export const createPricePreferencesWorkflow = createWorkflow( | ||
createPricePreferencesWorkflowId, | ||
(input: WorkflowData<WorkflowInputData>) => { | ||
return createPricePreferencesStep(input) | ||
} | ||
) |
10 changes: 10 additions & 0 deletions
10
packages/core/core-flows/src/pricing/workflows/delete-price-preferences.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
import { WorkflowData, createWorkflow } from "@medusajs/workflows-sdk" | ||
import { deletePricePreferencesStep } from "../steps" | ||
|
||
export const deletePricePreferencesWorkflowId = "delete-price-preferences" | ||
export const deletePricePreferencesWorkflow = createWorkflow( | ||
deletePricePreferencesWorkflowId, | ||
(input: WorkflowData<string[]>) => { | ||
return deletePricePreferencesStep(input) | ||
} | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
export * from "./create-price-preferences" | ||
export * from "./update-price-preferences" | ||
export * from "./delete-price-preferences" |
13 changes: 13 additions & 0 deletions
13
packages/core/core-flows/src/pricing/workflows/update-price-preferences.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
import { PricingWorkflow } from "@medusajs/types" | ||
import { WorkflowData, createWorkflow } from "@medusajs/workflows-sdk" | ||
import { updatePricePreferencesStep } from "../steps" | ||
|
||
type WorkflowInputData = PricingWorkflow.UpdatePricePreferencesWorkflowInput | ||
|
||
export const updatePricePreferencesWorkflowId = "update-price-preferences" | ||
export const updatePricePreferencesWorkflow = createWorkflow( | ||
updatePricePreferencesWorkflowId, | ||
(input: WorkflowData<WorkflowInputData>) => { | ||
return updatePricePreferencesStep(input) | ||
} | ||
) |
Oops, something went wrong.