creator-mcp 1.0.4 → 1.0.5

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/auth.js CHANGED
@@ -6,17 +6,23 @@
6
6
  * 2. Supabase JWT: validated via Supabase Auth API (backward compatible)
7
7
  */
8
8
  import { createUserClient, exchangeMcpToken } from "./client.js";
9
+ import { attachAuthToUsageContext } from "./usage.js";
9
10
  const MCP_TOKEN_PREFIX = "mcp_";
10
11
  /**
11
12
  * Exchange an MCP API token (mcp_...) for a short-lived Supabase session.
12
13
  */
13
14
  async function authenticateWithMcpToken(token) {
14
15
  const session = await exchangeMcpToken(token);
15
- return {
16
+ const authContext = {
16
17
  userId: session.userId,
17
18
  email: session.email,
18
19
  token: session.accessToken,
20
+ tokenId: session.tokenId,
21
+ tokenName: session.tokenName,
22
+ authType: "mcp_token",
19
23
  };
24
+ attachAuthToUsageContext(authContext);
25
+ return authContext;
20
26
  }
21
27
  /**
22
28
  * Validate a Supabase JWT token via the Auth API.
@@ -27,11 +33,16 @@ async function authenticateWithJwt(token) {
27
33
  const { data: sessionData, error: sessionError } = await client.auth.getSession();
28
34
  if (!sessionError && sessionData?.session?.user) {
29
35
  const user = sessionData.session.user;
30
- return {
36
+ const authContext = {
31
37
  userId: user.id,
32
38
  email: user.email ?? null,
33
39
  token,
40
+ tokenId: null,
41
+ tokenName: "JWT Session",
42
+ authType: "supabase_jwt",
34
43
  };
44
+ attachAuthToUsageContext(authContext);
45
+ return authContext;
35
46
  }
36
47
  // Fallback: validate via getUser
37
48
  const { data: { user }, error, } = await client.auth.getUser(token);
@@ -39,11 +50,16 @@ async function authenticateWithJwt(token) {
39
50
  throw new Error("Invalid Supabase token — authentication failed. " +
40
51
  "Ensure your CREATOR_OS_TOKEN is a valid access token.");
41
52
  }
42
- return {
53
+ const authContext = {
43
54
  userId: user.id,
44
55
  email: user.email ?? null,
45
56
  token,
57
+ tokenId: null,
58
+ tokenName: "JWT Session",
59
+ authType: "supabase_jwt",
46
60
  };
61
+ attachAuthToUsageContext(authContext);
62
+ return authContext;
47
63
  }
48
64
  /**
49
65
  * Authenticate using the CREATOR_OS_TOKEN environment variable.
package/dist/client.d.ts CHANGED
@@ -12,6 +12,8 @@ interface ExchangedSession {
12
12
  expiresAt: number;
13
13
  userId: string;
14
14
  email: string | null;
15
+ tokenId: string;
16
+ tokenName: string | null;
15
17
  }
16
18
  export declare function getRuntimeConfig(): RuntimeConfig;
17
19
  /**
package/dist/client.js CHANGED
@@ -91,6 +91,8 @@ export async function exchangeMcpToken(token) {
91
91
  expiresAt: data.session.expires_at ?? now + 3600,
92
92
  userId: data.user.id,
93
93
  email: data.user.email ?? payload.email,
94
+ tokenId: payload.token_id,
95
+ tokenName: payload.token_name ?? null,
94
96
  };
95
97
  exchangedSessionCache.set(token, session);
96
98
  return session;
package/dist/index.js CHANGED
@@ -21,9 +21,10 @@ import { registerSupportTools } from "./tools/support.js";
21
21
  import { registerAdminTools } from "./tools/admin.js";
22
22
  import { registerResources } from "./resources.js";
23
23
  import { registerPrompts } from "./prompts.js";
24
+ import { recordCurrentUsage, runWithUsageContext } from "./usage.js";
24
25
  const server = new McpServer({
25
26
  name: "creator-os-mcp",
26
- version: "1.0.4",
27
+ version: "1.0.5",
27
28
  }, {
28
29
  instructions: [
29
30
  "Creator OS MCP Server — a comprehensive toolkit for YouTube creators.",
@@ -47,6 +48,32 @@ const server = new McpServer({
47
48
  logging: {},
48
49
  },
49
50
  });
51
+ const instrumentedServer = server;
52
+ function instrumentHandlerRegistration(targetType, register) {
53
+ return (...args) => {
54
+ const name = typeof args[0] === "string" ? args[0] : "unknown";
55
+ const handler = args.at(-1);
56
+ if (typeof handler !== "function") {
57
+ return register(...args);
58
+ }
59
+ const wrappedArgs = [...args];
60
+ wrappedArgs[wrappedArgs.length - 1] = async (...handlerArgs) => runWithUsageContext(targetType, name, async () => {
61
+ try {
62
+ const result = await handler(...handlerArgs);
63
+ await recordCurrentUsage("success");
64
+ return result;
65
+ }
66
+ catch (error) {
67
+ await recordCurrentUsage("error", error);
68
+ throw error;
69
+ }
70
+ });
71
+ return register(...wrappedArgs);
72
+ };
73
+ }
74
+ instrumentedServer.tool = instrumentHandlerRegistration("tool", instrumentedServer.tool.bind(server));
75
+ instrumentedServer.resource = instrumentHandlerRegistration("resource", instrumentedServer.resource.bind(server));
76
+ instrumentedServer.prompt = instrumentHandlerRegistration("prompt", instrumentedServer.prompt.bind(server));
50
77
  // ── Register all capabilities ──────────────────────────────────────
51
78
  registerPipelineTools(server);
52
79
  registerDealTools(server);
package/dist/types.d.ts CHANGED
@@ -106,4 +106,7 @@ export interface AuthContext {
106
106
  userId: string;
107
107
  email: string | null;
108
108
  token: string;
109
+ tokenId: string | null;
110
+ tokenName: string | null;
111
+ authType: "mcp_token" | "supabase_jwt";
109
112
  }
@@ -0,0 +1,5 @@
1
+ import type { AuthContext } from "./types.js";
2
+ export type UsageTargetType = "tool" | "resource" | "prompt";
3
+ export declare function runWithUsageContext<T>(targetType: UsageTargetType, targetName: string, fn: () => Promise<T>): Promise<T>;
4
+ export declare function attachAuthToUsageContext(auth: AuthContext): void;
5
+ export declare function recordCurrentUsage(status: "success" | "error", error?: unknown): Promise<void>;
package/dist/usage.js ADDED
@@ -0,0 +1,64 @@
1
+ import { AsyncLocalStorage } from "node:async_hooks";
2
+ import { createUserClient } from "./client.js";
3
+ const usageStorage = new AsyncLocalStorage();
4
+ function getCurrentContext() {
5
+ return usageStorage.getStore();
6
+ }
7
+ function normalizeErrorMessage(error) {
8
+ if (!error)
9
+ return null;
10
+ if (error instanceof Error)
11
+ return error.message.slice(0, 2000);
12
+ if (typeof error === "string")
13
+ return error.slice(0, 2000);
14
+ try {
15
+ return JSON.stringify(error).slice(0, 2000);
16
+ }
17
+ catch {
18
+ return "Unknown MCP error";
19
+ }
20
+ }
21
+ export function runWithUsageContext(targetType, targetName, fn) {
22
+ return usageStorage.run({
23
+ targetType,
24
+ targetName,
25
+ startedAt: Date.now(),
26
+ auth: null,
27
+ }, fn);
28
+ }
29
+ export function attachAuthToUsageContext(auth) {
30
+ const context = getCurrentContext();
31
+ if (context) {
32
+ context.auth = auth;
33
+ }
34
+ }
35
+ export async function recordCurrentUsage(status, error) {
36
+ const context = getCurrentContext();
37
+ if (!context?.auth) {
38
+ return;
39
+ }
40
+ try {
41
+ const client = createUserClient(context.auth.token);
42
+ const durationMs = Date.now() - context.startedAt;
43
+ await client.from("mcp_usage_events").insert({
44
+ user_id: context.auth.userId,
45
+ token_id: context.auth.tokenId,
46
+ token_name: context.auth.tokenName ??
47
+ (context.auth.authType === "supabase_jwt"
48
+ ? "JWT Session"
49
+ : "Unknown token"),
50
+ auth_type: context.auth.authType,
51
+ target_type: context.targetType,
52
+ target_name: context.targetName,
53
+ status,
54
+ duration_ms: durationMs,
55
+ error_message: normalizeErrorMessage(error),
56
+ metadata: {
57
+ source: "creator-mcp",
58
+ },
59
+ });
60
+ }
61
+ catch (trackingError) {
62
+ console.error("Failed to record MCP usage event:", trackingError);
63
+ }
64
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "creator-mcp",
3
- "version": "1.0.4",
3
+ "version": "1.0.5",
4
4
  "description": "MCP server for Creator OS — access your pipeline, deals, analytics, AI tools, and more via any MCP-compatible client",
5
5
  "type": "module",
6
6
  "license": "MIT",