@evercam/mcp 0.0.1

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.
Files changed (146) hide show
  1. package/README.md +1017 -0
  2. package/dist/bin/evercam-mcp.d.ts +3 -0
  3. package/dist/bin/evercam-mcp.d.ts.map +1 -0
  4. package/dist/bin/evercam-mcp.js +87 -0
  5. package/dist/bin/evercam-mcp.js.map +1 -0
  6. package/dist/src/auth/auth.d.ts +9 -0
  7. package/dist/src/auth/auth.d.ts.map +1 -0
  8. package/dist/src/auth/auth.js +44 -0
  9. package/dist/src/auth/auth.js.map +1 -0
  10. package/dist/src/auth/tokenStore.d.ts +9 -0
  11. package/dist/src/auth/tokenStore.d.ts.map +1 -0
  12. package/dist/src/auth/tokenStore.js +42 -0
  13. package/dist/src/auth/tokenStore.js.map +1 -0
  14. package/dist/src/cli/auth.d.ts +13 -0
  15. package/dist/src/cli/auth.d.ts.map +1 -0
  16. package/dist/src/cli/auth.js +98 -0
  17. package/dist/src/cli/auth.js.map +1 -0
  18. package/dist/src/cli/doctor.d.ts +4 -0
  19. package/dist/src/cli/doctor.d.ts.map +1 -0
  20. package/dist/src/cli/doctor.js +54 -0
  21. package/dist/src/cli/doctor.js.map +1 -0
  22. package/dist/src/cli/profile.d.ts +10 -0
  23. package/dist/src/cli/profile.d.ts.map +1 -0
  24. package/dist/src/cli/profile.js +53 -0
  25. package/dist/src/cli/profile.js.map +1 -0
  26. package/dist/src/cli/run.d.ts +5 -0
  27. package/dist/src/cli/run.d.ts.map +1 -0
  28. package/dist/src/cli/run.js +63 -0
  29. package/dist/src/cli/run.js.map +1 -0
  30. package/dist/src/cli/serve.d.ts +13 -0
  31. package/dist/src/cli/serve.d.ts.map +1 -0
  32. package/dist/src/cli/serve.js +58 -0
  33. package/dist/src/cli/serve.js.map +1 -0
  34. package/dist/src/cli/tools.d.ts +3 -0
  35. package/dist/src/cli/tools.d.ts.map +1 -0
  36. package/dist/src/cli/tools.js +151 -0
  37. package/dist/src/cli/tools.js.map +1 -0
  38. package/dist/src/config/env.d.ts +3 -0
  39. package/dist/src/config/env.d.ts.map +1 -0
  40. package/dist/src/config/env.js +17 -0
  41. package/dist/src/config/env.js.map +1 -0
  42. package/dist/src/config/profiles.d.ts +17 -0
  43. package/dist/src/config/profiles.d.ts.map +1 -0
  44. package/dist/src/config/profiles.js +56 -0
  45. package/dist/src/config/profiles.js.map +1 -0
  46. package/dist/src/index.d.ts +7 -0
  47. package/dist/src/index.d.ts.map +1 -0
  48. package/dist/src/index.js +7 -0
  49. package/dist/src/index.js.map +1 -0
  50. package/dist/src/server.d.ts +8 -0
  51. package/dist/src/server.d.ts.map +1 -0
  52. package/dist/src/server.js +23 -0
  53. package/dist/src/server.js.map +1 -0
  54. package/dist/src/tools/anpr.d.ts +4 -0
  55. package/dist/src/tools/anpr.d.ts.map +1 -0
  56. package/dist/src/tools/anpr.js +75 -0
  57. package/dist/src/tools/anpr.js.map +1 -0
  58. package/dist/src/tools/bim.d.ts +4 -0
  59. package/dist/src/tools/bim.d.ts.map +1 -0
  60. package/dist/src/tools/bim.js +24 -0
  61. package/dist/src/tools/bim.js.map +1 -0
  62. package/dist/src/tools/cameras.d.ts +4 -0
  63. package/dist/src/tools/cameras.d.ts.map +1 -0
  64. package/dist/src/tools/cameras.js +31 -0
  65. package/dist/src/tools/cameras.js.map +1 -0
  66. package/dist/src/tools/copilot.d.ts +4 -0
  67. package/dist/src/tools/copilot.d.ts.map +1 -0
  68. package/dist/src/tools/copilot.js +58 -0
  69. package/dist/src/tools/copilot.js.map +1 -0
  70. package/dist/src/tools/detections.d.ts +4 -0
  71. package/dist/src/tools/detections.d.ts.map +1 -0
  72. package/dist/src/tools/detections.js +40 -0
  73. package/dist/src/tools/detections.js.map +1 -0
  74. package/dist/src/tools/index.d.ts +4 -0
  75. package/dist/src/tools/index.d.ts.map +1 -0
  76. package/dist/src/tools/index.js +31 -0
  77. package/dist/src/tools/index.js.map +1 -0
  78. package/dist/src/tools/media.d.ts +4 -0
  79. package/dist/src/tools/media.d.ts.map +1 -0
  80. package/dist/src/tools/media.js +38 -0
  81. package/dist/src/tools/media.js.map +1 -0
  82. package/dist/src/tools/mutations.d.ts +8 -0
  83. package/dist/src/tools/mutations.d.ts.map +1 -0
  84. package/dist/src/tools/mutations.js +41 -0
  85. package/dist/src/tools/mutations.js.map +1 -0
  86. package/dist/src/tools/notifications.d.ts +4 -0
  87. package/dist/src/tools/notifications.d.ts.map +1 -0
  88. package/dist/src/tools/notifications.js +21 -0
  89. package/dist/src/tools/notifications.js.map +1 -0
  90. package/dist/src/tools/progressPhotos.d.ts +4 -0
  91. package/dist/src/tools/progressPhotos.d.ts.map +1 -0
  92. package/dist/src/tools/progressPhotos.js +36 -0
  93. package/dist/src/tools/progressPhotos.js.map +1 -0
  94. package/dist/src/tools/projects.d.ts +4 -0
  95. package/dist/src/tools/projects.d.ts.map +1 -0
  96. package/dist/src/tools/projects.js +56 -0
  97. package/dist/src/tools/projects.js.map +1 -0
  98. package/dist/src/tools/ptz.d.ts +4 -0
  99. package/dist/src/tools/ptz.d.ts.map +1 -0
  100. package/dist/src/tools/ptz.js +38 -0
  101. package/dist/src/tools/ptz.js.map +1 -0
  102. package/dist/src/tools/shares.d.ts +4 -0
  103. package/dist/src/tools/shares.d.ts.map +1 -0
  104. package/dist/src/tools/shares.js +11 -0
  105. package/dist/src/tools/shares.js.map +1 -0
  106. package/dist/src/tools/siteAnalytics.d.ts +4 -0
  107. package/dist/src/tools/siteAnalytics.d.ts.map +1 -0
  108. package/dist/src/tools/siteAnalytics.js +51 -0
  109. package/dist/src/tools/siteAnalytics.js.map +1 -0
  110. package/dist/src/tools/snapshots.d.ts +4 -0
  111. package/dist/src/tools/snapshots.d.ts.map +1 -0
  112. package/dist/src/tools/snapshots.js +83 -0
  113. package/dist/src/tools/snapshots.js.map +1 -0
  114. package/dist/src/tools/weather.d.ts +4 -0
  115. package/dist/src/tools/weather.d.ts.map +1 -0
  116. package/dist/src/tools/weather.js +11 -0
  117. package/dist/src/tools/weather.js.map +1 -0
  118. package/dist/src/transports/http.d.ts +24 -0
  119. package/dist/src/transports/http.d.ts.map +1 -0
  120. package/dist/src/transports/http.js +373 -0
  121. package/dist/src/transports/http.js.map +1 -0
  122. package/dist/src/transports/stdio.d.ts +3 -0
  123. package/dist/src/transports/stdio.d.ts.map +1 -0
  124. package/dist/src/transports/stdio.js +6 -0
  125. package/dist/src/transports/stdio.js.map +1 -0
  126. package/dist/src/utils/callTool.d.ts +18 -0
  127. package/dist/src/utils/callTool.d.ts.map +1 -0
  128. package/dist/src/utils/callTool.js +54 -0
  129. package/dist/src/utils/callTool.js.map +1 -0
  130. package/dist/src/utils/errors.d.ts +7 -0
  131. package/dist/src/utils/errors.d.ts.map +1 -0
  132. package/dist/src/utils/errors.js +70 -0
  133. package/dist/src/utils/errors.js.map +1 -0
  134. package/dist/src/utils/logger.d.ts +10 -0
  135. package/dist/src/utils/logger.d.ts.map +1 -0
  136. package/dist/src/utils/logger.js +4 -0
  137. package/dist/src/utils/logger.js.map +1 -0
  138. package/dist/src/utils/retry.d.ts +12 -0
  139. package/dist/src/utils/retry.d.ts.map +1 -0
  140. package/dist/src/utils/retry.js +29 -0
  141. package/dist/src/utils/retry.js.map +1 -0
  142. package/dist/src/utils/toolOutput.d.ts +21 -0
  143. package/dist/src/utils/toolOutput.d.ts.map +1 -0
  144. package/dist/src/utils/toolOutput.js +35 -0
  145. package/dist/src/utils/toolOutput.js.map +1 -0
  146. package/package.json +65 -0
package/README.md ADDED
@@ -0,0 +1,1017 @@
1
+ # evercam-mcp
2
+
3
+ > MCP (Model Context Protocol) server + CLI for the Evercam platform.
4
+ > Talk to your cameras, AI analytics, copilot, and gate reports — from Claude, Cursor, scripts, or any MCP client.
5
+
6
+ [![npm](https://img.shields.io/npm/v/@evercam/mcp)](https://www.npmjs.com/package/@evercam/mcp)
7
+ [![License: ISC](https://img.shields.io/badge/License-ISC-blue.svg)](LICENSE)
8
+
9
+ ---
10
+
11
+ ## What is this?
12
+
13
+ `@evercam/mcp` exposes the full Evercam platform as **AI-callable tools** via the [Model Context Protocol](https://modelcontextprotocol.io). It wraps three Evercam backends through a single interface:
14
+
15
+ | Backend | URL | Features |
16
+ | ------------------- | --------------------- | -------------------------------------------------------- |
17
+ | **evercam-backend** | `media.evercam.io/v2` | Cameras, projects, snapshots, BIM, timelapses, media hub |
18
+ | **evercam-labs** | `labs.evercam.io` | AI Copilot, presence detection, luminance, heatmaps |
19
+ | **evercam-ai** | `data.evercam.io` | ANPR, gate reports, smart search, site analytics |
20
+
21
+ Built on [`@evercam/sdk`](https://github.com/evercam/evercam-sdk) — no custom HTTP clients, no vendored types.
22
+
23
+ ---
24
+
25
+ ## Table of Contents
26
+
27
+ - [Installation](#installation)
28
+ - [Authentication](#authentication)
29
+ - [Quickstart (HTTP + REST tools)](#quickstart-http--rest-tools)
30
+ - [CLI Reference](#cli-reference)
31
+ - [Use with Claude Desktop](#use-with-claude-desktop)
32
+ - [Use with Claude Code](#use-with-claude-code)
33
+ - [Use with Codex](#use-with-codex)
34
+ - [Use with Cursor](#use-with-cursor)
35
+ - [Use with Windsurf](#use-with-windsurf)
36
+ - [Use with Zed](#use-with-zed)
37
+ - [Use with Continue.dev](#use-with-continuedev)
38
+ - [Use with Cline](#use-with-cline)
39
+ - [Use with Goose](#use-with-goose)
40
+ - [Streamable HTTP Server](#streamable-http-server)
41
+ - [Use as a Node.js Library](#use-as-a-nodejs-library)
42
+ - [All Tools](#all-tools)
43
+ - [Profiles & Multi-environment](#profiles--multi-environment)
44
+ - [Environment Variables](#environment-variables)
45
+ - [Architecture](#architecture)
46
+ - [Development](#development)
47
+ - [Publishing](#publishing)
48
+
49
+ ---
50
+
51
+ ## Installation
52
+
53
+ **Global install (recommended):**
54
+
55
+ ```bash
56
+ npm install -g @evercam/mcp
57
+ # or
58
+ pnpm add -g @evercam/mcp
59
+ ```
60
+
61
+ **Without installing (npx):**
62
+
63
+ ```bash
64
+ npx @evercam/mcp <command>
65
+ ```
66
+
67
+ Note: `npx evercam-mcp <command>` will not work unless an unscoped `evercam-mcp` package is published.
68
+
69
+ **From source:**
70
+
71
+ ```bash
72
+ git clone git@github.com:evercam/evercam-mcp.git
73
+ cd evercam-mcp
74
+ pnpm install
75
+ pnpm -C packages/evercam-mcp build
76
+ ```
77
+
78
+ ---
79
+
80
+ ## Authentication
81
+
82
+ Login with your Evercam credentials:
83
+
84
+ ```bash
85
+ evercam-mcp auth login
86
+ # Username or email: you@evercam.io
87
+ # Password: ••••••••
88
+ # ✓ Logged in successfully (profile: default)
89
+ ```
90
+
91
+ Token is stored securely in `~/.evercam/tokens.json` (chmod 0600) and reused on every subsequent command.
92
+
93
+ For local Claude/ChatGPT MCP usage, `EVERCAM_TOKEN` is not required after `auth login` on the same machine.
94
+
95
+ Note: the SDK currently has no token refresh endpoint; when a token expires, run `evercam-mcp auth relogin`.
96
+
97
+ ```bash
98
+ evercam-mcp auth status # Check current login state
99
+ evercam-mcp auth logout # Clear stored token
100
+ evercam-mcp auth relogin # Re-authenticate and replace stored token
101
+ ```
102
+
103
+ Alternatively, skip the login flow entirely using an environment variable:
104
+
105
+ ```bash
106
+ EVERCAM_TOKEN=your-token evercam-mcp serve
107
+ ```
108
+
109
+ Use `EVERCAM_TOKEN` when running in CI, Docker, remote hosts, or shared machines where `~/.evercam/tokens.json` is unavailable.
110
+
111
+ ---
112
+
113
+ ## Quickstart (HTTP + REST tools)
114
+
115
+ ```bash
116
+ # 1) Authenticate once (or set EVERCAM_TOKEN)
117
+ npx @evercam/mcp auth login
118
+
119
+ # 2) Start the HTTP server
120
+ npx @evercam/mcp serve --transport http --port 4004
121
+
122
+ # 3) List tools
123
+ curl http://localhost:4004/tools
124
+
125
+ # 4) Call a tool directly
126
+ curl -X POST http://localhost:4004/tools/list-cameras \
127
+ -H "Content-Type: application/json" \
128
+ -d '{}'
129
+ ```
130
+
131
+ ---
132
+
133
+ ## CLI Reference
134
+
135
+ ```
136
+ evercam-mcp <command> [options]
137
+ ```
138
+
139
+ ### `auth`
140
+
141
+ ```bash
142
+ evercam-mcp auth login [--profile <name>] # Log in (prompts username + password)
143
+ evercam-mcp auth logout [--profile <name>] # Log out
144
+ evercam-mcp auth relogin [--profile <name>] # Re-authenticate and replace token
145
+ evercam-mcp auth status [--profile <name>] # Show login state + masked token
146
+ ```
147
+
148
+ ### `profile`
149
+
150
+ ```bash
151
+ evercam-mcp profile list # List all profiles (active marked ●)
152
+ evercam-mcp profile add <name> [options] # Add a new profile
153
+ --base-url <url> # Override backend URL
154
+ --ai-url <url> # Override AI API URL
155
+ --labs-url <url> # Override Labs URL
156
+ --ingest-url <url> # Override Ingest URL
157
+ evercam-mcp profile switch <name> # Switch active profile
158
+ ```
159
+
160
+ ### `tools`
161
+
162
+ ```bash
163
+ evercam-mcp tools list # Show all tools grouped by domain
164
+ ```
165
+
166
+ ### `run`
167
+
168
+ Call any tool directly from the shell. Arguments are passed as `key=value` pairs.
169
+
170
+ ```bash
171
+ evercam-mcp run <tool-name> [key=value ...] [--profile <name>]
172
+ ```
173
+
174
+ **Examples:**
175
+
176
+ ```bash
177
+ evercam-mcp run list-cameras
178
+ evercam-mcp run get-camera cameraExid=roof-cam
179
+ evercam-mcp run list-projects
180
+ evercam-mcp run get-gate-report-events \
181
+ projectExid=site-abc \
182
+ fromDate=2024-01-01T00:00:00Z \
183
+ toDate=2024-01-31T23:59:59Z
184
+ evercam-mcp run list-anpr-events projectExid=site-abc plate=ABC123
185
+ evercam-mcp run smart-search projectExid=site-abc labels='["person","car"]'
186
+ evercam-mcp run list-copilot-conversations page=1 limit=10
187
+ evercam-mcp run get-presence-intervals \
188
+ cameraExid=roof-cam \
189
+ fromDate=2024-01-15T00:00:00Z \
190
+ toDate=2024-01-15T23:59:59Z
191
+ ```
192
+
193
+ ### `serve`
194
+
195
+ Start the MCP server.
196
+
197
+ ```bash
198
+ evercam-mcp serve # stdio transport (default)
199
+ evercam-mcp serve --transport http # Streamable HTTP transport
200
+ evercam-mcp serve --transport http --port 4004
201
+ evercam-mcp serve --profile staging # Use a specific profile
202
+ evercam-mcp serve --allowed-origins https://app.example.com
203
+ evercam-mcp serve --timeout 60000 # Tool timeout in ms
204
+ evercam-mcp serve --api-key $MCP_API_KEY # Require ApiKey auth on HTTP endpoints
205
+ evercam-mcp serve --allowed-tools list-cameras,get-camera
206
+ evercam-mcp serve --denied-tools delete-progress-photo
207
+ evercam-mcp serve --rate-limit 120 # 120 REST tool calls/min per IP
208
+ evercam-mcp serve --enable-mutations # Allow create/update/delete/action tools
209
+ ```
210
+
211
+ ---
212
+
213
+ ## Use with Claude Desktop
214
+
215
+ **1. Log in:**
216
+
217
+ ```bash
218
+ npx @evercam/mcp auth login
219
+ ```
220
+
221
+ **2. Add to Claude Desktop config:**
222
+
223
+ - Linux: `~/.config/Claude/claude_desktop_config.json`
224
+ - macOS: `~/Library/Application Support/Claude/claude_desktop_config.json`
225
+
226
+ ```json
227
+ {
228
+ "mcpServers": {
229
+ "evercam": {
230
+ "command": "npx",
231
+ "args": ["-y", "@evercam/mcp", "serve"]
232
+ }
233
+ }
234
+ }
235
+ ```
236
+
237
+ Or with an explicit token (useful for CI or shared machines):
238
+
239
+ ```json
240
+ {
241
+ "mcpServers": {
242
+ "evercam": {
243
+ "command": "npx",
244
+ "args": ["-y", "@evercam/mcp", "serve"],
245
+ "env": {
246
+ "EVERCAM_TOKEN": "your-token-here"
247
+ }
248
+ }
249
+ }
250
+ }
251
+ ```
252
+
253
+ **3. Restart Claude Desktop.**
254
+
255
+ You can now ask Claude things like:
256
+
257
+ > _"Which cameras are offline right now?"_
258
+ > _"Show gate report events for project abc from last week"_
259
+ > _"How many vehicles were detected at the main gate yesterday?"_
260
+ > _"Create a timelapse for camera roof-cam for all of January"_
261
+ > _"Search for persons in project abc between 9am and 5pm today"_
262
+ > _"List my last Copilot conversations"_
263
+ > _"What days in March had recordings on camera roof-cam?"_
264
+
265
+ Claude will call the right tools, chain results, and reason over them.
266
+
267
+ ---
268
+
269
+ ## Use with Claude Code
270
+
271
+ **1. Log in:**
272
+
273
+ ```bash
274
+ npx @evercam/mcp auth login
275
+ ```
276
+
277
+ **2. Add the MCP server via CLI:**
278
+
279
+ ```bash
280
+ claude mcp add evercam -- npx -y @evercam/mcp serve
281
+ ```
282
+
283
+ Or add manually to `~/.claude/settings.json`:
284
+
285
+ ```json
286
+ {
287
+ "mcpServers": {
288
+ "evercam": {
289
+ "command": "npx",
290
+ "args": ["-y", "@evercam/mcp", "serve"]
291
+ }
292
+ }
293
+ }
294
+ ```
295
+
296
+ With an explicit token:
297
+
298
+ ```json
299
+ {
300
+ "mcpServers": {
301
+ "evercam": {
302
+ "command": "npx",
303
+ "args": ["-y", "@evercam/mcp", "serve"],
304
+ "env": {
305
+ "EVERCAM_TOKEN": "your-token-here"
306
+ }
307
+ }
308
+ }
309
+ }
310
+ ```
311
+
312
+ **3. Verify tools are loaded:**
313
+
314
+ ```bash
315
+ claude mcp list
316
+ # evercam: npx -y @evercam/mcp serve
317
+ ```
318
+
319
+ Claude Code can now call all Evercam tools while you code — pull real camera exids, fetch live API shapes for type generation, or check gate report data without leaving the terminal.
320
+
321
+ ---
322
+
323
+ ## Use with Codex
324
+
325
+ **1. Log in:**
326
+
327
+ ```bash
328
+ npx @evercam/mcp auth login
329
+ ```
330
+
331
+ **2. Add to `~/.codex/config.toml`:**
332
+
333
+ ```toml
334
+ [[mcp_servers]]
335
+ name = "evercam"
336
+ command = "npx"
337
+ args = ["-y", "@evercam/mcp", "serve"]
338
+ ```
339
+
340
+ With an explicit token:
341
+
342
+ ```toml
343
+ [[mcp_servers]]
344
+ name = "evercam"
345
+ command = "npx"
346
+ args = ["-y", "@evercam/mcp", "serve"]
347
+
348
+ [mcp_servers.env]
349
+ EVERCAM_TOKEN = "your-token-here"
350
+ ```
351
+
352
+ ---
353
+
354
+ ## Use with Cursor
355
+
356
+ Add to `.cursor/mcp.json` at your project root:
357
+
358
+ ```json
359
+ {
360
+ "mcpServers": {
361
+ "evercam": {
362
+ "command": "npx",
363
+ "args": ["-y", "@evercam/mcp", "serve"]
364
+ }
365
+ }
366
+ }
367
+ ```
368
+
369
+ While coding, Cursor can:
370
+
371
+ - Pull real camera/project exids to use in tests instead of fake placeholders
372
+ - Fetch actual API response shapes to generate correct TypeScript types
373
+ - Verify fixes against real gate report data without leaving the editor
374
+
375
+ ---
376
+
377
+ ## Use with Windsurf
378
+
379
+ **1. Log in:**
380
+
381
+ ```bash
382
+ npx @evercam/mcp auth login
383
+ ```
384
+
385
+ **2. Add to Windsurf MCP config:**
386
+
387
+ Global (`~/.windsurf/mcp.json`) or project-level (`.windsurf/mcp.json`):
388
+
389
+ ```json
390
+ {
391
+ "mcpServers": {
392
+ "evercam": {
393
+ "command": "npx",
394
+ "args": ["-y", "@evercam/mcp", "serve"]
395
+ }
396
+ }
397
+ }
398
+ ```
399
+
400
+ **3. Reload Windsurf.** The Evercam tools will appear in the Cascade agent tool list.
401
+
402
+ ---
403
+
404
+ ## Use with Zed
405
+
406
+ **1. Log in:**
407
+
408
+ ```bash
409
+ npx @evercam/mcp auth login
410
+ ```
411
+
412
+ **2. Add to `~/.config/zed/settings.json`:**
413
+
414
+ ```json
415
+ {
416
+ "context_servers": {
417
+ "evercam": {
418
+ "command": {
419
+ "path": "npx",
420
+ "args": ["-y", "@evercam/mcp", "serve"]
421
+ },
422
+ "settings": {}
423
+ }
424
+ }
425
+ }
426
+ ```
427
+
428
+ With an explicit token:
429
+
430
+ ```json
431
+ {
432
+ "context_servers": {
433
+ "evercam": {
434
+ "command": {
435
+ "path": "npx",
436
+ "args": ["-y", "@evercam/mcp", "serve"],
437
+ "env": {
438
+ "EVERCAM_TOKEN": "your-token-here"
439
+ }
440
+ },
441
+ "settings": {}
442
+ }
443
+ }
444
+ }
445
+ ```
446
+
447
+ **3.** Evercam tools become available as slash commands and in the Agent panel.
448
+
449
+ ---
450
+
451
+ ## Use with Continue.dev
452
+
453
+ **1. Log in:**
454
+
455
+ ```bash
456
+ npx @evercam/mcp auth login
457
+ ```
458
+
459
+ **2. Add to `~/.continue/config.yaml`:**
460
+
461
+ ```yaml
462
+ mcpServers:
463
+ - name: evercam
464
+ command: npx
465
+ args:
466
+ - -y
467
+ - "@evercam/mcp"
468
+ - serve
469
+ ```
470
+
471
+ With an explicit token:
472
+
473
+ ```yaml
474
+ mcpServers:
475
+ - name: evercam
476
+ command: npx
477
+ args:
478
+ - -y
479
+ - "@evercam/mcp"
480
+ - serve
481
+ env:
482
+ EVERCAM_TOKEN: your-token-here
483
+ ```
484
+
485
+ **3.** Reload VS Code / JetBrains. The `@evercam` context provider and tools will be available in the Continue chat panel.
486
+
487
+ ---
488
+
489
+ ## Use with Cline
490
+
491
+ **1. Log in:**
492
+
493
+ ```bash
494
+ npx @evercam/mcp auth login
495
+ ```
496
+
497
+ **2.** Open VS Code → Cline extension → click **MCP Servers** → **Edit MCP Settings**.
498
+
499
+ Add to the settings JSON:
500
+
501
+ ```json
502
+ {
503
+ "evercam": {
504
+ "command": "npx",
505
+ "args": ["-y", "@evercam/mcp", "serve"],
506
+ "disabled": false,
507
+ "autoApprove": []
508
+ }
509
+ }
510
+ ```
511
+
512
+ With an explicit token:
513
+
514
+ ```json
515
+ {
516
+ "evercam": {
517
+ "command": "npx",
518
+ "args": ["-y", "@evercam/mcp", "serve"],
519
+ "env": {
520
+ "EVERCAM_TOKEN": "your-token-here"
521
+ },
522
+ "disabled": false,
523
+ "autoApprove": []
524
+ }
525
+ }
526
+ ```
527
+
528
+ **3.** The server connects automatically. You'll see a green indicator next to `evercam` in the MCP Servers list.
529
+
530
+ ---
531
+
532
+ ## Use with Goose
533
+
534
+ **1. Log in:**
535
+
536
+ ```bash
537
+ npx @evercam/mcp auth login
538
+ ```
539
+
540
+ **2. Add to `~/.config/goose/config.yaml`:**
541
+
542
+ ```yaml
543
+ extensions:
544
+ evercam:
545
+ name: evercam
546
+ type: stdio
547
+ cmd: npx
548
+ args:
549
+ - -y
550
+ - "@evercam/mcp"
551
+ - serve
552
+ enabled: true
553
+ ```
554
+
555
+ With an explicit token:
556
+
557
+ ```yaml
558
+ extensions:
559
+ evercam:
560
+ name: evercam
561
+ type: stdio
562
+ cmd: npx
563
+ args:
564
+ - -y
565
+ - "@evercam/mcp"
566
+ - serve
567
+ envs:
568
+ EVERCAM_TOKEN: your-token-here
569
+ enabled: true
570
+ ```
571
+
572
+ Or via CLI:
573
+
574
+ ```bash
575
+ goose mcp add evercam --command "npx -y @evercam/mcp serve"
576
+ ```
577
+
578
+ ---
579
+
580
+ ## Streamable HTTP Server
581
+
582
+ Run as a persistent HTTP server instead of a stdio subprocess. This is useful for:
583
+
584
+ - Remote deployments (server, Docker)
585
+ - Connecting multiple clients simultaneously
586
+ - Integrating with evercam-labs or other services over the network
587
+
588
+ ```bash
589
+ evercam-mcp serve --transport http --port 4004
590
+ # Evercam MCP server listening on http://localhost:4004
591
+ # MCP endpoint: ALL http://localhost:4004/mcp
592
+ ```
593
+
594
+ ### HTTP endpoints
595
+
596
+ | Endpoint | Method | Description |
597
+ | ----------------------- | ------ | ----------------------------------------------- |
598
+ | `/health` | `GET` | Health check `{ status: "ok", tools: <count> }` |
599
+ | `/tools` | `GET` | List all tools (name, description, inputSchema) |
600
+ | `/tools/:toolName` | `POST` | Call a tool directly with JSON args |
601
+ | `/snapshot/:cameraExid` | `GET` | Authenticated latest snapshot proxy |
602
+ | `/mcp` | `ALL` | Streamable HTTP MCP endpoint |
603
+
604
+ **Authorization header:** For REST tool calls, you can pass `Authorization: Bearer <token>` to override the server token for that request.
605
+
606
+ ### How it works
607
+
608
+ ```
609
+ Client evercam-mcp HTTP server
610
+ │ │
611
+ ├── POST /mcp (initialize) ───────────────►│ Creates session
612
+ │◄── sessionId ───────────────────────────┤ Server returns sessionId
613
+ │ │
614
+ ├── GET /mcp (SSE stream) ────────────────►│ Opens persistent SSE stream
615
+ │ │
616
+ ├── POST /mcp (tool call) ────────────────►│ Send tool call
617
+ │◄── result (via SSE stream) ─────────────┤ Server streams response back
618
+ ```
619
+
620
+ ### Connect Claude Desktop to a remote server
621
+
622
+ ```json
623
+ {
624
+ "mcpServers": {
625
+ "evercam": {
626
+ "url": "http://your-server:4004/mcp"
627
+ }
628
+ }
629
+ }
630
+ ```
631
+
632
+ ### Connect from Node.js (evercam-labs / custom service)
633
+
634
+ ```typescript
635
+ import { Client } from "@modelcontextprotocol/sdk/client/index.js"
636
+ import { StreamableHTTPClientTransport } from "@modelcontextprotocol/sdk/client/streamableHttp.js"
637
+
638
+ const client = new Client({ name: "my-app", version: "1.0.0" })
639
+ const transport = new StreamableHTTPClientTransport(new URL("http://localhost:4004/mcp"))
640
+ await client.connect(transport)
641
+
642
+ // Call any evercam-mcp tool
643
+ const result = await client.callTool("list-cameras", {})
644
+ const cameras = await client.callTool("smart-search", {
645
+ projectExid: "site-abc",
646
+ labels: ["person", "car"],
647
+ fromDate: "2024-01-15T09:00:00Z",
648
+ toDate: "2024-01-15T17:00:00Z",
649
+ })
650
+ ```
651
+
652
+ ### Call a tool without MCP
653
+
654
+ ```bash
655
+ curl -X POST http://localhost:4004/tools/get-camera \
656
+ -H "Content-Type: application/json" \
657
+ -d '{"cameraExid":"roof-cam"}'
658
+ ```
659
+
660
+ ### Docker
661
+
662
+ ```dockerfile
663
+ FROM node:22-alpine
664
+ RUN npm install -g @evercam/mcp
665
+ EXPOSE 4004
666
+ CMD ["evercam-mcp", "serve", "--transport", "http", "--port", "4004"]
667
+ ```
668
+
669
+ ```bash
670
+ docker run -e EVERCAM_TOKEN=your-token -p 4004:4004 evercam-mcp
671
+ ```
672
+
673
+ ### Multiple environments simultaneously
674
+
675
+ ```bash
676
+ EVERCAM_TOKEN=$PROD_TOKEN evercam-mcp serve --transport http --port 4004
677
+ EVERCAM_TOKEN=$STAGING_TOKEN evercam-mcp serve --transport http --port 4002
678
+ ```
679
+
680
+ > **Note:** MCP sessions share the server’s base Evercam identity. REST tool calls can override per-request using the `Authorization` header.
681
+
682
+ ---
683
+
684
+ ## Use as a Node.js Library
685
+
686
+ Install as a dependency:
687
+
688
+ ```bash
689
+ pnpm add @evercam/mcp
690
+ ```
691
+
692
+ **With a token:**
693
+
694
+ ```typescript
695
+ import { createEvercamMcpServer, startHttp } from "@evercam/mcp"
696
+
697
+ const { server, evercam } = await createEvercamMcpServer({
698
+ credentials: { token: process.env.EVERCAM_TOKEN },
699
+ })
700
+ await startHttp(server, evercam, 4004)
701
+ ```
702
+
703
+ **With username/password:**
704
+
705
+ ```typescript
706
+ import { createEvercamMcpServer, startStdio } from "@evercam/mcp"
707
+
708
+ const { server } = await createEvercamMcpServer({
709
+ credentials: {
710
+ username: "you@evercam.io",
711
+ password: "your-password",
712
+ },
713
+ })
714
+ await startStdio(server)
715
+ ```
716
+
717
+ **With custom URLs (staging, local dev):**
718
+
719
+ ```typescript
720
+ import { createEvercamMcpServer } from "@evercam/mcp"
721
+
722
+ const { server, evercam } = await createEvercamMcpServer({
723
+ credentials: { token: process.env.EVERCAM_TOKEN },
724
+ baseUrls: {
725
+ baseUrl: "https://staging.evercam.io/v2",
726
+ aiApiUrl: "https://staging-data.evercam.io",
727
+ evercamLabsUrl: "https://staging-labs.evercam.io",
728
+ },
729
+ })
730
+ ```
731
+
732
+ ---
733
+
734
+ ## All Tools
735
+
736
+ ### Cameras
737
+
738
+ | Tool | Description | Required | Optional |
739
+ | --------------- | --------------------------- | ------------ | ------------------------------ |
740
+ | `list-cameras` | List all accessible cameras | — | `projectExid`, `page`, `limit` |
741
+ | `get-camera` | Get camera details | `cameraExid` | — |
742
+ | `update-camera` | Update camera properties | `cameraExid` | `name`, `isOnline`, `timezone` |
743
+
744
+ ### Snapshots
745
+
746
+ | Tool | Description | Required | Optional |
747
+ | ----------------------- | ------------------------------------ | ----------------------------- | -------- |
748
+ | `get-live-snapshot-url` | Get live snapshot URL | `cameraExid` | — |
749
+ | `get-snapshot-at` | Get snapshot nearest to timestamp | `cameraExid`, `timestamp` | — |
750
+ | `get-latest-snapshot` | Get most recent snapshot | `cameraExid` | — |
751
+ | `get-oldest-snapshot` | Get oldest snapshot | `cameraExid` | — |
752
+ | `list-available-days` | List days with recordings in a month | `cameraExid`, `year`, `month` | — |
753
+
754
+ ### Projects
755
+
756
+ | Tool | Description | Required | Optional |
757
+ | ---------------------- | ---------------------------- | ------------- | -------- |
758
+ | `list-projects` | List all accessible projects | — | — |
759
+ | `list-project-cameras` | List cameras in a project | `projectExid` | — |
760
+ | `list-project-users` | List users in a project | `projectExid` | — |
761
+ | `list-project-members` | List members with roles | `projectExid` | — |
762
+
763
+ ### Media
764
+
765
+ | Tool | Description | Required | Optional |
766
+ | ------------------ | ---------------------------- | ------------------------------------------------- | --------------- |
767
+ | `list-timelapses` | List timelapses for a camera | `cameraExid`, `fromDate`, `toDate` | — |
768
+ | `create-timelapse` | Create a timelapse | `projectExid`, `cameraExid`, `fromDate`, `toDate` | `title` |
769
+ | `list-media-hub` | List clips in the media hub | `projectExid` | `page`, `limit` |
770
+
771
+ ### BIM
772
+
773
+ | Tool | Description | Required | Optional |
774
+ | ------------------ | ----------------------------- | ------------------------- | -------- |
775
+ | `list-bim-layers` | List BIM layers for a camera | `cameraExid` | — |
776
+ | `get-bim-snapshot` | Get BIM snapshot at timestamp | `cameraExid`, `timestamp` | — |
777
+ | `get-bim-model` | Get BIM model info | `cameraExid` | — |
778
+
779
+ ### Copilot
780
+
781
+ | Tool | Description | Required | Optional |
782
+ | ---------------------------- | ------------------------------- | --------------------------------------- | -------------------------------------------- |
783
+ | `list-copilot-conversations` | List AI Copilot conversations | — | `page`, `limit`, `projectExid`, `cameraExid` |
784
+ | `get-copilot-conversation` | Get a conversation by ID | `conversationId` | — |
785
+ | `list-copilot-messages` | List messages in a conversation | `conversationId` | `page`, `limit` |
786
+ | `send-copilot-message` | Send a message | `conversationId`, `message` | — |
787
+ | `submit-copilot-feedback` | Submit message feedback | `conversationId`, `messageId`, `rating` | `comment` |
788
+
789
+ `rating` accepts `"positive"` or `"negative"`.
790
+
791
+ ### Detections
792
+
793
+ | Tool | Description | Required | Optional |
794
+ | -------------------------------------- | ---------------------------- | ---------------------------------- | --------------------------- |
795
+ | `get-presence-intervals` | Presence detection intervals | `cameraExid`, `fromDate`, `toDate` | — |
796
+ | `get-luminance-readings` | Light level readings | `cameraExid`, `fromDate`, `toDate` | — |
797
+ | `get-site-analytics-processing-status` | Processing status | — | `projectExid`, `cameraExid` |
798
+ | `get-heatmap-intersections` | Heatmap intersection data | `cameraExid`, `fromDate`, `toDate` | — |
799
+
800
+ ### ANPR / Gate Report
801
+
802
+ | Tool | Description | Required | Optional |
803
+ | ------------------------ | -------------------------------- | ----------------------------------- | ------------------------------------------------------------ |
804
+ | `list-anpr-events` | License plate recognition events | `projectExid` | `fromDate`, `toDate`, `cameraExid`, `plate`, `page`, `limit` |
805
+ | `get-gate-report-events` | Gate report events | `projectExid`, `fromDate`, `toDate` | `cameraExid`, `page`, `limit` |
806
+ | `list-verified-days` | Verified gate report days | `projectExid` | `fromDate`, `toDate` |
807
+ | `list-rois` | ROI configurations | `projectExid` | `cameraExid` |
808
+
809
+ ### Site Analytics
810
+
811
+ | Tool | Description | Required | Optional |
812
+ | --------------------------- | ----------------------------------- | ----------------------------------------------------------- | ------------------------------------------------------------------------- |
813
+ | `smart-search` | Semantic/visual search over footage | `projectExid` | `cameraExid`, `query`, `labels`, `fromDate`, `toDate`, `page`, `pageSize` |
814
+ | `list-smart-search-queries` | Saved smart search queries | `projectExid` | — |
815
+ | `get-detections-heatmap` | Detection heatmap data | `projectExid`, `cameraExid`, `fromDate`, `toDate`, `labels` | — |
816
+ | `get-gate-report-counts` | Event count statistics | `projectExid`, `fromDate`, `toDate` | `cameraExid` |
817
+
818
+ ---
819
+
820
+ ## Profiles & Multi-environment
821
+
822
+ Profiles let you switch between production, staging, and local environments without changing env vars.
823
+
824
+ ```bash
825
+ # Add a staging profile
826
+ evercam-mcp profile add staging \
827
+ --base-url https://staging.evercam.io/v2 \
828
+ --ai-url https://staging-data.evercam.io \
829
+ --labs-url https://staging-labs.evercam.io
830
+
831
+ # Log in on staging
832
+ evercam-mcp auth login --profile staging
833
+
834
+ # List all profiles
835
+ evercam-mcp profile list
836
+ # ● default
837
+ # staging
838
+
839
+ # Switch active profile
840
+ evercam-mcp profile switch staging
841
+
842
+ # Or pass --profile to any command without switching
843
+ evercam-mcp run list-cameras --profile staging
844
+ evercam-mcp serve --profile staging
845
+ ```
846
+
847
+ Profile config is stored in `~/.evercam/config.json`. Tokens per profile in `~/.evercam/tokens.json`.
848
+
849
+ ---
850
+
851
+ ## Environment Variables
852
+
853
+ Environment variables take highest priority — they override both profile config and SDK defaults.
854
+
855
+ `EVERCAM_BASE_URL`, `EVERCAM_AI_URL`, `EVERCAM_LABS_URL`, and `EVERCAM_INGEST_URL` are optional. If omitted, the SDK uses production defaults.
856
+
857
+ | Variable | Default | Description |
858
+ | -------------------- | ----------------------------- | -------------------------------------- |
859
+ | `EVERCAM_TOKEN` | — | Auth token (skips login flow entirely) |
860
+ | `EVERCAM_BASE_URL` | `https://media.evercam.io/v2` | Evercam backend URL |
861
+ | `EVERCAM_AI_URL` | `https://data.evercam.io` | Evercam AI API URL |
862
+ | `EVERCAM_LABS_URL` | `https://labs.evercam.io` | Evercam Labs URL |
863
+ | `EVERCAM_INGEST_URL` | `https://ingest.evercam.io` | Evercam Ingest URL |
864
+ | `EVERCAM_PROFILE` | `default` | Active profile name |
865
+
866
+ Copy `.env.example` to `.env` — it's loaded automatically on startup.
867
+
868
+ ---
869
+
870
+ ## Architecture
871
+
872
+ ```
873
+ ┌─────────────────────────────────────┐
874
+ MCP Client │ evercam-mcp │
875
+ (Claude, Cursor, │ │
876
+ custom app) │ McpServer │
877
+ │ │ tools/cameras.ts │
878
+ │ MCP │ tools/snapshots.ts │
879
+ │ protocol │ tools/projects.ts │
880
+ ▼ │ tools/media.ts │
881
+ ┌─────────┐ │ tools/bim.ts │
882
+ │ stdio │ │ tools/copilot.ts │
883
+ │ or │ │ tools/detections.ts │
884
+ │ HTTP │ │ tools/anpr.ts │
885
+ │ stream │ │ tools/siteAnalytics.ts │
886
+ └────┬────┘ │ │ │
887
+ │ │ @evercam/sdk — Evercam class │
888
+ │ │ evercam.api ────────────────────►│──► media.evercam.io/v2
889
+ │ │ evercam.ai ────────────────────►│──► data.evercam.io
890
+ │ │ evercam.axios ───────────────────►│──► labs.evercam.io
891
+ └────────────┘ │
892
+ └──────────────────────
893
+ ```
894
+
895
+ ### Config resolution order
896
+
897
+ For each setting, priority is:
898
+
899
+ ```
900
+ EVERCAM_TOKEN env var
901
+ → ~/.evercam/tokens.json[activeProfile]
902
+ → @evercam/sdk DEFAULT_BASE_URLS
903
+ ```
904
+
905
+ ### Auth flow
906
+
907
+ ```
908
+ evercam-mcp auth login
909
+ 1. Prompts username + password
910
+ 2. new Evercam({ credentials: { username, password } }).connect()
911
+ → POST media.evercam.io/v2/users/login
912
+ 3. Stores returned token in ~/.evercam/tokens.json (chmod 0600)
913
+
914
+ On serve/run:
915
+ 1. Reads EVERCAM_TOKEN env var OR ~/.evercam/tokens.json[profile]
916
+ 2. new Evercam({ credentials: { token } }); evercam.setToken(token)
917
+ ```
918
+
919
+ ### Labs API note
920
+
921
+ `EvercamLabsApi` from `@evercam/api` references `window.location.href` internally (browser-only). Copilot and detection tools bypass this by calling `evercam.axios` directly with `evercam.axios.env.evercamLabsUrl`.
922
+
923
+ ---
924
+
925
+ ## Development
926
+
927
+ ```bash
928
+ git clone git@github.com:evercam/evercam-mcp.git
929
+ cd evercam-mcp
930
+ pnpm install
931
+ pnpm -C packages/evercam-mcp build # Compile TypeScript → dist/
932
+ pnpm -C packages/evercam-mcp dev # Watch mode (tsx watch)
933
+ ```
934
+
935
+ ### Adding a new tool
936
+
937
+ 1. Find the method in [`evercam-frontend/packages/api/api/`](https://github.com/evercam/evercam-frontend/tree/master/packages/api/api)
938
+ 2. Add to the relevant `packages/evercam-mcp/src/tools/<domain>.ts` file:
939
+
940
+ ```typescript
941
+ server.tool(
942
+ "tool-name",
943
+ "Human description shown to the AI",
944
+ {
945
+ requiredArg: z.string().describe("What this is"),
946
+ optionalArg: z.number().optional().describe("Page number"),
947
+ },
948
+ async ({ requiredArg, optionalArg }) => {
949
+ const data = await evercam.api.namespace.method(requiredArg, { optionalArg })
950
+ return { content: [{ type: "text" as const, text: JSON.stringify(data, null, 2) }] }
951
+ }
952
+ )
953
+ ```
954
+
955
+ 3. Register in `packages/evercam-mcp/src/tools/index.ts`
956
+ 4. Add to `TOOL_DESCRIPTIONS` in `packages/evercam-mcp/src/cli/tools.ts`
957
+ 5. Run `pnpm -C packages/evercam-mcp build` — must compile with zero errors
958
+
959
+ ### SDK namespace map
960
+
961
+ | What you want | Use |
962
+ | ---------------------------------------------- | ----------------------------------------------------------------- |
963
+ | Cameras, projects, recordings, BIM, media | `evercam.api.*` |
964
+ | ANPR, gate report, ROIs, smart search, heatmap | `evercam.ai.*` |
965
+ | Copilot, luminance, presence, labs heatmap | `evercam.axios.get(\`\${evercam.axios.env.evercamLabsUrl}/...\`)` |
966
+
967
+ ---
968
+
969
+ ## Publishing
970
+
971
+ ```bash
972
+ # Monorepo release scripts (repo root)
973
+ pnpm mcp:publish:patch
974
+ pnpm mcp:publish:minor
975
+ pnpm mcp:publish:major
976
+ pnpm mcp:publish:patch:commit
977
+ pnpm mcp:publish:patch:push
978
+ pnpm mcp:publish:dry-run
979
+
980
+ # Or direct:
981
+ node ci-scripts/mcp-release.js patch
982
+ node ci-scripts/mcp-release.js patch --mutate --commit
983
+ node ci-scripts/mcp-release.js patch --mutate --push
984
+ node ci-scripts/mcp-release.js patch --dry-run
985
+ ```
986
+
987
+ Release types:
988
+
989
+ - `patch`: `x.y.z -> x.y.(z+1)`
990
+ - `minor`: `x.y.z -> x.(y+1).0`
991
+ - `major`: `x.y.z -> (x+1).0.0`
992
+
993
+ The package `prepublishOnly` script still runs `pnpm -C packages/evercam-mcp build` before packaging. Only the `dist/` folder is included in the published package.
994
+
995
+ After publishing:
996
+
997
+ ```bash
998
+ npm install -g @evercam/mcp # global install → evercam-mcp command in PATH
999
+ npx @evercam/mcp serve # no install required
1000
+ # npx evercam-mcp serve # won't work unless an unscoped package exists
1001
+ ```
1002
+
1003
+ ---
1004
+
1005
+ ## Related
1006
+
1007
+ - [`@evercam/sdk`](https://github.com/evercam/evercam-sdk) — TypeScript SDK this is built on
1008
+ - [`evercam-frontend`](https://github.com/evercam/evercam-frontend) — Source of API types
1009
+ - [`evercam-labs`](https://github.com/evercam/evercam-labs) — AI copilot backend
1010
+ - [`evercam-ai`](https://github.com/evercam/evercam-ai) — ML analytics backend
1011
+ - [Model Context Protocol](https://modelcontextprotocol.io) — MCP specification
1012
+
1013
+ ---
1014
+
1015
+ ## License
1016
+
1017
+ ISC © [Evercam](https://evercam.io)