{"version":3,"file":"dev-server-middleware.cjs","names":[],"sources":["../../../src/build/rspack/dev-server-middleware.ts"],"sourcesContent":["import type { PluginInfo } from \"./utils\";\n\nconst corsHeaders = {\n  \"Access-Control-Allow-Origin\": \"*\",\n  \"Access-Control-Allow-Methods\": \"GET, POST, PUT, DELETE, PATCH, OPTIONS\",\n  \"Access-Control-Allow-Headers\": \"X-Requested-With, content-type, Authorization\",\n};\n\nconst applyCorsHeaders = (res: any) => {\n  Object.entries(corsHeaders).forEach(([key, value]) => {\n    res.setHeader(key, value);\n  });\n};\n\nconst normalizePrefix = (prefix?: string): string => {\n  if (!prefix) return \"\";\n  const cleaned = prefix.replace(/^\\/+|\\/+$/g, \"\");\n  return cleaned ? `/${cleaned}` : \"\";\n};\n\nexport function setupPluginMiddleware(\n  devServer: any,\n  pluginInfo: PluginInfo,\n  devConfig: any,\n  port: number,\n) {\n  const rpcPrefix = normalizePrefix(devConfig?.prefix);\n  const handlers: { rpc: any; api: any } = { rpc: null, api: null };\n  let cleanup: (() => Promise<void>) | null = null;\n\n  const performCleanup = async () => {\n    if (cleanup) {\n      await cleanup();\n      cleanup = null;\n    }\n  };\n\n  (async () => {\n    await performCleanup();\n\n    try {\n      const { createPluginRuntime } = await import(\"every-plugin\");\n      const { RPCHandler } = await import(\"@orpc/server/fetch\");\n      const { OpenAPIHandler } = await import(\"@orpc/openapi/fetch\");\n      const { OpenAPIReferencePlugin } = await import(\"@orpc/openapi/plugins\");\n      const { ZodToJsonSchemaConverter } = await import(\"@orpc/zod/zod4\");\n      const { onError } = await import(\"every-plugin/orpc\");\n      const { formatORPCError } = await import(\"every-plugin/errors\");\n\n      const pluginId = devConfig?.pluginId || pluginInfo.normalizedName;\n\n      const runtime = createPluginRuntime({\n        registry: {\n          [pluginId]: {\n            remote: `http://localhost:${port}/remoteEntry.js`,\n          },\n        },\n      });\n\n      const defaultConfig = { variables: {}, secrets: {} };\n\n      // @ts-expect-error we don't know the plugin id\n      const loaded = await runtime.usePlugin(pluginId, (devConfig?.config ?? defaultConfig) as any);\n\n      cleanup = async () => {\n        handlers.rpc = null;\n        handlers.api = null;\n        if (devServer.app.locals.handlers) {\n          devServer.app.locals.handlers = null;\n        }\n        if (runtime) await runtime.shutdown();\n      };\n\n      handlers.rpc = new RPCHandler(loaded.router, {\n        interceptors: [\n          onError((error: any) => {\n            const formatted = formatORPCError(error);\n            if (formatted) console.error(formatted);\n          }),\n        ],\n      });\n\n      handlers.api = new OpenAPIHandler(loaded.router, {\n        plugins: [\n          new OpenAPIReferencePlugin({\n            schemaConverters: [new ZodToJsonSchemaConverter()],\n          }),\n        ],\n        interceptors: [\n          onError((error: any) => {\n            const formatted = formatORPCError(error);\n            if (formatted) console.error(formatted);\n          }),\n        ],\n      });\n\n      console.log(`╭─────────────────────────────────────────────`);\n      console.log(`│  ✅ Plugin dev server ready: `);\n      console.log(`├─────────────────────────────────────────────`);\n      console.log(`│  📡 RPC:    http://localhost:${port}/api/rpc${rpcPrefix}`);\n      console.log(`│  📖 Docs:   http://localhost:${port}/api`);\n      console.log(`│  💚 Health: http://localhost:${port}/`);\n      console.log(`╰─────────────────────────────────────────────`);\n\n      devServer.app.locals.handlers = handlers;\n\n      if (devServer.server) {\n        devServer.server.once(\"close\", async () => {\n          await performCleanup();\n        });\n      }\n    } catch (error) {\n      console.error(\"❌ Failed to load plugin:\", error);\n      await performCleanup();\n    }\n  })().catch((err) => {\n    console.error(\"❌ Plugin dev server fatal error:\", err);\n  });\n\n  process.once(\"SIGINT\", async () => {\n    const timeout = setTimeout(() => process.exit(0), 3000);\n    await performCleanup();\n    clearTimeout(timeout);\n  });\n  process.once(\"SIGTERM\", async () => {\n    const timeout = setTimeout(() => process.exit(0), 3000);\n    await performCleanup();\n    clearTimeout(timeout);\n  });\n\n  devServer.app.options(\"*\", (_req: any, res: any) => {\n    applyCorsHeaders(res);\n    res.status(200).end();\n  });\n\n  devServer.app.get(\"/\", (_req: any, res: any) => {\n    applyCorsHeaders(res);\n    res.json({\n      ok: true,\n      plugin: pluginInfo.normalizedName,\n      version: pluginInfo.version,\n      status: devServer.app.locals.handlers?.rpc ? \"ready\" : \"loading\",\n      endpoints: {\n        health: \"/\",\n        docs: \"/api\",\n        rpc: `/api/rpc${rpcPrefix}`,\n      },\n    });\n  });\n\n  devServer.app.get(\"/health\", (_req: any, res: any) => {\n    applyCorsHeaders(res);\n    res.status(200).send(\"OK\");\n  });\n\n  const buildDevContext = (_req: any, webRequest: Request) => {\n    const rawClone =\n      webRequest.method === \"GET\" || webRequest.method === \"HEAD\" ? null : webRequest.clone();\n    let cachedRawBody: string | null = null;\n    return {\n      reqHeaders: webRequest.headers,\n      getRawBody: async (): Promise<string> => {\n        if (cachedRawBody !== null) return cachedRawBody;\n        if (!rawClone) {\n          cachedRawBody = \"\";\n          return cachedRawBody;\n        }\n        cachedRawBody = await rawClone.text();\n        return cachedRawBody;\n      },\n    };\n  };\n\n  const handleApiRequest = async (req: any, res: any) => {\n    applyCorsHeaders(res);\n    const apiHandler = devServer.app.locals.handlers?.api;\n    if (!apiHandler) {\n      return res.status(503).json({ error: \"Plugin still loading...\" });\n    }\n\n    try {\n      const url = `http://${req.headers.host}${req.url}`;\n      const webRequest = new Request(url, {\n        method: req.method,\n        headers: req.headers,\n        body: req.method !== \"GET\" && req.method !== \"HEAD\" ? req : undefined,\n        duplex: req.method !== \"GET\" && req.method !== \"HEAD\" ? \"half\" : undefined,\n      } as RequestInit);\n\n      const result = await apiHandler.handle(webRequest, {\n        prefix: \"/api\",\n        context: buildDevContext(req, webRequest),\n      });\n\n      if (result.response) {\n        res.status(result.response.status);\n        result.response.headers.forEach((value: string, key: string) => {\n          res.setHeader(key, value);\n        });\n        const text = await result.response.text();\n        res.send(text);\n      } else {\n        res.status(404).send(\"Not Found\");\n      }\n    } catch (error) {\n      console.error(\"OpenAPI error:\", error);\n      res.status(500).json({ error: (error as Error).message });\n    }\n  };\n\n  devServer.app.all(`/api/rpc${rpcPrefix}/*`, async (req: any, res: any) => {\n    applyCorsHeaders(res);\n    const rpcHandler = devServer.app.locals.handlers?.rpc;\n    if (!rpcHandler) {\n      return res.status(503).json({ error: \"Plugin still loading...\" });\n    }\n\n    try {\n      const url = `http://${req.headers.host}${req.url}`;\n      const webRequest = new Request(url, {\n        method: req.method,\n        headers: req.headers,\n        body: req.method !== \"GET\" && req.method !== \"HEAD\" ? req : undefined,\n        duplex: req.method !== \"GET\" && req.method !== \"HEAD\" ? \"half\" : undefined,\n      } as RequestInit);\n\n      const result = await rpcHandler.handle(webRequest, {\n        prefix: `/api/rpc${rpcPrefix}`,\n        context: buildDevContext(req, webRequest),\n      });\n\n      if (result.response) {\n        res.status(result.response.status);\n        result.response.headers.forEach((value: string, key: string) => {\n          res.setHeader(key, value);\n        });\n        const text = await result.response.text();\n        res.send(text);\n      } else {\n        res.status(404).send(\"Not Found\");\n      }\n    } catch (error) {\n      console.error(\"RPC error:\", error);\n      res.status(500).json({ error: (error as Error).message });\n    }\n  });\n\n  devServer.app.all(\"/api\", handleApiRequest);\n  devServer.app.all(\"/api/*\", handleApiRequest);\n}\n"],"mappings":"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"}