{"version":3,"file":"config.cjs","names":["BosConfigSchema","isPlainObject","rebuildOrderedConfig","bosConfigMerger","resolveExtendsRef","getNetworkIdForAccount","fetchBosConfigFromFastKv","mergeBosConfigWithExtends"],"sources":["../src/config.ts"],"sourcesContent":["import { existsSync, mkdirSync, readFileSync, writeFileSync } from \"node:fs\";\nimport { dirname, isAbsolute, join, resolve } from \"node:path\";\nimport { fetchBosConfigFromFastKv } from \"./fastkv\";\nimport {\n  type BosEnv,\n  bosConfigMerger,\n  isPlainObject,\n  mergeBosConfigWithExtends,\n  type ResolvedConfigMeta,\n  rebuildOrderedConfig,\n  resolveExtendsRef,\n} from \"./merge\";\nimport { getNetworkIdForAccount } from \"./network\";\nimport type {\n  BosConfig,\n  BosConfigInput,\n  BosPluginRef,\n  ExtendsConfig,\n  PluginEntryValue,\n  RuntimeConfig,\n  RuntimePluginConfig,\n} from \"./types\";\nimport { BosConfigSchema } from \"./types\";\n\nconst LOCAL_PREFIX = \"local:\";\nconst DEFAULT_HOST_PORT = 3000;\nconst RESOLVED_CONFIG_FILENAME = \"bos.resolved-config.json\";\n\ninterface RuntimeTarget {\n  source: \"local\" | \"remote\";\n  url: string;\n  localPath?: string;\n  port?: number;\n}\n\nlet cachedConfig: BosConfig | null = null;\nlet projectRoot: string | null = null;\n\nexport function clearConfigCache(): void {\n  cachedConfig = null;\n  projectRoot = null;\n}\n\nexport function findConfigPath(cwd?: string): string | null {\n  let dir = cwd ?? process.cwd();\n  while (dir !== \"/\") {\n    const configPath = join(dir, \"bos.config.json\");\n    if (existsSync(configPath)) {\n      return configPath;\n    }\n    dir = dirname(dir);\n  }\n  return null;\n}\n\nexport function getConfig(): BosConfig | null {\n  return cachedConfig;\n}\n\nexport function getProjectRoot(): string {\n  if (!projectRoot) {\n    throw new Error(\"Config not loaded. Call loadConfig() first.\");\n  }\n  return projectRoot;\n}\n\nexport interface ConfigResult {\n  config: BosConfig;\n  runtime: RuntimeConfig;\n  source: {\n    path: string;\n    extended?: string[];\n    remote?: boolean;\n  };\n}\n\nexport interface ResolvedComposableReference {\n  entry: BosPluginRef;\n  providerBaseDir: string;\n  targetPath: string;\n  associatedUi?: Record<string, unknown>;\n}\n\ninterface ParsedExtendsTarget {\n  configPath: string;\n  targetPath?: string;\n}\n\nexport async function loadConfig(options?: {\n  cwd?: string;\n  path?: string;\n  env?: BosEnv;\n}): Promise<ConfigResult | null> {\n  const configPath = options?.path ?? findConfigPath(options?.cwd);\n  if (!configPath) {\n    projectRoot = options?.cwd ?? process.cwd();\n    return null;\n  }\n\n  const baseDir = dirname(configPath);\n  const env = options?.env ?? \"development\";\n  const runtimeEnv: BosEnv = env === \"staging\" ? \"production\" : env;\n\n  try {\n    const extendedChain: string[] = [];\n    const parsed = await resolveConfigWithExtends(\n      configPath,\n      baseDir,\n      new Set(),\n      extendedChain,\n      env,\n    );\n    const config = await resolveRootComposableEntries(\n      BosConfigSchema.parse(parsed),\n      baseDir,\n      runtimeEnv,\n    );\n\n    cachedConfig = config;\n    projectRoot = baseDir;\n\n    const pluginRuntime = await resolveRuntimePlugins(config.plugins ?? {}, baseDir, runtimeEnv);\n    const runtime = buildRuntimeConfig(config, baseDir, runtimeEnv, {\n      plugins: pluginRuntime,\n    });\n\n    return {\n      config,\n      runtime,\n      source: {\n        path: configPath,\n        extended: extendedChain.length > 0 ? extendedChain : undefined,\n        remote: extendedChain.some((entry) => entry.startsWith(\"bos://\")),\n      },\n    };\n  } catch (error) {\n    throw new Error(`Failed to load config from ${configPath}: ${error}`);\n  }\n}\n\nexport async function loadBosConfig(options?: {\n  cwd?: string;\n  path?: string;\n  env?: BosEnv;\n}): Promise<RuntimeConfig> {\n  const result = await loadConfig(options);\n  if (!result) {\n    throw new Error(\"No bos.config.json found\");\n  }\n\n  return result.runtime;\n}\n\nexport async function buildRuntimePluginsForConfig(\n  config: BosConfig,\n  baseDir: string,\n  env: BosEnv,\n): Promise<Record<string, RuntimePluginConfig> | undefined> {\n  const plugins = await resolveRuntimePlugins(config.plugins ?? {}, baseDir, env);\n  return Object.keys(plugins).length > 0 ? plugins : undefined;\n}\n\nasync function resolveRootComposableEntries(\n  config: BosConfig,\n  baseDir: string,\n  env: BosEnv,\n): Promise<BosConfig> {\n  const resolvedApi = await resolveComposableReference(\n    config.app.api as BosPluginRef,\n    baseDir,\n    env,\n    \"app.api\",\n  );\n  const resolvedAuth = config.app.auth\n    ? await resolveComposableReference(config.app.auth as BosPluginRef, baseDir, env, \"app.auth\")\n    : undefined;\n\n  return {\n    ...config,\n    app: {\n      ...config.app,\n      api: resolvedApi.entry,\n      auth: resolvedAuth?.entry,\n    },\n  };\n}\n\nexport function getResolvedConfigPath(configDir: string): string {\n  return join(configDir, \".bos\", RESOLVED_CONFIG_FILENAME);\n}\n\nexport function loadResolvedConfig(configDir: string): BosConfig | null {\n  const resolvedPath = getResolvedConfigPath(configDir);\n  if (!existsSync(resolvedPath)) return null;\n  try {\n    const raw = JSON.parse(readFileSync(resolvedPath, \"utf-8\"));\n    if (!isPlainObject(raw)) return null;\n    const { _resolved, ...configData } = raw;\n    return BosConfigSchema.parse(configData);\n  } catch {\n    return null;\n  }\n}\n\nexport function writeResolvedConfig(\n  configDir: string,\n  config: BosConfig,\n  env: BosEnv,\n  extendsChain?: string[],\n  source?: string,\n): void {\n  const resolvedPath = getResolvedConfigPath(configDir);\n  const resolvedDir = dirname(resolvedPath);\n  if (!existsSync(resolvedDir)) {\n    mkdirSync(resolvedDir, { recursive: true });\n  }\n\n  const ordered = rebuildOrderedConfig(config);\n  const meta: ResolvedConfigMeta = {\n    env,\n    resolvedAt: new Date().toISOString(),\n    extendsChain: extendsChain ?? [],\n    ...(source ? { source } : {}),\n  };\n  const output = {\n    _resolved: meta,\n    ...ordered,\n  };\n\n  const content = `${JSON.stringify(output, null, 2)}\\n`;\n  try {\n    if (readFileSync(resolvedPath, \"utf-8\") === content) return;\n  } catch {\n    // file doesn't exist yet\n  }\n  writeFileSync(resolvedPath, content);\n}\n\nexport function resolveBosConfigPath(configDir: string): string {\n  const resolvedPath = getResolvedConfigPath(configDir);\n  if (existsSync(resolvedPath)) return resolvedPath;\n  return join(configDir, \"bos.config.json\");\n}\n\nexport function readBosConfigForBuild(configDir: string): Record<string, unknown> {\n  const resolvedPath = getResolvedConfigPath(configDir);\n  if (existsSync(resolvedPath)) {\n    try {\n      const raw = JSON.parse(readFileSync(resolvedPath, \"utf-8\"));\n      if (isPlainObject(raw)) {\n        const { _resolved, ...configData } = raw;\n        return configData as Record<string, unknown>;\n      }\n    } catch {}\n  }\n  const bosConfigPath = join(configDir, \"bos.config.json\");\n  return JSON.parse(readFileSync(bosConfigPath, \"utf-8\")) as Record<string, unknown>;\n}\n\nfunction parseExtendsTarget(ref: string): ParsedExtendsTarget {\n  const hashIndex = ref.indexOf(\"#\");\n  if (hashIndex === -1) {\n    return { configPath: ref };\n  }\n\n  const configPath = ref.slice(0, hashIndex);\n  const targetPath = ref.slice(hashIndex + 1);\n  return {\n    configPath,\n    targetPath: targetPath.length > 0 ? targetPath : undefined,\n  };\n}\n\nfunction getConfigBaseDir(configPath: string, baseDir: string): string {\n  if (configPath.startsWith(\"bos://\")) return baseDir;\n  return dirname(isAbsolute(configPath) ? configPath : resolve(baseDir, configPath));\n}\n\nfunction asComposableEntry(value: unknown): BosPluginRef {\n  if (typeof value === \"string\") {\n    return { extends: value };\n  }\n  if (!isPlainObject(value)) {\n    throw new Error(`Expected config entry object, received ${typeof value}`);\n  }\n  return value as BosPluginRef;\n}\n\nfunction getTargetedEntry(config: BosConfigInput, targetPath: string): BosPluginRef {\n  if (targetPath === \"app.api\") {\n    return asComposableEntry(config.app?.api);\n  }\n\n  if (targetPath === \"app.auth\") {\n    return asComposableEntry(config.app?.auth);\n  }\n\n  if (targetPath.startsWith(\"plugins.\")) {\n    const pluginId = targetPath.slice(\"plugins.\".length);\n    if (pluginId.length === 0) {\n      throw new Error(`Invalid plugin target path: ${targetPath}`);\n    }\n    return asComposableEntry(config.plugins?.[pluginId]);\n  }\n\n  throw new Error(`Unsupported extends target path: ${targetPath}`);\n}\n\nfunction getAssociatedUi(\n  config: BosConfigInput,\n  _targetPath: string,\n): Record<string, unknown> | undefined {\n  return isPlainObject(config.app?.ui) ? (config.app.ui as Record<string, unknown>) : undefined;\n}\n\nfunction mergeComposableEntries(\n  parent: Partial<BosPluginRef>,\n  child: Partial<BosPluginRef>,\n): BosPluginRef {\n  return bosConfigMerger({ ...child }, parent) as BosPluginRef;\n}\n\nfunction stripUnsafeLocalDevelopment<T extends Record<string, unknown> | undefined>(\n  entry: T,\n  allowLocalPaths: boolean,\n): T {\n  if (!entry || allowLocalPaths) {\n    return entry;\n  }\n\n  if (typeof entry.development === \"string\" && entry.development.startsWith(LOCAL_PREFIX)) {\n    const { development: _ignored, ...rest } = entry;\n    return rest as T;\n  }\n\n  return entry;\n}\n\nexport async function resolveComposableReference(\n  source: BosPluginRef,\n  baseDir: string,\n  env: BosEnv,\n  defaultTargetPath: string,\n): Promise<ResolvedComposableReference> {\n  let resolvedEntry: BosPluginRef = {};\n  let providerBaseDir = baseDir;\n  let targetPath = defaultTargetPath;\n  let associatedUi: Record<string, unknown> | undefined;\n  let allowLocalPaths = false;\n  let extendsError: unknown;\n\n  const extendsRef = source.extends ? resolveExtendsRef(source.extends, env) : undefined;\n  if (extendsRef) {\n    const parsed = parseExtendsTarget(extendsRef);\n    targetPath = parsed.targetPath ?? defaultTargetPath;\n    const extendsBaseDir = getConfigBaseDir(parsed.configPath, baseDir);\n    try {\n      const extendedConfig = await resolveConfigWithExtends(\n        parsed.configPath,\n        extendsBaseDir,\n        new Set(),\n        [],\n        env,\n      );\n      resolvedEntry = mergeComposableEntries(\n        resolvedEntry,\n        getTargetedEntry(extendedConfig, targetPath),\n      );\n      providerBaseDir = extendsBaseDir;\n      associatedUi = getAssociatedUi(extendedConfig, targetPath);\n    } catch (error) {\n      extendsError = error;\n    }\n  }\n\n  const localDevelopment =\n    typeof source.development === \"string\" && source.development.startsWith(LOCAL_PREFIX)\n      ? source.development\n      : undefined;\n\n  if (localDevelopment) {\n    const localPath = resolve(baseDir, localDevelopment.slice(LOCAL_PREFIX.length).trim());\n    const localConfigPath = join(localPath, \"bos.config.json\");\n    if (existsSync(localConfigPath)) {\n      const localConfig = await resolveConfigWithExtends(\n        localConfigPath,\n        localPath,\n        new Set(),\n        [],\n        env,\n      );\n      resolvedEntry = mergeComposableEntries(\n        resolvedEntry,\n        getTargetedEntry(localConfig, targetPath),\n      );\n      providerBaseDir = localPath;\n      associatedUi = getAssociatedUi(localConfig, targetPath);\n      allowLocalPaths = true;\n    }\n  }\n\n  const sourceOverrides = { ...source };\n  if (allowLocalPaths && localDevelopment) {\n    delete sourceOverrides.development;\n  }\n\n  resolvedEntry = mergeComposableEntries(resolvedEntry, sourceOverrides);\n\n  if (\n    extendsError &&\n    !allowLocalPaths &&\n    typeof resolvedEntry.development !== \"string\" &&\n    typeof resolvedEntry.production !== \"string\" &&\n    typeof resolvedEntry.name !== \"string\"\n  ) {\n    throw extendsError;\n  }\n\n  return {\n    entry: stripUnsafeLocalDevelopment(resolvedEntry, allowLocalPaths || Boolean(localDevelopment)),\n    providerBaseDir,\n    targetPath,\n    associatedUi: stripUnsafeLocalDevelopment(associatedUi, allowLocalPaths),\n  };\n}\n\nfunction resolveDevelopmentTarget(\n  development: string | undefined,\n  production: string | undefined,\n  baseDir: string,\n  forceSource?: \"local\" | \"remote\",\n): RuntimeTarget {\n  if (forceSource === \"remote\") {\n    return resolveRuntimeTarget(production, baseDir, \"remote\");\n  }\n  if (!development) {\n    return resolveRuntimeTarget(production, baseDir, \"remote\");\n  }\n  const devTarget = resolveRuntimeTarget(development, baseDir);\n  if (devTarget.source === \"local\" && (!devTarget.localPath || !existsSync(devTarget.localPath))) {\n    return resolveRuntimeTarget(production, baseDir, \"remote\");\n  }\n  return devTarget;\n}\n\nexport interface BuildRuntimeConfigOptions {\n  plugins?: Record<string, RuntimePluginConfig>;\n  hostSource?: \"local\" | \"remote\";\n  uiSource?: \"local\" | \"remote\";\n  apiSource?: \"local\" | \"remote\";\n  authSource?: \"local\" | \"remote\";\n  proxy?: string;\n}\n\nexport function buildRuntimeConfig(\n  config: BosConfig,\n  baseDir: string,\n  env: BosEnv,\n  options?: BuildRuntimeConfigOptions,\n): RuntimeConfig {\n  const uiConfig = config.app.ui;\n  const apiConfig = config.app.api;\n  const authConfig = config.app.auth;\n  const uiRuntime =\n    env === \"development\"\n      ? resolveDevelopmentTarget(\n          uiConfig.development,\n          uiConfig.production,\n          baseDir,\n          options?.uiSource,\n        )\n      : resolveRuntimeTarget(uiConfig.production, baseDir, \"remote\");\n  const apiRuntime =\n    env === \"development\"\n      ? resolveDevelopmentTarget(\n          apiConfig.development,\n          apiConfig.production,\n          baseDir,\n          options?.apiSource,\n        )\n      : resolveRuntimeTarget(apiConfig.production, baseDir, \"remote\");\n  const authRuntime = authConfig\n    ? env === \"development\"\n      ? resolveDevelopmentTarget(\n          authConfig.development,\n          authConfig.production,\n          baseDir,\n          options?.authSource,\n        )\n      : resolveRuntimeTarget(authConfig.production, baseDir, \"remote\")\n    : undefined;\n\n  const hostConfig = config.app.host;\n  const hostRuntime =\n    env === \"development\"\n      ? resolveDevelopmentTarget(\n          hostConfig.development,\n          hostConfig.production,\n          baseDir,\n          options?.hostSource,\n        )\n      : resolveRuntimeTarget(hostConfig.production, baseDir, \"remote\");\n\n  const hostListeningUrl =\n    env === \"development\"\n      ? resolveDevelopmentHostUrl(hostConfig.development)\n      : `http://localhost:${hostRuntime.port ?? DEFAULT_HOST_PORT}`;\n\n  const hostIsRemote = hostRuntime.source === \"remote\";\n  const uiIsRemote = uiRuntime.source === \"remote\";\n  const apiIsRemote = apiRuntime.source === \"remote\";\n  const resolvedApiName = resolvePluginRuntimeName(apiConfig.name, apiRuntime.localPath, \"api\");\n\n  return {\n    env,\n    account: config.account,\n    domain: config.domain,\n    title: config.title,\n    description: config.description,\n    networkId: getNetworkIdForAccount(config.account),\n    repository: config.repository,\n    host: {\n      name: \"host\",\n      url: hostListeningUrl,\n      entry: `${hostListeningUrl}/mf-manifest.json`,\n      localPath: hostRuntime.localPath,\n      port: hostRuntime.port ?? DEFAULT_HOST_PORT,\n      secrets: hostConfig.secrets,\n      integrity: hostIsRemote ? hostConfig.integrity : undefined,\n      source: hostRuntime.source,\n      remoteUrl: hostIsRemote ? hostRuntime.url : undefined,\n    },\n    shared: config.shared,\n    ui: {\n      name: uiConfig.name,\n      url: uiRuntime.url,\n      entry: uiRuntime.url ? `${uiRuntime.url}/mf-manifest.json` : \"/mf-manifest.json\",\n      localPath: uiRuntime.localPath,\n      port: uiRuntime.port,\n      ssrUrl: uiIsRemote ? uiConfig.ssr : undefined,\n      ssrIntegrity: uiIsRemote ? uiConfig.ssrIntegrity : undefined,\n      integrity: uiIsRemote ? uiConfig.integrity : undefined,\n      source: uiRuntime.source,\n    },\n    api: {\n      name: resolvedApiName,\n      url: apiRuntime.url,\n      entry: apiRuntime.url ? `${apiRuntime.url}/mf-manifest.json` : \"/mf-manifest.json\",\n      localPath: apiRuntime.localPath,\n      port: apiRuntime.port,\n      source: apiRuntime.source,\n      proxy: options?.proxy ?? apiConfig.proxy,\n      variables: apiConfig.variables,\n      secrets: apiConfig.secrets,\n      integrity: apiIsRemote ? apiConfig.integrity : undefined,\n    },\n    auth: (() => {\n      if (!authConfig || !authRuntime) return undefined;\n      return {\n        name: resolvePluginRuntimeName(authConfig.name, authRuntime.localPath, \"auth\"),\n        url: authRuntime.url,\n        entry: authRuntime.url ? `${authRuntime.url}/mf-manifest.json` : \"/mf-manifest.json\",\n        localPath: authRuntime.localPath,\n        port: authRuntime.port,\n        source: authRuntime.source,\n        proxy: authConfig.proxy,\n        variables: authConfig.variables,\n        secrets: authConfig.secrets,\n        integrity: authRuntime.source === \"remote\" ? authConfig.integrity : undefined,\n        sidebar: authConfig.sidebar?.map((item) => ({\n          ...item,\n          to: item.to ?? \"/auth\",\n          roleRequired: item.roleRequired ?? (\"member\" as const),\n        })),\n      };\n    })(),\n    plugins:\n      options?.plugins && Object.keys(options.plugins).length > 0 ? options.plugins : undefined,\n  };\n}\n\nasync function loadConfigFile(configPath: string, baseDir: string): Promise<BosConfigInput> {\n  if (configPath.startsWith(\"bos://\")) {\n    return fetchBosConfigFromFastKv<BosConfigInput>(configPath);\n  }\n\n  const resolvedPath = isAbsolute(configPath) ? configPath : resolve(baseDir, configPath);\n  return JSON.parse(readFileSync(resolvedPath, \"utf-8\")) as BosConfigInput;\n}\n\nasync function resolveConfigWithExtends(\n  configPath: string,\n  baseDir: string,\n  visited: Set<string>,\n  chain: string[],\n  env: BosEnv = \"development\",\n): Promise<BosConfigInput> {\n  if (visited.has(configPath)) {\n    throw new Error(`Circular extends detected: ${[...visited, configPath].join(\" -> \")}`);\n  }\n\n  const config = await loadConfigFile(configPath, baseDir);\n  chain.push(configPath);\n\n  if (!config.extends) {\n    return config;\n  }\n\n  const extendsRef = resolveExtendsRef(config.extends as string | ExtendsConfig, env);\n  if (!extendsRef) {\n    return config;\n  }\n\n  const parsedParentRef = parseExtendsTarget(extendsRef);\n\n  const nextVisited = new Set(visited);\n  nextVisited.add(configPath);\n  const parentBaseDir = getConfigBaseDir(parsedParentRef.configPath, baseDir);\n  const parent = await resolveConfigWithExtends(\n    parsedParentRef.configPath,\n    parentBaseDir,\n    nextVisited,\n    chain,\n    env,\n  );\n\n  return mergeBosConfigWithExtends(parent, config);\n}\n\ntype PluginOverrideValue = PluginEntryValue | null | false;\n\nfunction normalizePluginEntry(raw: PluginOverrideValue): BosPluginRef | null | false {\n  if (raw === null || raw === false) return raw;\n  if (typeof raw === \"string\") {\n    return { extends: raw };\n  }\n  return raw;\n}\n\nasync function resolveRuntimePlugins(\n  plugins: Record<string, PluginOverrideValue>,\n  baseDir: string,\n  env: BosEnv,\n): Promise<Record<string, RuntimePluginConfig>> {\n  const out: Record<string, RuntimePluginConfig> = {};\n\n  for (const [pluginId, rawInput] of Object.entries(plugins)) {\n    const normalized = normalizePluginEntry(rawInput);\n    if (normalized === null || normalized === false) continue;\n\n    const resolvedReference = await resolveComposableReference(\n      normalized,\n      baseDir,\n      env,\n      `plugins.${pluginId}`,\n    );\n\n    const pluginRuntime = buildRuntimePluginConfig(pluginId, env, resolvedReference);\n\n    if (!pluginRuntime.localPath && !pluginRuntime.url) {\n      continue;\n    }\n\n    if (\n      pluginRuntime.source === \"remote\" &&\n      pluginRuntime.url &&\n      !pluginRuntime.localPath &&\n      typeof resolvedReference.entry.name !== \"string\"\n    ) {\n      pluginRuntime.name = await resolveRemotePluginRuntimeName(\n        pluginRuntime.url,\n        pluginRuntime.name,\n      );\n    }\n\n    out[pluginId] = pluginRuntime;\n  }\n\n  return out;\n}\n\nasync function resolveRemotePluginRuntimeName(baseUrl: string, fallback: string): Promise<string> {\n  try {\n    const controller = new AbortController();\n    const timeout = setTimeout(() => controller.abort(), 5000);\n    const response = await fetch(`${baseUrl.replace(/\\/$/, \"\")}/plugin.manifest.json`, {\n      signal: controller.signal,\n    });\n    clearTimeout(timeout);\n\n    if (!response.ok) {\n      return fallback;\n    }\n\n    const manifest = (await response.json()) as {\n      plugin?: { name?: unknown };\n    };\n\n    return typeof manifest.plugin?.name === \"string\" && manifest.plugin.name.length > 0\n      ? manifest.plugin.name\n      : fallback;\n  } catch {\n    return fallback;\n  }\n}\n\nfunction buildRuntimePluginConfig(\n  pluginId: string,\n  env: BosEnv,\n  resolved: ResolvedComposableReference,\n): RuntimePluginConfig {\n  const source = resolved.entry;\n  const development = typeof source.development === \"string\" ? source.development : undefined;\n  const production = typeof source.production === \"string\" ? source.production : undefined;\n\n  if (production?.startsWith(\"bos://\")) {\n    throw new Error(\n      `Plugin \"${pluginId}\" has unsupported production target \"${production}\". Use extends: \"bos://account/domain\" for plugin configs or a CDN URL for production.`,\n    );\n  }\n\n  const runtimeTarget =\n    env === \"development\"\n      ? resolveDevelopmentTarget(development, production, resolved.providerBaseDir)\n      : resolveRuntimeTarget(production, resolved.providerBaseDir, \"remote\");\n  const apiName = resolvePluginRuntimeName(source.name, runtimeTarget.localPath, pluginId);\n\n  const uiConfig = resolved.associatedUi;\n  const uiDevelopment =\n    typeof uiConfig?.development === \"string\" ? uiConfig.development : undefined;\n  const uiProduction = typeof uiConfig?.production === \"string\" ? uiConfig.production : undefined;\n  const uiRuntime =\n    uiConfig && (uiDevelopment || uiProduction)\n      ? env === \"development\"\n        ? resolveDevelopmentTarget(uiDevelopment, uiProduction, resolved.providerBaseDir)\n        : resolveRuntimeTarget(uiProduction, resolved.providerBaseDir, \"remote\")\n      : undefined;\n\n  const sidebar = source.sidebar?.map((item) => ({\n    ...item,\n    to: item.to ?? `/${pluginId}`,\n    roleRequired: item.roleRequired ?? (\"member\" as const),\n  }));\n\n  const routes = source.routes;\n\n  return {\n    name: apiName,\n    url: runtimeTarget.url,\n    entry: runtimeTarget.url\n      ? `${runtimeTarget.url.replace(/\\/$/, \"\")}/mf-manifest.json`\n      : \"/mf-manifest.json\",\n    source: runtimeTarget.source,\n    localPath: runtimeTarget.localPath,\n    port: runtimeTarget.port,\n    proxy: typeof source.proxy === \"string\" ? source.proxy : undefined,\n    variables: normalizeStringRecord(source.variables),\n    secrets: normalizeStringArray(source.secrets),\n    integrity: runtimeTarget.source === \"remote\" ? source.integrity : undefined,\n    ui: uiRuntime\n      ? {\n          name: typeof uiConfig?.name === \"string\" ? uiConfig.name : `${apiName}-ui`,\n          url: uiRuntime.url,\n          entry: uiRuntime.url\n            ? `${uiRuntime.url.replace(/\\/$/, \"\")}/mf-manifest.json`\n            : \"/mf-manifest.json\",\n          source: uiRuntime.source,\n          localPath: uiRuntime.localPath,\n          port: uiRuntime.port,\n          integrity:\n            uiRuntime.source === \"remote\" && typeof uiConfig?.integrity === \"string\"\n              ? uiConfig.integrity\n              : undefined,\n        }\n      : undefined,\n    sidebar,\n    routes,\n  };\n}\n\nexport function resolvePluginRuntimeName(\n  explicitName: string | undefined,\n  localPath: string | undefined,\n  fallback: string,\n): string {\n  if (explicitName) {\n    return explicitName;\n  }\n\n  if (!localPath) {\n    return fallback;\n  }\n\n  try {\n    const packageJsonPath = join(localPath, \"package.json\");\n    const packageJson = JSON.parse(readFileSync(packageJsonPath, \"utf-8\")) as { name?: unknown };\n    if (typeof packageJson.name === \"string\" && packageJson.name.length > 0) {\n      return packageJson.name;\n    }\n  } catch {}\n\n  return fallback;\n}\n\nfunction normalizeStringRecord(value: unknown): Record<string, string> | undefined {\n  if (!isPlainObject(value)) return undefined;\n  const out: Record<string, string> = {};\n  for (const [key, raw] of Object.entries(value)) {\n    if (typeof raw === \"string\") {\n      out[key] = raw;\n    }\n  }\n  return Object.keys(out).length > 0 ? out : undefined;\n}\n\nfunction normalizeStringArray(value: unknown): string[] | undefined {\n  if (!Array.isArray(value)) return undefined;\n  const out = value.filter((item): item is string => typeof item === \"string\" && item.length > 0);\n  return out.length > 0 ? out : undefined;\n}\n\nfunction resolveRuntimeTarget(\n  value: string | undefined,\n  baseDir: string,\n  defaultSource: \"local\" | \"remote\" = \"remote\",\n): RuntimeTarget {\n  if (!value) {\n    return { source: defaultSource, url: \"\" };\n  }\n\n  if (value.startsWith(LOCAL_PREFIX)) {\n    const localTarget = value?.slice(LOCAL_PREFIX.length).trim();\n    if (!localTarget) {\n      throw new Error(`Invalid local development target: ${value}`);\n    }\n\n    const localPath = resolve(baseDir, localTarget);\n    if (!existsSync(localPath)) {\n      return { source: \"local\", url: \"\" };\n    }\n\n    return {\n      source: \"local\",\n      url: \"\",\n      localPath,\n    };\n  }\n\n  return {\n    source: defaultSource,\n    url: value.replace(/\\/$/, \"\"),\n    port: parsePort(value),\n  };\n}\n\nexport function isLocalDevelopmentTarget(\n  value: string | undefined,\n): value is `${typeof LOCAL_PREFIX}${string}` {\n  return typeof value === \"string\" && value.startsWith(LOCAL_PREFIX);\n}\n\nexport function resolveLocalDevelopmentPath(\n  value: string | undefined,\n  baseDir: string,\n): string | null {\n  if (!isLocalDevelopmentTarget(value)) {\n    return null;\n  }\n\n  const localTarget = value.slice(LOCAL_PREFIX.length).trim();\n  return localTarget ? resolve(baseDir, localTarget) : null;\n}\n\nexport function resolveDevelopmentHostUrl(value: string | undefined): string {\n  if (!value || isLocalDevelopmentTarget(value)) {\n    return `http://localhost:${DEFAULT_HOST_PORT}`;\n  }\n\n  return value.replace(/\\/$/, \"\");\n}\n\nexport function getHostDevelopmentPort(value: string | undefined): number {\n  return parsePort(resolveDevelopmentHostUrl(value));\n}\n\nexport function parsePort(url: string): number {\n  try {\n    const parsed = new URL(url);\n    return parsed.port ? parseInt(parsed.port, 10) : parsed.protocol === \"https:\" ? 443 : 80;\n  } catch {\n    return 3000;\n  }\n}\n\nexport { BOS_CONFIG_ORDER, rebuildOrderedConfig } from \"./merge\";\nexport type { BosConfig, RuntimeConfig } from \"./types\";\nexport { BosConfigSchema } from \"./types\";\n"],"mappings":"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"}