@lovable.dev/mcp-js 0.12.1 → 0.13.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{authorize-HTd0GKmB.d.ts → authorize-BMeXd_Sh.d.ts} +7 -0
- package/dist/{chunk-Y2FTHVL3.js → chunk-SIITHGUD.js} +1 -1
- package/dist/chunk-UQK5UO6C.js +26 -0
- package/dist/cli/extract-manifest.cjs +1 -1
- package/dist/cli/extract-manifest.js +1 -1
- package/dist/protocols/mcp/index.d.cts +1 -1
- package/dist/protocols/mcp/index.d.ts +1 -1
- package/dist/protocols/oauth-metadata.d.cts +1 -1
- package/dist/protocols/oauth-metadata.d.ts +1 -1
- package/dist/protocols/rest/index.d.cts +1 -1
- package/dist/protocols/rest/index.d.ts +1 -1
- package/dist/stacks/supabase/index.cjs +27 -11
- package/dist/stacks/supabase/index.d.cts +9 -0
- package/dist/stacks/supabase/index.d.ts +9 -0
- package/dist/stacks/supabase/index.js +7 -11
- package/dist/stacks/supabase/vite.cjs +1 -1
- package/dist/stacks/supabase/vite.js +1 -1
- package/dist/stacks/tanstack/index.cjs +30 -4
- package/dist/stacks/tanstack/index.d.cts +1 -1
- package/dist/stacks/tanstack/index.d.ts +1 -1
- package/dist/stacks/tanstack/index.js +10 -4
- package/dist/stacks/tanstack/vite.cjs +12 -3
- package/dist/stacks/tanstack/vite.d.cts +11 -0
- package/dist/stacks/tanstack/vite.d.ts +11 -0
- package/dist/stacks/tanstack/vite.js +12 -3
- package/package.json +1 -1
|
@@ -13,6 +13,13 @@ interface McpRuntimeOptions {
|
|
|
13
13
|
* an externally hosted document). Defaults to the well-known path when absent.
|
|
14
14
|
*/
|
|
15
15
|
metadataPath?: string;
|
|
16
|
+
/**
|
|
17
|
+
* Derive the request origin (and thus the advertised `resource`/metadata URLs)
|
|
18
|
+
* from `X-Forwarded-Host` rather than the rewritten `Host`. Stack adapters read
|
|
19
|
+
* this before invoking the handler, so the OAuth runtime never sees it; safe
|
|
20
|
+
* only behind a proxy that overwrites the header (see `core/forwarded.ts`).
|
|
21
|
+
*/
|
|
22
|
+
trustForwardedHost?: boolean;
|
|
16
23
|
}
|
|
17
24
|
|
|
18
25
|
export type { McpRuntimeOptions as M };
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
// src/core/forwarded.ts
|
|
2
|
+
function applyForwardedOrigin(request, options) {
|
|
3
|
+
const proto = options.trustForwardedProto ? firstForwardedValue(request, "x-forwarded-proto") : void 0;
|
|
4
|
+
const host = options.trustForwardedHost ? firstForwardedValue(request, "x-forwarded-host") : void 0;
|
|
5
|
+
if (proto === void 0 && host === void 0)
|
|
6
|
+
return request;
|
|
7
|
+
const url = new URL(request.url);
|
|
8
|
+
let changed = false;
|
|
9
|
+
if (proto !== void 0 && `${proto}:` !== url.protocol) {
|
|
10
|
+
url.protocol = `${proto}:`;
|
|
11
|
+
changed = true;
|
|
12
|
+
}
|
|
13
|
+
if (host !== void 0 && host !== url.host) {
|
|
14
|
+
url.host = host;
|
|
15
|
+
changed = true;
|
|
16
|
+
}
|
|
17
|
+
return changed ? new Request(url.href, request) : request;
|
|
18
|
+
}
|
|
19
|
+
function firstForwardedValue(request, header) {
|
|
20
|
+
const value = request.headers.get(header)?.split(",")[0]?.trim();
|
|
21
|
+
return value ? value : void 0;
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
export {
|
|
25
|
+
applyForwardedOrigin
|
|
26
|
+
};
|
|
@@ -72,6 +72,29 @@ function resolveResourcePath(resourcePath, request) {
|
|
|
72
72
|
return resourcePath;
|
|
73
73
|
}
|
|
74
74
|
|
|
75
|
+
// src/core/forwarded.ts
|
|
76
|
+
function applyForwardedOrigin(request, options) {
|
|
77
|
+
const proto = options.trustForwardedProto ? firstForwardedValue(request, "x-forwarded-proto") : void 0;
|
|
78
|
+
const host = options.trustForwardedHost ? firstForwardedValue(request, "x-forwarded-host") : void 0;
|
|
79
|
+
if (proto === void 0 && host === void 0)
|
|
80
|
+
return request;
|
|
81
|
+
const url = new URL(request.url);
|
|
82
|
+
let changed = false;
|
|
83
|
+
if (proto !== void 0 && `${proto}:` !== url.protocol) {
|
|
84
|
+
url.protocol = `${proto}:`;
|
|
85
|
+
changed = true;
|
|
86
|
+
}
|
|
87
|
+
if (host !== void 0 && host !== url.host) {
|
|
88
|
+
url.host = host;
|
|
89
|
+
changed = true;
|
|
90
|
+
}
|
|
91
|
+
return changed ? new Request(url.href, request) : request;
|
|
92
|
+
}
|
|
93
|
+
function firstForwardedValue(request, header) {
|
|
94
|
+
const value = request.headers.get(header)?.split(",")[0]?.trim();
|
|
95
|
+
return value ? value : void 0;
|
|
96
|
+
}
|
|
97
|
+
|
|
75
98
|
// src/protocols/mcp/protocol.ts
|
|
76
99
|
var import_mcp = require("@modelcontextprotocol/sdk/server/mcp.js");
|
|
77
100
|
var import_webStandardStreamableHttp = require("@modelcontextprotocol/sdk/server/webStandardStreamableHttp.js");
|
|
@@ -924,16 +947,6 @@ function dispatchFor(pathname) {
|
|
|
924
947
|
}
|
|
925
948
|
return { kind: "mcp" };
|
|
926
949
|
}
|
|
927
|
-
function applyForwardedProto(request) {
|
|
928
|
-
const proto = request.headers.get("x-forwarded-proto")?.split(",")[0]?.trim();
|
|
929
|
-
if (!proto)
|
|
930
|
-
return request;
|
|
931
|
-
const url = new URL(request.url);
|
|
932
|
-
if (`${proto}:` === url.protocol)
|
|
933
|
-
return request;
|
|
934
|
-
url.protocol = `${proto}:`;
|
|
935
|
-
return new Request(url.href, request);
|
|
936
|
-
}
|
|
937
950
|
function createSupabaseHandler(mcp, options = {}) {
|
|
938
951
|
const resourcePath = deriveResourcePath(options);
|
|
939
952
|
if (resourcePath !== void 0)
|
|
@@ -946,7 +959,10 @@ function createSupabaseHandler(mcp, options = {}) {
|
|
|
946
959
|
const invokeToolHandler = createInvokeToolHandler(mcp, runtimeOptions);
|
|
947
960
|
const metadataHandler = createOAuthProtectedResourceMetadataHandler(mcp, runtimeOptions);
|
|
948
961
|
return async (request) => {
|
|
949
|
-
const req =
|
|
962
|
+
const req = applyForwardedOrigin(request, {
|
|
963
|
+
trustForwardedProto: true,
|
|
964
|
+
trustForwardedHost: options.trustForwardedHost
|
|
965
|
+
});
|
|
950
966
|
const target = dispatchFor(new URL(req.url).pathname);
|
|
951
967
|
switch (target.kind) {
|
|
952
968
|
case "metadata":
|
|
@@ -19,6 +19,15 @@ interface SupabaseHandlerOptions {
|
|
|
19
19
|
* a Lovable Cloud–style host that rewrites the public URL.
|
|
20
20
|
*/
|
|
21
21
|
resourcePath?: string;
|
|
22
|
+
/**
|
|
23
|
+
* Derive the advertised `resource`/metadata host from `X-Forwarded-Host`
|
|
24
|
+
* instead of the request `Host`, so a function fronted by a custom-domain
|
|
25
|
+
* proxy advertises the public host. Off by default: enable only behind a
|
|
26
|
+
* proxy that overwrites the header (an unsanitized one lets a client spoof
|
|
27
|
+
* the advertised resource). `X-Forwarded-Proto` is trusted regardless —
|
|
28
|
+
* Supabase terminates TLS upstream and forwards over http.
|
|
29
|
+
*/
|
|
30
|
+
trustForwardedHost?: boolean;
|
|
22
31
|
}
|
|
23
32
|
/**
|
|
24
33
|
* Build a single Web-Standard handler that serves the full MCP surface from
|
|
@@ -19,6 +19,15 @@ interface SupabaseHandlerOptions {
|
|
|
19
19
|
* a Lovable Cloud–style host that rewrites the public URL.
|
|
20
20
|
*/
|
|
21
21
|
resourcePath?: string;
|
|
22
|
+
/**
|
|
23
|
+
* Derive the advertised `resource`/metadata host from `X-Forwarded-Host`
|
|
24
|
+
* instead of the request `Host`, so a function fronted by a custom-domain
|
|
25
|
+
* proxy advertises the public host. Off by default: enable only behind a
|
|
26
|
+
* proxy that overwrites the header (an unsanitized one lets a client spoof
|
|
27
|
+
* the advertised resource). `X-Forwarded-Proto` is trusted regardless —
|
|
28
|
+
* Supabase terminates TLS upstream and forwards over http.
|
|
29
|
+
*/
|
|
30
|
+
trustForwardedHost?: boolean;
|
|
22
31
|
}
|
|
23
32
|
/**
|
|
24
33
|
* Build a single Web-Standard handler that serves the full MCP surface from
|
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
import {
|
|
2
|
+
applyForwardedOrigin
|
|
3
|
+
} from "../../chunk-UQK5UO6C.js";
|
|
1
4
|
import {
|
|
2
5
|
createMcpProtocolHandler
|
|
3
6
|
} from "../../chunk-WLNT2FX7.js";
|
|
@@ -54,16 +57,6 @@ function dispatchFor(pathname) {
|
|
|
54
57
|
}
|
|
55
58
|
return { kind: "mcp" };
|
|
56
59
|
}
|
|
57
|
-
function applyForwardedProto(request) {
|
|
58
|
-
const proto = request.headers.get("x-forwarded-proto")?.split(",")[0]?.trim();
|
|
59
|
-
if (!proto)
|
|
60
|
-
return request;
|
|
61
|
-
const url = new URL(request.url);
|
|
62
|
-
if (`${proto}:` === url.protocol)
|
|
63
|
-
return request;
|
|
64
|
-
url.protocol = `${proto}:`;
|
|
65
|
-
return new Request(url.href, request);
|
|
66
|
-
}
|
|
67
60
|
function createSupabaseHandler(mcp, options = {}) {
|
|
68
61
|
const resourcePath = deriveResourcePath(options);
|
|
69
62
|
if (resourcePath !== void 0)
|
|
@@ -76,7 +69,10 @@ function createSupabaseHandler(mcp, options = {}) {
|
|
|
76
69
|
const invokeToolHandler = createInvokeToolHandler(mcp, runtimeOptions);
|
|
77
70
|
const metadataHandler = createOAuthProtectedResourceMetadataHandler(mcp, runtimeOptions);
|
|
78
71
|
return async (request) => {
|
|
79
|
-
const req =
|
|
72
|
+
const req = applyForwardedOrigin(request, {
|
|
73
|
+
trustForwardedProto: true,
|
|
74
|
+
trustForwardedHost: options.trustForwardedHost
|
|
75
|
+
});
|
|
80
76
|
const target = dispatchFor(new URL(req.url).pathname);
|
|
81
77
|
switch (target.kind) {
|
|
82
78
|
case "metadata":
|
|
@@ -27,6 +27,29 @@ __export(tanstack_exports, {
|
|
|
27
27
|
});
|
|
28
28
|
module.exports = __toCommonJS(tanstack_exports);
|
|
29
29
|
|
|
30
|
+
// src/core/forwarded.ts
|
|
31
|
+
function applyForwardedOrigin(request, options) {
|
|
32
|
+
const proto = options.trustForwardedProto ? firstForwardedValue(request, "x-forwarded-proto") : void 0;
|
|
33
|
+
const host = options.trustForwardedHost ? firstForwardedValue(request, "x-forwarded-host") : void 0;
|
|
34
|
+
if (proto === void 0 && host === void 0)
|
|
35
|
+
return request;
|
|
36
|
+
const url = new URL(request.url);
|
|
37
|
+
let changed = false;
|
|
38
|
+
if (proto !== void 0 && `${proto}:` !== url.protocol) {
|
|
39
|
+
url.protocol = `${proto}:`;
|
|
40
|
+
changed = true;
|
|
41
|
+
}
|
|
42
|
+
if (host !== void 0 && host !== url.host) {
|
|
43
|
+
url.host = host;
|
|
44
|
+
changed = true;
|
|
45
|
+
}
|
|
46
|
+
return changed ? new Request(url.href, request) : request;
|
|
47
|
+
}
|
|
48
|
+
function firstForwardedValue(request, header) {
|
|
49
|
+
const value = request.headers.get(header)?.split(",")[0]?.trim();
|
|
50
|
+
return value ? value : void 0;
|
|
51
|
+
}
|
|
52
|
+
|
|
30
53
|
// src/protocols/mcp/protocol.ts
|
|
31
54
|
var import_mcp = require("@modelcontextprotocol/sdk/server/mcp.js");
|
|
32
55
|
var import_webStandardStreamableHttp = require("@modelcontextprotocol/sdk/server/webStandardStreamableHttp.js");
|
|
@@ -889,21 +912,24 @@ function createInvokeToolHandler(mcp, options = {}) {
|
|
|
889
912
|
}
|
|
890
913
|
|
|
891
914
|
// src/stacks/tanstack/handlers.ts
|
|
915
|
+
function forwarded(request, options) {
|
|
916
|
+
return applyForwardedOrigin(request, { trustForwardedHost: options.trustForwardedHost });
|
|
917
|
+
}
|
|
892
918
|
function createTanStackMcpHandler(mcp, options = {}) {
|
|
893
919
|
const handler = createMcpProtocolHandler(mcp, options);
|
|
894
|
-
return ({ request }) => handler(request);
|
|
920
|
+
return ({ request }) => handler(forwarded(request, options));
|
|
895
921
|
}
|
|
896
922
|
function createTanStackListToolsHandler(mcp, options = {}) {
|
|
897
923
|
const handler = createListToolsHandler(mcp, options);
|
|
898
|
-
return ({ request }) => handler(request);
|
|
924
|
+
return ({ request }) => handler(forwarded(request, options));
|
|
899
925
|
}
|
|
900
926
|
function createTanStackInvokeToolHandler(mcp, options = {}) {
|
|
901
927
|
const handler = createInvokeToolHandler(mcp, options);
|
|
902
|
-
return ({ request, params }) => handler(request, params.tool);
|
|
928
|
+
return ({ request, params }) => handler(forwarded(request, options), params.tool);
|
|
903
929
|
}
|
|
904
930
|
function createTanStackOAuthProtectedResourceMetadataHandler(mcp, options = {}) {
|
|
905
931
|
const handler = createOAuthProtectedResourceMetadataHandler(mcp, options);
|
|
906
|
-
return ({ request }) => handler(request);
|
|
932
|
+
return ({ request }) => handler(forwarded(request, options));
|
|
907
933
|
}
|
|
908
934
|
// Annotate the CommonJS export names for ESM import in node:
|
|
909
935
|
0 && (module.exports = {
|
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
import {
|
|
2
|
+
applyForwardedOrigin
|
|
3
|
+
} from "../../chunk-UQK5UO6C.js";
|
|
1
4
|
import {
|
|
2
5
|
createMcpProtocolHandler
|
|
3
6
|
} from "../../chunk-WLNT2FX7.js";
|
|
@@ -16,21 +19,24 @@ import "../../chunk-QC3DXQTH.js";
|
|
|
16
19
|
import "../../chunk-6DXGZZA4.js";
|
|
17
20
|
|
|
18
21
|
// src/stacks/tanstack/handlers.ts
|
|
22
|
+
function forwarded(request, options) {
|
|
23
|
+
return applyForwardedOrigin(request, { trustForwardedHost: options.trustForwardedHost });
|
|
24
|
+
}
|
|
19
25
|
function createTanStackMcpHandler(mcp, options = {}) {
|
|
20
26
|
const handler = createMcpProtocolHandler(mcp, options);
|
|
21
|
-
return ({ request }) => handler(request);
|
|
27
|
+
return ({ request }) => handler(forwarded(request, options));
|
|
22
28
|
}
|
|
23
29
|
function createTanStackListToolsHandler(mcp, options = {}) {
|
|
24
30
|
const handler = createListToolsHandler(mcp, options);
|
|
25
|
-
return ({ request }) => handler(request);
|
|
31
|
+
return ({ request }) => handler(forwarded(request, options));
|
|
26
32
|
}
|
|
27
33
|
function createTanStackInvokeToolHandler(mcp, options = {}) {
|
|
28
34
|
const handler = createInvokeToolHandler(mcp, options);
|
|
29
|
-
return ({ request, params }) => handler(request, params.tool);
|
|
35
|
+
return ({ request, params }) => handler(forwarded(request, options), params.tool);
|
|
30
36
|
}
|
|
31
37
|
function createTanStackOAuthProtectedResourceMetadataHandler(mcp, options = {}) {
|
|
32
38
|
const handler = createOAuthProtectedResourceMetadataHandler(mcp, options);
|
|
33
|
-
return ({ request }) => handler(request);
|
|
39
|
+
return ({ request }) => handler(forwarded(request, options));
|
|
34
40
|
}
|
|
35
41
|
export {
|
|
36
42
|
createTanStackInvokeToolHandler,
|
|
@@ -116,11 +116,16 @@ function relativeImportSpecifier(routeFile, target) {
|
|
|
116
116
|
const withoutExt = rel.replace(/\.ts$/, "");
|
|
117
117
|
return withoutExt.startsWith(".") ? withoutExt : `./${withoutExt}`;
|
|
118
118
|
}
|
|
119
|
-
function buildRouteSource(route, resourcePath, metadataPath, mcpEntry, projectRoot) {
|
|
119
|
+
function buildRouteSource(route, resourcePath, metadataPath, trustForwardedHost, mcpEntry, projectRoot) {
|
|
120
120
|
const mcpImport = relativeImportSpecifier(route.file, mcpEntry);
|
|
121
121
|
const routeRel = normalizePath((0, import_node_path.relative)(projectRoot, route.file));
|
|
122
122
|
const note = route.spaFallbackNote ? " // ANY: TanStack returns SPA HTML for methods not in `handlers`; the SDK 405s instead.\n" : "";
|
|
123
|
-
const
|
|
123
|
+
const optionEntries = [`resourcePath: "${resourcePath}"`];
|
|
124
|
+
if (metadataPath !== void 0)
|
|
125
|
+
optionEntries.push(`metadataPath: "${metadataPath}"`);
|
|
126
|
+
if (trustForwardedHost)
|
|
127
|
+
optionEntries.push("trustForwardedHost: true");
|
|
128
|
+
const runtimeOptions = `{ ${optionEntries.join(", ")} }`;
|
|
124
129
|
return `${GENERATED_BANNER}
|
|
125
130
|
// route: ${route.routeLiteral}
|
|
126
131
|
// emitted to: ${routeRel}
|
|
@@ -223,6 +228,7 @@ function mcpPlugin(options = {}) {
|
|
|
223
228
|
}
|
|
224
229
|
const metadataUrlPath = canonicalUrlPath(options.metadataPath ?? OAUTH_PROTECTED_RESOURCE_METADATA_PATH);
|
|
225
230
|
const injectedMetadataPath = emitProtectedResourceMetadataRoute ? metadataUrlPath : void 0;
|
|
231
|
+
const trustForwardedHost = options.trustForwardedHost !== false;
|
|
226
232
|
let projectRoot = process.cwd();
|
|
227
233
|
let mcpEntry = (0, import_node_path.resolve)(projectRoot, mcpEntryOption);
|
|
228
234
|
let { routesDir, mcpRouteFile, metadataRouteFile, listToolsRouteFile, invokeToolRouteFile } = resolveAllRoutes(
|
|
@@ -270,7 +276,10 @@ function mcpPlugin(options = {}) {
|
|
|
270
276
|
}
|
|
271
277
|
for (const route of routes) {
|
|
272
278
|
expected.add(route.file);
|
|
273
|
-
writeIfChanged(
|
|
279
|
+
writeIfChanged(
|
|
280
|
+
route.file,
|
|
281
|
+
buildRouteSource(route, urlPath, injectedMetadataPath, trustForwardedHost, mcpEntry, projectRoot)
|
|
282
|
+
);
|
|
274
283
|
}
|
|
275
284
|
}
|
|
276
285
|
for (const file of findAdoptedFiles(routesDir)) {
|
|
@@ -64,6 +64,17 @@ interface McpPluginOptions {
|
|
|
64
64
|
* @default "/.well-known/oauth-protected-resource"
|
|
65
65
|
*/
|
|
66
66
|
metadataPath?: string;
|
|
67
|
+
/**
|
|
68
|
+
* Derive the public origin of the advertised OAuth `resource`/metadata URLs
|
|
69
|
+
* from `X-Forwarded-Host` instead of the rewritten `Host`. Lovable's web-proxy
|
|
70
|
+
* serves a custom domain by rewriting `Host` to the internal backend and
|
|
71
|
+
* overwriting `X-Forwarded-Host` with the real public host, so the default is
|
|
72
|
+
* `true` to make custom domains work out of the box. Set `false` only when
|
|
73
|
+
* deploying behind a proxy that does not overwrite the header (a client could
|
|
74
|
+
* then spoof it to redirect the advertised resource).
|
|
75
|
+
* @default true
|
|
76
|
+
*/
|
|
77
|
+
trustForwardedHost?: boolean;
|
|
67
78
|
}
|
|
68
79
|
|
|
69
80
|
declare function assertUrlPathShape(urlPath: string): string;
|
|
@@ -64,6 +64,17 @@ interface McpPluginOptions {
|
|
|
64
64
|
* @default "/.well-known/oauth-protected-resource"
|
|
65
65
|
*/
|
|
66
66
|
metadataPath?: string;
|
|
67
|
+
/**
|
|
68
|
+
* Derive the public origin of the advertised OAuth `resource`/metadata URLs
|
|
69
|
+
* from `X-Forwarded-Host` instead of the rewritten `Host`. Lovable's web-proxy
|
|
70
|
+
* serves a custom domain by rewriting `Host` to the internal backend and
|
|
71
|
+
* overwriting `X-Forwarded-Host` with the real public host, so the default is
|
|
72
|
+
* `true` to make custom domains work out of the box. Set `false` only when
|
|
73
|
+
* deploying behind a proxy that does not overwrite the header (a client could
|
|
74
|
+
* then spoof it to redirect the advertised resource).
|
|
75
|
+
* @default true
|
|
76
|
+
*/
|
|
77
|
+
trustForwardedHost?: boolean;
|
|
67
78
|
}
|
|
68
79
|
|
|
69
80
|
declare function assertUrlPathShape(urlPath: string): string;
|
|
@@ -85,11 +85,16 @@ function relativeImportSpecifier(routeFile, target) {
|
|
|
85
85
|
const withoutExt = rel.replace(/\.ts$/, "");
|
|
86
86
|
return withoutExt.startsWith(".") ? withoutExt : `./${withoutExt}`;
|
|
87
87
|
}
|
|
88
|
-
function buildRouteSource(route, resourcePath, metadataPath, mcpEntry, projectRoot) {
|
|
88
|
+
function buildRouteSource(route, resourcePath, metadataPath, trustForwardedHost, mcpEntry, projectRoot) {
|
|
89
89
|
const mcpImport = relativeImportSpecifier(route.file, mcpEntry);
|
|
90
90
|
const routeRel = normalizePath(relative(projectRoot, route.file));
|
|
91
91
|
const note = route.spaFallbackNote ? " // ANY: TanStack returns SPA HTML for methods not in `handlers`; the SDK 405s instead.\n" : "";
|
|
92
|
-
const
|
|
92
|
+
const optionEntries = [`resourcePath: "${resourcePath}"`];
|
|
93
|
+
if (metadataPath !== void 0)
|
|
94
|
+
optionEntries.push(`metadataPath: "${metadataPath}"`);
|
|
95
|
+
if (trustForwardedHost)
|
|
96
|
+
optionEntries.push("trustForwardedHost: true");
|
|
97
|
+
const runtimeOptions = `{ ${optionEntries.join(", ")} }`;
|
|
93
98
|
return `${GENERATED_BANNER}
|
|
94
99
|
// route: ${route.routeLiteral}
|
|
95
100
|
// emitted to: ${routeRel}
|
|
@@ -192,6 +197,7 @@ function mcpPlugin(options = {}) {
|
|
|
192
197
|
}
|
|
193
198
|
const metadataUrlPath = canonicalUrlPath(options.metadataPath ?? OAUTH_PROTECTED_RESOURCE_METADATA_PATH);
|
|
194
199
|
const injectedMetadataPath = emitProtectedResourceMetadataRoute ? metadataUrlPath : void 0;
|
|
200
|
+
const trustForwardedHost = options.trustForwardedHost !== false;
|
|
195
201
|
let projectRoot = process.cwd();
|
|
196
202
|
let mcpEntry = resolve(projectRoot, mcpEntryOption);
|
|
197
203
|
let { routesDir, mcpRouteFile, metadataRouteFile, listToolsRouteFile, invokeToolRouteFile } = resolveAllRoutes(
|
|
@@ -239,7 +245,10 @@ function mcpPlugin(options = {}) {
|
|
|
239
245
|
}
|
|
240
246
|
for (const route of routes) {
|
|
241
247
|
expected.add(route.file);
|
|
242
|
-
writeIfChanged(
|
|
248
|
+
writeIfChanged(
|
|
249
|
+
route.file,
|
|
250
|
+
buildRouteSource(route, urlPath, injectedMetadataPath, trustForwardedHost, mcpEntry, projectRoot)
|
|
251
|
+
);
|
|
243
252
|
}
|
|
244
253
|
}
|
|
245
254
|
for (const file of findAdoptedFiles(routesDir)) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@lovable.dev/mcp-js",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.13.0",
|
|
4
4
|
"description": "Author MCP servers for Lovable apps. Declare tools with defineTool, register them in defineMcp, and a framework adapter (TanStack or Supabase Edge Functions) emits the route(s) at build time.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"repository": {
|