feat: Modify api key and sales channel link to use modules and add test (#6546)
This commit is contained in:
1 parent
55275f0eba
commit
196e821ff2
12 files changed
+146
-17
No files matched your search
+105
@@ -0,0 +1,105 @@
|
|||||||
|
import { ModuleRegistrationName, Modules } from "@medusajs/modules-sdk"
|
||||||
|
import {
|
||||||
|
IApiKeyModuleService,
|
||||||
|
ISalesChannelModuleService,
|
||||||
|
} from "@medusajs/types"
|
||||||
|
import path from "path"
|
||||||
|
import { startBootstrapApp } from "../../../environment-helpers/bootstrap-app"
|
||||||
|
import { getContainer } from "../../../environment-helpers/use-container"
|
||||||
|
import { initDb, useDb } from "../../../environment-helpers/use-db"
|
||||||
|
import { remoteQueryObjectFromString } from "@medusajs/utils"
|
||||||
|
|
||||||
|
jest.setTimeout(50000)
|
||||||
|
|
||||||
|
const env = { MEDUSA_FF_MEDUSA_V2: true }
|
||||||
|
|
||||||
|
describe("Publishable keys and sales channel link", () => {
|
||||||
|
let dbConnection
|
||||||
|
let appContainer
|
||||||
|
let shutdownServer
|
||||||
|
let apiKeyModule: IApiKeyModuleService
|
||||||
|
let scModuleService: ISalesChannelModuleService
|
||||||
|
let remoteQuery
|
||||||
|
let remoteLink
|
||||||
|
|
||||||
|
beforeAll(async () => {
|
||||||
|
const cwd = path.resolve(path.join(__dirname, "..", ".."))
|
||||||
|
dbConnection = await initDb({ cwd, env } as any)
|
||||||
|
shutdownServer = await startBootstrapApp({ cwd, env })
|
||||||
|
appContainer = getContainer()
|
||||||
|
apiKeyModule = appContainer.resolve(ModuleRegistrationName.API_KEY)
|
||||||
|
scModuleService = appContainer.resolve(ModuleRegistrationName.SALES_CHANNEL)
|
||||||
|
remoteQuery = appContainer.resolve("remoteQuery")
|
||||||
|
remoteLink = appContainer.resolve("remoteLink")
|
||||||
|
})
|
||||||
|
|
||||||
|
afterAll(async () => {
|
||||||
|
const db = useDb()
|
||||||
|
await db.shutdown()
|
||||||
|
await shutdownServer()
|
||||||
|
})
|
||||||
|
|
||||||
|
afterEach(async () => {
|
||||||
|
const db = useDb()
|
||||||
|
await db.teardown()
|
||||||
|
})
|
||||||
|
|
||||||
|
it("should query api key and sales channels link with remote query", async () => {
|
||||||
|
const salesChannel = await scModuleService.create({
|
||||||
|
name: "Webshop",
|
||||||
|
})
|
||||||
|
|
||||||
|
const apiKeys = await apiKeyModule.create([
|
||||||
|
{
|
||||||
|
title: "Api key",
|
||||||
|
type: "publishable",
|
||||||
|
created_by: "test",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Api key 2",
|
||||||
|
type: "publishable",
|
||||||
|
created_by: "test",
|
||||||
|
},
|
||||||
|
])
|
||||||
|
|
||||||
|
await remoteLink.create([
|
||||||
|
{
|
||||||
|
[Modules.API_KEY]: {
|
||||||
|
publishable_key_id: apiKeys[0].id,
|
||||||
|
},
|
||||||
|
[Modules.SALES_CHANNEL]: {
|
||||||
|
sales_channel_id: salesChannel.id,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
[Modules.API_KEY]: {
|
||||||
|
publishable_key_id: apiKeys[1].id,
|
||||||
|
},
|
||||||
|
[Modules.SALES_CHANNEL]: {
|
||||||
|
sales_channel_id: salesChannel.id,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
])
|
||||||
|
|
||||||
|
const queryObject = remoteQueryObjectFromString({
|
||||||
|
entryPoint: "api_key",
|
||||||
|
variables: {
|
||||||
|
filters: { token: apiKeys[0].token },
|
||||||
|
},
|
||||||
|
fields: ["id", "sales_channels.id"],
|
||||||
|
})
|
||||||
|
const keyLinks = await remoteQuery(queryObject)
|
||||||
|
|
||||||
|
expect(keyLinks).toHaveLength(1)
|
||||||
|
expect(keyLinks).toEqual(
|
||||||
|
expect.arrayContaining([
|
||||||
|
expect.objectContaining({
|
||||||
|
id: apiKeys[0].id,
|
||||||
|
sales_channels: expect.arrayContaining([
|
||||||
|
expect.objectContaining({ id: salesChannel.id }),
|
||||||
|
]),
|
||||||
|
}),
|
||||||
|
])
|
||||||
|
)
|
||||||
|
})
|
||||||
|
})
|
||||||
@@ -284,6 +284,19 @@ moduleIntegrationTestRunner({
|
|||||||
expect(apiKeysInDatabase).toHaveLength(2)
|
expect(apiKeysInDatabase).toHaveLength(2)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
it("should only return keys with matching token", async function () {
|
||||||
|
const created = await service.create([
|
||||||
|
createPublishableKeyFixture,
|
||||||
|
createPublishableKeyFixture,
|
||||||
|
])
|
||||||
|
|
||||||
|
const apiKeysInDatabase = await service.list({
|
||||||
|
token: created[0].token,
|
||||||
|
})
|
||||||
|
expect(apiKeysInDatabase).toHaveLength(1)
|
||||||
|
expect(apiKeysInDatabase[0].token).toEqual(created[0].token)
|
||||||
|
})
|
||||||
|
|
||||||
it("should not return the token and salt for secret keys when listing", async function () {
|
it("should not return the token and salt for secret keys when listing", async function () {
|
||||||
await service.create([createSecretKeyFixture])
|
await service.create([createSecretKeyFixture])
|
||||||
|
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ export const joinerConfig: ModuleJoinerConfig = {
|
|||||||
linkableKeys: LinkableKeys,
|
linkableKeys: LinkableKeys,
|
||||||
alias: [
|
alias: [
|
||||||
{
|
{
|
||||||
name: ["api-key", "api-keys"],
|
name: ["api_key", "api_keys"],
|
||||||
args: { entity: ApiKey.name },
|
args: { entity: ApiKey.name },
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ import { CreateApiKeyDTO, IApiKeyModuleService } from "@medusajs/types"
|
|||||||
import { StepResponse, createStep } from "@medusajs/workflows-sdk"
|
import { StepResponse, createStep } from "@medusajs/workflows-sdk"
|
||||||
|
|
||||||
type CreateApiKeysStepInput = {
|
type CreateApiKeysStepInput = {
|
||||||
apiKeysData: CreateApiKeyDTO[]
|
api_keys: CreateApiKeyDTO[]
|
||||||
}
|
}
|
||||||
|
|
||||||
export const createApiKeysStepId = "create-api-keys"
|
export const createApiKeysStepId = "create-api-keys"
|
||||||
@@ -13,7 +13,7 @@ export const createApiKeysStep = createStep(
|
|||||||
const service = container.resolve<IApiKeyModuleService>(
|
const service = container.resolve<IApiKeyModuleService>(
|
||||||
ModuleRegistrationName.API_KEY
|
ModuleRegistrationName.API_KEY
|
||||||
)
|
)
|
||||||
const created = await service.create(data.apiKeysData)
|
const created = await service.create(data.api_keys)
|
||||||
return new StepResponse(
|
return new StepResponse(
|
||||||
created,
|
created,
|
||||||
created.map((apiKey) => apiKey.id)
|
created.map((apiKey) => apiKey.id)
|
||||||
|
|||||||
@@ -2,7 +2,7 @@ import { ApiKeyDTO, CreateApiKeyDTO } from "@medusajs/types"
|
|||||||
import { WorkflowData, createWorkflow } from "@medusajs/workflows-sdk"
|
import { WorkflowData, createWorkflow } from "@medusajs/workflows-sdk"
|
||||||
import { createApiKeysStep } from "../steps"
|
import { createApiKeysStep } from "../steps"
|
||||||
|
|
||||||
type WorkflowInput = { apiKeysData: CreateApiKeyDTO[] }
|
type WorkflowInput = { api_keys: CreateApiKeyDTO[] }
|
||||||
|
|
||||||
export const createApiKeysWorkflowId = "create-api-keys"
|
export const createApiKeysWorkflowId = "create-api-keys"
|
||||||
export const createApiKeysWorkflow = createWorkflow(
|
export const createApiKeysWorkflow = createWorkflow(
|
||||||
|
|||||||
@@ -9,4 +9,3 @@ export * from "./product-shipping-profile"
|
|||||||
export * from "./product-variant-inventory-item"
|
export * from "./product-variant-inventory-item"
|
||||||
export * from "./product-variant-price-set"
|
export * from "./product-variant-price-set"
|
||||||
export * from "./publishable-api-key-sales-channel"
|
export * from "./publishable-api-key-sales-channel"
|
||||||
|
|
||||||
@@ -1,5 +1,6 @@
|
|||||||
import { ModuleJoinerConfig } from "@medusajs/types"
|
import { ModuleJoinerConfig } from "@medusajs/types"
|
||||||
import { LINKS } from "../links"
|
import { LINKS } from "../links"
|
||||||
|
import { Modules } from "@medusajs/modules-sdk"
|
||||||
|
|
||||||
export const PublishableApiKeySalesChannel: ModuleJoinerConfig = {
|
export const PublishableApiKeySalesChannel: ModuleJoinerConfig = {
|
||||||
serviceName: LINKS.PublishableApiKeySalesChannel,
|
serviceName: LINKS.PublishableApiKeySalesChannel,
|
||||||
@@ -19,14 +20,14 @@ export const PublishableApiKeySalesChannel: ModuleJoinerConfig = {
|
|||||||
primaryKeys: ["id", "publishable_key_id", "sales_channel_id"],
|
primaryKeys: ["id", "publishable_key_id", "sales_channel_id"],
|
||||||
relationships: [
|
relationships: [
|
||||||
{
|
{
|
||||||
serviceName: "publishableApiKeyService",
|
serviceName: Modules.API_KEY,
|
||||||
isInternalService: true,
|
isInternalService: true,
|
||||||
primaryKey: "id",
|
primaryKey: "id",
|
||||||
foreignKey: "publishable_key_id",
|
foreignKey: "publishable_key_id",
|
||||||
alias: "publishable_key",
|
alias: "api_key",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
serviceName: "salesChannelService",
|
serviceName: Modules.SALES_CHANNEL,
|
||||||
isInternalService: true,
|
isInternalService: true,
|
||||||
primaryKey: "id",
|
primaryKey: "id",
|
||||||
foreignKey: "sales_channel_id",
|
foreignKey: "sales_channel_id",
|
||||||
@@ -35,7 +36,7 @@ export const PublishableApiKeySalesChannel: ModuleJoinerConfig = {
|
|||||||
],
|
],
|
||||||
extends: [
|
extends: [
|
||||||
{
|
{
|
||||||
serviceName: "publishableApiKeyService",
|
serviceName: Modules.API_KEY,
|
||||||
fieldAlias: {
|
fieldAlias: {
|
||||||
sales_channels: "sales_channels_link.sales_channel",
|
sales_channels: "sales_channels_link.sales_channel",
|
||||||
},
|
},
|
||||||
@@ -49,13 +50,16 @@ export const PublishableApiKeySalesChannel: ModuleJoinerConfig = {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
serviceName: "salesChannelService",
|
serviceName: Modules.SALES_CHANNEL,
|
||||||
|
fieldAlias: {
|
||||||
|
api_keys: "api_keys_link.api_key",
|
||||||
|
},
|
||||||
relationship: {
|
relationship: {
|
||||||
serviceName: LINKS.PublishableApiKeySalesChannel,
|
serviceName: LINKS.PublishableApiKeySalesChannel,
|
||||||
isInternalService: true,
|
isInternalService: true,
|
||||||
primaryKey: "sales_channel_id",
|
primaryKey: "sales_channel_id",
|
||||||
foreignKey: "id",
|
foreignKey: "id",
|
||||||
alias: "publishable_keys_link",
|
alias: "api_keys_link",
|
||||||
isList: true,
|
isList: true,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -41,8 +41,8 @@ export const LINKS = {
|
|||||||
"sales_channel_id"
|
"sales_channel_id"
|
||||||
),
|
),
|
||||||
PublishableApiKeySalesChannel: composeLinkName(
|
PublishableApiKeySalesChannel: composeLinkName(
|
||||||
"publishableApiKeyService",
|
Modules.API_KEY,
|
||||||
"publishable_key_id",
|
"api_key_id",
|
||||||
Modules.SALES_CHANNEL,
|
Modules.SALES_CHANNEL,
|
||||||
"sales_channel_id"
|
"sales_channel_id"
|
||||||
),
|
),
|
||||||
|
|||||||
@@ -20,7 +20,7 @@ export const GET = async (
|
|||||||
const variables = { id: req.params.id }
|
const variables = { id: req.params.id }
|
||||||
|
|
||||||
const queryObject = remoteQueryObjectFromString({
|
const queryObject = remoteQueryObjectFromString({
|
||||||
entryPoint: "api-key",
|
entryPoint: "api_key",
|
||||||
variables,
|
variables,
|
||||||
fields: defaultAdminApiKeyFields,
|
fields: defaultAdminApiKeyFields,
|
||||||
})
|
})
|
||||||
@@ -66,7 +66,7 @@ export const DELETE = async (
|
|||||||
|
|
||||||
res.status(200).json({
|
res.status(200).json({
|
||||||
id,
|
id,
|
||||||
object: "api-key",
|
object: "api_key",
|
||||||
deleted: true,
|
deleted: true,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@@ -15,7 +15,7 @@ export const GET = async (
|
|||||||
const remoteQuery = req.scope.resolve("remoteQuery")
|
const remoteQuery = req.scope.resolve("remoteQuery")
|
||||||
|
|
||||||
const queryObject = remoteQueryObjectFromString({
|
const queryObject = remoteQueryObjectFromString({
|
||||||
entryPoint: "api-key",
|
entryPoint: "api_key",
|
||||||
variables: {
|
variables: {
|
||||||
filters: req.filterableFields,
|
filters: req.filterableFields,
|
||||||
order: req.listConfig.order,
|
order: req.listConfig.order,
|
||||||
@@ -47,7 +47,7 @@ export const POST = async (
|
|||||||
]
|
]
|
||||||
|
|
||||||
const { result, errors } = await createApiKeysWorkflow(req.scope).run({
|
const { result, errors } = await createApiKeysWorkflow(req.scope).run({
|
||||||
input: { apiKeysData: input },
|
input: { api_keys: input },
|
||||||
throwOnError: false,
|
throwOnError: false,
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|||||||
@@ -34,6 +34,13 @@ export class AdminGetApiKeysParams extends extendedFindParamsMixin({
|
|||||||
@IsOptional()
|
@IsOptional()
|
||||||
title?: string | string[]
|
title?: string | string[]
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Filter by token
|
||||||
|
*/
|
||||||
|
@IsString({ each: true })
|
||||||
|
@IsOptional()
|
||||||
|
token?: string | string[]
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Filter by type
|
* Filter by type
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -17,6 +17,7 @@ export interface ApiKeyDTO {
|
|||||||
export interface FilterableApiKeyProps
|
export interface FilterableApiKeyProps
|
||||||
extends BaseFilterable<FilterableApiKeyProps> {
|
extends BaseFilterable<FilterableApiKeyProps> {
|
||||||
id?: string | string[]
|
id?: string | string[]
|
||||||
|
token?: string | string[]
|
||||||
title?: string | string[]
|
title?: string | string[]
|
||||||
type?: ApiKeyType
|
type?: ApiKeyType
|
||||||
}
|
}
|
||||||
Reference in new issue
Block a user