@fml-inc/fml 0.0.24 → 0.0.26

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.
@@ -0,0 +1,12 @@
1
+ {
2
+ "name": "fml",
3
+ "description": "FML agent tools for Claude Code",
4
+ "mcpServers": {
5
+ "fml": {
6
+ "command": "node",
7
+ "args": [
8
+ "${CLAUDE_PLUGIN_ROOT}/bin/mcp-server"
9
+ ]
10
+ }
11
+ }
12
+ }
package/README.md ADDED
@@ -0,0 +1,101 @@
1
+ # FML
2
+
3
+ Agent tools for AI coding assistants. Installs as a [Claude Code plugin](https://docs.anthropic.com/en/docs/claude-code/plugins) with MCP tools for session analytics, cost tracking, integrations, and team workflows — powered by [Panopticon](https://github.com/fml-inc/panopticon) for local data collection.
4
+
5
+ ## Install
6
+
7
+ ```bash
8
+ npm install -g @fml-inc/fml
9
+ ```
10
+
11
+ This installs the plugin, registers hooks and MCP tools in Claude Code, and bootstraps Panopticon for local data collection. Start a new session to activate.
12
+
13
+ Then sign in:
14
+
15
+ ```bash
16
+ fml login
17
+ ```
18
+
19
+ ## What it does
20
+
21
+ **Local observability** — Panopticon captures OpenTelemetry signals, hook events, session files, and API traffic from Claude Code, Gemini CLI, and Codex CLI into a local SQLite database.
22
+
23
+ **MCP tools for your agent** — Once installed, Claude Code gets tools to query your sessions, costs, activity, and connected integrations directly in conversation.
24
+
25
+ **Cloud sync** — Optionally sync local data to the FML dashboard for team-wide visibility, config snapshots, and automations.
26
+
27
+ ## MCP tools
28
+
29
+ These tools are available to Claude Code via the plugin:
30
+
31
+ | Tool | Description |
32
+ |------|-------------|
33
+ | `get_engineering_activity` | Activity summary — sessions, prompts, tools, costs |
34
+ | `list_engineering_sessions` | List recent sessions with stats |
35
+ | `search_engineering_sessions` | Search across all sessions |
36
+ | `get_session_timeline` | Messages and tool calls for a session |
37
+ | `get_session_turns` | Per-turn token usage for a session |
38
+ | `get_ai_spending` | Token usage and cost breakdowns |
39
+ | `whoami` | Current auth and org status |
40
+ | `fml_list_integrations` | Connected integrations (Slack, GitHub, Linear, Sentry, etc.) |
41
+ | `fml_query_*` | Query connected integrations directly |
42
+ | `fml_list_messages` | Conversation messages |
43
+ | `fml_search_analysis` | Search codebase analysis results |
44
+ | `fml_run_analysis_workflow` | Run deep analysis workflows |
45
+ | `fml_list_skills` | Browse and load skills |
46
+ | `list_repo_configs` | Team config snapshots |
47
+
48
+ ## CLI
49
+
50
+ ```
51
+ fml install Register plugin, hooks, and daemons
52
+ fml uninstall Remove plugin and hooks
53
+ --target <t> Target: claude, gemini, codex, claude-desktop, all
54
+ --purge Also remove all data, logs, and auth tokens
55
+ fml update Update to the latest version
56
+
57
+ fml login Sign in to your FML account
58
+ fml logout Sign out and clear credentials
59
+ fml org [slug] Show or select organization
60
+ fml status Show auth and daemon status
61
+ fml doctor Check configuration and connectivity
62
+
63
+ fml open Open FML dashboard in browser
64
+ fml start Start panopticon server
65
+ fml stop Stop panopticon server
66
+
67
+ fml activity Activity summary
68
+ --since <duration> Time window (e.g. "24h", "7d")
69
+ fml sessions List recent sessions
70
+ fml timeline <id> Events for a session
71
+ fml spending Token usage and cost breakdown
72
+ fml search <query> Search across sessions
73
+
74
+ fml sync setup Configure sync targets
75
+ fml sync list List sync targets
76
+ fml sync add <n> <url> Add a sync target
77
+ fml sync remove <name> Remove a sync target
78
+ fml sync status Show sync status
79
+ fml sync reset [name] Reset sync watermarks
80
+ ```
81
+
82
+ ## Development
83
+
84
+ ```bash
85
+ pnpm install # Install dependencies
86
+ pnpm dev # Watch mode (tsup)
87
+ pnpm test # Run tests (Vitest)
88
+ pnpm type-check # Type check
89
+ ```
90
+
91
+ To test the full install flow:
92
+
93
+ ```bash
94
+ pnpm build && pnpm pack
95
+ npm install -g ./fml-inc-fml-*.tgz
96
+ fml install
97
+ ```
98
+
99
+ ## License
100
+
101
+ Proprietary — see [LICENSE](LICENSE).
package/dist/cli.js CHANGED
@@ -554,7 +554,7 @@ function handleUninstall(opts) {
554
554
  // src/commands/update.ts
555
555
  import { execSync as execSync2 } from "child_process";
556
556
  async function handleUpdate() {
557
- const currentVersion = true ? "0.0.24+355a206" : "unknown";
557
+ const currentVersion = true ? "0.0.26+def4e37" : "unknown";
558
558
  console.log(`Current: ${currentVersion}`);
559
559
  console.log("Updating via npm...\n");
560
560
  try {
@@ -1615,7 +1615,7 @@ if (process.argv.length <= 2 || process.argv.includes("--help") || process.argv.
1615
1615
  printBanner();
1616
1616
  }
1617
1617
  var program = new Command().name("fml").description("FML agent tools for Claude Code").version(
1618
- true ? "0.0.24+355a206" : "dev"
1618
+ true ? "0.0.26+def4e37" : "dev"
1619
1619
  );
1620
1620
  program.command("tools", { hidden: true }).description("List all available CLI commands (including hidden agent tools)").action(() => {
1621
1621
  function formatCmd(cmd, prefix = "") {
@@ -1,4 +1,5 @@
1
1
  #!/usr/bin/env node
2
+ import "./chunk-PZ5AY32C.js";
2
3
 
3
4
  // src/postinstall.ts
4
5
  import { execFileSync } from "child_process";
@@ -78,4 +79,7 @@ try {
78
79
  });
79
80
  } catch {
80
81
  }
82
+ export {
83
+ bootstrapPanopticon
84
+ };
81
85
  //# sourceMappingURL=postinstall.js.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/postinstall.ts"],"sourcesContent":["#!/usr/bin/env node\n/**\n * Lightweight postinstall script — runs BEFORE any @fml-inc/panopticon imports.\n *\n * 1. Bootstrap panopticon globally if missing or outdated\n * 2. Spawn `fml install` (which can now resolve panopticon)\n */\nimport { execFileSync } from \"node:child_process\";\nimport { dirname, join } from \"node:path\";\nimport { fileURLToPath } from \"node:url\";\n\nconst __dirname = dirname(fileURLToPath(import.meta.url));\n\nfunction bootstrapPanopticon(): void {\n const npmEnv = { ...process.env };\n delete npmEnv.npm_config_registry; // Let scoped registry from .npmrc take effect\n\n // Check if panopticon is installed globally\n let globalVersion: string | null = null;\n try {\n const json = execFileSync(\n \"npm\",\n [\"ls\", \"-g\", \"@fml-inc/panopticon\", \"--json\", \"--depth=0\"],\n { encoding: \"utf-8\", timeout: 15_000, stdio: \"pipe\", env: npmEnv },\n );\n const parsed = JSON.parse(json);\n globalVersion =\n parsed?.dependencies?.[\"@fml-inc/panopticon\"]?.version ?? null;\n } catch {\n // Not installed globally or npm ls failed\n }\n\n if (!globalVersion) {\n console.log(\"[postinstall] Installing @fml-inc/panopticon globally...\");\n try {\n execFileSync(\"npm\", [\"install\", \"-g\", \"@fml-inc/panopticon@latest\"], {\n encoding: \"utf-8\",\n timeout: 120_000,\n stdio: \"pipe\",\n env: npmEnv,\n });\n console.log(\"[postinstall] Installed @fml-inc/panopticon\");\n } catch (err: unknown) {\n const msg = err instanceof Error ? err.message : String(err);\n console.error(`[postinstall] Failed to install panopticon: ${msg}`);\n console.error(\n \"[postinstall] Install manually: npm install -g @fml-inc/panopticon@latest\",\n );\n return;\n }\n } else {\n // Check if outdated (best effort)\n let isOutdated = false;\n try {\n execFileSync(\"npm\", [\"outdated\", \"-g\", \"@fml-inc/panopticon\"], {\n encoding: \"utf-8\",\n timeout: 30_000,\n stdio: \"pipe\",\n env: npmEnv,\n });\n } catch (err: unknown) {\n const e = err as { status?: number };\n if (e.status === 1) isOutdated = true;\n }\n\n if (isOutdated) {\n console.log(\"[postinstall] Updating @fml-inc/panopticon...\");\n try {\n execFileSync(\"npm\", [\"install\", \"-g\", \"@fml-inc/panopticon@latest\"], {\n encoding: \"utf-8\",\n timeout: 120_000,\n stdio: \"pipe\",\n env: npmEnv,\n });\n console.log(\"[postinstall] Updated @fml-inc/panopticon\");\n } catch {\n // Not fatal — continue with current version\n }\n } else {\n console.log(\n `[postinstall] @fml-inc/panopticon@${globalVersion} (up to date)`,\n );\n }\n }\n}\n\n// Step 1: Bootstrap panopticon\nbootstrapPanopticon();\n\n// Step 2: Run fml install (panopticon is now resolvable)\nconst fmlBin = join(__dirname, \"..\", \"bin\", \"fml\");\ntry {\n execFileSync(\"node\", [fmlBin, \"install\"], {\n stdio: \"inherit\",\n timeout: 120_000,\n });\n} catch {\n // fml install failed — not fatal for postinstall\n}\n"],"mappings":";;;AAOA,SAAS,oBAAoB;AAC7B,SAAS,SAAS,YAAY;AAC9B,SAAS,qBAAqB;AAE9B,IAAM,YAAY,QAAQ,cAAc,YAAY,GAAG,CAAC;AAExD,SAAS,sBAA4B;AACnC,QAAM,SAAS,EAAE,GAAG,QAAQ,IAAI;AAChC,SAAO,OAAO;AAGd,MAAI,gBAA+B;AACnC,MAAI;AACF,UAAM,OAAO;AAAA,MACX;AAAA,MACA,CAAC,MAAM,MAAM,uBAAuB,UAAU,WAAW;AAAA,MACzD,EAAE,UAAU,SAAS,SAAS,MAAQ,OAAO,QAAQ,KAAK,OAAO;AAAA,IACnE;AACA,UAAM,SAAS,KAAK,MAAM,IAAI;AAC9B,oBACE,QAAQ,eAAe,qBAAqB,GAAG,WAAW;AAAA,EAC9D,QAAQ;AAAA,EAER;AAEA,MAAI,CAAC,eAAe;AAClB,YAAQ,IAAI,0DAA0D;AACtE,QAAI;AACF,mBAAa,OAAO,CAAC,WAAW,MAAM,4BAA4B,GAAG;AAAA,QACnE,UAAU;AAAA,QACV,SAAS;AAAA,QACT,OAAO;AAAA,QACP,KAAK;AAAA,MACP,CAAC;AACD,cAAQ,IAAI,6CAA6C;AAAA,IAC3D,SAAS,KAAc;AACrB,YAAM,MAAM,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG;AAC3D,cAAQ,MAAM,+CAA+C,GAAG,EAAE;AAClE,cAAQ;AAAA,QACN;AAAA,MACF;AACA;AAAA,IACF;AAAA,EACF,OAAO;AAEL,QAAI,aAAa;AACjB,QAAI;AACF,mBAAa,OAAO,CAAC,YAAY,MAAM,qBAAqB,GAAG;AAAA,QAC7D,UAAU;AAAA,QACV,SAAS;AAAA,QACT,OAAO;AAAA,QACP,KAAK;AAAA,MACP,CAAC;AAAA,IACH,SAAS,KAAc;AACrB,YAAM,IAAI;AACV,UAAI,EAAE,WAAW,EAAG,cAAa;AAAA,IACnC;AAEA,QAAI,YAAY;AACd,cAAQ,IAAI,+CAA+C;AAC3D,UAAI;AACF,qBAAa,OAAO,CAAC,WAAW,MAAM,4BAA4B,GAAG;AAAA,UACnE,UAAU;AAAA,UACV,SAAS;AAAA,UACT,OAAO;AAAA,UACP,KAAK;AAAA,QACP,CAAC;AACD,gBAAQ,IAAI,2CAA2C;AAAA,MACzD,QAAQ;AAAA,MAER;AAAA,IACF,OAAO;AACL,cAAQ;AAAA,QACN,qCAAqC,aAAa;AAAA,MACpD;AAAA,IACF;AAAA,EACF;AACF;AAGA,oBAAoB;AAGpB,IAAM,SAAS,KAAK,WAAW,MAAM,OAAO,KAAK;AACjD,IAAI;AACF,eAAa,QAAQ,CAAC,QAAQ,SAAS,GAAG;AAAA,IACxC,OAAO;AAAA,IACP,SAAS;AAAA,EACX,CAAC;AACH,QAAQ;AAER;","names":[]}
1
+ {"version":3,"sources":["../src/postinstall.ts"],"sourcesContent":["#!/usr/bin/env node\n/**\n * Lightweight postinstall script — runs BEFORE any @fml-inc/panopticon imports.\n *\n * 1. Bootstrap panopticon globally if missing or outdated\n * 2. Spawn `fml install` (which can now resolve panopticon)\n */\nimport { execFileSync } from \"node:child_process\";\nimport { dirname, join } from \"node:path\";\nimport { fileURLToPath } from \"node:url\";\n\nconst __dirname = dirname(fileURLToPath(import.meta.url));\n\nexport function bootstrapPanopticon(): void {\n const npmEnv = { ...process.env };\n delete npmEnv.npm_config_registry; // Let scoped registry from .npmrc take effect\n\n // Check if panopticon is installed globally\n let globalVersion: string | null = null;\n try {\n const json = execFileSync(\n \"npm\",\n [\"ls\", \"-g\", \"@fml-inc/panopticon\", \"--json\", \"--depth=0\"],\n { encoding: \"utf-8\", timeout: 15_000, stdio: \"pipe\", env: npmEnv },\n );\n const parsed = JSON.parse(json);\n globalVersion =\n parsed?.dependencies?.[\"@fml-inc/panopticon\"]?.version ?? null;\n } catch {\n // Not installed globally or npm ls failed\n }\n\n if (!globalVersion) {\n console.log(\"[postinstall] Installing @fml-inc/panopticon globally...\");\n try {\n execFileSync(\"npm\", [\"install\", \"-g\", \"@fml-inc/panopticon@latest\"], {\n encoding: \"utf-8\",\n timeout: 120_000,\n stdio: \"pipe\",\n env: npmEnv,\n });\n console.log(\"[postinstall] Installed @fml-inc/panopticon\");\n } catch (err: unknown) {\n const msg = err instanceof Error ? err.message : String(err);\n console.error(`[postinstall] Failed to install panopticon: ${msg}`);\n console.error(\n \"[postinstall] Install manually: npm install -g @fml-inc/panopticon@latest\",\n );\n return;\n }\n } else {\n // Check if outdated (best effort)\n let isOutdated = false;\n try {\n execFileSync(\"npm\", [\"outdated\", \"-g\", \"@fml-inc/panopticon\"], {\n encoding: \"utf-8\",\n timeout: 30_000,\n stdio: \"pipe\",\n env: npmEnv,\n });\n } catch (err: unknown) {\n const e = err as { status?: number };\n if (e.status === 1) isOutdated = true;\n }\n\n if (isOutdated) {\n console.log(\"[postinstall] Updating @fml-inc/panopticon...\");\n try {\n execFileSync(\"npm\", [\"install\", \"-g\", \"@fml-inc/panopticon@latest\"], {\n encoding: \"utf-8\",\n timeout: 120_000,\n stdio: \"pipe\",\n env: npmEnv,\n });\n console.log(\"[postinstall] Updated @fml-inc/panopticon\");\n } catch {\n // Not fatal — continue with current version\n }\n } else {\n console.log(\n `[postinstall] @fml-inc/panopticon@${globalVersion} (up to date)`,\n );\n }\n }\n}\n\n// Step 1: Bootstrap panopticon\nbootstrapPanopticon();\n\n// Step 2: Run fml install (panopticon is now resolvable)\nconst fmlBin = join(__dirname, \"..\", \"bin\", \"fml\");\ntry {\n execFileSync(\"node\", [fmlBin, \"install\"], {\n stdio: \"inherit\",\n timeout: 120_000,\n });\n} catch {\n // fml install failed — not fatal for postinstall\n}\n"],"mappings":";;;;AAOA,SAAS,oBAAoB;AAC7B,SAAS,SAAS,YAAY;AAC9B,SAAS,qBAAqB;AAE9B,IAAM,YAAY,QAAQ,cAAc,YAAY,GAAG,CAAC;AAEjD,SAAS,sBAA4B;AAC1C,QAAM,SAAS,EAAE,GAAG,QAAQ,IAAI;AAChC,SAAO,OAAO;AAGd,MAAI,gBAA+B;AACnC,MAAI;AACF,UAAM,OAAO;AAAA,MACX;AAAA,MACA,CAAC,MAAM,MAAM,uBAAuB,UAAU,WAAW;AAAA,MACzD,EAAE,UAAU,SAAS,SAAS,MAAQ,OAAO,QAAQ,KAAK,OAAO;AAAA,IACnE;AACA,UAAM,SAAS,KAAK,MAAM,IAAI;AAC9B,oBACE,QAAQ,eAAe,qBAAqB,GAAG,WAAW;AAAA,EAC9D,QAAQ;AAAA,EAER;AAEA,MAAI,CAAC,eAAe;AAClB,YAAQ,IAAI,0DAA0D;AACtE,QAAI;AACF,mBAAa,OAAO,CAAC,WAAW,MAAM,4BAA4B,GAAG;AAAA,QACnE,UAAU;AAAA,QACV,SAAS;AAAA,QACT,OAAO;AAAA,QACP,KAAK;AAAA,MACP,CAAC;AACD,cAAQ,IAAI,6CAA6C;AAAA,IAC3D,SAAS,KAAc;AACrB,YAAM,MAAM,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG;AAC3D,cAAQ,MAAM,+CAA+C,GAAG,EAAE;AAClE,cAAQ;AAAA,QACN;AAAA,MACF;AACA;AAAA,IACF;AAAA,EACF,OAAO;AAEL,QAAI,aAAa;AACjB,QAAI;AACF,mBAAa,OAAO,CAAC,YAAY,MAAM,qBAAqB,GAAG;AAAA,QAC7D,UAAU;AAAA,QACV,SAAS;AAAA,QACT,OAAO;AAAA,QACP,KAAK;AAAA,MACP,CAAC;AAAA,IACH,SAAS,KAAc;AACrB,YAAM,IAAI;AACV,UAAI,EAAE,WAAW,EAAG,cAAa;AAAA,IACnC;AAEA,QAAI,YAAY;AACd,cAAQ,IAAI,+CAA+C;AAC3D,UAAI;AACF,qBAAa,OAAO,CAAC,WAAW,MAAM,4BAA4B,GAAG;AAAA,UACnE,UAAU;AAAA,UACV,SAAS;AAAA,UACT,OAAO;AAAA,UACP,KAAK;AAAA,QACP,CAAC;AACD,gBAAQ,IAAI,2CAA2C;AAAA,MACzD,QAAQ;AAAA,MAER;AAAA,IACF,OAAO;AACL,cAAQ;AAAA,QACN,qCAAqC,aAAa;AAAA,MACpD;AAAA,IACF;AAAA,EACF;AACF;AAGA,oBAAoB;AAGpB,IAAM,SAAS,KAAK,WAAW,MAAM,OAAO,KAAK;AACjD,IAAI;AACF,eAAa,QAAQ,CAAC,QAAQ,SAAS,GAAG;AAAA,IACxC,OAAO;AAAA,IACP,SAAS;AAAA,EACX,CAAC;AACH,QAAQ;AAER;","names":[]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@fml-inc/fml",
3
- "version": "0.0.24",
3
+ "version": "0.0.26",
4
4
  "description": "FML agent tools for Claude Code",
5
5
  "license": "SEE LICENSE IN LICENSE",
6
6
  "type": "module",
@@ -27,6 +27,7 @@
27
27
  "scripts": {
28
28
  "build": "tsup",
29
29
  "dev": "tsup --watch",
30
+ "prepack": "node scripts/generate-plugin-manifest.js",
30
31
  "pack:local": "pnpm build && pnpm pack",
31
32
  "postinstall": "node ./dist/postinstall.js && claude plugin update 2>/dev/null || true",
32
33
  "type-check": "tsc --noEmit",
@@ -34,7 +35,7 @@
34
35
  "test:watch": "vitest"
35
36
  },
36
37
  "dependencies": {
37
- "@fml-inc/panopticon": "^0.1.4",
38
+ "@fml-inc/panopticon": "^0.1.8",
38
39
  "@modelcontextprotocol/sdk": "^1.0.0",
39
40
  "better-sqlite3": "^11.0.0",
40
41
  "commander": "^13.1.0",