beeswax-mcp 1.1.0 → 1.3.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/README.md +36 -6
- package/dist/tools.js +101 -4
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -7,8 +7,9 @@ quotes, expenses, payments, journals, time entries, milestones, products & servi
|
|
|
7
7
|
and tax returns.
|
|
8
8
|
|
|
9
9
|
It is **read-mostly**: writes are limited to quotes, manual journals, tax-return
|
|
10
|
-
fields
|
|
11
|
-
own token scope — everything
|
|
10
|
+
fields, the products & services catalogue, freeform project documents and custom
|
|
11
|
+
document themes, and each write is gated behind its own token scope — everything
|
|
12
|
+
else is strictly read-only.
|
|
12
13
|
|
|
13
14
|
**Nothing here sends anything to your clients.** The quote tools create and edit
|
|
14
15
|
drafts; emailing a quote, and marking one accepted, stay human actions in the
|
|
@@ -59,18 +60,37 @@ account.
|
|
|
59
60
|
`journal_entries:read`, `tax_returns:read`, `events:read`, `milestones:read`,
|
|
60
61
|
`projects:read`, `time_entries:read`, `transaction_templates:read`,
|
|
61
62
|
`transaction_accounts:read`, …) rather than `all` — `all` grants read **and**
|
|
62
|
-
write. Add `quotes:write`, `journal_entries:write`, `tax_returns:write
|
|
63
|
-
`transaction_templates:write`
|
|
64
|
-
matching write tools.
|
|
63
|
+
write. Add `quotes:write`, `journal_entries:write`, `tax_returns:write`,
|
|
64
|
+
`transaction_templates:write`, `project_documents:write` or `themes:write` only
|
|
65
|
+
if the agent should be able to use the matching write tools.
|
|
65
66
|
|
|
66
67
|
To build quotes you need `quotes:write` plus the three lookups a quote is
|
|
67
68
|
assembled from: `companies:read` (the client), `projects:read` (the project) and
|
|
68
|
-
`transaction_accounts:read` (the chart of accounts each line bills to
|
|
69
|
+
`transaction_accounts:read` (the chart of accounts each line bills to — the same
|
|
70
|
+
scope also covers the account's tax codes).
|
|
69
71
|
|
|
70
72
|
**Keep the token secret.** It sits in plain text in your client's config file, and
|
|
71
73
|
anyone who can read that file can read your account data. Revoke tokens you no
|
|
72
74
|
longer use from the same settings page.
|
|
73
75
|
|
|
76
|
+
## Multiple accounts
|
|
77
|
+
|
|
78
|
+
A token is bound to one account, so you connect several accounts by registering **one
|
|
79
|
+
server entry per account**, each with its own token and a distinct name
|
|
80
|
+
(`beeswax-acme`, `beeswax-steamuk`, …). Tools are namespaced by server name, so the
|
|
81
|
+
agent picks the account by picking the tool.
|
|
82
|
+
|
|
83
|
+
In Claude Desktop the one-click `.mcpb` extension and manual
|
|
84
|
+
`claude_desktop_config.json` entries can be enabled side by side. Two things catch
|
|
85
|
+
people out. A freshly installed extension is **disabled** until you flip the toggle at
|
|
86
|
+
the top of its settings — saving the token does not enable it, and while it is
|
|
87
|
+
disabled it exposes no tools at all. And the config file is read only at launch, so
|
|
88
|
+
adding an entry or changing a token in one needs a **full restart** of the app; a
|
|
89
|
+
Cowork or cloud session already linked to your computer needs that restart *and* a
|
|
90
|
+
re-link before it sees the change. The Connectors screen, the naming trade-offs and
|
|
91
|
+
the Cowork details are in the setup guide:
|
|
92
|
+
<https://www.beeswaxapp.com/support/mcp-setup#connecting-more-than-one-account>
|
|
93
|
+
|
|
74
94
|
## Configuration
|
|
75
95
|
|
|
76
96
|
| Environment variable | Required | Default |
|
|
@@ -105,9 +125,11 @@ reports the same on demand.
|
|
|
105
125
|
| `list_milestones`, `get_milestone` | `/milestones` |
|
|
106
126
|
| `list_projects`, `get_project` | `/active_account/projects` |
|
|
107
127
|
| `list_transaction_accounts` | `/active_account/transaction_accounts` |
|
|
128
|
+
| `list_taxes` | `/active_account/taxes` |
|
|
108
129
|
| `list_companies` | `/active_account/companies` |
|
|
109
130
|
| `list_task_files`, `list_task_file_versions` | `/tasks/:id/files` (+ per-file version history) |
|
|
110
131
|
| `list_project_documents`, `get_project_document`, `create_project_document` (write), `update_project_document` (write), `list_project_document_versions`, `get_project_document_version`, `restore_project_document_version` (write) | `/project_documents` (+ per-document version history) |
|
|
132
|
+
| `list_themes`, `get_theme_spec`, `get_theme`, `upsert_theme` (write), `validate_theme` (write), `preview_theme`, `activate_theme` (write), `delete_theme` (write) | `/themes` (custom document themes, THEME_SPEC v1) |
|
|
111
133
|
| `list_products_services`, `get_product_service`, `create_product_service` (write), `update_product_service` (write), `delete_product_service` (write) | `/transaction_templates` |
|
|
112
134
|
| `list_manual_journals`, `get_manual_journal`, `create_manual_journal` (write), `finalise_manual_journal` (write) | `/raw_journal_entries` |
|
|
113
135
|
| `list_tax_returns`, `get_tax_return`, `get_tax_return_field_transactions`, `list_tax_return_findings`, `update_tax_return_field` (write), `confirm_tax_return_section` (write) | `/tax_returns` |
|
|
@@ -125,6 +147,14 @@ reports the same on demand.
|
|
|
125
147
|
fetches. `outstanding: true` is the looser "not paid/draft, any due date" set.
|
|
126
148
|
- **Dates.** `from` / `to` accept ISO (`2026-01-01`) or loose strings
|
|
127
149
|
(`Jan 1 2026`); they are normalized to `YYYY-MM-DD` before being sent.
|
|
150
|
+
- **Tax codes.** `list_taxes` is the lookup a product's `sell_tax_id` /
|
|
151
|
+
`buy_tax_id` needs. Read `sides` rather than `tax_type` to decide whether a
|
|
152
|
+
code can be used on a document: an account that is not registered for GST/VAT
|
|
153
|
+
still carries usable zero-rated codes, and those are stored as `tax_type`
|
|
154
|
+
`"none"` rather than income or expense. `side: "sell"` returns what a sale
|
|
155
|
+
(invoice or quote) offers, `"buy"` what an expense offers, `"payroll"` the
|
|
156
|
+
withholding codes. `default` marks the code Beeswax reaches for on its own.
|
|
157
|
+
Needs `transaction_accounts:read`.
|
|
128
158
|
- **Products & services.** Beeswax stores the catalogue as *transaction
|
|
129
159
|
templates*. `kind` is the **buy/sell mode**, not a product-vs-service label:
|
|
130
160
|
`"sell"` offers the item on invoices and quotes, `"buy"` on expenses,
|
package/dist/tools.js
CHANGED
|
@@ -315,6 +315,85 @@ export const TOOLS = [
|
|
|
315
315
|
},
|
|
316
316
|
handler: (client, args) => client.mutate("POST", `/project_documents/${args.id}/versions/${args.version_number}/restore`, {}),
|
|
317
317
|
},
|
|
318
|
+
// ── Document themes (built-in + custom, THEME_SPEC v1 authoring) ────────
|
|
319
|
+
{
|
|
320
|
+
name: "list_themes",
|
|
321
|
+
description: "All document themes available to the account: the user's custom themes (with validation state) plus the built-in registry, and active_theme_key showing which one is live. Themes style every invoice, quote and freeform document the account sends.",
|
|
322
|
+
inputSchema: { type: "object", properties: {} },
|
|
323
|
+
handler: (client) => client.getOne("/themes", ""),
|
|
324
|
+
},
|
|
325
|
+
{
|
|
326
|
+
name: "get_theme_spec",
|
|
327
|
+
description: "THEME_SPEC v1 — the complete contract for authoring a custom theme (page structure, required CSS variables, every data-bx marker, the mirrored font list, forbidden constructs). Read this BEFORE writing theme HTML; validation enforces it exactly.",
|
|
328
|
+
inputSchema: { type: "object", properties: {} },
|
|
329
|
+
handler: (client) => client.getOne("/themes/spec", ""),
|
|
330
|
+
},
|
|
331
|
+
{
|
|
332
|
+
name: "get_theme",
|
|
333
|
+
description: "A single custom theme including its stored invoice_html / document_html layouts and current validation errors.",
|
|
334
|
+
inputSchema: { type: "object", properties: { key: { type: "string" } }, required: ["key"] },
|
|
335
|
+
handler: (client, args) => client.getOne(`/themes/${args.key}`, "theme"),
|
|
336
|
+
},
|
|
337
|
+
{
|
|
338
|
+
name: "upsert_theme",
|
|
339
|
+
description: "Create or update a custom theme. Pass `key` to update an existing theme (only the fields you pass change); omit it to create one (the key derives from the name). Layout HTML must follow THEME_SPEC v1 (get_theme_spec); validation runs on every save and failures come back as the theme's validation_errors list — fix and resend. Requires themes:write and an admin-level user.",
|
|
340
|
+
inputSchema: {
|
|
341
|
+
type: "object",
|
|
342
|
+
properties: {
|
|
343
|
+
key: { type: "string", description: "Existing theme key to update; omit to create" },
|
|
344
|
+
name: { type: "string" },
|
|
345
|
+
description: { type: "string" },
|
|
346
|
+
invoice_html: { type: "string", description: "Complete THEME_SPEC v1 invoice layout (required on create)" },
|
|
347
|
+
document_html: { type: "string", description: "Optional freeform-document layout (data-bx=\"document-body\")" },
|
|
348
|
+
accent_color: { type: "string", description: "#rrggbb default accent (the account's own accent overrides it)" },
|
|
349
|
+
font: { type: "string", description: "Primary font family, from the mirrored set in the spec" },
|
|
350
|
+
},
|
|
351
|
+
},
|
|
352
|
+
handler: (client, args) => {
|
|
353
|
+
const theme = {
|
|
354
|
+
name: args.name,
|
|
355
|
+
description: args.description,
|
|
356
|
+
invoice_html: args.invoice_html,
|
|
357
|
+
document_html: args.document_html,
|
|
358
|
+
accent_color: args.accent_color,
|
|
359
|
+
font: args.font,
|
|
360
|
+
};
|
|
361
|
+
return args.key
|
|
362
|
+
? client.mutate("PATCH", `/themes/${args.key}`, { theme })
|
|
363
|
+
: client.mutate("POST", "/themes", { theme });
|
|
364
|
+
},
|
|
365
|
+
},
|
|
366
|
+
{
|
|
367
|
+
name: "validate_theme",
|
|
368
|
+
description: "Re-run THEME_SPEC validation on a stored theme. Returns { valid, validation_errors, state } — a theme becomes selectable once valid.",
|
|
369
|
+
inputSchema: { type: "object", properties: { key: { type: "string" } }, required: ["key"] },
|
|
370
|
+
handler: (client, args) => client.mutate("POST", `/themes/${args.key}/validate`, {}),
|
|
371
|
+
},
|
|
372
|
+
{
|
|
373
|
+
name: "preview_theme",
|
|
374
|
+
description: "Render a sample through the theme and return the full HTML: a synthetic invoice by default, or the sample markdown document with document: \"markdown\". Works on drafts that pass validation — this is the iteration loop before activating.",
|
|
375
|
+
inputSchema: {
|
|
376
|
+
type: "object",
|
|
377
|
+
properties: {
|
|
378
|
+
key: { type: "string" },
|
|
379
|
+
document: { type: "string", enum: ["invoice", "markdown"], description: "Which layout to preview (default invoice)" },
|
|
380
|
+
},
|
|
381
|
+
required: ["key"],
|
|
382
|
+
},
|
|
383
|
+
handler: (client, args) => client.getOne(`/themes/${args.key}/preview${args.document ? `?document=${args.document}` : ""}`, ""),
|
|
384
|
+
},
|
|
385
|
+
{
|
|
386
|
+
name: "activate_theme",
|
|
387
|
+
description: "Switch the account's active theme — every invoice, quote and freeform document restyles immediately. Accepts a custom theme's resolver key (\"custom/<slug>\", must be validated) or any built-in key from list_themes (e.g. \"swiss\"). Requires themes:write and an admin-level user.",
|
|
388
|
+
inputSchema: { type: "object", properties: { key: { type: "string" } }, required: ["key"] },
|
|
389
|
+
handler: (client, args) => client.mutate("POST", "/themes/activate", { key: args.key }),
|
|
390
|
+
},
|
|
391
|
+
{
|
|
392
|
+
name: "delete_theme",
|
|
393
|
+
description: "Disable a custom theme (soft delete — it leaves the picker; an account still pointing at it falls back to the default theme). Requires themes:write and an admin-level user.",
|
|
394
|
+
inputSchema: { type: "object", properties: { key: { type: "string" } }, required: ["key"] },
|
|
395
|
+
handler: (client, args) => client.mutate("DELETE", `/themes/${args.key}`),
|
|
396
|
+
},
|
|
318
397
|
// ── Products & services catalogue (transaction templates) ──────────────
|
|
319
398
|
{
|
|
320
399
|
name: "list_products_services",
|
|
@@ -394,8 +473,8 @@ export const TOOLS = [
|
|
|
394
473
|
},
|
|
395
474
|
sell_amount: { type: "number", description: "Sell price per unit. Defaults to 0 — pass it." },
|
|
396
475
|
buy_amount: { type: "number", description: "Buy price per unit. Defaults to 0." },
|
|
397
|
-
sell_tax_id: { type: "integer", description: "Tax code applied when the item is sold." },
|
|
398
|
-
buy_tax_id: { type: "integer", description: "Tax code applied when the item is bought." },
|
|
476
|
+
sell_tax_id: { type: "integer", description: "Tax code applied when the item is sold — resolve it with list_taxes (side 'sell')." },
|
|
477
|
+
buy_tax_id: { type: "integer", description: "Tax code applied when the item is bought — resolve it with list_taxes (side 'buy')." },
|
|
399
478
|
description: { type: "string", description: "Longer description shown on documents." },
|
|
400
479
|
item_category_id: { type: "integer", description: "Category by id instead of by name. Takes precedence over item_category." },
|
|
401
480
|
active: { type: "boolean", description: "Defaults to true. false files it as archived." },
|
|
@@ -447,8 +526,8 @@ export const TOOLS = [
|
|
|
447
526
|
buy_transaction_account_id: { type: "integer", description: "Expense account the item is bought to." },
|
|
448
527
|
sell_amount: { type: "number" },
|
|
449
528
|
buy_amount: { type: "number" },
|
|
450
|
-
sell_tax_id: { type: "integer" },
|
|
451
|
-
buy_tax_id: { type: "integer" },
|
|
529
|
+
sell_tax_id: { type: "integer", description: "Tax code applied when the item is sold — see list_taxes." },
|
|
530
|
+
buy_tax_id: { type: "integer", description: "Tax code applied when the item is bought — see list_taxes." },
|
|
452
531
|
description: { type: "string" },
|
|
453
532
|
active: { type: "boolean", description: "false archives the item — it stays on existing documents but is no longer offered." },
|
|
454
533
|
physical_resource: { type: "boolean" },
|
|
@@ -847,6 +926,24 @@ export const TOOLS = [
|
|
|
847
926
|
bank: args.bank,
|
|
848
927
|
}),
|
|
849
928
|
},
|
|
929
|
+
{
|
|
930
|
+
name: "list_taxes",
|
|
931
|
+
description: "List the account's tax codes — the ids `sell_tax_id` / `buy_tax_id` on a product, and a document line's tax, have to point at. " +
|
|
932
|
+
"Read `sides` rather than `tax_type` to decide whether a code can be used: 'sell' means invoices and quotes, 'buy' means expenses, and a zero-rated 'no tax' code often appears on both. " +
|
|
933
|
+
"An account that is not registered for GST/VAT still has usable codes here — they are the zero-percent ones. `default` marks the code Beeswax applies when nothing else is chosen. " +
|
|
934
|
+
"Requires a token with transaction_accounts:read.",
|
|
935
|
+
inputSchema: {
|
|
936
|
+
type: "object",
|
|
937
|
+
properties: {
|
|
938
|
+
side: {
|
|
939
|
+
type: "string",
|
|
940
|
+
enum: ["sell", "buy", "payroll"],
|
|
941
|
+
description: "Return only the codes offered on this side: 'sell' = invoices and quotes, 'buy' = expenses, 'payroll' = payroll withholding codes.",
|
|
942
|
+
},
|
|
943
|
+
},
|
|
944
|
+
},
|
|
945
|
+
handler: (client, args) => client.getList("/active_account/taxes", "taxes", { side: args.side }),
|
|
946
|
+
},
|
|
850
947
|
{
|
|
851
948
|
name: "list_companies",
|
|
852
949
|
description: "List the account's clients and suppliers. Use this to resolve a client name to the company_id create_quote needs. " +
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "beeswax-mcp",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.3.0",
|
|
4
4
|
"description": "Official MCP server for Beeswax (beeswaxapp.com) — query invoices, quotes, expenses, payments, journals, time entries, projects, products & services and tax returns from Claude and other MCP clients, and build quotes priced from your catalogue.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"homepage": "https://www.beeswaxapp.com/support/mcp-setup",
|