feat: Add currency module and remove currency models from region and pricing modules (#6536)
What: - Creates a new currency module - Removes currency model from the pricing module - Removes currency model from region module
This commit is contained in:
@@ -42,7 +42,7 @@ describe("API Keys - Admin", () => {
|
||||
await createAdminUser(dbConnection, adminHeaders)
|
||||
|
||||
// Used for testing cross-module authentication checks
|
||||
await regionService.createDefaultCountriesAndCurrencies()
|
||||
await regionService.createDefaultCountries()
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
|
||||
@@ -63,7 +63,7 @@ describe("Carts workflows", () => {
|
||||
|
||||
beforeEach(async () => {
|
||||
await adminSeeder(dbConnection)
|
||||
await regionModuleService.createDefaultCountriesAndCurrencies()
|
||||
await regionModuleService.createDefaultCountries()
|
||||
|
||||
// Here, so we don't have to create a region for each test
|
||||
defaultRegion = await regionModuleService.create({
|
||||
|
||||
@@ -59,7 +59,7 @@ describe("Store Carts API", () => {
|
||||
|
||||
beforeEach(async () => {
|
||||
await adminSeeder(dbConnection)
|
||||
await regionModuleService.createDefaultCountriesAndCurrencies()
|
||||
await regionModuleService.createDefaultCountries()
|
||||
|
||||
// Here, so we don't have to create a region for each test
|
||||
defaultRegion = await regionModuleService.create({
|
||||
|
||||
@@ -0,0 +1,67 @@
|
||||
import { ModuleRegistrationName } from "@medusajs/modules-sdk"
|
||||
import { ICurrencyModuleService } from "@medusajs/types"
|
||||
import path from "path"
|
||||
import { startBootstrapApp } from "../../../../environment-helpers/bootstrap-app"
|
||||
import { useApi } from "../../../../environment-helpers/use-api"
|
||||
import { getContainer } from "../../../../environment-helpers/use-container"
|
||||
import { initDb, useDb } from "../../../../environment-helpers/use-db"
|
||||
import { DataSource } from "typeorm"
|
||||
import { createAdminUser } from "../../../helpers/create-admin-user"
|
||||
|
||||
jest.setTimeout(50000)
|
||||
|
||||
const env = { MEDUSA_FF_MEDUSA_V2: true }
|
||||
const adminHeaders = {
|
||||
headers: { "x-medusa-access-token": "test_token" },
|
||||
}
|
||||
|
||||
describe("Currency - Admin", () => {
|
||||
let dbConnection: DataSource
|
||||
let appContainer
|
||||
let shutdownServer
|
||||
let service: ICurrencyModuleService
|
||||
|
||||
beforeAll(async () => {
|
||||
const cwd = path.resolve(path.join(__dirname, "..", "..", ".."))
|
||||
dbConnection = await initDb({ cwd, env } as any)
|
||||
shutdownServer = await startBootstrapApp({ cwd, env })
|
||||
appContainer = getContainer()
|
||||
service = appContainer.resolve(ModuleRegistrationName.CURRENCY)
|
||||
})
|
||||
|
||||
afterAll(async () => {
|
||||
const db = useDb()
|
||||
await db.shutdown()
|
||||
await shutdownServer()
|
||||
})
|
||||
|
||||
beforeEach(async () => {
|
||||
await createAdminUser(dbConnection, adminHeaders)
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
const db = useDb()
|
||||
await db.teardown()
|
||||
})
|
||||
|
||||
it("should correctly retrieve and list currencies", async () => {
|
||||
const api = useApi() as any
|
||||
const listResp = await api.get("/admin/currencies", adminHeaders)
|
||||
|
||||
expect(listResp.data.currencies).toEqual(
|
||||
expect.arrayContaining([
|
||||
expect.objectContaining({
|
||||
code: "aud",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "cad",
|
||||
}),
|
||||
])
|
||||
)
|
||||
|
||||
const retrieveResp = await api.get(`/admin/currencies/aud`, adminHeaders)
|
||||
expect(retrieveResp.data.currency).toEqual(
|
||||
listResp.data.currencies.find((c) => c.code === "aud")
|
||||
)
|
||||
})
|
||||
})
|
||||
@@ -0,0 +1,62 @@
|
||||
import { ModuleRegistrationName } from "@medusajs/modules-sdk"
|
||||
import { ICurrencyModuleService } from "@medusajs/types"
|
||||
import path from "path"
|
||||
import { startBootstrapApp } from "../../../../environment-helpers/bootstrap-app"
|
||||
import { useApi } from "../../../../environment-helpers/use-api"
|
||||
import { getContainer } from "../../../../environment-helpers/use-container"
|
||||
import { initDb, useDb } from "../../../../environment-helpers/use-db"
|
||||
import { DataSource } from "typeorm"
|
||||
|
||||
jest.setTimeout(50000)
|
||||
|
||||
const env = { MEDUSA_FF_MEDUSA_V2: true }
|
||||
const storeHeaders = {
|
||||
headers: {},
|
||||
}
|
||||
|
||||
describe("Currency - Store", () => {
|
||||
let dbConnection: DataSource
|
||||
let appContainer
|
||||
let shutdownServer
|
||||
let service: ICurrencyModuleService
|
||||
|
||||
beforeAll(async () => {
|
||||
const cwd = path.resolve(path.join(__dirname, "..", "..", ".."))
|
||||
dbConnection = await initDb({ cwd, env } as any)
|
||||
shutdownServer = await startBootstrapApp({ cwd, env })
|
||||
appContainer = getContainer()
|
||||
service = appContainer.resolve(ModuleRegistrationName.CURRENCY)
|
||||
})
|
||||
|
||||
afterAll(async () => {
|
||||
const db = useDb()
|
||||
await db.shutdown()
|
||||
await shutdownServer()
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
const db = useDb()
|
||||
await db.teardown()
|
||||
})
|
||||
|
||||
it("should correctly retrieve and list currencies", async () => {
|
||||
const api = useApi() as any
|
||||
const listResp = await api.get("/store/currencies", storeHeaders)
|
||||
|
||||
expect(listResp.data.currencies).toEqual(
|
||||
expect.arrayContaining([
|
||||
expect.objectContaining({
|
||||
code: "aud",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "cad",
|
||||
}),
|
||||
])
|
||||
)
|
||||
|
||||
const retrieveResp = await api.get(`/store/currencies/aud`, storeHeaders)
|
||||
expect(retrieveResp.data.currency).toEqual(
|
||||
listResp.data.currencies.find((c) => c.code === "aud")
|
||||
)
|
||||
})
|
||||
})
|
||||
@@ -45,7 +45,7 @@ describe("Cart links", () => {
|
||||
|
||||
beforeEach(async () => {
|
||||
// @ts-ignore
|
||||
await regionModule.createDefaultCountriesAndCurrencies()
|
||||
await regionModule.createDefaultCountries()
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
|
||||
@@ -35,7 +35,7 @@ describe("Link: Cart Region", () => {
|
||||
|
||||
beforeEach(async () => {
|
||||
// @ts-ignore
|
||||
await regionModule.createDefaultCountriesAndCurrencies()
|
||||
await regionModule.createDefaultCountries()
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
|
||||
@@ -38,7 +38,7 @@ describe("Regions - Admin", () => {
|
||||
beforeEach(async () => {
|
||||
await createAdminUser(dbConnection, adminHeaders)
|
||||
|
||||
await service.createDefaultCountriesAndCurrencies()
|
||||
await service.createDefaultCountries()
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
@@ -127,25 +127,6 @@ describe("Regions - Admin", () => {
|
||||
)
|
||||
})
|
||||
|
||||
it("should throw on unknown currency in create", async () => {
|
||||
const api = useApi() as any
|
||||
const error = await api
|
||||
.post(
|
||||
`/admin/regions`,
|
||||
{
|
||||
currency_code: "foo",
|
||||
name: "Test Region",
|
||||
},
|
||||
adminHeaders
|
||||
)
|
||||
.catch((e) => e)
|
||||
|
||||
expect(error.response.status).toEqual(400)
|
||||
expect(error.response.data.message).toEqual(
|
||||
'Currencies with codes: "foo" were not found'
|
||||
)
|
||||
})
|
||||
|
||||
it("should throw on unknown properties in create", async () => {
|
||||
const api = useApi() as any
|
||||
const error = await api
|
||||
|
||||
@@ -128,5 +128,10 @@ module.exports = {
|
||||
resources: "shared",
|
||||
resolve: "@medusajs/tax",
|
||||
},
|
||||
[Modules.CURRENCY]: {
|
||||
scope: "internal",
|
||||
resources: "shared",
|
||||
resolve: "@medusajs/currency",
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
"@medusajs/api-key": "workspace:^",
|
||||
"@medusajs/auth": "workspace:*",
|
||||
"@medusajs/cache-inmemory": "workspace:*",
|
||||
"@medusajs/currency": "workspace:^",
|
||||
"@medusajs/customer": "workspace:^",
|
||||
"@medusajs/event-bus-local": "workspace:*",
|
||||
"@medusajs/inventory": "workspace:^",
|
||||
|
||||
@@ -0,0 +1,6 @@
|
||||
/dist
|
||||
node_modules
|
||||
.DS_store
|
||||
.env*
|
||||
.env
|
||||
*.sql
|
||||
@@ -0,0 +1 @@
|
||||
# Currency Module
|
||||
@@ -0,0 +1,199 @@
|
||||
import { Modules } from "@medusajs/modules-sdk"
|
||||
import { ICurrencyModuleService } from "@medusajs/types"
|
||||
import { moduleIntegrationTestRunner, SuiteOptions } from "medusa-test-utils"
|
||||
|
||||
jest.setTimeout(100000)
|
||||
|
||||
moduleIntegrationTestRunner({
|
||||
moduleName: Modules.CURRENCY,
|
||||
testSuite: ({
|
||||
MikroOrmWrapper,
|
||||
service,
|
||||
}: SuiteOptions<ICurrencyModuleService>) => {
|
||||
describe("Currency Module Service", () => {
|
||||
describe("list", () => {
|
||||
it("list currencies", async () => {
|
||||
const currenciesResult = await service.list({}, { take: null })
|
||||
expect(currenciesResult).toEqual(
|
||||
expect.arrayContaining([
|
||||
expect.objectContaining({
|
||||
code: "cad",
|
||||
name: "Canadian Dollar",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "usd",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
)
|
||||
})
|
||||
|
||||
it("list currencies by code", async () => {
|
||||
const currenciesResult = await service.list(
|
||||
{ code: ["usd"] },
|
||||
{ take: null }
|
||||
)
|
||||
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "usd",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("list currencies by code regardless of case-sensitivity", async () => {
|
||||
const currenciesResult = await service.list(
|
||||
{ code: ["Usd"] },
|
||||
{ take: null }
|
||||
)
|
||||
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "usd",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
})
|
||||
|
||||
describe("listAndCount", () => {
|
||||
it("should return currencies and count", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCount(
|
||||
{},
|
||||
{ take: null }
|
||||
)
|
||||
|
||||
expect(count).toEqual(120)
|
||||
expect(currenciesResult).toEqual(
|
||||
expect.arrayContaining([
|
||||
expect.objectContaining({
|
||||
code: "cad",
|
||||
name: "Canadian Dollar",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "usd",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
)
|
||||
})
|
||||
|
||||
it("should return currencies and count when filtered", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCount(
|
||||
{
|
||||
code: ["usd"],
|
||||
},
|
||||
{ take: null }
|
||||
)
|
||||
|
||||
expect(count).toEqual(1)
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "usd",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("should return currencies and count when using skip and take", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCount(
|
||||
{},
|
||||
{ skip: 5, take: 1 }
|
||||
)
|
||||
|
||||
expect(count).toEqual(120)
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "aud",
|
||||
name: "Australian Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("should return requested fields", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCount(
|
||||
{},
|
||||
{
|
||||
take: 1,
|
||||
select: ["code"],
|
||||
}
|
||||
)
|
||||
|
||||
const serialized = JSON.parse(JSON.stringify(currenciesResult))
|
||||
|
||||
expect(count).toEqual(120)
|
||||
expect(serialized).toEqual([
|
||||
{
|
||||
code: "aed",
|
||||
},
|
||||
])
|
||||
})
|
||||
})
|
||||
|
||||
describe("retrieve", () => {
|
||||
const code = "usd"
|
||||
const name = "US Dollar"
|
||||
|
||||
it("should return currency for the given code", async () => {
|
||||
const currency = await service.retrieve(code)
|
||||
|
||||
expect(currency).toEqual(
|
||||
expect.objectContaining({
|
||||
code,
|
||||
})
|
||||
)
|
||||
})
|
||||
|
||||
it("should return currency for the given code in a case-insensitive manner", async () => {
|
||||
const currency = await service.retrieve(code.toUpperCase())
|
||||
|
||||
expect(currency).toEqual(
|
||||
expect.objectContaining({
|
||||
code,
|
||||
})
|
||||
)
|
||||
})
|
||||
|
||||
it("should throw an error when currency with code does not exist", async () => {
|
||||
let error
|
||||
|
||||
try {
|
||||
await service.retrieve("does-not-exist")
|
||||
} catch (e) {
|
||||
error = e
|
||||
}
|
||||
|
||||
expect(error.message).toEqual(
|
||||
"Currency with code: does-not-exist was not found"
|
||||
)
|
||||
})
|
||||
|
||||
it("should throw an error when a code is not provided", async () => {
|
||||
let error
|
||||
|
||||
try {
|
||||
await service.retrieve(undefined as unknown as string)
|
||||
} catch (e) {
|
||||
error = e
|
||||
}
|
||||
|
||||
expect(error.message).toEqual("currency - code must be defined")
|
||||
})
|
||||
|
||||
it("should return currency based on config select param", async () => {
|
||||
const currency = await service.retrieve(code, {
|
||||
select: ["code", "name"],
|
||||
})
|
||||
|
||||
const serialized = JSON.parse(JSON.stringify(currency))
|
||||
|
||||
expect(serialized).toEqual({
|
||||
code,
|
||||
name,
|
||||
})
|
||||
})
|
||||
})
|
||||
})
|
||||
},
|
||||
})
|
||||
@@ -0,0 +1,20 @@
|
||||
module.exports = {
|
||||
moduleNameMapper: {
|
||||
"^@models": "<rootDir>/src/models",
|
||||
"^@services": "<rootDir>/src/services",
|
||||
"^@repositories": "<rootDir>/src/repositories",
|
||||
"^@types": "<rootDir>/src/types",
|
||||
},
|
||||
transform: {
|
||||
"^.+\\.[jt]s?$": [
|
||||
"ts-jest",
|
||||
{
|
||||
tsConfig: "tsconfig.spec.json",
|
||||
isolatedModules: true,
|
||||
},
|
||||
],
|
||||
},
|
||||
testEnvironment: `node`,
|
||||
moduleFileExtensions: [`js`, `ts`],
|
||||
modulePathIgnorePatterns: ["dist/"],
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
import * as entities from "./src/models"
|
||||
|
||||
module.exports = {
|
||||
entities: Object.values(entities),
|
||||
schema: "public",
|
||||
clientUrl: "postgres://postgres@localhost/medusa-currency",
|
||||
type: "postgresql",
|
||||
}
|
||||
@@ -0,0 +1,61 @@
|
||||
{
|
||||
"name": "@medusajs/currency",
|
||||
"version": "0.1.0",
|
||||
"description": "Medusa Currency module",
|
||||
"main": "dist/index.js",
|
||||
"types": "dist/index.d.ts",
|
||||
"files": [
|
||||
"dist"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">=16"
|
||||
},
|
||||
"bin": {
|
||||
"medusa-currency-seed": "dist/scripts/bin/run-seed.js"
|
||||
},
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/medusajs/medusa",
|
||||
"directory": "packages/currency"
|
||||
},
|
||||
"publishConfig": {
|
||||
"access": "public"
|
||||
},
|
||||
"author": "Medusa",
|
||||
"license": "MIT",
|
||||
"scripts": {
|
||||
"watch": "tsc --build --watch",
|
||||
"watch:test": "tsc --build tsconfig.spec.json --watch",
|
||||
"prepublishOnly": "cross-env NODE_ENV=production tsc --build && tsc-alias -p tsconfig.json",
|
||||
"build": "rimraf dist && tsc --build && tsc-alias -p tsconfig.json",
|
||||
"test": "jest --runInBand --bail --forceExit -- src/**/__tests__/**/*.ts",
|
||||
"test:integration": "jest --runInBand --forceExit -- integration-tests/**/__tests__/**/*.ts",
|
||||
"migration:generate": " MIKRO_ORM_CLI=./mikro-orm.config.dev.ts mikro-orm migration:generate",
|
||||
"migration:initial": " MIKRO_ORM_CLI=./mikro-orm.config.dev.ts mikro-orm migration:create --initial",
|
||||
"migration:create": " MIKRO_ORM_CLI=./mikro-orm.config.dev.ts mikro-orm migration:create",
|
||||
"migration:up": " MIKRO_ORM_CLI=./mikro-orm.config.dev.ts mikro-orm migration:up",
|
||||
"orm:cache:clear": " MIKRO_ORM_CLI=./mikro-orm.config.dev.ts mikro-orm cache:clear"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@mikro-orm/cli": "5.9.7",
|
||||
"cross-env": "^5.2.1",
|
||||
"jest": "^29.6.3",
|
||||
"medusa-test-utils": "workspace:^",
|
||||
"rimraf": "^3.0.2",
|
||||
"ts-jest": "^29.1.1",
|
||||
"ts-node": "^10.9.1",
|
||||
"tsc-alias": "^1.8.6",
|
||||
"typescript": "^5.1.6"
|
||||
},
|
||||
"dependencies": {
|
||||
"@medusajs/modules-sdk": "^1.12.4",
|
||||
"@medusajs/types": "^1.11.8",
|
||||
"@medusajs/utils": "^1.11.1",
|
||||
"@mikro-orm/core": "5.9.7",
|
||||
"@mikro-orm/migrations": "5.9.7",
|
||||
"@mikro-orm/postgresql": "5.9.7",
|
||||
"awilix": "^8.0.0",
|
||||
"dotenv": "^16.1.4",
|
||||
"knex": "2.4.2"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
import { moduleDefinition } from "./module-definition"
|
||||
import { initializeFactory, Modules } from "@medusajs/modules-sdk"
|
||||
|
||||
export * from "./types"
|
||||
export * from "./models"
|
||||
export * from "./services"
|
||||
|
||||
export const initialize = initializeFactory({
|
||||
moduleName: Modules.CURRENCY,
|
||||
moduleDefinition,
|
||||
})
|
||||
export const runMigrations = moduleDefinition.runMigrations
|
||||
export const revertMigration = moduleDefinition.revertMigration
|
||||
export default moduleDefinition
|
||||
@@ -0,0 +1,29 @@
|
||||
import { Modules } from "@medusajs/modules-sdk"
|
||||
import { ModuleJoinerConfig } from "@medusajs/types"
|
||||
import { MapToConfig } from "@medusajs/utils"
|
||||
import Currency from "./models/currency"
|
||||
|
||||
export const LinkableKeys: Record<string, string> = {}
|
||||
|
||||
const entityLinkableKeysMap: MapToConfig = {}
|
||||
Object.entries(LinkableKeys).forEach(([key, value]) => {
|
||||
entityLinkableKeysMap[value] ??= []
|
||||
entityLinkableKeysMap[value].push({
|
||||
mapTo: key,
|
||||
valueFrom: key.split("_").pop()!,
|
||||
})
|
||||
})
|
||||
|
||||
export const entityNameToLinkableKeysMap: MapToConfig = entityLinkableKeysMap
|
||||
|
||||
export const joinerConfig: ModuleJoinerConfig = {
|
||||
serviceName: Modules.CURRENCY,
|
||||
primaryKeys: ["code"],
|
||||
linkableKeys: LinkableKeys,
|
||||
alias: [
|
||||
{
|
||||
name: ["currency", "currencies"],
|
||||
args: { entity: Currency.name },
|
||||
},
|
||||
],
|
||||
} as ModuleJoinerConfig
|
||||
@@ -0,0 +1,30 @@
|
||||
import { ModuleRegistrationName } from "@medusajs/modules-sdk"
|
||||
import { ModulesSdkTypes, LoaderOptions } from "@medusajs/types"
|
||||
import { defaultCurrencies } from "@medusajs/utils"
|
||||
import { Currency } from "@models"
|
||||
|
||||
export default async ({
|
||||
container,
|
||||
options,
|
||||
}: LoaderOptions<
|
||||
| ModulesSdkTypes.ModuleServiceInitializeOptions
|
||||
| ModulesSdkTypes.ModuleServiceInitializeCustomDataLayerOptions
|
||||
>): Promise<void> => {
|
||||
try {
|
||||
const {
|
||||
currencyService_,
|
||||
}: { currencyService_: ModulesSdkTypes.InternalModuleService<Currency> } =
|
||||
container.resolve(ModuleRegistrationName.CURRENCY)
|
||||
|
||||
const normalizedCurrencies = Object.values(defaultCurrencies).map((c) => ({
|
||||
...c,
|
||||
code: c.code.toLowerCase(),
|
||||
}))
|
||||
const resp = await currencyService_.upsert(normalizedCurrencies)
|
||||
console.log(`Loaded ${resp.length} currencies`)
|
||||
} catch (error) {
|
||||
console.error(
|
||||
`Failed to load currencies, skipping loader. Original error: ${error.message}`
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,63 @@
|
||||
{
|
||||
"namespaces": [
|
||||
"public"
|
||||
],
|
||||
"name": "public",
|
||||
"tables": [
|
||||
{
|
||||
"columns": {
|
||||
"code": {
|
||||
"name": "code",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"symbol": {
|
||||
"name": "symbol",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"symbol_native": {
|
||||
"name": "symbol_native",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
}
|
||||
},
|
||||
"name": "currency",
|
||||
"schema": "public",
|
||||
"indexes": [
|
||||
{
|
||||
"keyName": "currency_pkey",
|
||||
"columnNames": [
|
||||
"code"
|
||||
],
|
||||
"composite": false,
|
||||
"primary": true,
|
||||
"unique": true
|
||||
}
|
||||
],
|
||||
"checks": [],
|
||||
"foreignKeys": {}
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
import { Migration } from "@mikro-orm/migrations"
|
||||
|
||||
export class InitialSetup20240228133303 extends Migration {
|
||||
async up(): Promise<void> {
|
||||
this.addSql(`create table if not exists "currency"
|
||||
("code" text not null, "symbol" text not null, "symbol_native" text not null, "name" text not null,
|
||||
constraint "currency_pkey" primary key ("code"));`)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
export { default as Currency } from "./currency"
|
||||
@@ -0,0 +1,45 @@
|
||||
import { ModuleExports } from "@medusajs/types"
|
||||
import * as ModuleServices from "@services"
|
||||
import { CurrencyModuleService } from "@services"
|
||||
import { Modules } from "@medusajs/modules-sdk"
|
||||
import * as Models from "@models"
|
||||
import * as ModuleModels from "@models"
|
||||
import { ModulesSdkUtils } from "@medusajs/utils"
|
||||
import * as ModuleRepositories from "@repositories"
|
||||
import initialDataLoader from "./loaders/initial-data"
|
||||
|
||||
const migrationScriptOptions = {
|
||||
moduleName: Modules.CURRENCY,
|
||||
models: Models,
|
||||
pathToMigrations: __dirname + "/migrations",
|
||||
}
|
||||
|
||||
const runMigrations = ModulesSdkUtils.buildMigrationScript(
|
||||
migrationScriptOptions
|
||||
)
|
||||
|
||||
const revertMigration = ModulesSdkUtils.buildRevertMigrationScript(
|
||||
migrationScriptOptions
|
||||
)
|
||||
|
||||
const containerLoader = ModulesSdkUtils.moduleContainerLoaderFactory({
|
||||
moduleModels: ModuleModels,
|
||||
moduleRepositories: ModuleRepositories,
|
||||
moduleServices: ModuleServices,
|
||||
})
|
||||
|
||||
const connectionLoader = ModulesSdkUtils.mikroOrmConnectionLoaderFactory({
|
||||
moduleName: Modules.CURRENCY,
|
||||
moduleModels: Object.values(Models),
|
||||
migrationsPath: __dirname + "/migrations",
|
||||
})
|
||||
|
||||
const service = CurrencyModuleService
|
||||
const loaders = [containerLoader, connectionLoader, initialDataLoader] as any
|
||||
|
||||
export const moduleDefinition: ModuleExports = {
|
||||
service,
|
||||
loaders,
|
||||
revertMigration,
|
||||
runMigrations,
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
export { MikroOrmBaseRepository as BaseRepository } from "@medusajs/utils"
|
||||
@@ -0,0 +1,29 @@
|
||||
#!/usr/bin/env node
|
||||
|
||||
import { ModulesSdkUtils } from "@medusajs/utils"
|
||||
import { Modules } from "@medusajs/modules-sdk"
|
||||
import * as Models from "@models"
|
||||
import { EOL } from "os"
|
||||
|
||||
const args = process.argv
|
||||
const path = args.pop() as string
|
||||
|
||||
export default (async () => {
|
||||
const { config } = await import("dotenv")
|
||||
config()
|
||||
if (!path) {
|
||||
throw new Error(
|
||||
`filePath is required.${EOL}Example: medusa-currency-seed <filePath>`
|
||||
)
|
||||
}
|
||||
|
||||
const run = ModulesSdkUtils.buildSeedScript({
|
||||
moduleName: Modules.CURRENCY,
|
||||
models: Models,
|
||||
pathToMigrations: __dirname + "/../../migrations",
|
||||
seedHandler: async ({ manager, data }) => {
|
||||
// TODO: Add seed logic
|
||||
},
|
||||
})
|
||||
await run({ path })
|
||||
})()
|
||||
@@ -0,0 +1,5 @@
|
||||
describe("noop", function () {
|
||||
it("should run", function () {
|
||||
expect(true).toBe(true)
|
||||
})
|
||||
})
|
||||
@@ -0,0 +1,131 @@
|
||||
import {
|
||||
DAL,
|
||||
InternalModuleDeclaration,
|
||||
ModuleJoinerConfig,
|
||||
ModulesSdkTypes,
|
||||
ICurrencyModuleService,
|
||||
CurrencyTypes,
|
||||
Context,
|
||||
FindConfig,
|
||||
FilterableCurrencyProps,
|
||||
BaseFilterable,
|
||||
} from "@medusajs/types"
|
||||
import { ModulesSdkUtils } from "@medusajs/utils"
|
||||
|
||||
import { Currency } from "@models"
|
||||
import { entityNameToLinkableKeysMap, joinerConfig } from "../joiner-config"
|
||||
|
||||
const generateMethodForModels = []
|
||||
|
||||
type InjectedDependencies = {
|
||||
baseRepository: DAL.RepositoryService
|
||||
currencyService: ModulesSdkTypes.InternalModuleService<any>
|
||||
}
|
||||
|
||||
export default class CurrencyModuleService<TEntity extends Currency = Currency>
|
||||
extends ModulesSdkUtils.abstractModuleServiceFactory<
|
||||
InjectedDependencies,
|
||||
CurrencyTypes.CurrencyDTO,
|
||||
{
|
||||
Currency: { dto: CurrencyTypes.CurrencyDTO }
|
||||
}
|
||||
>(Currency, generateMethodForModels, entityNameToLinkableKeysMap)
|
||||
implements ICurrencyModuleService
|
||||
{
|
||||
protected baseRepository_: DAL.RepositoryService
|
||||
protected readonly currencyService_: ModulesSdkTypes.InternalModuleService<TEntity>
|
||||
|
||||
constructor(
|
||||
{ baseRepository, currencyService }: InjectedDependencies,
|
||||
protected readonly moduleDeclaration: InternalModuleDeclaration
|
||||
) {
|
||||
// @ts-ignore
|
||||
super(...arguments)
|
||||
this.baseRepository_ = baseRepository
|
||||
this.currencyService_ = currencyService
|
||||
}
|
||||
|
||||
__joinerConfig(): ModuleJoinerConfig {
|
||||
return joinerConfig
|
||||
}
|
||||
|
||||
retrieve(
|
||||
code: string,
|
||||
config?: FindConfig<CurrencyTypes.CurrencyDTO>,
|
||||
sharedContext?: Context
|
||||
): Promise<CurrencyTypes.CurrencyDTO> {
|
||||
return this.currencyService_.retrieve(
|
||||
code?.toLowerCase(),
|
||||
config,
|
||||
sharedContext
|
||||
)
|
||||
}
|
||||
|
||||
list(
|
||||
filters?: FilterableCurrencyProps,
|
||||
config?: FindConfig<CurrencyTypes.CurrencyDTO>,
|
||||
sharedContext?: Context
|
||||
): Promise<CurrencyTypes.CurrencyDTO[]> {
|
||||
return this.currencyService_.list(
|
||||
CurrencyModuleService.normalizeFilters(filters),
|
||||
config,
|
||||
sharedContext
|
||||
)
|
||||
}
|
||||
|
||||
listAndCount(
|
||||
filters?: FilterableCurrencyProps,
|
||||
config?: FindConfig<CurrencyTypes.CurrencyDTO>,
|
||||
sharedContext?: Context
|
||||
): Promise<[CurrencyTypes.CurrencyDTO[], number]> {
|
||||
return this.currencyService_.listAndCount(
|
||||
CurrencyModuleService.normalizeFilters(filters),
|
||||
config,
|
||||
sharedContext
|
||||
)
|
||||
}
|
||||
|
||||
protected static normalizeFilters(
|
||||
filters: FilterableCurrencyProps | undefined
|
||||
): FilterableCurrencyProps | undefined {
|
||||
return normalizeFilterable<
|
||||
CurrencyTypes.CurrencyDTO,
|
||||
FilterableCurrencyProps
|
||||
>(filters, (fieldName, value) => {
|
||||
if (fieldName === "code" && !!value) {
|
||||
return value.toLowerCase()
|
||||
}
|
||||
|
||||
return value
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: Move normalizer support to `buildQuery` so we don't even need to override the list/retrieve methods just for normalization
|
||||
const normalizeFilterable = <TModel, TFilter extends BaseFilterable<TFilter>>(
|
||||
filters: TFilter | undefined,
|
||||
normalizer: (fieldName: keyof TModel, value: any) => any
|
||||
): TFilter | undefined => {
|
||||
if (!filters) {
|
||||
return filters
|
||||
}
|
||||
|
||||
const normalizedFilters = {} as TFilter
|
||||
for (const key in filters) {
|
||||
if (key === "$and" || key === "$or") {
|
||||
normalizedFilters[key] = (filters[key] as any).map((filter) =>
|
||||
normalizeFilterable(filter, normalizer)
|
||||
)
|
||||
} else if (filters[key] !== undefined) {
|
||||
if (Array.isArray(filters[key])) {
|
||||
normalizedFilters[key] = (filters[key] as any).map((val) =>
|
||||
normalizer(key as any, val)
|
||||
)
|
||||
} else {
|
||||
normalizedFilters[key] = normalizer(key as any, filters[key])
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return normalizedFilters
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
export { default as CurrencyModuleService } from "./currency-module-service"
|
||||
@@ -0,0 +1,6 @@
|
||||
import { IEventBusModuleService, Logger } from "@medusajs/types"
|
||||
|
||||
export type InitializeModuleInjectableDependencies = {
|
||||
logger?: Logger
|
||||
eventBusService?: IEventBusModuleService
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
{
|
||||
"compilerOptions": {
|
||||
"lib": ["es2020"],
|
||||
"target": "es2020",
|
||||
"outDir": "./dist",
|
||||
"esModuleInterop": true,
|
||||
"declaration": true,
|
||||
"module": "commonjs",
|
||||
"moduleResolution": "node",
|
||||
"emitDecoratorMetadata": true,
|
||||
"experimentalDecorators": true,
|
||||
"sourceMap": false,
|
||||
"noImplicitReturns": true,
|
||||
"strictNullChecks": true,
|
||||
"strictFunctionTypes": true,
|
||||
"noImplicitThis": true,
|
||||
"allowJs": true,
|
||||
"skipLibCheck": true,
|
||||
"downlevelIteration": true, // to use ES5 specific tooling
|
||||
"baseUrl": ".",
|
||||
"resolveJsonModule": true,
|
||||
"paths": {
|
||||
"@models": ["./src/models"],
|
||||
"@services": ["./src/services"],
|
||||
"@repositories": ["./src/repositories"],
|
||||
"@types": ["./src/types"]
|
||||
}
|
||||
},
|
||||
"include": ["src"],
|
||||
"exclude": [
|
||||
"dist",
|
||||
"./src/**/__tests__",
|
||||
"./src/**/__mocks__",
|
||||
"./src/**/__fixtures__",
|
||||
"node_modules"
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
{
|
||||
"extends": "./tsconfig.json",
|
||||
"include": ["src", "integration-tests"],
|
||||
"exclude": ["node_modules", "dist"],
|
||||
"compilerOptions": {
|
||||
"sourceMap": true
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
import { remoteQueryObjectFromString } from "@medusajs/utils"
|
||||
import { MedusaRequest, MedusaResponse } from "../../../../types/routing"
|
||||
import { defaultAdminCurrencyFields } from "../query-config"
|
||||
|
||||
export const GET = async (req: MedusaRequest, res: MedusaResponse) => {
|
||||
const remoteQuery = req.scope.resolve("remoteQuery")
|
||||
|
||||
const variables = { code: req.params.code }
|
||||
|
||||
const queryObject = remoteQueryObjectFromString({
|
||||
entryPoint: "currency",
|
||||
variables,
|
||||
fields: defaultAdminCurrencyFields,
|
||||
})
|
||||
|
||||
const [currency] = await remoteQuery(queryObject)
|
||||
res.status(200).json({ currency })
|
||||
}
|
||||
@@ -0,0 +1,36 @@
|
||||
import { transformQuery } from "../../../api/middlewares"
|
||||
import { MiddlewareRoute } from "../../../loaders/helpers/routing/types"
|
||||
import { authenticate } from "../../../utils/authenticate-middleware"
|
||||
import * as QueryConfig from "./query-config"
|
||||
import {
|
||||
AdminGetCurrenciesCurrencyParams,
|
||||
AdminGetCurrenciesParams,
|
||||
} from "./validators"
|
||||
|
||||
export const adminCurrencyRoutesMiddlewares: MiddlewareRoute[] = [
|
||||
{
|
||||
method: ["ALL"],
|
||||
matcher: "/admin/currencies*",
|
||||
middlewares: [authenticate("admin", ["bearer", "session", "api-key"])],
|
||||
},
|
||||
{
|
||||
method: ["GET"],
|
||||
matcher: "/admin/currencies",
|
||||
middlewares: [
|
||||
transformQuery(
|
||||
AdminGetCurrenciesParams,
|
||||
QueryConfig.listTransformQueryConfig
|
||||
),
|
||||
],
|
||||
},
|
||||
{
|
||||
method: ["GET"],
|
||||
matcher: "/admin/currencies/:code",
|
||||
middlewares: [
|
||||
transformQuery(
|
||||
AdminGetCurrenciesCurrencyParams,
|
||||
QueryConfig.retrieveTransformQueryConfig
|
||||
),
|
||||
],
|
||||
},
|
||||
]
|
||||
@@ -0,0 +1,20 @@
|
||||
export const defaultAdminCurrencyRelations = []
|
||||
export const allowedAdminCurrencyRelations = []
|
||||
export const defaultAdminCurrencyFields = [
|
||||
"code",
|
||||
"name",
|
||||
"symbol",
|
||||
"symbol_native",
|
||||
]
|
||||
|
||||
export const retrieveTransformQueryConfig = {
|
||||
defaultFields: defaultAdminCurrencyFields,
|
||||
defaultRelations: defaultAdminCurrencyRelations,
|
||||
allowedRelations: allowedAdminCurrencyRelations,
|
||||
isList: false,
|
||||
}
|
||||
|
||||
export const listTransformQueryConfig = {
|
||||
defaultLimit: 50,
|
||||
isList: true,
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
import { remoteQueryObjectFromString } from "@medusajs/utils"
|
||||
import { MedusaRequest, MedusaResponse } from "../../../types/routing"
|
||||
import { defaultAdminCurrencyFields } from "./query-config"
|
||||
|
||||
export const GET = async (req: MedusaRequest, res: MedusaResponse) => {
|
||||
const remoteQuery = req.scope.resolve("remoteQuery")
|
||||
|
||||
const queryObject = remoteQueryObjectFromString({
|
||||
entryPoint: "currency",
|
||||
variables: {
|
||||
filters: req.filterableFields,
|
||||
order: req.listConfig.order,
|
||||
skip: req.listConfig.skip,
|
||||
take: req.listConfig.take,
|
||||
},
|
||||
fields: defaultAdminCurrencyFields,
|
||||
})
|
||||
|
||||
const { rows: currencies, metadata } = await remoteQuery(queryObject)
|
||||
|
||||
res.json({
|
||||
currencies,
|
||||
count: metadata.count,
|
||||
offset: metadata.skip,
|
||||
limit: metadata.take,
|
||||
})
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
import { Type } from "class-transformer"
|
||||
import { IsOptional, IsString, ValidateNested } from "class-validator"
|
||||
import { FindParams, extendedFindParamsMixin } from "../../../types/common"
|
||||
|
||||
export class AdminGetCurrenciesCurrencyParams extends FindParams {}
|
||||
/**
|
||||
* Parameters used to filter and configure the pagination of the retrieved currencies.
|
||||
*/
|
||||
export class AdminGetCurrenciesParams extends extendedFindParamsMixin({
|
||||
limit: 50,
|
||||
offset: 0,
|
||||
}) {
|
||||
/**
|
||||
* Search parameter for currencies.
|
||||
*/
|
||||
@IsString({ each: true })
|
||||
@IsOptional()
|
||||
code?: string | string[]
|
||||
|
||||
// Additional filters from BaseFilterable
|
||||
@IsOptional()
|
||||
@ValidateNested({ each: true })
|
||||
@Type(() => AdminGetCurrenciesParams)
|
||||
$and?: AdminGetCurrenciesParams[]
|
||||
|
||||
@IsOptional()
|
||||
@ValidateNested({ each: true })
|
||||
@Type(() => AdminGetCurrenciesParams)
|
||||
$or?: AdminGetCurrenciesParams[]
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
export const defaultAdminRegionRelations = ["countries", "currency"]
|
||||
export const allowedAdminRegionRelations = ["countries", "currency"]
|
||||
export const defaultAdminRegionRelations = ["countries"]
|
||||
export const allowedAdminRegionRelations = ["countries"]
|
||||
export const defaultAdminRegionFields = [
|
||||
"id",
|
||||
"name",
|
||||
@@ -13,10 +13,6 @@ export const defaultAdminRegionFields = [
|
||||
"countries.iso_3",
|
||||
"countries.num_code",
|
||||
"countries.name",
|
||||
"currency.code",
|
||||
"currency.symbol",
|
||||
"currency.symbol_native",
|
||||
"currency.name",
|
||||
]
|
||||
|
||||
export const retrieveTransformQueryConfig = {
|
||||
|
||||
@@ -16,6 +16,8 @@ import { storeCartRoutesMiddlewares } from "./store/carts/middlewares"
|
||||
import { storeCustomerRoutesMiddlewares } from "./store/customers/middlewares"
|
||||
import { storeRegionRoutesMiddlewares } from "./store/regions/middlewares"
|
||||
import { hooksRoutesMiddlewares } from "./hooks/middlewares"
|
||||
import { adminCurrencyRoutesMiddlewares } from "./admin/currencies/middlewares"
|
||||
import { storeCurrencyRoutesMiddlewares } from "./store/currencies/middlewares"
|
||||
|
||||
export const config: MiddlewaresConfig = {
|
||||
routes: [
|
||||
@@ -37,5 +39,7 @@ export const config: MiddlewaresConfig = {
|
||||
...adminApiKeyRoutesMiddlewares,
|
||||
...hooksRoutesMiddlewares,
|
||||
...adminStoreRoutesMiddlewares,
|
||||
...adminCurrencyRoutesMiddlewares,
|
||||
...storeCurrencyRoutesMiddlewares,
|
||||
],
|
||||
}
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
import { remoteQueryObjectFromString } from "@medusajs/utils"
|
||||
import { MedusaRequest, MedusaResponse } from "../../../../types/routing"
|
||||
import { defaultStoreCurrencyFields } from "../query-config"
|
||||
|
||||
export const GET = async (req: MedusaRequest, res: MedusaResponse) => {
|
||||
const remoteQuery = req.scope.resolve("remoteQuery")
|
||||
|
||||
const variables = { code: req.params.code }
|
||||
|
||||
const queryObject = remoteQueryObjectFromString({
|
||||
entryPoint: "currency",
|
||||
variables,
|
||||
fields: defaultStoreCurrencyFields,
|
||||
})
|
||||
|
||||
const [currency] = await remoteQuery(queryObject)
|
||||
res.status(200).json({ currency })
|
||||
}
|
||||
@@ -0,0 +1,31 @@
|
||||
import { transformQuery } from "../../../api/middlewares"
|
||||
import { MiddlewareRoute } from "../../../loaders/helpers/routing/types"
|
||||
import { authenticate } from "../../../utils/authenticate-middleware"
|
||||
import * as QueryConfig from "./query-config"
|
||||
import {
|
||||
StoreGetCurrenciesCurrencyParams,
|
||||
StoreGetCurrenciesParams,
|
||||
} from "./validators"
|
||||
|
||||
export const storeCurrencyRoutesMiddlewares: MiddlewareRoute[] = [
|
||||
{
|
||||
method: ["GET"],
|
||||
matcher: "/store/currencies",
|
||||
middlewares: [
|
||||
transformQuery(
|
||||
StoreGetCurrenciesParams,
|
||||
QueryConfig.listTransformQueryConfig
|
||||
),
|
||||
],
|
||||
},
|
||||
{
|
||||
method: ["GET"],
|
||||
matcher: "/store/currencies/:code",
|
||||
middlewares: [
|
||||
transformQuery(
|
||||
StoreGetCurrenciesCurrencyParams,
|
||||
QueryConfig.retrieveTransformQueryConfig
|
||||
),
|
||||
],
|
||||
},
|
||||
]
|
||||
@@ -0,0 +1,20 @@
|
||||
export const defaultStoreCurrencyRelations = []
|
||||
export const allowedStoreCurrencyRelations = []
|
||||
export const defaultStoreCurrencyFields = [
|
||||
"code",
|
||||
"name",
|
||||
"symbol",
|
||||
"symbol_native",
|
||||
]
|
||||
|
||||
export const retrieveTransformQueryConfig = {
|
||||
defaultFields: defaultStoreCurrencyFields,
|
||||
defaultRelations: defaultStoreCurrencyRelations,
|
||||
allowedRelations: allowedStoreCurrencyRelations,
|
||||
isList: false,
|
||||
}
|
||||
|
||||
export const listTransformQueryConfig = {
|
||||
defaultLimit: 20,
|
||||
isList: true,
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
import { remoteQueryObjectFromString } from "@medusajs/utils"
|
||||
import { MedusaRequest, MedusaResponse } from "../../../types/routing"
|
||||
import { defaultStoreCurrencyFields } from "./query-config"
|
||||
|
||||
export const GET = async (req: MedusaRequest, res: MedusaResponse) => {
|
||||
const remoteQuery = req.scope.resolve("remoteQuery")
|
||||
|
||||
const queryObject = remoteQueryObjectFromString({
|
||||
entryPoint: "currency",
|
||||
variables: {
|
||||
filters: req.filterableFields,
|
||||
order: req.listConfig.order,
|
||||
skip: req.listConfig.skip,
|
||||
take: req.listConfig.take,
|
||||
},
|
||||
fields: defaultStoreCurrencyFields,
|
||||
})
|
||||
|
||||
const { rows: currencies, metadata } = await remoteQuery(queryObject)
|
||||
|
||||
res.json({
|
||||
currencies,
|
||||
count: metadata.count,
|
||||
offset: metadata.skip,
|
||||
limit: metadata.take,
|
||||
})
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
import { Type } from "class-transformer"
|
||||
import { IsOptional, IsString, ValidateNested } from "class-validator"
|
||||
import { FindParams, extendedFindParamsMixin } from "../../../types/common"
|
||||
|
||||
export class StoreGetCurrenciesCurrencyParams extends FindParams {}
|
||||
/**
|
||||
* Parameters used to filter and configure the pagination of the retrieved currencies.
|
||||
*/
|
||||
export class StoreGetCurrenciesParams extends extendedFindParamsMixin({
|
||||
limit: 50,
|
||||
offset: 0,
|
||||
}) {
|
||||
/**
|
||||
* Search parameter for currencies.
|
||||
*/
|
||||
@IsString({ each: true })
|
||||
@IsOptional()
|
||||
code?: string | string[]
|
||||
|
||||
// Additional filters from BaseFilterable
|
||||
@IsOptional()
|
||||
@ValidateNested({ each: true })
|
||||
@Type(() => StoreGetCurrenciesParams)
|
||||
$and?: StoreGetCurrenciesParams[]
|
||||
|
||||
@IsOptional()
|
||||
@ValidateNested({ each: true })
|
||||
@Type(() => StoreGetCurrenciesParams)
|
||||
$or?: StoreGetCurrenciesParams[]
|
||||
}
|
||||
@@ -176,33 +176,6 @@ const migratePriceLists = async (container: AwilixContainer) => {
|
||||
}
|
||||
}
|
||||
|
||||
const ensureCurrencies = async (container: AwilixContainer) => {
|
||||
const currenciesService: CurrencyService =
|
||||
container.resolve("currencyService")
|
||||
|
||||
const pricingModuleService: IPricingModuleService = container.resolve(
|
||||
"pricingModuleService"
|
||||
)
|
||||
|
||||
const [coreCurrencies, totalCurrencies] =
|
||||
await currenciesService.listAndCount({}, {})
|
||||
|
||||
const moduleCurrencies = await pricingModuleService.listCurrencies(
|
||||
{},
|
||||
{ take: 100000 }
|
||||
)
|
||||
|
||||
const moduleCurrenciesSet = new Set(moduleCurrencies.map(({ code }) => code))
|
||||
|
||||
const currenciesToCreate = coreCurrencies
|
||||
.filter(({ code }) => {
|
||||
return !moduleCurrenciesSet.has(code)
|
||||
})
|
||||
.map(({ includes_tax, ...currency }) => currency)
|
||||
|
||||
await pricingModuleService.createCurrencies(currenciesToCreate)
|
||||
}
|
||||
|
||||
const migrate = async function ({ directory }) {
|
||||
const app = express()
|
||||
|
||||
@@ -212,11 +185,6 @@ const migrate = async function ({ directory }) {
|
||||
isTest: false,
|
||||
})
|
||||
|
||||
Logger.info("-----------------------------------------------")
|
||||
Logger.info("------------- Creating currencies -------------")
|
||||
Logger.info("-----------------------------------------------")
|
||||
await ensureCurrencies(container)
|
||||
|
||||
Logger.info("-----------------------------------------------")
|
||||
Logger.info("--------- Creating default rule types ---------")
|
||||
Logger.info("-----------------------------------------------")
|
||||
|
||||
@@ -28,6 +28,7 @@ export enum Modules {
|
||||
ORDER = "order",
|
||||
API_KEY = "apiKey",
|
||||
STORE = "store",
|
||||
CURRENCY = "currency",
|
||||
}
|
||||
|
||||
export enum ModuleRegistrationName {
|
||||
@@ -51,6 +52,7 @@ export enum ModuleRegistrationName {
|
||||
ORDER = "orderModuleService",
|
||||
API_KEY = "apiKeyModuleService",
|
||||
STORE = "storeModuleService",
|
||||
CURRENCY = "currencyModuleService",
|
||||
}
|
||||
|
||||
export const MODULE_PACKAGE_NAMES = {
|
||||
@@ -75,6 +77,7 @@ export const MODULE_PACKAGE_NAMES = {
|
||||
[Modules.ORDER]: "@medusajs/order",
|
||||
[Modules.API_KEY]: "@medusajs/api-key",
|
||||
[Modules.STORE]: "@medusajs/store",
|
||||
[Modules.CURRENCY]: "@medusajs/currency",
|
||||
}
|
||||
|
||||
export const ModulesDefinition: { [key: string | Modules]: ModuleDefinition } =
|
||||
@@ -340,6 +343,19 @@ export const ModulesDefinition: { [key: string | Modules]: ModuleDefinition } =
|
||||
resources: MODULE_RESOURCE_TYPE.SHARED,
|
||||
},
|
||||
},
|
||||
[Modules.CURRENCY]: {
|
||||
key: Modules.CURRENCY,
|
||||
registrationName: ModuleRegistrationName.CURRENCY,
|
||||
defaultPackage: false,
|
||||
label: upperCaseFirst(ModuleRegistrationName.CURRENCY),
|
||||
isRequired: false,
|
||||
isQueryable: true,
|
||||
dependencies: ["logger"],
|
||||
defaultModuleDeclaration: {
|
||||
scope: MODULE_SCOPE.INTERNAL,
|
||||
resources: MODULE_RESOURCE_TYPE.SHARED,
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
export const MODULE_DEFINITIONS: ModuleDefinition[] =
|
||||
|
||||
@@ -1,20 +0,0 @@
|
||||
export const defaultCurrencyData = [
|
||||
{
|
||||
symbol: "$",
|
||||
name: "US Dollar",
|
||||
symbol_native: "$",
|
||||
code: "USD",
|
||||
},
|
||||
{
|
||||
symbol: "CA$",
|
||||
name: "Canadian Dollar",
|
||||
symbol_native: "$",
|
||||
code: "CAD",
|
||||
},
|
||||
{
|
||||
symbol: "€",
|
||||
name: "Euro",
|
||||
symbol_native: "€",
|
||||
code: "EUR",
|
||||
},
|
||||
]
|
||||
@@ -1,22 +0,0 @@
|
||||
import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
import { Currency } from "@models"
|
||||
import { defaultCurrencyData } from "./data"
|
||||
|
||||
export * from "./data"
|
||||
|
||||
export async function createCurrencies(
|
||||
manager: SqlEntityManager,
|
||||
currencyData: any[] = defaultCurrencyData
|
||||
): Promise<Currency[]> {
|
||||
const currencies: Currency[] = []
|
||||
|
||||
for (let curr of currencyData) {
|
||||
const currency = manager.create(Currency, curr)
|
||||
|
||||
currencies.push(currency)
|
||||
}
|
||||
|
||||
await manager.persistAndFlush(currencies)
|
||||
|
||||
return currencies
|
||||
}
|
||||
@@ -1,6 +1,5 @@
|
||||
import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
|
||||
import { createCurrencies, defaultCurrencyData } from "./currency"
|
||||
import { createMoneyAmounts, defaultMoneyAmountsData } from "./money-amount"
|
||||
import { createPriceRules, defaultPriceRuleData } from "./price-rule"
|
||||
import { createPriceSets, defaultPriceSetsData } from "./price-set"
|
||||
@@ -21,14 +20,12 @@ export async function seedPriceData(
|
||||
{
|
||||
moneyAmountsData = defaultMoneyAmountsData,
|
||||
priceSetsData = defaultPriceSetsData,
|
||||
currencyData = defaultCurrencyData,
|
||||
priceRuleData = defaultPriceRuleData,
|
||||
priceSetMoneyAmountsData = defaultPriceSetMoneyAmountsData,
|
||||
priceSetMoneyAmountRulesData = defaultPriceSetMoneyAmountRulesData,
|
||||
ruleTypesData = defaultRuleTypesData,
|
||||
} = {}
|
||||
) {
|
||||
await createCurrencies(testManager, currencyData)
|
||||
await createMoneyAmounts(testManager, moneyAmountsData)
|
||||
await createPriceSets(testManager, priceSetsData)
|
||||
await createPriceSetMoneyAmounts(testManager, priceSetMoneyAmountsData)
|
||||
|
||||
@@ -1,278 +0,0 @@
|
||||
import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
|
||||
import { Currency } from "@models"
|
||||
|
||||
import { createCurrencies } from "../../../__fixtures__/currency"
|
||||
import { MikroOrmWrapper } from "../../../utils"
|
||||
import { createMedusaContainer } from "@medusajs/utils"
|
||||
import { asValue } from "awilix"
|
||||
import ContainerLoader from "../../../../src/loaders/container"
|
||||
import { ModulesSdkTypes } from "@medusajs/types"
|
||||
|
||||
jest.setTimeout(30000)
|
||||
|
||||
describe("Currency Service", () => {
|
||||
let service: ModulesSdkTypes.InternalModuleService<any>
|
||||
let testManager: SqlEntityManager
|
||||
let repositoryManager: SqlEntityManager
|
||||
let data!: Currency[]
|
||||
|
||||
const currencyData = [
|
||||
{
|
||||
symbol: "$",
|
||||
name: "US Dollar",
|
||||
symbol_native: "$",
|
||||
code: "USD",
|
||||
},
|
||||
{
|
||||
symbol: "CA$",
|
||||
name: "Canadian Dollar",
|
||||
symbol_native: "$",
|
||||
code: "CAD",
|
||||
},
|
||||
]
|
||||
|
||||
beforeEach(async () => {
|
||||
await MikroOrmWrapper.setupDatabase()
|
||||
repositoryManager = await MikroOrmWrapper.forkManager()
|
||||
|
||||
const container = createMedusaContainer()
|
||||
container.register("manager", asValue(repositoryManager))
|
||||
|
||||
await ContainerLoader({ container })
|
||||
|
||||
service = container.resolve("currencyService")
|
||||
|
||||
testManager = await MikroOrmWrapper.forkManager()
|
||||
|
||||
data = await createCurrencies(testManager, currencyData)
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
await MikroOrmWrapper.clearDatabase()
|
||||
})
|
||||
|
||||
describe("list", () => {
|
||||
it("list currencies", async () => {
|
||||
const currenciesResult = await service.list()
|
||||
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "CAD",
|
||||
name: "Canadian Dollar",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "USD",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("list currencies by code", async () => {
|
||||
const currenciesResult = await service.list({ code: ["USD"] })
|
||||
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "USD",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
})
|
||||
|
||||
describe("listAndCount", () => {
|
||||
it("should return currencies and count", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCount()
|
||||
|
||||
expect(count).toEqual(2)
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "CAD",
|
||||
name: "Canadian Dollar",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "USD",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("should return currencies and count when filtered", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCount({
|
||||
code: ["USD"],
|
||||
})
|
||||
|
||||
expect(count).toEqual(1)
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "USD",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("should return currencies and count when using skip and take", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCount(
|
||||
{},
|
||||
{ skip: 1, take: 1 }
|
||||
)
|
||||
|
||||
expect(count).toEqual(2)
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "USD",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("should return requested fields", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCount(
|
||||
{},
|
||||
{
|
||||
take: 1,
|
||||
select: ["code"],
|
||||
}
|
||||
)
|
||||
|
||||
const serialized = JSON.parse(JSON.stringify(currenciesResult))
|
||||
|
||||
expect(count).toEqual(2)
|
||||
expect(serialized).toEqual([
|
||||
{
|
||||
code: "CAD",
|
||||
},
|
||||
])
|
||||
})
|
||||
})
|
||||
|
||||
describe("retrieve", () => {
|
||||
const code = "USD"
|
||||
const name = "US Dollar"
|
||||
|
||||
it("should return currency for the given code", async () => {
|
||||
const currency = await service.retrieve(code)
|
||||
|
||||
expect(currency).toEqual(
|
||||
expect.objectContaining({
|
||||
code,
|
||||
})
|
||||
)
|
||||
})
|
||||
|
||||
it("should throw an error when currency with code does not exist", async () => {
|
||||
let error
|
||||
|
||||
try {
|
||||
await service.retrieve("does-not-exist")
|
||||
} catch (e) {
|
||||
error = e
|
||||
}
|
||||
|
||||
expect(error.message).toEqual(
|
||||
"Currency with code: does-not-exist was not found"
|
||||
)
|
||||
})
|
||||
|
||||
it("should throw an error when a code is not provided", async () => {
|
||||
let error
|
||||
|
||||
try {
|
||||
await service.retrieve(undefined as unknown as string)
|
||||
} catch (e) {
|
||||
error = e
|
||||
}
|
||||
|
||||
expect(error.message).toEqual("currency - code must be defined")
|
||||
})
|
||||
|
||||
it("should return currency based on config select param", async () => {
|
||||
const currency = await service.retrieve(code, {
|
||||
select: ["code", "name"],
|
||||
})
|
||||
|
||||
const serialized = JSON.parse(JSON.stringify(currency))
|
||||
|
||||
expect(serialized).toEqual({
|
||||
code,
|
||||
name,
|
||||
})
|
||||
})
|
||||
})
|
||||
|
||||
describe("delete", () => {
|
||||
const code = "USD"
|
||||
|
||||
it("should delete the currencies given an code successfully", async () => {
|
||||
await service.delete([code])
|
||||
|
||||
const currencies = await service.list({
|
||||
code: [code],
|
||||
})
|
||||
|
||||
expect(currencies).toHaveLength(0)
|
||||
})
|
||||
})
|
||||
|
||||
describe("update", () => {
|
||||
const code = "USD"
|
||||
|
||||
it("should update the name of the currency successfully", async () => {
|
||||
await service.update([
|
||||
{
|
||||
code,
|
||||
name: "United States Pounds",
|
||||
},
|
||||
])
|
||||
|
||||
const currency = await service.retrieve(code)
|
||||
|
||||
expect(currency.name).toEqual("United States Pounds")
|
||||
})
|
||||
|
||||
it("should throw an error when a code does not exist", async () => {
|
||||
let error
|
||||
|
||||
try {
|
||||
await service.update([
|
||||
{
|
||||
code: "does-not-exist",
|
||||
name: "UK",
|
||||
},
|
||||
])
|
||||
} catch (e) {
|
||||
error = e
|
||||
}
|
||||
|
||||
expect(error.message).toEqual(
|
||||
'Currency with code "does-not-exist" not found'
|
||||
)
|
||||
})
|
||||
})
|
||||
|
||||
describe("create", () => {
|
||||
it("should create a currency successfully", async () => {
|
||||
await service.create([
|
||||
{
|
||||
code: "TES",
|
||||
name: "Test Dollars",
|
||||
symbol: "TES1",
|
||||
symbol_native: "TES2",
|
||||
},
|
||||
])
|
||||
|
||||
const [currency] = await service.list({
|
||||
code: ["TES"],
|
||||
})
|
||||
|
||||
expect(currency).toEqual(
|
||||
expect.objectContaining({
|
||||
code: "TES",
|
||||
name: "Test Dollars",
|
||||
symbol: "TES1",
|
||||
symbol_native: "TES2",
|
||||
})
|
||||
)
|
||||
})
|
||||
})
|
||||
})
|
||||
@@ -3,7 +3,6 @@ import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
import { Currency, MoneyAmount } from "@models"
|
||||
import { MoneyAmountService } from "@services"
|
||||
|
||||
import { createCurrencies } from "../../../__fixtures__/currency"
|
||||
import { createMoneyAmounts } from "../../../__fixtures__/money-amount"
|
||||
import { MikroOrmWrapper } from "../../../utils"
|
||||
import { createMedusaContainer } from "@medusajs/utils"
|
||||
@@ -17,7 +16,6 @@ describe("MoneyAmount Service", () => {
|
||||
let testManager: SqlEntityManager
|
||||
let repositoryManager: SqlEntityManager
|
||||
let data!: MoneyAmount[]
|
||||
let currencyData!: Currency[]
|
||||
|
||||
beforeEach(async () => {
|
||||
await MikroOrmWrapper.setupDatabase()
|
||||
@@ -31,7 +29,6 @@ describe("MoneyAmount Service", () => {
|
||||
service = container.resolve("moneyAmountService")
|
||||
|
||||
testManager = await MikroOrmWrapper.forkManager()
|
||||
currencyData = await createCurrencies(testManager)
|
||||
data = await createMoneyAmounts(testManager)
|
||||
})
|
||||
|
||||
@@ -79,8 +76,7 @@ describe("MoneyAmount Service", () => {
|
||||
id: ["money-amount-USD"],
|
||||
},
|
||||
{
|
||||
select: ["id", "min_quantity", "currency.code", "amount"],
|
||||
relations: ["currency"],
|
||||
select: ["id", "min_quantity", "currency_code", "amount"],
|
||||
}
|
||||
)
|
||||
|
||||
@@ -92,9 +88,6 @@ describe("MoneyAmount Service", () => {
|
||||
amount: 500,
|
||||
min_quantity: "1",
|
||||
currency_code: "USD",
|
||||
currency: {
|
||||
code: "USD",
|
||||
},
|
||||
},
|
||||
])
|
||||
})
|
||||
@@ -105,8 +98,7 @@ describe("MoneyAmount Service", () => {
|
||||
currency_code: ["USD"],
|
||||
},
|
||||
{
|
||||
select: ["id", "min_quantity", "currency.code", "amount"],
|
||||
relations: ["currency"],
|
||||
select: ["id", "min_quantity", "currency_code", "amount"],
|
||||
}
|
||||
)
|
||||
|
||||
@@ -118,9 +110,6 @@ describe("MoneyAmount Service", () => {
|
||||
min_quantity: "1",
|
||||
currency_code: "USD",
|
||||
amount: 500,
|
||||
currency: {
|
||||
code: "USD",
|
||||
},
|
||||
},
|
||||
])
|
||||
})
|
||||
@@ -165,8 +154,7 @@ describe("MoneyAmount Service", () => {
|
||||
id: ["money-amount-USD"],
|
||||
},
|
||||
{
|
||||
select: ["id", "min_quantity", "currency.code", "amount"],
|
||||
relations: ["currency"],
|
||||
select: ["id", "min_quantity", "currency_code", "amount"],
|
||||
}
|
||||
)
|
||||
|
||||
@@ -179,9 +167,6 @@ describe("MoneyAmount Service", () => {
|
||||
amount: 500,
|
||||
min_quantity: "1",
|
||||
currency_code: "USD",
|
||||
currency: {
|
||||
code: "USD",
|
||||
},
|
||||
},
|
||||
])
|
||||
})
|
||||
@@ -316,7 +301,6 @@ describe("MoneyAmount Service", () => {
|
||||
const moneyAmount = await service.retrieve(id)
|
||||
|
||||
expect(moneyAmount.currency_code).toEqual("EUR")
|
||||
expect(moneyAmount.currency?.code).toEqual("EUR")
|
||||
})
|
||||
|
||||
it("should throw an error when a id does not exist", async () => {
|
||||
|
||||
@@ -3,7 +3,6 @@ import { PriceSetMoneyAmount } from "@models"
|
||||
import { CreatePriceRuleDTO } from "@medusajs/types"
|
||||
import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
import { PriceRuleService } from "@services"
|
||||
import { createCurrencies } from "../../../__fixtures__/currency"
|
||||
import { createMoneyAmounts } from "../../../__fixtures__/money-amount"
|
||||
import { createPriceRules } from "../../../__fixtures__/price-rule"
|
||||
import { createPriceSets } from "../../../__fixtures__/price-set"
|
||||
@@ -34,7 +33,6 @@ describe("PriceRule Service", () => {
|
||||
|
||||
service = container.resolve("priceRuleService")
|
||||
|
||||
await createCurrencies(testManager)
|
||||
await createMoneyAmounts(testManager)
|
||||
await createPriceSets(testManager)
|
||||
await createRuleTypes(testManager)
|
||||
|
||||
@@ -3,7 +3,6 @@ import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
import { MoneyAmount, PriceSet } from "@models"
|
||||
import { PriceSetService } from "@services"
|
||||
|
||||
import { createCurrencies } from "../../../__fixtures__/currency"
|
||||
import { createMoneyAmounts } from "../../../__fixtures__/money-amount"
|
||||
import { createPriceSets } from "../../../__fixtures__/price-set"
|
||||
import { MikroOrmWrapper } from "../../../utils"
|
||||
@@ -63,8 +62,6 @@ describe("PriceSet Service", () => {
|
||||
|
||||
service = container.resolve("priceSetService")
|
||||
|
||||
await createCurrencies(testManager)
|
||||
|
||||
moneyAmountsData = await createMoneyAmounts(
|
||||
testManager,
|
||||
moneyAmountsInputData
|
||||
|
||||
-16
@@ -85,21 +85,6 @@ describe("PricingModule Service - Calculate Price", () => {
|
||||
|
||||
describe("calculatePrices", () => {
|
||||
beforeEach(async () => {
|
||||
const currencyData = [
|
||||
{
|
||||
symbol: "zł",
|
||||
name: "Polish Zloty",
|
||||
symbol_native: "zł",
|
||||
code: "PLN",
|
||||
},
|
||||
{
|
||||
symbol: "€",
|
||||
name: "Euro",
|
||||
symbol_native: "€",
|
||||
code: "EUR",
|
||||
},
|
||||
]
|
||||
|
||||
const moneyAmountsData = [
|
||||
{
|
||||
id: "money-amount-PLN",
|
||||
@@ -373,7 +358,6 @@ describe("PricingModule Service - Calculate Price", () => {
|
||||
] as unknown as CreatePriceRuleDTO[]
|
||||
|
||||
await seedPriceData(MikroOrmWrapper.forkManager(), {
|
||||
currencyData,
|
||||
moneyAmountsData,
|
||||
priceSetsData,
|
||||
priceSetMoneyAmountsData,
|
||||
|
||||
-277
@@ -1,277 +0,0 @@
|
||||
import { IPricingModuleService } from "@medusajs/types"
|
||||
import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
import { Currency } from "@models"
|
||||
import { createCurrencies } from "../../../__fixtures__/currency"
|
||||
import { MikroOrmWrapper } from "../../../utils"
|
||||
import { getInitModuleConfig } from "../../../utils/get-init-module-config"
|
||||
import { Modules } from "@medusajs/modules-sdk"
|
||||
import { initModules } from "medusa-test-utils"
|
||||
|
||||
describe("PricingModule Service - Currency", () => {
|
||||
let service: IPricingModuleService
|
||||
let testManager: SqlEntityManager
|
||||
let repositoryManager: SqlEntityManager
|
||||
let data!: Currency[]
|
||||
|
||||
let shutdownFunc: () => Promise<void>
|
||||
|
||||
beforeAll(async () => {
|
||||
const initModulesConfig = getInitModuleConfig()
|
||||
|
||||
const { medusaApp, shutdown } = await initModules(initModulesConfig)
|
||||
|
||||
service = medusaApp.modules[Modules.PRICING]
|
||||
|
||||
shutdownFunc = shutdown
|
||||
})
|
||||
|
||||
afterAll(async () => {
|
||||
await shutdownFunc()
|
||||
})
|
||||
|
||||
beforeEach(async () => {
|
||||
await MikroOrmWrapper.setupDatabase()
|
||||
repositoryManager = MikroOrmWrapper.forkManager()
|
||||
testManager = MikroOrmWrapper.forkManager()
|
||||
|
||||
data = await createCurrencies(testManager)
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
await MikroOrmWrapper.clearDatabase()
|
||||
})
|
||||
|
||||
describe("listCurrencies", () => {
|
||||
it("list currencies", async () => {
|
||||
const currenciesResult = await service.listCurrencies()
|
||||
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "CAD",
|
||||
name: "Canadian Dollar",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "EUR",
|
||||
name: "Euro",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "USD",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("list currencies by code", async () => {
|
||||
const currenciesResult = await service.listCurrencies({ code: ["USD"] })
|
||||
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "USD",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
})
|
||||
|
||||
describe("listAndCountCurrencies", () => {
|
||||
it("should return currencies and count", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCountCurrencies()
|
||||
|
||||
expect(count).toEqual(3)
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "CAD",
|
||||
name: "Canadian Dollar",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "EUR",
|
||||
name: "Euro",
|
||||
}),
|
||||
expect.objectContaining({
|
||||
code: "USD",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("should return currencies and count when filtered", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCountCurrencies({
|
||||
code: ["USD"],
|
||||
})
|
||||
|
||||
expect(count).toEqual(1)
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "USD",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("should return currencies and count when using skip and take", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCountCurrencies(
|
||||
{},
|
||||
{ skip: 1, take: 1 }
|
||||
)
|
||||
|
||||
expect(count).toEqual(3)
|
||||
expect(currenciesResult).toEqual([
|
||||
expect.objectContaining({
|
||||
code: "EUR",
|
||||
name: "Euro",
|
||||
symbol: "€",
|
||||
symbol_native: "€",
|
||||
}),
|
||||
])
|
||||
})
|
||||
|
||||
it("should return requested fields", async () => {
|
||||
const [currenciesResult, count] = await service.listAndCountCurrencies(
|
||||
{},
|
||||
{
|
||||
take: 1,
|
||||
select: ["code"],
|
||||
}
|
||||
)
|
||||
|
||||
const serialized = JSON.parse(JSON.stringify(currenciesResult))
|
||||
|
||||
expect(count).toEqual(3)
|
||||
expect(serialized).toEqual([
|
||||
{
|
||||
code: "CAD",
|
||||
},
|
||||
])
|
||||
})
|
||||
})
|
||||
|
||||
describe("retrieveCurrency", () => {
|
||||
const code = "USD"
|
||||
const name = "US Dollar"
|
||||
|
||||
it("should return currency for the given code", async () => {
|
||||
const currency = await service.retrieveCurrency(code)
|
||||
|
||||
expect(currency).toEqual(
|
||||
expect.objectContaining({
|
||||
code,
|
||||
})
|
||||
)
|
||||
})
|
||||
|
||||
it("should throw an error when currency with code does not exist", async () => {
|
||||
let error
|
||||
|
||||
try {
|
||||
await service.retrieveCurrency("does-not-exist")
|
||||
} catch (e) {
|
||||
error = e
|
||||
}
|
||||
|
||||
expect(error.message).toEqual(
|
||||
"Currency with code: does-not-exist was not found"
|
||||
)
|
||||
})
|
||||
|
||||
it("should throw an error when a code is not provided", async () => {
|
||||
let error
|
||||
|
||||
try {
|
||||
await service.retrieveCurrency(undefined as unknown as string)
|
||||
} catch (e) {
|
||||
error = e
|
||||
}
|
||||
|
||||
expect(error.message).toEqual("currency - code must be defined")
|
||||
})
|
||||
|
||||
it("should return currency based on config select param", async () => {
|
||||
const currency = await service.retrieveCurrency(code, {
|
||||
select: ["code", "name"],
|
||||
})
|
||||
|
||||
const serialized = JSON.parse(JSON.stringify(currency))
|
||||
|
||||
expect(serialized).toEqual({
|
||||
code,
|
||||
name,
|
||||
})
|
||||
})
|
||||
})
|
||||
|
||||
describe("deleteCurrencies", () => {
|
||||
const code = "USD"
|
||||
|
||||
it("should delete the currencies given an code successfully", async () => {
|
||||
await service.deleteCurrencies([code])
|
||||
|
||||
const currencies = await service.listCurrencies({
|
||||
code: [code],
|
||||
})
|
||||
|
||||
expect(currencies).toHaveLength(0)
|
||||
})
|
||||
})
|
||||
|
||||
describe("updateCurrencies", () => {
|
||||
const code = "USD"
|
||||
|
||||
it("should update the name of the currency successfully", async () => {
|
||||
await service.updateCurrencies([
|
||||
{
|
||||
code,
|
||||
name: "United States Pounds",
|
||||
},
|
||||
])
|
||||
|
||||
const currency = await service.retrieveCurrency(code)
|
||||
|
||||
expect(currency.name).toEqual("United States Pounds")
|
||||
})
|
||||
|
||||
it("should throw an error when a code does not exist", async () => {
|
||||
let error
|
||||
|
||||
try {
|
||||
await service.updateCurrencies([
|
||||
{
|
||||
code: "does-not-exist",
|
||||
name: "UK",
|
||||
},
|
||||
])
|
||||
} catch (e) {
|
||||
error = e
|
||||
}
|
||||
|
||||
expect(error.message).toEqual(
|
||||
'Currency with code "does-not-exist" not found'
|
||||
)
|
||||
})
|
||||
})
|
||||
|
||||
describe("createCurrencies", () => {
|
||||
it("should create a currency successfully", async () => {
|
||||
await service.createCurrencies([
|
||||
{
|
||||
code: "TES",
|
||||
name: "Test Dollars",
|
||||
symbol: "TES1",
|
||||
symbol_native: "TES2",
|
||||
},
|
||||
])
|
||||
|
||||
const [currency] = await service.listCurrencies({
|
||||
code: ["TES"],
|
||||
})
|
||||
|
||||
expect(currency).toEqual(
|
||||
expect.objectContaining({
|
||||
code: "TES",
|
||||
name: "Test Dollars",
|
||||
symbol: "TES1",
|
||||
symbol_native: "TES2",
|
||||
})
|
||||
)
|
||||
})
|
||||
})
|
||||
})
|
||||
+4
-18
@@ -1,7 +1,6 @@
|
||||
import { IPricingModuleService } from "@medusajs/types"
|
||||
import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
import { Currency, MoneyAmount } from "@models"
|
||||
import { createCurrencies } from "../../../__fixtures__/currency"
|
||||
import { MoneyAmount } from "@models"
|
||||
import { createMoneyAmounts } from "../../../__fixtures__/money-amount"
|
||||
import { MikroOrmWrapper } from "../../../utils"
|
||||
import { createPriceSetMoneyAmounts } from "../../../__fixtures__/price-set-money-amount"
|
||||
@@ -20,7 +19,6 @@ describe("PricingModule Service - MoneyAmount", () => {
|
||||
let testManager: SqlEntityManager
|
||||
let repositoryManager: SqlEntityManager
|
||||
let data!: MoneyAmount[]
|
||||
let currencyData!: Currency[]
|
||||
let shutdownFunc: () => Promise<void>
|
||||
|
||||
beforeAll(async () => {
|
||||
@@ -42,7 +40,6 @@ describe("PricingModule Service - MoneyAmount", () => {
|
||||
repositoryManager = MikroOrmWrapper.forkManager()
|
||||
testManager = MikroOrmWrapper.forkManager()
|
||||
|
||||
currencyData = await createCurrencies(testManager)
|
||||
data = await createMoneyAmounts(testManager)
|
||||
})
|
||||
|
||||
@@ -90,8 +87,7 @@ describe("PricingModule Service - MoneyAmount", () => {
|
||||
id: ["money-amount-USD"],
|
||||
},
|
||||
{
|
||||
select: ["id", "min_quantity", "currency.code"],
|
||||
relations: ["currency"],
|
||||
select: ["id", "min_quantity", "currency_code"],
|
||||
}
|
||||
)
|
||||
|
||||
@@ -103,9 +99,6 @@ describe("PricingModule Service - MoneyAmount", () => {
|
||||
amount: null,
|
||||
min_quantity: "1",
|
||||
currency_code: "USD",
|
||||
currency: {
|
||||
code: "USD",
|
||||
},
|
||||
},
|
||||
])
|
||||
})
|
||||
@@ -153,8 +146,7 @@ describe("PricingModule Service - MoneyAmount", () => {
|
||||
id: ["money-amount-USD"],
|
||||
},
|
||||
{
|
||||
select: ["id", "min_quantity", "currency.code", "amount"],
|
||||
relations: ["currency"],
|
||||
select: ["id", "min_quantity", "currency_code", "amount"],
|
||||
}
|
||||
)
|
||||
|
||||
@@ -167,9 +159,6 @@ describe("PricingModule Service - MoneyAmount", () => {
|
||||
amount: 500,
|
||||
min_quantity: "1",
|
||||
currency_code: "USD",
|
||||
currency: {
|
||||
code: "USD",
|
||||
},
|
||||
},
|
||||
])
|
||||
})
|
||||
@@ -392,12 +381,9 @@ describe("PricingModule Service - MoneyAmount", () => {
|
||||
},
|
||||
])
|
||||
|
||||
const moneyAmount = await service.retrieveMoneyAmount(id, {
|
||||
relations: ["currency"],
|
||||
})
|
||||
const moneyAmount = await service.retrieveMoneyAmount(id, {})
|
||||
|
||||
expect(moneyAmount.currency_code).toEqual("EUR")
|
||||
expect(moneyAmount.currency?.code).toEqual("EUR")
|
||||
})
|
||||
|
||||
it("should throw an error when a id does not exist", async () => {
|
||||
|
||||
-2
@@ -2,7 +2,6 @@ import { MikroOrmWrapper } from "../../../utils"
|
||||
|
||||
import { IPricingModuleService } from "@medusajs/types"
|
||||
import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
import { createCurrencies } from "../../../__fixtures__/currency"
|
||||
import { createPriceLists } from "../../../__fixtures__/price-list"
|
||||
import { createPriceSets } from "../../../__fixtures__/price-set"
|
||||
import { Modules } from "@medusajs/modules-sdk"
|
||||
@@ -35,7 +34,6 @@ describe("PriceList Service", () => {
|
||||
await MikroOrmWrapper.forkManager()
|
||||
|
||||
testManager = await MikroOrmWrapper.forkManager()
|
||||
await createCurrencies(testManager)
|
||||
await createPriceSets(testManager)
|
||||
await createPriceLists(testManager)
|
||||
await service.createRuleTypes([
|
||||
|
||||
-2
@@ -2,7 +2,6 @@ import { CreatePriceRuleDTO, IPricingModuleService } from "@medusajs/types"
|
||||
import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
|
||||
import { PriceSetMoneyAmount } from "../../../../src"
|
||||
import { createCurrencies } from "../../../__fixtures__/currency"
|
||||
import { createMoneyAmounts } from "../../../__fixtures__/money-amount"
|
||||
import { createPriceRules } from "../../../__fixtures__/price-rule"
|
||||
import { createPriceSets } from "../../../__fixtures__/price-set"
|
||||
@@ -39,7 +38,6 @@ describe("PricingModule Service - PriceRule", () => {
|
||||
await MikroOrmWrapper.setupDatabase()
|
||||
testManager = MikroOrmWrapper.forkManager()
|
||||
|
||||
await createCurrencies(testManager)
|
||||
await createMoneyAmounts(testManager)
|
||||
await createPriceSets(testManager)
|
||||
await createRuleTypes(testManager)
|
||||
|
||||
-2
@@ -1,6 +1,5 @@
|
||||
import { IPricingModuleService } from "@medusajs/types"
|
||||
import { SqlEntityManager } from "@mikro-orm/postgresql"
|
||||
import { createCurrencies } from "../../../__fixtures__/currency"
|
||||
import { createMoneyAmounts } from "../../../__fixtures__/money-amount"
|
||||
import { createPriceSets } from "../../../__fixtures__/price-set"
|
||||
import { createPriceSetMoneyAmounts } from "../../../__fixtures__/price-set-money-amount"
|
||||
@@ -38,7 +37,6 @@ describe("PricingModule Service - PriceSetMoneyAmountRules", () => {
|
||||
repositoryManager = await MikroOrmWrapper.forkManager()
|
||||
testManager = await MikroOrmWrapper.forkManager()
|
||||
|
||||
await createCurrencies(testManager)
|
||||
await createMoneyAmounts(testManager)
|
||||
await createPriceSets(testManager)
|
||||
await createRuleTypes(testManager)
|
||||
|
||||
@@ -1,18 +1,11 @@
|
||||
import { Modules } from "@medusajs/modules-sdk"
|
||||
import { ModuleJoinerConfig } from "@medusajs/types"
|
||||
import { MapToConfig } from "@medusajs/utils"
|
||||
import {
|
||||
Currency,
|
||||
MoneyAmount,
|
||||
PriceList,
|
||||
PriceSet,
|
||||
PriceSetMoneyAmount,
|
||||
} from "@models"
|
||||
import { MoneyAmount, PriceList, PriceSet, PriceSetMoneyAmount } from "@models"
|
||||
import schema from "./schema"
|
||||
|
||||
export const LinkableKeys = {
|
||||
money_amount_id: MoneyAmount.name,
|
||||
currency_code: Currency.name,
|
||||
price_set_id: PriceSet.name,
|
||||
price_list_id: PriceList.name,
|
||||
price_set_money_amount_id: PriceSetMoneyAmount.name,
|
||||
@@ -48,13 +41,6 @@ export const joinerConfig: ModuleJoinerConfig = {
|
||||
entity: "MoneyAmount",
|
||||
},
|
||||
},
|
||||
{
|
||||
name: ["currency", "currencies"],
|
||||
args: {
|
||||
methodSuffix: "Currencies",
|
||||
entity: "Currency",
|
||||
},
|
||||
},
|
||||
{
|
||||
name: ["price_list", "price_lists"],
|
||||
args: {
|
||||
|
||||
@@ -4,61 +4,6 @@
|
||||
],
|
||||
"name": "public",
|
||||
"tables": [
|
||||
{
|
||||
"columns": {
|
||||
"code": {
|
||||
"name": "code",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"symbol": {
|
||||
"name": "symbol",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"symbol_native": {
|
||||
"name": "symbol_native",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
}
|
||||
},
|
||||
"name": "currency",
|
||||
"schema": "public",
|
||||
"indexes": [
|
||||
{
|
||||
"keyName": "currency_pkey",
|
||||
"columnNames": [
|
||||
"code"
|
||||
],
|
||||
"composite": false,
|
||||
"primary": true,
|
||||
"unique": true
|
||||
}
|
||||
],
|
||||
"checks": [],
|
||||
"foreignKeys": {}
|
||||
},
|
||||
{
|
||||
"columns": {
|
||||
"id": {
|
||||
@@ -172,19 +117,6 @@
|
||||
],
|
||||
"checks": [],
|
||||
"foreignKeys": {
|
||||
"money_amount_currency_code_foreign": {
|
||||
"constraintName": "money_amount_currency_code_foreign",
|
||||
"columnNames": [
|
||||
"currency_code"
|
||||
],
|
||||
"localTableName": "public.money_amount",
|
||||
"referencedColumnNames": [
|
||||
"code"
|
||||
],
|
||||
"referencedTableName": "public.currency",
|
||||
"deleteRule": "set null",
|
||||
"updateRule": "cascade"
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
|
||||
@@ -2,10 +2,6 @@ import { Migration } from "@mikro-orm/migrations"
|
||||
|
||||
export class Migration20230929122253 extends Migration {
|
||||
async up(): Promise<void> {
|
||||
this.addSql(
|
||||
'create table if not exists "currency" ("code" text not null, "symbol" text not null, "symbol_native" text not null, "name" text not null, constraint "currency_pkey" primary key ("code"));'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'create table if not exists "money_amount" ("id" text not null, "currency_code" text null, "amount" numeric null, "min_quantity" numeric null, "max_quantity" numeric null, constraint "money_amount_pkey" primary key ("id"));'
|
||||
)
|
||||
@@ -67,10 +63,6 @@ export class Migration20230929122253 extends Migration {
|
||||
'create index "IDX_price_rule_price_set_money_amount_id" on "price_rule" ("price_set_money_amount_id");'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "money_amount" add constraint "money_amount_currency_code_foreign" foreign key ("currency_code") references "currency" ("code") on update cascade on delete set null;'
|
||||
)
|
||||
|
||||
this.addSql(
|
||||
'alter table "price_set_money_amount" add constraint "price_set_money_amount_price_set_id_foreign" foreign key ("price_set_id") references "price_set" ("id") on update cascade on delete cascade;'
|
||||
)
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
export { default as Currency } from "./currency"
|
||||
export { default as MoneyAmount } from "./money-amount"
|
||||
export { default as PriceList } from "./price-list"
|
||||
export { default as PriceListRule } from "./price-list-rule"
|
||||
|
||||
@@ -14,7 +14,6 @@ import {
|
||||
Property,
|
||||
} from "@mikro-orm/core"
|
||||
|
||||
import Currency from "./currency"
|
||||
import { PriceSetMoneyAmount } from "./index"
|
||||
import PriceSet from "./price-set"
|
||||
|
||||
@@ -47,13 +46,6 @@ class MoneyAmount {
|
||||
})
|
||||
price_set_money_amount: PriceSetMoneyAmount
|
||||
|
||||
@ManyToOne(() => Currency, {
|
||||
nullable: true,
|
||||
index: "IDX_money_amount_currency_code",
|
||||
fieldName: "currency_code",
|
||||
})
|
||||
currency: Currency
|
||||
|
||||
@Property({
|
||||
columnType: "numeric",
|
||||
nullable: true,
|
||||
|
||||
@@ -7,7 +7,6 @@ type PriceSet {
|
||||
type MoneyAmount {
|
||||
id: String!
|
||||
currency_code: String
|
||||
currency: Currency
|
||||
amount: Float
|
||||
min_quantity: Float
|
||||
max_quantity: Float
|
||||
|
||||
@@ -22,17 +22,13 @@ export async function run({
|
||||
|
||||
logger.info(`Loading seed data from ${path}...`)
|
||||
|
||||
const {
|
||||
currenciesData,
|
||||
moneyAmountsData,
|
||||
priceSetsData,
|
||||
priceSetMoneyAmountsData,
|
||||
} = await import(resolve(process.cwd(), path)).catch((e) => {
|
||||
logger?.error(
|
||||
`Failed to load seed data from ${path}. Please, provide a relative path and check that you export the following: priceSetsData, currenciesData, moneyAmountsData and priceSetMoneyAmountsData.${EOL}${e}`
|
||||
)
|
||||
throw e
|
||||
})
|
||||
const { moneyAmountsData, priceSetsData, priceSetMoneyAmountsData } =
|
||||
await import(resolve(process.cwd(), path)).catch((e) => {
|
||||
logger?.error(
|
||||
`Failed to load seed data from ${path}. Please, provide a relative path and check that you export the following: priceSetsData, moneyAmountsData and priceSetMoneyAmountsData.${EOL}${e}`
|
||||
)
|
||||
throw e
|
||||
})
|
||||
|
||||
const dbData = ModulesSdkUtils.loadDatabaseConfig("pricing", options)!
|
||||
const entities = Object.values(PricingModels) as unknown as EntitySchema[]
|
||||
@@ -47,9 +43,8 @@ export async function run({
|
||||
const manager = orm.em.fork()
|
||||
|
||||
try {
|
||||
logger.info("Inserting price_sets, currencies & money_amounts")
|
||||
logger.info("Inserting price_sets & money_amounts")
|
||||
|
||||
await createCurrencies(manager as any, currenciesData)
|
||||
await createMoneyAmounts(manager as any, moneyAmountsData)
|
||||
await createPriceSets(manager as any, priceSetsData)
|
||||
await createPriceSetMoneyAmounts(manager as any, priceSetMoneyAmountsData)
|
||||
@@ -62,19 +57,6 @@ export async function run({
|
||||
await orm.close(true)
|
||||
}
|
||||
|
||||
async function createCurrencies(
|
||||
manager: SqlEntityManager<PostgreSqlDriver>,
|
||||
data: RequiredEntityData<PricingModels.Currency>[]
|
||||
) {
|
||||
const currencies = data.map((currencyData) => {
|
||||
return manager.create(PricingModels.Currency, currencyData)
|
||||
})
|
||||
|
||||
await manager.persistAndFlush(currencies)
|
||||
|
||||
return currencies
|
||||
}
|
||||
|
||||
async function createMoneyAmounts(
|
||||
manager: SqlEntityManager<PostgreSqlDriver>,
|
||||
data: RequiredEntityData<PricingModels.MoneyAmount>[]
|
||||
|
||||
@@ -1,24 +0,0 @@
|
||||
import { Currency } from "@models"
|
||||
import { asValue } from "awilix"
|
||||
|
||||
;(Currency as any).meta = {
|
||||
/**
|
||||
* Need to mock the Currency model as well to expose the primary keys when it is different than `id`
|
||||
*/
|
||||
primaryKeys: ["code"],
|
||||
}
|
||||
|
||||
export const nonExistingCurrencyCode = "non-existing-code"
|
||||
export const currencyRepositoryMock = {
|
||||
currencyRepository: asValue({
|
||||
find: jest.fn().mockImplementation(async ({ where: { code } }) => {
|
||||
if (code === nonExistingCurrencyCode) {
|
||||
return []
|
||||
}
|
||||
|
||||
return [{}]
|
||||
}),
|
||||
findAndCount: jest.fn().mockResolvedValue([[], 0]),
|
||||
getFreshManager: jest.fn().mockResolvedValue({}),
|
||||
}),
|
||||
}
|
||||
@@ -1,228 +0,0 @@
|
||||
import {
|
||||
currencyRepositoryMock,
|
||||
nonExistingCurrencyCode,
|
||||
} from "../__fixtures__/currency"
|
||||
import { createMedusaContainer } from "@medusajs/utils"
|
||||
import { asValue } from "awilix"
|
||||
import ContainerLoader from "../../loaders/container"
|
||||
import { MedusaContainer } from "@medusajs/types"
|
||||
|
||||
const code = "existing-currency"
|
||||
|
||||
describe("Currency service", function () {
|
||||
let container: MedusaContainer
|
||||
|
||||
beforeEach(async function () {
|
||||
jest.clearAllMocks()
|
||||
|
||||
container = createMedusaContainer()
|
||||
container.register("manager", asValue({}))
|
||||
|
||||
await ContainerLoader({ container })
|
||||
|
||||
container.register(currencyRepositoryMock)
|
||||
})
|
||||
|
||||
it("should retrieve a currency", async function () {
|
||||
const currencyService = container.resolve("currencyService")
|
||||
const currencyRepository = container.resolve("currencyRepository")
|
||||
|
||||
await currencyService.retrieve(code)
|
||||
|
||||
expect(currencyRepository.find).toHaveBeenCalledWith(
|
||||
{
|
||||
where: {
|
||||
code,
|
||||
},
|
||||
options: {
|
||||
fields: undefined,
|
||||
limit: 15,
|
||||
offset: 0,
|
||||
populate: [],
|
||||
},
|
||||
},
|
||||
expect.any(Object)
|
||||
)
|
||||
})
|
||||
|
||||
it("should fail to retrieve a currency", async function () {
|
||||
const currencyService = container.resolve("currencyService")
|
||||
const currencyRepository = container.resolve("currencyRepository")
|
||||
|
||||
const err = await currencyService
|
||||
.retrieve(nonExistingCurrencyCode)
|
||||
.catch((e) => e)
|
||||
|
||||
expect(currencyRepository.find).toHaveBeenCalledWith(
|
||||
{
|
||||
where: {
|
||||
code: nonExistingCurrencyCode,
|
||||
},
|
||||
options: {
|
||||
fields: undefined,
|
||||
limit: 15,
|
||||
offset: 0,
|
||||
populate: [],
|
||||
withDeleted: undefined,
|
||||
},
|
||||
},
|
||||
expect.any(Object)
|
||||
)
|
||||
|
||||
expect(err.message).toBe(
|
||||
`Currency with code: ${nonExistingCurrencyCode} was not found`
|
||||
)
|
||||
})
|
||||
|
||||
it("should list currencys", async function () {
|
||||
const currencyService = container.resolve("currencyService")
|
||||
const currencyRepository = container.resolve("currencyRepository")
|
||||
|
||||
const filters = {}
|
||||
const config = {
|
||||
relations: [],
|
||||
}
|
||||
|
||||
await currencyService.list(filters, config)
|
||||
|
||||
expect(currencyRepository.find).toHaveBeenCalledWith(
|
||||
{
|
||||
where: {},
|
||||
options: {
|
||||
fields: undefined,
|
||||
limit: 15,
|
||||
offset: 0,
|
||||
orderBy: {
|
||||
code: "ASC",
|
||||
},
|
||||
populate: [],
|
||||
withDeleted: undefined,
|
||||
},
|
||||
},
|
||||
expect.any(Object)
|
||||
)
|
||||
})
|
||||
|
||||
it("should list currencys with filters", async function () {
|
||||
const currencyService = container.resolve("currencyService")
|
||||
const currencyRepository = container.resolve("currencyRepository")
|
||||
|
||||
const filters = {
|
||||
tags: {
|
||||
value: {
|
||||
$in: ["test"],
|
||||
},
|
||||
},
|
||||
}
|
||||
const config = {
|
||||
relations: [],
|
||||
}
|
||||
|
||||
await currencyService.list(filters, config)
|
||||
|
||||
expect(currencyRepository.find).toHaveBeenCalledWith(
|
||||
{
|
||||
where: {
|
||||
tags: {
|
||||
value: {
|
||||
$in: ["test"],
|
||||
},
|
||||
},
|
||||
},
|
||||
options: {
|
||||
fields: undefined,
|
||||
limit: 15,
|
||||
offset: 0,
|
||||
orderBy: {
|
||||
code: "ASC",
|
||||
},
|
||||
populate: [],
|
||||
withDeleted: undefined,
|
||||
},
|
||||
},
|
||||
expect.any(Object)
|
||||
)
|
||||
})
|
||||
|
||||
it("should list currencys with filters and relations", async function () {
|
||||
const currencyService = container.resolve("currencyService")
|
||||
const currencyRepository = container.resolve("currencyRepository")
|
||||
|
||||
const filters = {
|
||||
tags: {
|
||||
value: {
|
||||
$in: ["test"],
|
||||
},
|
||||
},
|
||||
}
|
||||
const config = {
|
||||
relations: ["tags"],
|
||||
}
|
||||
|
||||
await currencyService.list(filters, config)
|
||||
|
||||
expect(currencyRepository.find).toHaveBeenCalledWith(
|
||||
{
|
||||
where: {
|
||||
tags: {
|
||||
value: {
|
||||
$in: ["test"],
|
||||
},
|
||||
},
|
||||
},
|
||||
options: {
|
||||
fields: undefined,
|
||||
limit: 15,
|
||||
offset: 0,
|
||||
orderBy: {
|
||||
code: "ASC",
|
||||
},
|
||||
withDeleted: undefined,
|
||||
populate: ["tags"],
|
||||
},
|
||||
},
|
||||
expect.any(Object)
|
||||
)
|
||||
})
|
||||
|
||||
it("should list and count the currencies with filters and relations", async function () {
|
||||
const currencyService = container.resolve("currencyService")
|
||||
const currencyRepository = container.resolve("currencyRepository")
|
||||
|
||||
const filters = {
|
||||
tags: {
|
||||
value: {
|
||||
$in: ["test"],
|
||||
},
|
||||
},
|
||||
}
|
||||
const config = {
|
||||
relations: ["tags"],
|
||||
}
|
||||
|
||||
await currencyService.listAndCount(filters, config)
|
||||
|
||||
expect(currencyRepository.findAndCount).toHaveBeenCalledWith(
|
||||
{
|
||||
where: {
|
||||
tags: {
|
||||
value: {
|
||||
$in: ["test"],
|
||||
},
|
||||
},
|
||||
},
|
||||
options: {
|
||||
fields: undefined,
|
||||
limit: 15,
|
||||
offset: 0,
|
||||
orderBy: {
|
||||
code: "ASC",
|
||||
},
|
||||
withDeleted: undefined,
|
||||
populate: ["tags"],
|
||||
},
|
||||
},
|
||||
expect.any(Object)
|
||||
)
|
||||
})
|
||||
})
|
||||
@@ -0,0 +1,6 @@
|
||||
describe("Noop test", () => {
|
||||
it("noop check", async () => {
|
||||
expect(true).toBe(true)
|
||||
})
|
||||
})
|
||||
|
||||
@@ -28,7 +28,6 @@ import {
|
||||
} from "@medusajs/utils"
|
||||
|
||||
import {
|
||||
Currency,
|
||||
MoneyAmount,
|
||||
PriceList,
|
||||
PriceListRule,
|
||||
@@ -55,7 +54,6 @@ import { ServiceTypes } from "@types"
|
||||
type InjectedDependencies = {
|
||||
baseRepository: DAL.RepositoryService
|
||||
pricingRepository: PricingRepositoryService
|
||||
currencyService: ModulesSdkTypes.InternalModuleService<any>
|
||||
moneyAmountService: ModulesSdkTypes.InternalModuleService<any>
|
||||
priceSetService: ModulesSdkTypes.InternalModuleService<any>
|
||||
priceSetMoneyAmountRulesService: ModulesSdkTypes.InternalModuleService<any>
|
||||
@@ -69,7 +67,6 @@ type InjectedDependencies = {
|
||||
}
|
||||
|
||||
const generateMethodForModels = [
|
||||
Currency,
|
||||
MoneyAmount,
|
||||
PriceList,
|
||||
PriceListRule,
|
||||
@@ -84,7 +81,6 @@ const generateMethodForModels = [
|
||||
export default class PricingModuleService<
|
||||
TPriceSet extends PriceSet = PriceSet,
|
||||
TMoneyAmount extends MoneyAmount = MoneyAmount,
|
||||
TCurrency extends Currency = Currency,
|
||||
TRuleType extends RuleType = RuleType,
|
||||
TPriceSetMoneyAmountRules extends PriceSetMoneyAmountRules = PriceSetMoneyAmountRules,
|
||||
TPriceRule extends PriceRule = PriceRule,
|
||||
@@ -98,7 +94,6 @@ export default class PricingModuleService<
|
||||
InjectedDependencies,
|
||||
PricingTypes.PriceSetDTO,
|
||||
{
|
||||
Currency: { dto: PricingTypes.CurrencyDTO }
|
||||
MoneyAmount: { dto: PricingTypes.MoneyAmountDTO }
|
||||
PriceSetMoneyAmount: { dto: PricingTypes.PriceSetMoneyAmountDTO }
|
||||
PriceSetMoneyAmountRules: {
|
||||
@@ -114,7 +109,6 @@ export default class PricingModuleService<
|
||||
{
|
||||
protected baseRepository_: DAL.RepositoryService
|
||||
protected readonly pricingRepository_: PricingRepositoryService
|
||||
protected readonly currencyService_: ModulesSdkTypes.InternalModuleService<TCurrency>
|
||||
protected readonly moneyAmountService_: ModulesSdkTypes.InternalModuleService<TMoneyAmount>
|
||||
protected readonly ruleTypeService_: RuleTypeService<TRuleType>
|
||||
protected readonly priceSetService_: ModulesSdkTypes.InternalModuleService<TPriceSet>
|
||||
@@ -131,7 +125,6 @@ export default class PricingModuleService<
|
||||
baseRepository,
|
||||
pricingRepository,
|
||||
moneyAmountService,
|
||||
currencyService,
|
||||
ruleTypeService,
|
||||
priceSetService,
|
||||
priceSetMoneyAmountRulesService,
|
||||
@@ -149,7 +142,6 @@ export default class PricingModuleService<
|
||||
|
||||
this.baseRepository_ = baseRepository
|
||||
this.pricingRepository_ = pricingRepository
|
||||
this.currencyService_ = currencyService
|
||||
this.moneyAmountService_ = moneyAmountService
|
||||
this.ruleTypeService_ = ruleTypeService
|
||||
this.priceSetService_ = priceSetService
|
||||
@@ -749,36 +741,6 @@ export default class PricingModuleService<
|
||||
)
|
||||
}
|
||||
|
||||
@InjectTransactionManager("baseRepository_")
|
||||
async createCurrencies(
|
||||
data: PricingTypes.CreateCurrencyDTO[],
|
||||
@MedusaContext() sharedContext: Context = {}
|
||||
) {
|
||||
const currencies = await this.currencyService_.create(data, sharedContext)
|
||||
|
||||
return await this.baseRepository_.serialize<PricingTypes.CurrencyDTO[]>(
|
||||
currencies,
|
||||
{
|
||||
populate: true,
|
||||
}
|
||||
)
|
||||
}
|
||||
|
||||
@InjectTransactionManager("baseRepository_")
|
||||
async updateCurrencies(
|
||||
data: PricingTypes.UpdateCurrencyDTO[],
|
||||
@MedusaContext() sharedContext: Context = {}
|
||||
) {
|
||||
const currencies = await this.currencyService_.update(data, sharedContext)
|
||||
|
||||
return await this.baseRepository_.serialize<PricingTypes.CurrencyDTO[]>(
|
||||
currencies,
|
||||
{
|
||||
populate: true,
|
||||
}
|
||||
)
|
||||
}
|
||||
|
||||
@InjectTransactionManager("baseRepository_")
|
||||
async createRuleTypes(
|
||||
data: PricingTypes.CreateRuleTypeDTO[],
|
||||
|
||||
@@ -1,13 +0,0 @@
|
||||
export interface CreateCurrencyDTO {
|
||||
code: string
|
||||
symbol: string
|
||||
symbol_native: string
|
||||
name: string
|
||||
}
|
||||
|
||||
export interface UpdateCurrencyDTO {
|
||||
code: string
|
||||
symbol?: string
|
||||
symbol_native?: string
|
||||
name?: string
|
||||
}
|
||||
@@ -1,4 +1,3 @@
|
||||
export * from "./currency"
|
||||
export * from "./money-amount"
|
||||
export * from "./price-list-rule-value"
|
||||
export * from "./price-list-rule"
|
||||
|
||||
@@ -1,9 +1,6 @@
|
||||
import { Currency } from "@models"
|
||||
|
||||
export interface CreateMoneyAmountDTO {
|
||||
id?: string
|
||||
currency_code: string
|
||||
currency?: Currency
|
||||
amount: number
|
||||
min_quantity?: number | null
|
||||
max_quantity?: number | null
|
||||
|
||||
@@ -1,27 +0,0 @@
|
||||
import { BaseFilterable } from "@medusajs/types"
|
||||
|
||||
export interface CreateCurrencyDTO {
|
||||
code: string
|
||||
symbol: string
|
||||
symbol_native: string
|
||||
name: string
|
||||
}
|
||||
|
||||
export interface UpdateCurrencyDTO {
|
||||
code: string
|
||||
symbol?: string
|
||||
symbol_native?: string
|
||||
name?: string
|
||||
}
|
||||
|
||||
export interface FilterableCurrencyProps
|
||||
extends BaseFilterable<FilterableCurrencyProps> {
|
||||
code?: string[]
|
||||
}
|
||||
|
||||
export interface CurrencyDTO {
|
||||
code: string
|
||||
symbol?: string
|
||||
symbol_native?: string
|
||||
name?: string
|
||||
}
|
||||
@@ -1,4 +1,3 @@
|
||||
export * from "./currency"
|
||||
export * from "./money-amount"
|
||||
export * from "./price-list-rule-value"
|
||||
export * from "./price-list-rule"
|
||||
@@ -9,4 +8,4 @@ export * from "./price-set-money-amount"
|
||||
export * from "./price-set-rule-type"
|
||||
export * from "./price-set"
|
||||
export * from "./pricing"
|
||||
export * from "./rule-type"
|
||||
export * from "./rule-type"
|
||||
|
||||
@@ -1,14 +1,8 @@
|
||||
import {
|
||||
BaseFilterable,
|
||||
CreateCurrencyDTO,
|
||||
CurrencyDTO,
|
||||
PriceSetMoneyAmountDTO,
|
||||
} from "@medusajs/types"
|
||||
import { BaseFilterable, PriceSetMoneyAmountDTO } from "@medusajs/types"
|
||||
|
||||
export interface CreateMoneyAmountDTO {
|
||||
id?: string
|
||||
currency_code: string
|
||||
currency?: CreateCurrencyDTO
|
||||
amount: number
|
||||
min_quantity?: number | null
|
||||
max_quantity?: number | null
|
||||
@@ -25,7 +19,6 @@ export interface UpdateMoneyAmountDTO {
|
||||
export interface MoneyAmountDTO {
|
||||
id: string
|
||||
currency_code?: string
|
||||
currency?: CurrencyDTO
|
||||
amount?: number
|
||||
min_quantity?: number
|
||||
max_quantity?: number
|
||||
|
||||
@@ -26,12 +26,9 @@ describe("Region Module Service", () => {
|
||||
await shutdownFunc()
|
||||
})
|
||||
|
||||
it("should create countries and currencies on application start", async () => {
|
||||
it("should create countries on application start", async () => {
|
||||
const countries = await service.listCountries()
|
||||
const currencies = await service.listCurrencies()
|
||||
|
||||
expect(countries.length).toBeGreaterThan(0)
|
||||
expect(currencies.length).toBeGreaterThan(0)
|
||||
})
|
||||
|
||||
it("should create countries added to default ones", async () => {
|
||||
@@ -47,7 +44,7 @@ describe("Region Module Service", () => {
|
||||
numeric: "420",
|
||||
})
|
||||
|
||||
await service.createDefaultCountriesAndCurrencies()
|
||||
await service.createDefaultCountries()
|
||||
|
||||
const [, newCount] = await service.listAndCountCountries()
|
||||
expect(newCount).toEqual(initialCountries + 1)
|
||||
@@ -69,7 +66,7 @@ describe("Region Module Service", () => {
|
||||
)
|
||||
|
||||
const region = await service.retrieve(createdRegion.id, {
|
||||
relations: ["currency", "countries"],
|
||||
relations: ["countries"],
|
||||
})
|
||||
|
||||
expect(region).toEqual(
|
||||
@@ -77,10 +74,6 @@ describe("Region Module Service", () => {
|
||||
id: region.id,
|
||||
name: "Europe",
|
||||
currency_code: "eur",
|
||||
currency: expect.objectContaining({
|
||||
code: "eur",
|
||||
name: "Euro",
|
||||
}),
|
||||
countries: [],
|
||||
})
|
||||
)
|
||||
@@ -94,7 +87,7 @@ describe("Region Module Service", () => {
|
||||
})
|
||||
|
||||
const region = await service.retrieve(createdRegion.id, {
|
||||
relations: ["countries", "currency"],
|
||||
relations: ["countries"],
|
||||
})
|
||||
|
||||
expect(region).toEqual(
|
||||
@@ -102,10 +95,6 @@ describe("Region Module Service", () => {
|
||||
id: region.id,
|
||||
name: "North America",
|
||||
currency_code: "usd",
|
||||
currency: expect.objectContaining({
|
||||
code: "usd",
|
||||
name: "US Dollar",
|
||||
}),
|
||||
countries: [
|
||||
expect.objectContaining({
|
||||
display_name: "Canada",
|
||||
@@ -182,7 +171,7 @@ describe("Region Module Service", () => {
|
||||
})
|
||||
|
||||
const latestRegion = await service.retrieve(createdRegion.id, {
|
||||
relations: ["currency", "countries"],
|
||||
relations: ["countries"],
|
||||
})
|
||||
|
||||
expect(latestRegion).toMatchObject({
|
||||
@@ -243,7 +232,7 @@ describe("Region Module Service", () => {
|
||||
})
|
||||
|
||||
const latestRegion = await service.retrieve(createdRegion.id, {
|
||||
relations: ["currency", "countries"],
|
||||
relations: ["countries"],
|
||||
})
|
||||
|
||||
expect(latestRegion).toMatchObject({
|
||||
@@ -268,7 +257,7 @@ describe("Region Module Service", () => {
|
||||
})
|
||||
|
||||
const updatedRegion = await service.retrieve(createdRegion.id, {
|
||||
relations: ["currency", "countries"],
|
||||
relations: ["countries"],
|
||||
})
|
||||
|
||||
expect(updatedRegion).toMatchObject({
|
||||
@@ -294,7 +283,7 @@ describe("Region Module Service", () => {
|
||||
})
|
||||
|
||||
const updatedRegion = await service.retrieve(createdRegion.id, {
|
||||
relations: ["currency", "countries"],
|
||||
relations: ["countries"],
|
||||
})
|
||||
|
||||
expect(updatedRegion).toMatchObject({
|
||||
@@ -306,23 +295,6 @@ describe("Region Module Service", () => {
|
||||
expect(updatedRegion.countries).toHaveLength(0)
|
||||
})
|
||||
|
||||
it("should fail updating the region currency to a non-existent one", async () => {
|
||||
const createdRegion = await service.create({
|
||||
name: "North America",
|
||||
currency_code: "USD",
|
||||
countries: ["us", "ca"],
|
||||
})
|
||||
|
||||
await expect(
|
||||
service.update(
|
||||
{ id: createdRegion.id },
|
||||
{
|
||||
currency_code: "DOGECOIN",
|
||||
}
|
||||
)
|
||||
).rejects.toThrowError('Currencies with codes: "dogecoin" were not found')
|
||||
})
|
||||
|
||||
it("should fail updating the region countries to non-existent ones", async () => {
|
||||
const createdRegion = await service.create({
|
||||
name: "North America",
|
||||
@@ -384,13 +356,4 @@ describe("Region Module Service", () => {
|
||||
'Countries with codes: "mx" are already assigned to a region'
|
||||
)
|
||||
})
|
||||
|
||||
it("should fail when currency does not exist", async () => {
|
||||
await expect(
|
||||
service.create({
|
||||
name: "Europe",
|
||||
currency_code: "DOGECOIN",
|
||||
})
|
||||
).rejects.toThrowError('Currencies with codes: "dogecoin" were not found')
|
||||
})
|
||||
})
|
||||
|
||||
@@ -1,11 +1,10 @@
|
||||
import { Modules } from "@medusajs/modules-sdk"
|
||||
import { ModuleJoinerConfig } from "@medusajs/types"
|
||||
import { MapToConfig } from "@medusajs/utils"
|
||||
import { Country, Currency, Region } from "@models"
|
||||
import { Country, Region } from "@models"
|
||||
|
||||
export const LinkableKeys = {
|
||||
region_id: Region.name,
|
||||
currency_code: Country.name,
|
||||
country_id: Region.name,
|
||||
}
|
||||
|
||||
@@ -29,10 +28,6 @@ export const joinerConfig: ModuleJoinerConfig = {
|
||||
name: ["region", "regions"],
|
||||
args: { entity: Region.name },
|
||||
},
|
||||
{
|
||||
name: ["currency", "currencies"],
|
||||
args: { entity: Currency.name },
|
||||
},
|
||||
{
|
||||
name: ["country", "countries"],
|
||||
args: { entity: Country.name },
|
||||
|
||||
@@ -8,6 +8,6 @@ export default async ({ container }: LoaderOptions): Promise<void> => {
|
||||
|
||||
// TODO: Remove when legacy modules have been migrated
|
||||
if (!!process.env.MEDUSA_FF_MEDUSA_V2) {
|
||||
await service.createDefaultCountriesAndCurrencies()
|
||||
await service.createDefaultCountries()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,64 +1,7 @@
|
||||
{
|
||||
"namespaces": [
|
||||
"public"
|
||||
],
|
||||
"namespaces": ["public"],
|
||||
"name": "public",
|
||||
"tables": [
|
||||
{
|
||||
"columns": {
|
||||
"code": {
|
||||
"name": "code",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"symbol": {
|
||||
"name": "symbol",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"symbol_native": {
|
||||
"name": "symbol_native",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"unsigned": false,
|
||||
"autoincrement": false,
|
||||
"primary": false,
|
||||
"nullable": false,
|
||||
"mappedType": "text"
|
||||
}
|
||||
},
|
||||
"name": "region_currency",
|
||||
"schema": "public",
|
||||
"indexes": [
|
||||
{
|
||||
"keyName": "region_currency_pkey",
|
||||
"columnNames": [
|
||||
"code"
|
||||
],
|
||||
"composite": false,
|
||||
"primary": true,
|
||||
"unique": true
|
||||
}
|
||||
],
|
||||
"checks": [],
|
||||
"foreignKeys": {}
|
||||
},
|
||||
{
|
||||
"columns": {
|
||||
"id": {
|
||||
@@ -134,18 +77,7 @@
|
||||
"schema": "public",
|
||||
"indexes": [
|
||||
{
|
||||
"columnNames": [
|
||||
"currency_code"
|
||||
],
|
||||
"composite": false,
|
||||
"keyName": "IDX_region_currency_code",
|
||||
"primary": false,
|
||||
"unique": false
|
||||
},
|
||||
{
|
||||
"columnNames": [
|
||||
"deleted_at"
|
||||
],
|
||||
"columnNames": ["deleted_at"],
|
||||
"composite": false,
|
||||
"keyName": "IDX_region_deleted_at",
|
||||
"primary": false,
|
||||
@@ -153,30 +85,14 @@
|
||||
},
|
||||
{
|
||||
"keyName": "region_pkey",
|
||||
"columnNames": [
|
||||
"id"
|
||||
],
|
||||
"columnNames": ["id"],
|
||||
"composite": false,
|
||||
"primary": true,
|
||||
"unique": true
|
||||
}
|
||||
],
|
||||
"checks": [],
|
||||
"foreignKeys": {
|
||||
"region_currency_code_foreign": {
|
||||
"constraintName": "region_currency_code_foreign",
|
||||
"columnNames": [
|
||||
"currency_code"
|
||||
],
|
||||
"localTableName": "public.region",
|
||||
"referencedColumnNames": [
|
||||
"code"
|
||||
],
|
||||
"referencedTableName": "public.region_currency",
|
||||
"deleteRule": "set null",
|
||||
"updateRule": "cascade"
|
||||
}
|
||||
}
|
||||
"foreignKeys": {}
|
||||
},
|
||||
{
|
||||
"columns": {
|
||||
@@ -249,9 +165,7 @@
|
||||
"indexes": [
|
||||
{
|
||||
"keyName": "region_country_pkey",
|
||||
"columnNames": [
|
||||
"id"
|
||||
],
|
||||
"columnNames": ["id"],
|
||||
"composite": false,
|
||||
"primary": true,
|
||||
"unique": true
|
||||
@@ -261,13 +175,9 @@
|
||||
"foreignKeys": {
|
||||
"region_country_region_id_foreign": {
|
||||
"constraintName": "region_country_region_id_foreign",
|
||||
"columnNames": [
|
||||
"region_id"
|
||||
],
|
||||
"columnNames": ["region_id"],
|
||||
"localTableName": "public.region_country",
|
||||
"referencedColumnNames": [
|
||||
"id"
|
||||
],
|
||||
"referencedColumnNames": ["id"],
|
||||
"referencedTableName": "public.region",
|
||||
"deleteRule": "set null",
|
||||
"updateRule": "cascade"
|
||||
|
||||
@@ -16,15 +16,6 @@ CREATE TABLE IF NOT EXISTS "region" (
|
||||
CONSTRAINT "region_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- Create or update "region_currency" table
|
||||
CREATE TABLE IF NOT EXISTS "region_currency" (
|
||||
"code" text NOT NULL,
|
||||
"symbol" text NOT NULL,
|
||||
"symbol_native" text NOT NULL,
|
||||
"name" text NOT NULL,
|
||||
CONSTRAINT "region_currency_pkey" PRIMARY KEY ("code")
|
||||
);
|
||||
|
||||
-- Adjust "region" table
|
||||
ALTER TABLE "region" DROP CONSTRAINT IF EXISTS "FK_3bdd5896ec93be2f1c62a3309a5";
|
||||
ALTER TABLE "region" DROP CONSTRAINT IF EXISTS "FK_91f88052197680f9790272aaf5b";
|
||||
@@ -35,9 +26,6 @@ ${generatePostgresAlterColummnIfExistStatement(
|
||||
"DROP NOT NULL"
|
||||
)}
|
||||
|
||||
ALTER TABLE "region" ADD CONSTRAINT "region_currency_code_foreign" FOREIGN KEY ("currency_code") REFERENCES "region_currency" ("code") ON UPDATE CASCADE;
|
||||
|
||||
CREATE INDEX IF NOT EXISTS "IDX_region_currency_code" ON "region" ("currency_code");
|
||||
CREATE INDEX IF NOT EXISTS "IDX_region_deleted_at" ON "region" ("deleted_at") WHERE "deleted_at" IS NOT NULL;
|
||||
|
||||
-- Create or update "region_country" table
|
||||
|
||||
@@ -1,16 +0,0 @@
|
||||
import { Entity, PrimaryKey, Property } from "@mikro-orm/core"
|
||||
|
||||
@Entity({ tableName: "region_currency" })
|
||||
export default class Currency {
|
||||
@PrimaryKey({ columnType: "text" })
|
||||
code: string
|
||||
|
||||
@Property({ columnType: "text" })
|
||||
symbol: string
|
||||
|
||||
@Property({ columnType: "text" })
|
||||
symbol_native: string
|
||||
|
||||
@Property({ columnType: "text" })
|
||||
name: string
|
||||
}
|
||||
@@ -1,4 +1,2 @@
|
||||
export { default as Country } from "./country"
|
||||
export { default as Currency } from "./currency"
|
||||
export { default as Region } from "./region"
|
||||
|
||||
|
||||
@@ -14,12 +14,8 @@ import {
|
||||
Property,
|
||||
} from "@mikro-orm/core"
|
||||
import Country from "./country"
|
||||
import Currency from "./currency"
|
||||
|
||||
type RegionOptionalProps =
|
||||
| "currency"
|
||||
| "countries"
|
||||
| DAL.SoftDeletableEntityDateColumns
|
||||
type RegionOptionalProps = "countries" | DAL.SoftDeletableEntityDateColumns
|
||||
|
||||
@Entity({ tableName: "region" })
|
||||
@Filter(DALUtils.mikroOrmSoftDeletableFilterOptions)
|
||||
@@ -35,13 +31,6 @@ export default class Region {
|
||||
@Property({ columnType: "text" })
|
||||
currency_code: string
|
||||
|
||||
@ManyToOne({
|
||||
entity: () => Currency,
|
||||
index: "IDX_region_currency_code",
|
||||
nullable: true,
|
||||
})
|
||||
currency?: Currency
|
||||
|
||||
@OneToMany(() => Country, (country) => country.region)
|
||||
countries = new Collection<Country>(this)
|
||||
|
||||
|
||||
@@ -8,7 +8,6 @@ import {
|
||||
ModuleJoinerConfig,
|
||||
ModulesSdkTypes,
|
||||
RegionCountryDTO,
|
||||
RegionCurrencyDTO,
|
||||
RegionDTO,
|
||||
UpdateRegionDTO,
|
||||
UpsertRegionDTO,
|
||||
@@ -27,9 +26,9 @@ import {
|
||||
getDuplicates,
|
||||
} from "@medusajs/utils"
|
||||
|
||||
import { Country, Currency, Region } from "@models"
|
||||
import { Country, Region } from "@models"
|
||||
|
||||
import { CreateCountryDTO, CreateCurrencyDTO, UpdateRegionInput } from "@types"
|
||||
import { CreateCountryDTO, UpdateRegionInput } from "@types"
|
||||
import { entityNameToLinkableKeysMap, joinerConfig } from "../joiner-config"
|
||||
|
||||
const COUNTRIES_LIMIT = 1000
|
||||
@@ -38,15 +37,13 @@ type InjectedDependencies = {
|
||||
baseRepository: DAL.RepositoryService
|
||||
regionService: ModulesSdkTypes.InternalModuleService<any>
|
||||
countryService: ModulesSdkTypes.InternalModuleService<any>
|
||||
currencyService: ModulesSdkTypes.InternalModuleService<any>
|
||||
}
|
||||
|
||||
const generateMethodForModels = [Country, Currency]
|
||||
const generateMethodForModels = [Country]
|
||||
|
||||
export default class RegionModuleService<
|
||||
TRegion extends Region = Region,
|
||||
TCountry extends Country = Country,
|
||||
TCurrency extends Currency = Currency
|
||||
TCountry extends Country = Country
|
||||
>
|
||||
extends ModulesSdkUtils.abstractModuleServiceFactory<
|
||||
InjectedDependencies,
|
||||
@@ -55,9 +52,6 @@ export default class RegionModuleService<
|
||||
Country: {
|
||||
dto: RegionCountryDTO
|
||||
}
|
||||
Currency: {
|
||||
dto: RegionCurrencyDTO
|
||||
}
|
||||
}
|
||||
>(Region, generateMethodForModels, entityNameToLinkableKeysMap)
|
||||
implements IRegionModuleService
|
||||
@@ -65,15 +59,9 @@ export default class RegionModuleService<
|
||||
protected baseRepository_: DAL.RepositoryService
|
||||
protected readonly regionService_: ModulesSdkTypes.InternalModuleService<TRegion>
|
||||
protected readonly countryService_: ModulesSdkTypes.InternalModuleService<TCountry>
|
||||
protected readonly currencyService_: ModulesSdkTypes.InternalModuleService<TCurrency>
|
||||
|
||||
constructor(
|
||||
{
|
||||
baseRepository,
|
||||
regionService,
|
||||
countryService,
|
||||
currencyService,
|
||||
}: InjectedDependencies,
|
||||
{ baseRepository, regionService, countryService }: InjectedDependencies,
|
||||
protected readonly moduleDeclaration: InternalModuleDeclaration
|
||||
) {
|
||||
// @ts-ignore
|
||||
@@ -81,7 +69,6 @@ export default class RegionModuleService<
|
||||
this.baseRepository_ = baseRepository
|
||||
this.regionService_ = regionService
|
||||
this.countryService_ = countryService
|
||||
this.currencyService_ = currencyService
|
||||
}
|
||||
|
||||
__joinerConfig(): ModuleJoinerConfig {
|
||||
@@ -118,10 +105,6 @@ export default class RegionModuleService<
|
||||
let normalizedInput = RegionModuleService.normalizeInput(data)
|
||||
|
||||
const validations = [
|
||||
this.validateCurrencies(
|
||||
normalizedInput.map((r) => r.currency_code),
|
||||
sharedContext
|
||||
),
|
||||
this.validateCountries(
|
||||
normalizedInput.map((r) => r.countries ?? []).flat(),
|
||||
sharedContext
|
||||
@@ -129,7 +112,7 @@ export default class RegionModuleService<
|
||||
] as const
|
||||
|
||||
// Assign the full country object so the ORM updates the relationship
|
||||
const [, dbCountries] = await promiseAll(validations)
|
||||
const [dbCountries] = await promiseAll(validations)
|
||||
const dbCountriesMap = new Map(dbCountries.map((d) => [d.iso_2, d]))
|
||||
let normalizedDbRegions = normalizedInput.map((region) =>
|
||||
removeUndefined({
|
||||
@@ -246,10 +229,6 @@ export default class RegionModuleService<
|
||||
}
|
||||
|
||||
const validations = [
|
||||
this.validateCurrencies(
|
||||
normalizedInput.map((d) => d.currency_code),
|
||||
sharedContext
|
||||
),
|
||||
this.validateCountries(
|
||||
normalizedInput.map((d) => d.countries ?? []).flat(),
|
||||
sharedContext
|
||||
@@ -257,7 +236,7 @@ export default class RegionModuleService<
|
||||
] as const
|
||||
|
||||
// Assign the full country object so the ORM updates the relationship
|
||||
const [, dbCountries] = await promiseAll(validations)
|
||||
const [dbCountries] = await promiseAll(validations)
|
||||
const dbCountriesMap = new Map(dbCountries.map((d) => [d.iso_2, d]))
|
||||
let normalizedDbRegions = normalizedInput.map((region) =>
|
||||
removeUndefined({
|
||||
@@ -280,41 +259,6 @@ export default class RegionModuleService<
|
||||
)
|
||||
}
|
||||
|
||||
private async validateCurrencies(
|
||||
currencyCodes: (string | undefined)[] | undefined,
|
||||
sharedContext: Context
|
||||
): Promise<void> {
|
||||
const normalizedCurrencyCodes = currencyCodes
|
||||
?.filter((c) => c !== undefined)
|
||||
.map((c) => c!.toLowerCase())
|
||||
|
||||
if (!normalizedCurrencyCodes?.length) {
|
||||
return
|
||||
}
|
||||
|
||||
const uniqueCurrencyCodes = Array.from(new Set(normalizedCurrencyCodes))
|
||||
const dbCurrencies = await this.currencyService_.list(
|
||||
{ code: uniqueCurrencyCodes },
|
||||
{},
|
||||
sharedContext
|
||||
)
|
||||
const dbCurrencyCodes = dbCurrencies.map((c) => c.code.toLowerCase())
|
||||
|
||||
if (uniqueCurrencyCodes.length !== dbCurrencyCodes.length) {
|
||||
const missingCurrencies = arrayDifference(
|
||||
uniqueCurrencyCodes,
|
||||
dbCurrencyCodes
|
||||
)
|
||||
|
||||
throw new MedusaError(
|
||||
MedusaError.Types.INVALID_DATA,
|
||||
`Currencies with codes: "${missingCurrencies.join(
|
||||
", "
|
||||
)}" were not found`
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
private async validateCountries(
|
||||
countries: string[] | undefined,
|
||||
sharedContext: Context
|
||||
@@ -369,13 +313,10 @@ export default class RegionModuleService<
|
||||
}
|
||||
|
||||
@InjectManager("baseRepository_")
|
||||
public async createDefaultCountriesAndCurrencies(
|
||||
public async createDefaultCountries(
|
||||
@MedusaContext() sharedContext: Context = {}
|
||||
): Promise<void> {
|
||||
await promiseAll([
|
||||
await this.maybeCreateCountries(sharedContext),
|
||||
await this.maybeCreateCurrencies(sharedContext),
|
||||
])
|
||||
await this.maybeCreateCountries(sharedContext)
|
||||
}
|
||||
|
||||
@InjectTransactionManager("baseRepository_")
|
||||
@@ -409,31 +350,4 @@ export default class RegionModuleService<
|
||||
await this.countryService_.create(countsToCreate, sharedContext)
|
||||
}
|
||||
}
|
||||
|
||||
@InjectTransactionManager("baseRepository_")
|
||||
private async maybeCreateCurrencies(
|
||||
@MedusaContext() sharedContext: Context
|
||||
): Promise<void> {
|
||||
const [currency] = await this.currencyService_.list(
|
||||
{},
|
||||
{ select: ["code"], take: 1 },
|
||||
sharedContext
|
||||
)
|
||||
|
||||
let currsToCreate: CreateCurrencyDTO[] = []
|
||||
if (!currency) {
|
||||
currsToCreate = Object.entries(DefaultsUtils.defaultCurrencies).map(
|
||||
([code, currency]) => ({
|
||||
code: code.toLowerCase(),
|
||||
symbol: currency.symbol,
|
||||
symbol_native: currency.symbol_native,
|
||||
name: currency.name,
|
||||
})
|
||||
)
|
||||
}
|
||||
|
||||
if (currsToCreate.length) {
|
||||
await this.currencyService_.create(currsToCreate, sharedContext)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -10,13 +10,6 @@ export type UpdateCountryRegion = {
|
||||
region_id: string
|
||||
}
|
||||
|
||||
export type CreateCurrencyDTO = {
|
||||
code: string
|
||||
symbol: string
|
||||
name: string
|
||||
symbol_native: string
|
||||
}
|
||||
|
||||
export type CreateCountryDTO = {
|
||||
iso_2: string
|
||||
iso_3: string
|
||||
|
||||
@@ -24,3 +24,4 @@ export * as UserTypes from "./user"
|
||||
export * as WorkflowTypes from "./workflow"
|
||||
export * as ApiKeyTypes from "./api-key"
|
||||
export * as StoreTypes from "./store"
|
||||
export * as CurrencyTypes from "./currency"
|
||||
|
||||
@@ -0,0 +1,38 @@
|
||||
import { BaseFilterable } from "../../dal"
|
||||
|
||||
/**
|
||||
* @interface
|
||||
*
|
||||
* A currency's data.
|
||||
*/
|
||||
export interface CurrencyDTO {
|
||||
/**
|
||||
* The ISO 3 code of the currency.
|
||||
*/
|
||||
code: string
|
||||
/**
|
||||
* The symbol of the currency.
|
||||
*/
|
||||
symbol: string
|
||||
/**
|
||||
* The symbol of the currecy in its native form. This is typically the symbol used when displaying a price.
|
||||
*/
|
||||
symbol_native: string
|
||||
/**
|
||||
* The name of the currency.
|
||||
*/
|
||||
name: string
|
||||
}
|
||||
|
||||
/**
|
||||
* @interface
|
||||
*
|
||||
* Filters to apply on a currency.
|
||||
*/
|
||||
export interface FilterableCurrencyProps
|
||||
extends BaseFilterable<FilterableCurrencyProps> {
|
||||
/**
|
||||
* The codes to filter the currencies by.
|
||||
*/
|
||||
code?: string[]
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
export * from "./currency"
|
||||
@@ -0,0 +1,2 @@
|
||||
export * from "./common"
|
||||
export * from "./service"
|
||||
@@ -0,0 +1,238 @@
|
||||
import { FindConfig } from "../common"
|
||||
import { RestoreReturn, SoftDeleteReturn } from "../dal"
|
||||
import { IModuleService } from "../modules-sdk"
|
||||
import { Context } from "../shared-context"
|
||||
import { FilterableCurrencyProps, CurrencyDTO } from "./common"
|
||||
|
||||
/**
|
||||
* The main service interface for the currency module.
|
||||
*/
|
||||
export interface ICurrencyModuleService extends IModuleService {
|
||||
/**
|
||||
* This method retrieves a currency by its code and and optionally based on the provided configurations.
|
||||
*
|
||||
* @param {string} code - The code of the currency to retrieve.
|
||||
* @param {FindConfig<CurrencyDTO>} config -
|
||||
* The configurations determining how the currency is retrieved. Its properties, such as `select` or `relations`, accept the
|
||||
* attributes or relations associated with a currency.
|
||||
* @param {Context} sharedContext - A context used to share resources, such as transaction manager, between the application and the module.
|
||||
* @returns {Promise<CurrencyDTO>} The retrieved currency.
|
||||
*
|
||||
* @example
|
||||
* A simple example that retrieves a currency by its code:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializeCurrencyModule,
|
||||
* } from "@medusajs/currency"
|
||||
*
|
||||
* async function retrieveCurrency (code: string) {
|
||||
* const currencyModule = await initializeCurrencyModule()
|
||||
*
|
||||
* const currency = await currencyModule.retrieve(
|
||||
* code
|
||||
* )
|
||||
*
|
||||
* // do something with the currency or return it
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* To specify attributes that should be retrieved:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializeCurrencyModule,
|
||||
* } from "@medusajs/currency"
|
||||
*
|
||||
* async function retrieveCurrency (code: string) {
|
||||
* const currencyModule = await initializeCurrencyModule()
|
||||
*
|
||||
* const currency = await currencyModule.retrieve(
|
||||
* code,
|
||||
* {
|
||||
* select: ["symbol_native"]
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currency or return it
|
||||
* }
|
||||
* ```
|
||||
*/
|
||||
retrieve(
|
||||
code: string,
|
||||
config?: FindConfig<CurrencyDTO>,
|
||||
sharedContext?: Context
|
||||
): Promise<CurrencyDTO>
|
||||
|
||||
/**
|
||||
* This method is used to retrieve a paginated list of currencies based on optional filters and configuration.
|
||||
*
|
||||
* @param {FilterableCurrencyProps} filters - The filters to apply on the retrieved currencies.
|
||||
* @param {FindConfig<CurrencyDTO>} config -
|
||||
* The configurations determining how the currencies are retrieved. Its properties, such as `select` or `relations`, accept the
|
||||
* attributes or relations associated with a currency.
|
||||
* @param {Context} sharedContext - A context used to share resources, such as transaction manager, between the application and the module.
|
||||
* @returns {Promise<CurrencyDTO[]>} The list of currencies.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* To retrieve a list of currencies using their codes:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializeCurrencyModule,
|
||||
* } from "@medusajs/currency"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[]) {
|
||||
* const currencyModule = await initializeCurrencyModule()
|
||||
*
|
||||
* const currencies = await currencyModule.list(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* To specify attributes that should be retrieved within the money amounts:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializeCurrencyModule,
|
||||
* } from "@medusajs/currency"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[]) {
|
||||
* const currencyModule = await initializeCurrencyModule()
|
||||
*
|
||||
* const currencies = await currencyModule.list(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* {
|
||||
* select: ["symbol_native"]
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* By default, only the first `15` records are retrieved. You can control pagination by specifying the `skip` and `take` properties of the `config` parameter:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializeCurrencyModule,
|
||||
* } from "@medusajs/currency"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[], skip: number, take: number) {
|
||||
* const currencyModule = await initializeCurrencyModule()
|
||||
*
|
||||
* const currencies = await currencyModule.list(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* {
|
||||
* select: ["symbol_native"],
|
||||
* skip,
|
||||
* take
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*/
|
||||
list(
|
||||
filters?: FilterableCurrencyProps,
|
||||
config?: FindConfig<CurrencyDTO>,
|
||||
sharedContext?: Context
|
||||
): Promise<CurrencyDTO[]>
|
||||
|
||||
/**
|
||||
* This method is used to retrieve a paginated list of currencies along with the total count of available currencies satisfying the provided filters.
|
||||
*
|
||||
* @param {FilterableCurrencyProps} filters - The filters to apply on the retrieved currencies.
|
||||
* @param {FindConfig<CurrencyDTO>} config -
|
||||
* The configurations determining how the currencies are retrieved. Its properties, such as `select` or `relations`, accept the
|
||||
* attributes or relations associated with a currency.
|
||||
* @param {Context} sharedContext - A context used to share resources, such as transaction manager, between the application and the module.
|
||||
* @returns {Promise<[CurrencyDTO[], number]>} The list of currencies along with the total count.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* To retrieve a list of currencies using their codes:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializeCurrencyModule,
|
||||
* } from "@medusajs/currency"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[]) {
|
||||
* const currencyModule = await initializeCurrencyModule()
|
||||
*
|
||||
* const [currencies, count] = await currencyModule.listAndCount(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* To specify attributes that should be retrieved within the money amounts:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializeCurrencyModule,
|
||||
* } from "@medusajs/currency"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[]) {
|
||||
* const currencyModule = await initializeCurrencyModule()
|
||||
*
|
||||
* const [currencies, count] = await currencyModule.listAndCount(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* {
|
||||
* select: ["symbol_native"]
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* By default, only the first `15` records are retrieved. You can control pagination by specifying the `skip` and `take` properties of the `config` parameter:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializeCurrencyModule,
|
||||
* } from "@medusajs/currency"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[], skip: number, take: number) {
|
||||
* const currencyModule = await initializeCurrencyModule()
|
||||
*
|
||||
* const [currencies, count] = await currencyModule.listAndCount(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* {
|
||||
* select: ["symbol_native"],
|
||||
* skip,
|
||||
* take
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*/
|
||||
listAndCount(
|
||||
filters?: FilterableCurrencyProps,
|
||||
config?: FindConfig<CurrencyDTO>,
|
||||
sharedContext?: Context
|
||||
): Promise<[CurrencyDTO[], number]>
|
||||
}
|
||||
@@ -34,3 +34,4 @@ export * from "./totals"
|
||||
export * from "./transaction-base"
|
||||
export * from "./user"
|
||||
export * from "./workflow"
|
||||
export * from "./currency"
|
||||
|
||||
@@ -1,86 +0,0 @@
|
||||
import { BaseFilterable } from "../../dal"
|
||||
|
||||
/**
|
||||
* @interface
|
||||
*
|
||||
* A currency's data.
|
||||
*/
|
||||
export interface CurrencyDTO {
|
||||
/**
|
||||
* The code of the currency.
|
||||
*/
|
||||
code: string
|
||||
/**
|
||||
* The symbol of the currency.
|
||||
*/
|
||||
symbol?: string
|
||||
/**
|
||||
* The symbol of the currecy in its native form. This is typically the symbol used when displaying a price.
|
||||
*/
|
||||
symbol_native?: string
|
||||
/**
|
||||
* The name of the currency.
|
||||
*/
|
||||
name?: string
|
||||
}
|
||||
|
||||
/**
|
||||
* @interface
|
||||
*
|
||||
* A currency to create.
|
||||
*/
|
||||
export interface CreateCurrencyDTO {
|
||||
/**
|
||||
* The code of the currency.
|
||||
*/
|
||||
code: string
|
||||
/**
|
||||
* The symbol of the currency.
|
||||
*/
|
||||
symbol: string
|
||||
/**
|
||||
* The symbol of the currecy in its native form. This is typically the symbol used when displaying a price.
|
||||
*/
|
||||
symbol_native: string
|
||||
/**
|
||||
* The name of the currency.
|
||||
*/
|
||||
name: string
|
||||
}
|
||||
|
||||
/**
|
||||
* @interface
|
||||
*
|
||||
* The data to update in a currency. The `code` is used to identify which currency to update.
|
||||
*/
|
||||
export interface UpdateCurrencyDTO {
|
||||
/**
|
||||
* The code of the currency to update.
|
||||
*/
|
||||
code: string
|
||||
/**
|
||||
* The symbol of the currency.
|
||||
*/
|
||||
symbol?: string
|
||||
/**
|
||||
* The symbol of the currecy in its native form. This is typically the symbol used when displaying a price.
|
||||
*/
|
||||
symbol_native?: string
|
||||
/**
|
||||
* The name of the currency.
|
||||
*/
|
||||
name?: string
|
||||
}
|
||||
|
||||
/**
|
||||
* @interface
|
||||
*
|
||||
* Filters to apply on a currency.
|
||||
*/
|
||||
export interface FilterableCurrencyProps
|
||||
extends BaseFilterable<FilterableCurrencyProps> {
|
||||
/**
|
||||
* The codes to filter the currencies by.
|
||||
*/
|
||||
code?: string[]
|
||||
}
|
||||
@@ -1,4 +1,3 @@
|
||||
export * from "./currency"
|
||||
export * from "./money-amount"
|
||||
export * from "./price-rule"
|
||||
export * from "./price-set"
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
import { BaseFilterable } from "../../dal";
|
||||
import { CreateCurrencyDTO, CurrencyDTO } from "./currency";
|
||||
import { PriceSetMoneyAmountDTO } from "./price-set-money-amount";
|
||||
import { BaseFilterable } from "../../dal"
|
||||
import { PriceSetMoneyAmountDTO } from "./price-set-money-amount"
|
||||
|
||||
/**
|
||||
* @interface
|
||||
@@ -16,12 +15,6 @@ export interface MoneyAmountDTO {
|
||||
* The currency code of this money amount.
|
||||
*/
|
||||
currency_code?: string
|
||||
/**
|
||||
* The money amount's currency.
|
||||
*
|
||||
* @expandable
|
||||
*/
|
||||
currency?: CurrencyDTO
|
||||
/**
|
||||
* The price of this money amount.
|
||||
*/
|
||||
@@ -66,10 +59,6 @@ export interface CreateMoneyAmountDTO {
|
||||
* The currency code of this money amount.
|
||||
*/
|
||||
currency_code: string
|
||||
/**
|
||||
* The currency of this money amount.
|
||||
*/
|
||||
currency?: CreateCurrencyDTO
|
||||
/**
|
||||
* The amount of this money amount.
|
||||
*/
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
import { BaseFilterable } from "../../dal"
|
||||
import { PriceSetDTO } from "./price-set"
|
||||
import { PriceSetMoneyAmountDTO } from "./price-set-money-amount"
|
||||
import { RuleTypeDTO } from "./rule-type"
|
||||
|
||||
export interface PriceSetRuleTypeDTO {
|
||||
|
||||
@@ -3,7 +3,6 @@ import {
|
||||
AddPricesDTO,
|
||||
AddRulesDTO,
|
||||
CalculatedPriceSet,
|
||||
CreateCurrencyDTO,
|
||||
CreateMoneyAmountDTO,
|
||||
CreatePriceListDTO,
|
||||
CreatePriceListRuleDTO,
|
||||
@@ -11,8 +10,6 @@ import {
|
||||
CreatePriceSetDTO,
|
||||
CreatePriceSetMoneyAmountRulesDTO,
|
||||
CreateRuleTypeDTO,
|
||||
CurrencyDTO,
|
||||
FilterableCurrencyProps,
|
||||
FilterableMoneyAmountProps,
|
||||
FilterablePriceListProps,
|
||||
FilterablePriceListRuleProps,
|
||||
@@ -34,7 +31,6 @@ import {
|
||||
RemovePriceSetRulesDTO,
|
||||
RuleTypeDTO,
|
||||
SetPriceListRulesDTO,
|
||||
UpdateCurrencyDTO,
|
||||
UpdateMoneyAmountDTO,
|
||||
UpdatePriceListDTO,
|
||||
UpdatePriceListRuleDTO,
|
||||
@@ -935,7 +931,7 @@ export interface IPricingModuleService extends IModuleService {
|
||||
* const moneyAmount = await pricingService.retrieveMoneyAmount(
|
||||
* moneyAmountId,
|
||||
* {
|
||||
* relations: ["currency"]
|
||||
* relations: ["price_set_money_amount"]
|
||||
* }
|
||||
* )
|
||||
*
|
||||
@@ -996,7 +992,7 @@ export interface IPricingModuleService extends IModuleService {
|
||||
* id: moneyAmountIds
|
||||
* },
|
||||
* {
|
||||
* relations: ["currency"]
|
||||
* relations: ["price_set_money_amount"]
|
||||
* }
|
||||
* )
|
||||
*
|
||||
@@ -1019,7 +1015,7 @@ export interface IPricingModuleService extends IModuleService {
|
||||
* id: moneyAmountIds
|
||||
* },
|
||||
* {
|
||||
* relations: ["currency"],
|
||||
* relations: ["price_set_money_amount"],
|
||||
* skip,
|
||||
* take
|
||||
* }
|
||||
@@ -1051,7 +1047,7 @@ export interface IPricingModuleService extends IModuleService {
|
||||
* ]
|
||||
* },
|
||||
* {
|
||||
* relations: ["currency"],
|
||||
* relations: ["price_set_money_amount"],
|
||||
* skip,
|
||||
* take
|
||||
* }
|
||||
@@ -1114,7 +1110,7 @@ export interface IPricingModuleService extends IModuleService {
|
||||
* id: moneyAmountIds
|
||||
* },
|
||||
* {
|
||||
* relations: ["currency"]
|
||||
* relations: ["price_set_money_amount"]
|
||||
* }
|
||||
* )
|
||||
*
|
||||
@@ -1137,7 +1133,7 @@ export interface IPricingModuleService extends IModuleService {
|
||||
* id: moneyAmountIds
|
||||
* },
|
||||
* {
|
||||
* relations: ["currency"],
|
||||
* relations: ["price_set_money_amount"],
|
||||
* skip,
|
||||
* take
|
||||
* }
|
||||
@@ -1169,7 +1165,7 @@ export interface IPricingModuleService extends IModuleService {
|
||||
* ]
|
||||
* },
|
||||
* {
|
||||
* relations: ["currency"],
|
||||
* relations: ["price_set_money_amount"],
|
||||
* skip,
|
||||
* take
|
||||
* }
|
||||
@@ -1333,320 +1329,6 @@ export interface IPricingModuleService extends IModuleService {
|
||||
sharedContext?: Context
|
||||
): Promise<Record<string, string[]> | void>
|
||||
|
||||
/**
|
||||
* This method retrieves a currency by its code and and optionally based on the provided configurations.
|
||||
*
|
||||
* @param {string} code - The code of the currency to retrieve.
|
||||
* @param {FindConfig<CurrencyDTO>} config -
|
||||
* The configurations determining how the currency is retrieved. Its properties, such as `select` or `relations`, accept the
|
||||
* attributes or relations associated with a currency.
|
||||
* @param {Context} sharedContext - A context used to share resources, such as transaction manager, between the application and the module.
|
||||
* @returns {Promise<CurrencyDTO>} The retrieved currency.
|
||||
*
|
||||
* @example
|
||||
* A simple example that retrieves a currency by its code:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function retrieveCurrency (code: string) {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const currency = await pricingService.retrieveCurrency(
|
||||
* code
|
||||
* )
|
||||
*
|
||||
* // do something with the currency or return it
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* To specify attributes that should be retrieved:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function retrieveCurrency (code: string) {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const currency = await pricingService.retrieveCurrency(
|
||||
* code,
|
||||
* {
|
||||
* select: ["symbol_native"]
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currency or return it
|
||||
* }
|
||||
* ```
|
||||
*/
|
||||
retrieveCurrency(
|
||||
code: string,
|
||||
config?: FindConfig<CurrencyDTO>,
|
||||
sharedContext?: Context
|
||||
): Promise<CurrencyDTO>
|
||||
|
||||
/**
|
||||
* This method is used to retrieve a paginated list of currencies based on optional filters and configuration.
|
||||
*
|
||||
* @param {FilterableCurrencyProps} filters - The filters to apply on the retrieved currencies.
|
||||
* @param {FindConfig<CurrencyDTO>} config -
|
||||
* The configurations determining how the currencies are retrieved. Its properties, such as `select` or `relations`, accept the
|
||||
* attributes or relations associated with a currency.
|
||||
* @param {Context} sharedContext - A context used to share resources, such as transaction manager, between the application and the module.
|
||||
* @returns {Promise<CurrencyDTO[]>} The list of currencies.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* To retrieve a list of currencies using their codes:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[]) {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const currencies = await pricingService.listCurrencies(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* To specify attributes that should be retrieved within the money amounts:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[]) {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const currencies = await pricingService.listCurrencies(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* {
|
||||
* select: ["symbol_native"]
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* By default, only the first `15` records are retrieved. You can control pagination by specifying the `skip` and `take` properties of the `config` parameter:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[], skip: number, take: number) {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const currencies = await pricingService.listCurrencies(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* {
|
||||
* select: ["symbol_native"],
|
||||
* skip,
|
||||
* take
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*/
|
||||
listCurrencies(
|
||||
filters?: FilterableCurrencyProps,
|
||||
config?: FindConfig<CurrencyDTO>,
|
||||
sharedContext?: Context
|
||||
): Promise<CurrencyDTO[]>
|
||||
|
||||
/**
|
||||
* This method is used to retrieve a paginated list of currencies along with the total count of available currencies satisfying the provided filters.
|
||||
*
|
||||
* @param {FilterableCurrencyProps} filters - The filters to apply on the retrieved currencies.
|
||||
* @param {FindConfig<CurrencyDTO>} config -
|
||||
* The configurations determining how the currencies are retrieved. Its properties, such as `select` or `relations`, accept the
|
||||
* attributes or relations associated with a currency.
|
||||
* @param {Context} sharedContext - A context used to share resources, such as transaction manager, between the application and the module.
|
||||
* @returns {Promise<[CurrencyDTO[], number]>} The list of currencies along with the total count.
|
||||
*
|
||||
* @example
|
||||
*
|
||||
* To retrieve a list of currencies using their codes:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[]) {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const [currencies, count] = await pricingService.listAndCountCurrencies(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* To specify attributes that should be retrieved within the money amounts:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[]) {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const [currencies, count] = await pricingService.listAndCountCurrencies(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* {
|
||||
* select: ["symbol_native"]
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* By default, only the first `15` records are retrieved. You can control pagination by specifying the `skip` and `take` properties of the `config` parameter:
|
||||
*
|
||||
* ```ts
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function retrieveCurrencies (codes: string[], skip: number, take: number) {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const [currencies, count] = await pricingService.listAndCountCurrencies(
|
||||
* {
|
||||
* code: codes
|
||||
* },
|
||||
* {
|
||||
* select: ["symbol_native"],
|
||||
* skip,
|
||||
* take
|
||||
* }
|
||||
* )
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
* ```
|
||||
*/
|
||||
listAndCountCurrencies(
|
||||
filters?: FilterableCurrencyProps,
|
||||
config?: FindConfig<CurrencyDTO>,
|
||||
sharedContext?: Context
|
||||
): Promise<[CurrencyDTO[], number]>
|
||||
|
||||
/**
|
||||
* This method is used to create new currencies.
|
||||
*
|
||||
* @param {CreateCurrencyDTO[]} data - The currencies to create.
|
||||
* @param {Context} sharedContext - A context used to share resources, such as transaction manager, between the application and the module.
|
||||
* @returns {Promise<CurrencyDTO[]>} The list of created currencies.
|
||||
*
|
||||
* @example
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function createCurrencies () {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const currencies = await pricingService.createCurrencies([
|
||||
* {
|
||||
* code: "USD",
|
||||
* symbol: "$",
|
||||
* symbol_native: "$",
|
||||
* name: "US Dollar",
|
||||
* }
|
||||
* ])
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
*/
|
||||
createCurrencies(
|
||||
data: CreateCurrencyDTO[],
|
||||
sharedContext?: Context
|
||||
): Promise<CurrencyDTO[]>
|
||||
|
||||
/**
|
||||
* This method is used to update existing currencies with the provided data. In each currency object, the currency code must be provided to identify which currency to update.
|
||||
*
|
||||
* @param {UpdateCurrencyDTO[]} data - The currencies to update, each having the attributes that should be updated in a currency.
|
||||
* @param {Context} sharedContext - A context used to share resources, such as transaction manager, between the application and the module.
|
||||
* @returns {Promise<CurrencyDTO[]>} The list of updated currencies.
|
||||
*
|
||||
* @example
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function updateCurrencies () {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* const currencies = await pricingService.updateCurrencies([
|
||||
* {
|
||||
* code: "USD",
|
||||
* symbol: "$",
|
||||
* }
|
||||
* ])
|
||||
*
|
||||
* // do something with the currencies or return them
|
||||
* }
|
||||
*/
|
||||
updateCurrencies(
|
||||
data: UpdateCurrencyDTO[],
|
||||
sharedContext?: Context
|
||||
): Promise<CurrencyDTO[]>
|
||||
|
||||
/**
|
||||
* This method is used to delete currencies based on their currency code.
|
||||
*
|
||||
* @param {string[]} currencyCodes - Currency codes of the currencies to delete.
|
||||
* @param {Context} sharedContext - A context used to share resources, such as transaction manager, between the application and the module.
|
||||
* @returns {Promise<void>} Resolves once the currencies are deleted.
|
||||
*
|
||||
* @example
|
||||
* import {
|
||||
* initialize as initializePricingModule,
|
||||
* } from "@medusajs/pricing"
|
||||
*
|
||||
* async function deleteCurrencies () {
|
||||
* const pricingService = await initializePricingModule()
|
||||
*
|
||||
* await pricingService.deleteCurrencies(["USD"])
|
||||
*
|
||||
* }
|
||||
*/
|
||||
deleteCurrencies(
|
||||
currencyCodes: string[],
|
||||
sharedContext?: Context
|
||||
): Promise<void>
|
||||
|
||||
/**
|
||||
* This method is used to retrieve a rule type by its ID and and optionally based on the provided configurations.
|
||||
*
|
||||
|
||||
@@ -19,15 +19,10 @@ export interface RegionDTO {
|
||||
*/
|
||||
currency_code: string
|
||||
|
||||
/**
|
||||
* The associated region currency.
|
||||
*/
|
||||
currency: RegionCurrencyDTO
|
||||
|
||||
/**
|
||||
* The countries of the region.
|
||||
*/
|
||||
countries: CountryDTO[]
|
||||
countries: RegionCountryDTO[]
|
||||
metadata?: Record<string, any>
|
||||
created_at: string
|
||||
updated_at: string
|
||||
@@ -36,7 +31,7 @@ export interface RegionDTO {
|
||||
/**
|
||||
* The country details.
|
||||
*/
|
||||
export interface CountryDTO {
|
||||
export interface RegionCountryDTO {
|
||||
/**
|
||||
* The ID of the country.
|
||||
*/
|
||||
@@ -99,97 +94,6 @@ export interface FilterableRegionProps
|
||||
updated_at?: OperatorMap<string>
|
||||
}
|
||||
|
||||
/**
|
||||
* The details of a region's country.
|
||||
*/
|
||||
export interface RegionCountryDTO {
|
||||
/**
|
||||
* The ID of the country.
|
||||
*/
|
||||
id: string
|
||||
|
||||
/**
|
||||
* The ISO 2 code of the country.
|
||||
*/
|
||||
iso_2: string
|
||||
|
||||
/**
|
||||
* The ISO 3 code of the country.
|
||||
*/
|
||||
iso_3: string
|
||||
|
||||
/**
|
||||
* The code number of the country.
|
||||
*/
|
||||
num_code: number
|
||||
|
||||
/**
|
||||
* The name of the country.
|
||||
*/
|
||||
name: string
|
||||
|
||||
/**
|
||||
* The display name of the country.
|
||||
*/
|
||||
display_name: string
|
||||
}
|
||||
|
||||
/**
|
||||
* The details of a region's currency
|
||||
*/
|
||||
export interface RegionCurrencyDTO {
|
||||
/**
|
||||
* The code of the currency.
|
||||
*/
|
||||
code: string
|
||||
|
||||
/**
|
||||
* The symbol of the currency.
|
||||
*/
|
||||
symbol: string
|
||||
|
||||
/**
|
||||
* The name of the currency.
|
||||
*/
|
||||
name: string
|
||||
|
||||
/**
|
||||
* The symbol native of the currency.
|
||||
*/
|
||||
symbol_native: string
|
||||
}
|
||||
|
||||
/**
|
||||
* The filters to apply on the retrieved region's currencies.
|
||||
*/
|
||||
export interface FilterableRegionCurrencyProps
|
||||
extends BaseFilterable<FilterableRegionCurrencyProps> {
|
||||
/**
|
||||
* The IDs to filter the currencies by.
|
||||
*/
|
||||
id?: string[] | string
|
||||
|
||||
/**
|
||||
* Filter currencies by their code.
|
||||
*/
|
||||
code?: string[] | string
|
||||
|
||||
/**
|
||||
* Filter currencies by their symbol.
|
||||
*/
|
||||
symbol?: string[] | string
|
||||
|
||||
/**
|
||||
* Filter currencies by their name.
|
||||
*/
|
||||
name?: string[] | string
|
||||
|
||||
/**
|
||||
* Filter currencies by their native symbol.
|
||||
*/
|
||||
symbol_native?: string[] | string
|
||||
}
|
||||
|
||||
/**
|
||||
* The filters to apply on the retrieved region's countries.
|
||||
*/
|
||||
|
||||
@@ -1,5 +1,3 @@
|
||||
import { RegionCurrencyDTO } from "./common"
|
||||
|
||||
/**
|
||||
* The region to be created.
|
||||
*/
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user