@cyanheads/congressgov-mcp-server 0.7.1 → 0.7.3

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 (47) hide show
  1. package/AGENTS.md +20 -15
  2. package/CLAUDE.md +20 -15
  3. package/Dockerfile +23 -10
  4. package/README.md +90 -93
  5. package/changelog/0.7.x/0.7.2.md +20 -0
  6. package/changelog/0.7.x/0.7.3.md +36 -0
  7. package/dist/mcp-server/tools/definitions/bill-lookup.tool.d.ts +5 -4
  8. package/dist/mcp-server/tools/definitions/bill-lookup.tool.d.ts.map +1 -1
  9. package/dist/mcp-server/tools/definitions/bill-lookup.tool.js +93 -2
  10. package/dist/mcp-server/tools/definitions/bill-lookup.tool.js.map +1 -1
  11. package/dist/mcp-server/tools/definitions/bill-summaries.tool.d.ts.map +1 -1
  12. package/dist/mcp-server/tools/definitions/bill-summaries.tool.js +32 -4
  13. package/dist/mcp-server/tools/definitions/bill-summaries.tool.js.map +1 -1
  14. package/dist/mcp-server/tools/definitions/committee-reports.tool.d.ts +2 -2
  15. package/dist/mcp-server/tools/definitions/daily-record.tool.d.ts +2 -2
  16. package/dist/mcp-server/tools/format-helpers.d.ts.map +1 -1
  17. package/dist/mcp-server/tools/format-helpers.js +85 -30
  18. package/dist/mcp-server/tools/format-helpers.js.map +1 -1
  19. package/dist/mcp-server/tools/summary-window.d.ts +112 -0
  20. package/dist/mcp-server/tools/summary-window.d.ts.map +1 -0
  21. package/dist/mcp-server/tools/summary-window.js +182 -0
  22. package/dist/mcp-server/tools/summary-window.js.map +1 -0
  23. package/dist/mcp-server/tools/tool-helpers.d.ts +21 -4
  24. package/dist/mcp-server/tools/tool-helpers.d.ts.map +1 -1
  25. package/dist/mcp-server/tools/tool-helpers.js +21 -4
  26. package/dist/mcp-server/tools/tool-helpers.js.map +1 -1
  27. package/dist/services/congress-documents/extract-text-stream.js +1 -1
  28. package/dist/services/congress-documents/extract-text-stream.js.map +1 -1
  29. package/dist/services/congress-documents/extract-text.d.ts +0 -6
  30. package/dist/services/congress-documents/extract-text.d.ts.map +1 -1
  31. package/dist/services/congress-documents/extract-text.js +4 -37
  32. package/dist/services/congress-documents/extract-text.js.map +1 -1
  33. package/dist/services/congress-mirror/normalize.d.ts +4 -1
  34. package/dist/services/congress-mirror/normalize.d.ts.map +1 -1
  35. package/dist/services/congress-mirror/normalize.js +8 -12
  36. package/dist/services/congress-mirror/normalize.js.map +1 -1
  37. package/dist/services/senate-lis/parse.d.ts.map +1 -1
  38. package/dist/services/senate-lis/parse.js +74 -2
  39. package/dist/services/senate-lis/parse.js.map +1 -1
  40. package/dist/services/senate-lis/types.d.ts +8 -1
  41. package/dist/services/senate-lis/types.d.ts.map +1 -1
  42. package/dist/utils/character-references.d.ts +27 -0
  43. package/dist/utils/character-references.d.ts.map +1 -0
  44. package/dist/utils/character-references.js +60 -0
  45. package/dist/utils/character-references.js.map +1 -0
  46. package/package.json +7 -6
  47. package/server.json +3 -3
package/README.md CHANGED
@@ -7,13 +7,13 @@
7
7
 
8
8
  <div align="center">
9
9
 
10
- [![Version](https://img.shields.io/badge/Version-0.7.1-blue.svg?style=flat-square)](./CHANGELOG.md) [![License](https://img.shields.io/badge/License-Apache%202.0-orange.svg?style=flat-square)](./LICENSE) [![Docker](https://img.shields.io/badge/Docker-ghcr.io-2496ED?style=flat-square&logo=docker&logoColor=white)](https://github.com/users/cyanheads/packages/container/package/congressgov-mcp-server) [![MCP SDK](https://img.shields.io/badge/MCP%20SDK-^2.0.0-green.svg?style=flat-square)](https://modelcontextprotocol.io/) [![npm](https://img.shields.io/npm/v/@cyanheads/congressgov-mcp-server?style=flat-square&logo=npm&logoColor=white)](https://www.npmjs.com/package/@cyanheads/congressgov-mcp-server) [![TypeScript](https://img.shields.io/badge/TypeScript-^7.0.2-3178C6.svg?style=flat-square)](https://www.typescriptlang.org/) [![Bun](https://img.shields.io/badge/Bun-v1.4.0-blueviolet.svg?style=flat-square)](https://bun.sh/)
10
+ [![Version](https://img.shields.io/badge/Version-0.7.3-blue.svg?style=flat-square)](./CHANGELOG.md) [![License](https://img.shields.io/badge/License-Apache%202.0-orange.svg?style=flat-square)](./LICENSE) [![Docker](https://img.shields.io/badge/Docker-ghcr.io-2496ED?style=flat-square&logo=docker&logoColor=white)](https://github.com/users/cyanheads/packages/container/package/congressgov-mcp-server) [![MCP SDK](https://img.shields.io/badge/MCP%20SDK-^2.1.0-green.svg?style=flat-square)](https://modelcontextprotocol.io/) [![npm](https://img.shields.io/npm/v/@cyanheads/congressgov-mcp-server?style=flat-square&logo=npm&logoColor=white)](https://www.npmjs.com/package/@cyanheads/congressgov-mcp-server) [![TypeScript](https://img.shields.io/badge/TypeScript-^7.0.2-3178C6.svg?style=flat-square)](https://www.typescriptlang.org/) [![Bun](https://img.shields.io/badge/Bun-v1.4.2-blueviolet.svg?style=flat-square)](https://bun.sh/)
11
11
 
12
12
  </div>
13
13
 
14
14
  <div align="center">
15
15
 
16
- [![Install in Claude Desktop](https://img.shields.io/badge/Install_in-Claude_Desktop-D97757?style=for-the-badge&logo=anthropic&logoColor=white)](https://github.com/cyanheads/congressgov-mcp-server/releases/latest/download/congressgov-mcp-server.mcpb) [![Install in Cursor](https://cursor.com/deeplink/mcp-install-dark.svg)](https://cursor.com/en/install-mcp?name=congressgov-mcp-server&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyIteSIsIkBjeWFuaGVhZHMvY29uZ3Jlc3Nnb3YtbWNwLXNlcnZlciJdLCJlbnYiOnsiQ09OR1JFU1NfQVBJX0tFWSI6InlvdXItYXBpLWtleSJ9fQ==) [![Install in VS Code](https://img.shields.io/badge/VS_Code-Install_Server-0098FF?style=for-the-badge&logo=visualstudiocode&logoColor=white)](https://vscode.dev/redirect?url=vscode:mcp/install?%7B%22name%22%3A%22congressgov-mcp-server%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40cyanheads/congressgov-mcp-server%22%5D%2C%22env%22%3A%7B%22CONGRESS_API_KEY%22%3A%22your-api-key%22%7D%7D)
16
+ [![Install in Claude Desktop](https://img.shields.io/badge/Install_in-Claude_Desktop-D97757?style=for-the-badge&logo=anthropic&logoColor=white)](https://github.com/cyanheads/congressgov-mcp-server/releases/latest/download/congressgov-mcp-server.mcpb) [![Install in Cursor](https://cursor.com/deeplink/mcp-install-dark.svg)](https://cursor.com/en/install-mcp?name=congressgov-mcp-server&config=eyJjb21tYW5kIjoibnB4IiwiYXJncyI6WyIteSIsIkBjeWFuaGVhZHMvY29uZ3Jlc3Nnb3YtbWNwLXNlcnZlciJdLCJlbnYiOnsiQ09OR1JFU1NfQVBJX0tFWSI6InlvdXItYXBpLWtleSJ9fQ==) [![Install in VS Code](https://img.shields.io/badge/VS_Code-Install_Server-0098FF?style=for-the-badge&logo=visualstudiocode&logoColor=white)](https://vscode.dev/redirect?url=vscode:mcp/install?%7B%22name%22%3A%22congressgov-mcp-server%22%2C%22command%22%3A%22npx%22%2C%22args%22%3A%5B%22-y%22%2C%22%40cyanheads%2Fcongressgov-mcp-server%22%5D%2C%22env%22%3A%7B%22CONGRESS_API_KEY%22%3A%22your-api-key%22%7D%7D)
17
17
 
18
18
  [![Framework](https://img.shields.io/badge/Built%20on-@cyanheads/mcp--ts--core-67E8F9?style=flat-square)](https://www.npmjs.com/package/@cyanheads/mcp-ts-core)
19
19
 
@@ -29,23 +29,23 @@
29
29
 
30
30
  ## Overview
31
31
 
32
- U.S. congressional data from the Congress.gov API v3 and the Senate's official vote feed — bills, enacted laws, members, committees, roll call votes, and presidential nominations. Browse legislative activity, read bill and report text, and track the Senate confirmation pipeline from any MCP client. Runs as a stdio process, a local Streamable HTTP server, or the public hosted endpoint above.
32
+ U.S. congressional data from the Congress.gov API v3 and the Senate's official vote feed: bills, enacted laws, members, committees, roll call votes, nominations, CRS and committee reports, and the Congressional Record. Browse legislative activity, read bill and report text, and follow the Senate confirmation pipeline from any MCP client. Runs as a stdio process, a local Streamable HTTP server, or the public hosted endpoint above.
33
33
 
34
34
  ### Tools
35
35
 
36
36
  | Tool | Description |
37
37
  |:---|:---|
38
- | `congressgov_bill_lookup` | Browse and retrieve U.S. legislative bill data — actions, sponsors, summaries, text, related bills |
38
+ | `congressgov_bill_lookup` | Browse and retrieve bills: actions, sponsors, summaries, text, related bills |
39
39
  | `congressgov_enacted_laws` | Browse enacted public and private laws by congress |
40
- | `congressgov_member_lookup` | Discover congressional members by state/district/congress, retrieve legislative portfolios |
41
- | `congressgov_committee_lookup` | Browse congressional committees and their legislation, reports, and nominations |
42
- | `congressgov_roll_votes` | Retrieve House and Senate roll call votes and individual member voting positions |
43
- | `congressgov_senate_nominations` | Browse presidential nominations to federal positions and track the Senate confirmation process |
44
- | `congressgov_bill_summaries` | Browse recent CRS bill summaries — the "what's happening" feed |
45
- | `congressgov_crs_reports` | Browse and retrieve nonpartisan CRS policy analysis reports |
46
- | `congressgov_committee_reports` | Browse and retrieve committee reports accompanying legislation |
47
- | `congressgov_daily_record` | Browse the daily Congressional Record — floor speeches, debates, and proceedings |
48
- | `congressgov_search_bills` | Keyword-search bill titles and CRS summaries via a local full-text mirror (opt-in, off by default) |
40
+ | `congressgov_member_lookup` | Find members by state, district, or congress, and retrieve their legislative portfolios |
41
+ | `congressgov_committee_lookup` | Browse committees and their legislation, reports, and nominations |
42
+ | `congressgov_roll_votes` | Retrieve House and Senate roll call votes and each member's position |
43
+ | `congressgov_senate_nominations` | Browse presidential nominations and track Senate confirmation |
44
+ | `congressgov_bill_summaries` | Browse recently updated CRS bill summaries |
45
+ | `congressgov_crs_reports` | Browse and retrieve nonpartisan CRS policy reports |
46
+ | `congressgov_committee_reports` | Browse and read committee reports accompanying legislation |
47
+ | `congressgov_daily_record` | Browse and read the daily Congressional Record |
48
+ | `congressgov_search_bills` | Keyword-search bill titles and CRS summaries via a local full-text mirror (opt-in) |
49
49
 
50
50
  ### Resources
51
51
 
@@ -57,7 +57,7 @@ U.S. congressional data from the Congress.gov API v3 and the Senate's official v
57
57
  | `congress://bill/{congress}/{billType}/{billNumber}` | Bill detail by congress, type, and number |
58
58
  | `congress://committee/{committeeCode}` | Committee detail by committee code |
59
59
 
60
- Bill, member, and committee data is also reachable through `congressgov_bill_lookup`, `congressgov_member_lookup`, and `congressgov_committee_lookup` (operation `get`) — many MCP clients are tool-only and never surface resources.
60
+ Bill, member, and committee data is also reachable through `congressgov_bill_lookup`, `congressgov_member_lookup`, and `congressgov_committee_lookup` (operation `get`), since many MCP clients are tool-only and never surface resources.
61
61
 
62
62
  ### Prompts
63
63
 
@@ -70,146 +70,132 @@ Bill, member, and committee data is also reachable through `congressgov_bill_loo
70
70
 
71
71
  ### `congressgov_bill_lookup` <sub>tool</sub>
72
72
 
73
- - Operations: `list` (browse by congress/billType/date range — no keyword search), `get` (full detail), or drill into `actions`, `amendments`, `cosponsors`, `committees`, `subjects`, `summaries`, `text`, `titles`, `related`
74
- - `list` defaults to `order='recent'` (newest update-date first); `limit` 1–250, `offset` pagination
75
- - `content` reads a text version's actual document text: select the version with `textVersionIndex` (0-based, against `text`'s order), the window with `characterOffset`/`characterLimit` (1–100,000 chars, default 25,000), and follow `nextOffset` to walk a full bill
76
- - Typed failures on `content`: `document_unavailable`, `format_unavailable`, `document_fetch_failed`, `document_too_large`, `offset_past_end`, alongside the shared `not_found` / `rate_limited` / `invalid_request` / `upstream_error` set
73
+ - `list` browses one `congress`, narrowed by `billType` and a `fromDateTime`/`toDateTime` range on the record's update date, newest first unless `order: 'oldest'`; `get`, `actions`, `amendments`, `cosponsors`, `committees`, `subjects`, `summaries`, `text`, `titles`, `related`, and `content` need `congress` + `billType` + `billNumber`
74
+ - `content` reads the text version at `textVersionIndex` (0-based in `text` order, 0 is the most recent) and returns one character window in `content.text` with `totalCharacters`, `truncated`, and `nextOffset`
75
+ - `summaries` takes an optional `versionCode` (`00` introduced, `49` public law) and applies the same page budget and row window as `congressgov_bill_summaries`, steered by `characterOffset`/`characterLimit`; a cut row carries `textTotalCharacters`, `textTruncated`, and `textNextOffset`
77
76
 
78
77
  ---
79
78
 
80
79
  ### `congressgov_enacted_laws` <sub>tool</sub>
81
80
 
82
- - `list` filters by congress and `lawType` (`pub` public laws, `priv` private) — the enactment-status filter `congressgov_bill_lookup` doesn't offer
83
- - `get` returns the origin bill record; the law citation lives on the bill's `laws[]` array (e.g. `{"number":"118-2","type":"Public Law"}`)
84
- - `lawNumber` accepts either the bare number (`90`) or the full `{congress}-{number}` citation a `list` row carries; a citation naming a different congress than the `congress` param is rejected rather than silently resolved
85
- - `limit` 1–250, `offset` pagination for `list`
81
+ - `list` browses one `congress`, optionally by `lawType` (`pub` or `priv`), the enactment filter `congressgov_bill_lookup` lacks; `get` needs `lawType` + `lawNumber`, taken from a list row's `laws[].number` (`118-90`) or its bare number (`90`)
82
+ - `get` returns the origin bill record, with the law citation on its `laws[]` array
86
83
 
87
84
  ---
88
85
 
89
86
  ### `congressgov_member_lookup` <sub>tool</sub>
90
87
 
91
- - No name search — `list` filters by `stateCode` (+ optional `district`, which requires `stateCode`), `congress`, and `currentMember`
92
- - `get` returns the full profile by `bioguideId` (e.g. `P000197`); `sponsored`/`cosponsored` return that member's legislative portfolio
93
- - `limit` 1–250, `offset` pagination
88
+ - No name search: `list` filters by `stateCode` (plus `district`, `0` for at-large, which requires `stateCode`), `congress`, and `currentMember`
89
+ - `get` returns the profile for a `bioguideId` (e.g. `P000197`); `sponsored` and `cosponsored` return that member's legislation
94
90
 
95
91
  ---
96
92
 
97
93
  ### `congressgov_committee_lookup` <sub>tool</sub>
98
94
 
99
- - Committee codes are chamber-prefix (`h`/`s`/`j`) + abbreviation + 2-digit number (e.g. `hsju00`); `get` and sub-resources infer chamber from the prefix, or accept an explicit override
100
- - `committeeCode` also accepts a committee name, resolved automatically (all-token match, then a bigram-similarity fallback labeled `approximate: true`) against the full cross-chamber roster
101
- - `list` with `filter` name-matches the same way, paging past the 250-row upstream cap to search the complete roster before filtering
102
- - `bills` sub-resource defaults to `order='recent'` (newest update-date first, computed client-side since upstream ignores sort); rows carry no titles — chain `congressgov_bill_lookup get` per row
103
- - `nominations` sub-resource is Senate-only
95
+ - `committeeCode` is a chamber prefix (`h`/`s`/`j`), letters, and a 2-digit suffix (e.g. `hsju00`); `get`, `bills`, `reports`, and the Senate-only `nominations` infer `chamber` from the prefix
96
+ - A committee name in `committeeCode` resolves when exactly one committee matches, and otherwise returns the candidate rows with a notice; `list` with `filter` name-matches every committee in scope, past the 250-row page cap, and fuzzy hits carry `approximate: true`
97
+ - `bills` is newest first by default (`order`), and its rows carry no titles, so chain `congressgov_bill_lookup` `get` per row
104
98
 
105
99
  ---
106
100
 
107
101
  ### `congressgov_roll_votes` <sub>tool</sub>
108
102
 
109
- - `chamber` is `house` (default, Congress.gov API) or `senate` (the Senate's official LIS XML feed — the API exposes no Senate votes)
110
- - `list` browses by congress + session (1 or 2), newest-first by default (computed client-side for strict ordering); `get` returns tallies and party breakdown, `members` returns each member's recorded position
111
- - Roll call numbers reset each session and are specific to one chamber
112
- - `limit` 1–250, `offset` pagination for `list` and `members`
103
+ - `chamber` is `house` (default, Congress.gov API) or `senate` (the Senate's LIS feed); every call needs `congress` + `session` (1 or 2), and `get`/`members` add `voteNumber`, which resets each session and is specific to one chamber
104
+ - `list` is newest first unless `order: 'oldest'`; `get` returns the question, result, tallies, and party breakdown, and `members` returns each member's position
105
+ - Senate votes start at the 101st Congress (1989), and Senate rows pair the feed's year-less `voteDate` with a derived `voteDateIso`
113
106
 
114
107
  ---
115
108
 
116
109
  ### `congressgov_senate_nominations` <sub>tool</sub>
117
110
 
118
- - Nominations use `PN` numbering; `list` browses by congress, `get` returns detail, `actions`/`committees`/`hearings` cover the confirmation pipeline, `nominees` returns individuals in a batch (requires `ordinal`)
119
- - Multi-part parents (e.g. `PN851`) carry no activity of their own — sub-resources live on partitioned children (`851-1`, `851-2`, …); a bare-parent sub-resource call on such a nomination returns an enrichment notice pointing at the partitioned form
120
- - `ordinal` is discovered from the nomination's `nominees` array via `get` first
111
+ - `list` browses one `congress`; `get`, `actions`, `committees`, `hearings`, and `nominees` need a `nominationNumber` (`1000` for PN1000), and `nominees` also needs an `ordinal` from the `nominees` array `get` returns
112
+ - Multi-part nominations (e.g. PN851) keep their activity on partitioned children (`851-1`, `851-2`, …); an empty sub-resource call on the bare number returns a notice pointing there
121
113
 
122
114
  ---
123
115
 
124
116
  ### `congressgov_bill_summaries` <sub>tool</sub>
125
117
 
126
- - Filters by `congress` and `billType` (requires `congress`); date filters apply to the CRS summary's update time, not the bill's action date
127
- - Defaults to summaries updated in the last 7 days when neither date bound is supplied
128
- - For summaries of one specific bill, use `congressgov_bill_lookup` with `operation='summaries'` instead
118
+ - Optional `congress` and `billType` (which requires `congress`); `fromDateTime`/`toDateTime` filter on the summary's update time, not the bill's action date, and cover the last 7 days when both are omitted
119
+ - A page stops adding rows at 50,000 serialized characters (at least one row always returns, and `pagination.nextOffset` resumes); a summary over 25,000 characters arrives windowed with `textTotalCharacters`, `textTruncated`, and `textNextOffset`
120
+ - For one bill's summaries, or to read a windowed summary to the end, use `congressgov_bill_lookup` `summaries`
129
121
 
130
122
  ---
131
123
 
132
124
  ### `congressgov_crs_reports` <sub>tool</sub>
133
125
 
134
- - Report IDs use letter-number codes (e.g. `R40097`, `RL33612`, `IF12345`)
135
- - `list` browses the catalog; `get` returns full detail (authors, topics, summary, download formats) by `reportNumber`
136
- - `limit` 1–250, `offset` pagination for `list`
126
+ - `list` browses the catalog; `get` takes a `reportNumber` such as `R40097`, `RL33612`, or `IF12345`
127
+ - `get` returns authors, topics, summary, and download formats
137
128
 
138
129
  ---
139
130
 
140
131
  ### `congressgov_committee_reports` <sub>tool</sub>
141
132
 
142
- - Report types: `hrpt` (House), `srpt` (Senate), `erpt` (Executive); `list` browses by congress + optional `reportType`, `get` returns citation/title/committees/associated bill
143
- - `text` lists each format's `{type, url}` link (report formats arrive one per entry, unlike bill text versions); `content` then reads the actual text, a bounded character window at a time via `characterOffset`/`characterLimit` (1–100,000 chars, default 25,000)
144
- - Typed failures on `content`: `document_unavailable`, `format_unavailable`, `document_fetch_failed`, `document_too_large`, `offset_past_end`
133
+ - `list` browses one `congress`, optionally by `reportType` (`hrpt` House, `srpt` Senate, `erpt` Executive); `get`, `text`, and `content` need `reportType` + `reportNumber`
134
+ - `get` returns the citation, title, committees, and associated bill; `text` lists `{type, url}` format links, and `content` reads the report as one character window
145
135
 
146
136
  ---
147
137
 
148
138
  ### `congressgov_daily_record` <sub>tool</sub>
149
139
 
150
- - Hierarchical navigation: `list` (volumes) → `issues` (within a volume) → `articles` (within an issue)
151
- - `content` reads one article's text, selected by `articleIndex` (0-based) and bounded by `characterOffset`/`characterLimit`; the Congressional Record publishes Formatted Text and PDF only (no XML)
152
- - Typed failures on `content`: `document_unavailable`, `format_unavailable`, `document_fetch_failed`, `document_too_large`, `offset_past_end`
140
+ - Navigation runs `list` (volumes) → `issues` (by `volumeNumber`) → `articles` (by `volumeNumber` + `issueNumber`)
141
+ - `content` reads the article at `articleIndex` (0-based across the issue) as one character window; Record articles publish Formatted Text and PDF only, so `format: 'xml'` fails as `format_unavailable`
153
142
 
154
143
  ---
155
144
 
156
145
  ### `congressgov_search_bills` <sub>tool</sub>
157
146
 
158
- - **Opt-in:** off by default and absent from `tools/list` entirely until `CONGRESS_MIRROR_ENABLED=true`
159
- - Keyword-searches a local SQLite FTS5 mirror of bill titles + CRS summaries — the discovery path the Congress.gov API itself lacks; policy area and full bill text are not indexed
160
- - Narrows with `congress`, `billType`, and `originChamber`; returns BM25-ranked matches with each bill's derived id, ready for a follow-up `congressgov_bill_lookup` call
161
- - With the flag set but the index not yet built (`bun run mirror:init`), the tool answers with an empty result and a build-the-index notice instead of an error
162
- - `limit` 1–100 (a narrower cap than the other tools' 1–250), `offset` pagination
147
+ - `query` keywords (AND-combined) over bill titles and CRS summaries, narrowed by `congress`, `billType`, and `originChamber`; `limit` 1–100, `offset` pagination
148
+ - BM25-ranked rows carry `billId` plus `congress`/`billType`/`billNumber` for `congressgov_bill_lookup`, and a `summaryPreview`; policy area and full bill text are not indexed
149
+ - Listed only when `CONGRESS_MIRROR_ENABLED=true`; until `bun run mirror:init` builds the index, it returns an empty result with a notice
163
150
 
164
151
  ---
165
152
 
166
153
  ### `congress://current` <sub>resource</sub>
167
154
 
168
- - Current congress number, session dates, and chamber info — baseline context for other queries
155
+ - Current congress number, session dates, and chamber info, the baseline for other queries
169
156
  - Cached publicly for 1 hour
170
157
 
171
158
  ---
172
159
 
173
160
  ### `congress://bill-types` <sub>resource</sub>
174
161
 
175
- - Static reference table of the 8 valid bill type codes (`hr`, `s`, `hjres`, `sjres`, `hconres`, `sconres`, `hres`, `sres`) with chamber and an example citation
176
- - Cached publicly for 24 hours — fixed by chamber rules, not fetched upstream
162
+ - The 8 bill type codes (`hr`, `s`, `hjres`, `sjres`, `hconres`, `sconres`, `hres`, `sres`) with description, chamber, and an example citation
163
+ - Static, with no upstream call; cached publicly for 24 hours
177
164
 
178
165
  ---
179
166
 
180
167
  ### `congress://member/{bioguideId}` <sub>resource</sub>
181
168
 
182
- - `bioguideId` must match one uppercase letter followed by 6 digits (e.g. `P000197`)
183
- - Returns the member profile — name, state, party, terms, leadership, office, legislation counts
169
+ - `bioguideId` is one uppercase letter and 6 digits (e.g. `P000197`)
170
+ - Returns the member profile: name, state, party, terms, leadership, office, legislation counts
184
171
 
185
172
  ---
186
173
 
187
174
  ### `congress://bill/{congress}/{billType}/{billNumber}` <sub>resource</sub>
188
175
 
189
- - `congress` and `billNumber` must be positive integers; `billType` must be a valid bill type code
190
- - Returns bill detail — sponsor, status, policy area, committees, latest action
176
+ - `congress` and `billNumber` are positive integers; `billType` is one of the 8 bill type codes
177
+ - Returns bill detail: sponsor, status, policy area, committees, latest action
191
178
 
192
179
  ---
193
180
 
194
181
  ### `congress://committee/{committeeCode}` <sub>resource</sub>
195
182
 
196
- - `committeeCode` must match `h`/`s`/`j` followed by 3–8 lowercase alphanumeric characters (e.g. `hsju00`); chamber is inferred from the first letter
197
- - Returns committee detail — name, chamber, subcommittees, history, legislation counts
183
+ - `committeeCode` is `h`/`s`/`j` followed by 3–8 lowercase alphanumeric characters (e.g. `hsju00`); chamber comes from the first letter
184
+ - Returns committee detail: name, chamber, subcommittees, history, legislation counts
198
185
 
199
186
  ---
200
187
 
201
188
  ### `congressgov_bill_analysis` <sub>prompt</sub>
202
189
 
203
- - Arguments: `congress`, `billType`, `billNumber` — all required strings
204
- - Returns one user message framing a structured analysis (summary, sponsors, committee referrals, action timeline, related legislation, policy implications, outlook) and naming which tools to call for each section
190
+ - Arguments: `congress`, `billType`, and `billNumber`, all required
191
+ - Returns one user message framing a seven-part analysis, from summary to outlook, with the tools to call for each part
205
192
 
206
193
  ---
207
194
 
208
195
  ### `congressgov_legislative_research` <sub>prompt</sub>
209
196
 
210
- - Arguments: `topic` required; `congress` optional (defaults to the current congress)
211
- - The discovery plan is configuration-aware: with `CONGRESS_MIRROR_ENABLED` it opens with `congressgov_search_bills`; without it, it asks for a seed (a bill, member, committee, or CRS report id) since no registered tool accepts a topic string
212
- - Synthesizes findings into landscape, key players, substance, recent activity, and outlook
197
+ - Arguments: `topic` required; `congress` optional, defaulting to the current congress
198
+ - With `CONGRESS_MIRROR_ENABLED`, the plan opens with `congressgov_search_bills`; without it, the prompt asks for a seed bill, member, committee, or CRS report ID, since no other tool takes a topic
213
199
 
214
200
  ## Features
215
201
 
@@ -217,17 +203,17 @@ Built on [`@cyanheads/mcp-ts-core`](https://github.com/cyanheads/mcp-ts-core): s
217
203
 
218
204
  Congress.gov-specific:
219
205
 
220
- - Type-safe client for the Congress.gov REST API v3, plus a second client for the Senate's official LIS XML feed (`fast-xml-parser`) backing Senate roll votes
221
- - Optional API key from [api.data.gov](https://api.data.gov/signup/) — defaults to `DEMO_KEY` (30 req/hr); own key gets 5,000 req/hr
222
- - Bounded document-text retrieval for bill text, committee reports, and Congressional Record articles — a 25 MB fetch ceiling, 30s deadline, and a `www.congress.gov` host allowlist
223
- - Opt-in local SQLite FTS5 mirror (`CONGRESS_MIRROR_ENABLED`) adds keyword search over bill titles and CRS summaries, the one discovery path the API itself lacks
224
- - All tools are read-only and idempotent
206
+ - Type-safe client for the Congress.gov REST API v3, plus a client for the Senate's LIS XML feed that backs Senate roll votes
207
+ - The Congress.gov API has no keyword search, so tools browse by congress, type, date range, chamber, state, and district, and address bills by `congress` + `billType` + `billNumber`, members by `bioguideId`, and committees by system code; list operations page with `limit` 1–250 (default 20) and `offset`
208
+ - `content` on bill text, committee reports, and Record articles reads `format` `text` (default) or `xml` through a `characterOffset`/`characterLimit` window (1–100,000 characters, default 25,000), fetched only from `www.congress.gov` under a 25 MB ceiling and a 30s deadline
209
+ - Optional API key from [api.data.gov](https://api.data.gov/signup/): `DEMO_KEY` allows 30 req/hr, your own key 5,000 req/hr
210
+ - Opt-in local SQLite FTS5 mirror (`CONGRESS_MIRROR_ENABLED`) adds keyword search over bill titles and CRS summaries
225
211
 
226
212
  Agent-friendly output:
227
213
 
228
- - Effective-query echo and total-count enrichment on every browse/list operation, plus a notice when a query resolves to zero matches or an offset runs past the end
229
- - Character-exact document windows — `content` operations return `offset`/`nextOffset` so walking a multi-megabyte bill or report never skips or repeats a character
230
- - Typed failure reasons on document reads (`document_unavailable`, `format_unavailable`, `document_too_large`, `offset_past_end`, …) alongside the shared upstream-error set, each resolved to a recovery hint
214
+ - Every list response carries `effectiveQuery` and `totalCount`; a `notice` fires when nothing matched, and a page past the end says so in the rendered output
215
+ - Exact character windows: `content` returns `offset`, `truncated`, and `nextOffset`, so walking a multi-megabyte bill never skips or repeats a character
216
+ - Typed `content` failures (`document_unavailable`, `format_unavailable`, `document_fetch_failed`, `document_too_large`, `offset_past_end`) alongside the shared `not_found`, `rate_limited`, `invalid_request`, and `upstream_error` reasons, each with a recovery hint
231
217
 
232
218
  ## Getting started
233
219
 
@@ -305,8 +291,6 @@ Or with Docker:
305
291
  }
306
292
  ```
307
293
 
308
- Get a free API key at [api.data.gov/signup](https://api.data.gov/signup/) for 5,000 req/hr. Without a key the server falls back to `DEMO_KEY` (30 req/hr).
309
-
310
294
  For Streamable HTTP, set the transport and start the server:
311
295
 
312
296
  ```sh
@@ -317,6 +301,7 @@ MCP_TRANSPORT_TYPE=http MCP_HTTP_PORT=3010 CONGRESS_API_KEY=your-api-key bun run
317
301
  ### Prerequisites
318
302
 
319
303
  - [Bun v1.4.0](https://bun.sh/) or higher (or Node.js v24+).
304
+ - Optional: a free [api.data.gov key](https://api.data.gov/signup/) raises the limit from 30 to 5,000 requests per hour.
320
305
 
321
306
  ### Installation
322
307
 
@@ -342,27 +327,30 @@ bun install
342
327
 
343
328
  ```sh
344
329
  cp .env.example .env
345
- # edit .env and set required vars
330
+ # edit .env and set CONGRESS_API_KEY (and the mirror vars, if you want keyword search)
346
331
  ```
347
332
 
348
333
  ## Configuration
349
334
 
350
335
  | Variable | Description | Default |
351
336
  |:---|:---|:---|
352
- | `CONGRESS_API_KEY` | API key from [api.data.gov](https://api.data.gov/signup/). Omit to use `DEMO_KEY` (30 req/hr); own key: 5,000 req/hr. | `DEMO_KEY` |
337
+ | `CONGRESS_API_KEY` | API key from [api.data.gov](https://api.data.gov/signup/). `DEMO_KEY` allows 30 req/hr; your own key 5,000 req/hr. | `DEMO_KEY` |
353
338
  | `CONGRESS_API_BASE_URL` | Congress.gov API base URL. | `https://api.congress.gov/v3` |
354
339
  | `CONGRESS_MIRROR_ENABLED` | Enable the local bill search mirror and the `congressgov_search_bills` tool. | `false` |
355
340
  | `CONGRESS_MIRROR_PATH` | Filesystem path to the SQLite mirror index. | `.mirror/bills.sqlite3` |
356
- | `CONGRESS_MIRROR_REFRESH_CRON` | Cron schedule for the in-process mirror refresh (HTTP transport only). Unset runs `mirror:refresh` manually. | — |
341
+ | `CONGRESS_MIRROR_REFRESH_CRON` | Cron schedule for the in-process mirror refresh (HTTP transport only). Unset means running `mirror:refresh` yourself. | — |
357
342
  | `CONGRESS_MIRROR_CONGRESSES` | Comma-separated congress numbers to mirror (e.g. `118,119`). | current congress + 1 prior |
358
343
  | `MCP_TRANSPORT_TYPE` | Transport: `stdio` or `http`. | `stdio` |
359
344
  | `MCP_HTTP_PORT` | HTTP server port. | `3010` |
345
+ | `MCP_SESSION_MODE` | HTTP session mode: `stateless`, `stateful`, or `auto`; `auto` resolves to `stateful`. | `stateless` |
360
346
  | `MCP_AUTH_MODE` | Authentication: `none`, `jwt`, or `oauth`. | `none` |
361
- | `MCP_SESSION_MODE` | HTTP session mode: `auto`, `stateful`, or `stateless`; `auto` resolves to `stateful`. | `stateless` |
362
347
  | `MCP_LOG_LEVEL` | Log level (`debug`, `info`, `notice`, `warning`, `error`, etc.). | `info` |
363
348
  | `LOGS_DIR` | Directory for log files (Node.js only). | `<project-root>/logs` |
364
- | `STORAGE_PROVIDER_TYPE` | Storage backend. | `in-memory` |
365
- | `OTEL_ENABLED` | Enable [OpenTelemetry instrumentation](https://github.com/cyanheads/mcp-ts-core/tree/main/docs/telemetry) (spans, metrics, completion logs). | `false` |
349
+ | `OTEL_ENABLED` | Enable [OpenTelemetry](https://github.com/cyanheads/mcp-ts-core/tree/main/docs/telemetry). | `false` |
350
+ | `OTEL_EXPORTER_OTLP_ENDPOINT` | Base OTLP endpoint for traces and metrics. | — |
351
+ | `OTEL_EXPORTER_OTLP_LOGS_ENDPOINT` | Explicit OTLP logs endpoint; the base endpoint does not enable log export. | — |
352
+ | `LOG_TOOL_FAILURE_PAYLOADS` | Log failed-call input and output with key-based redaction; secrets inside free-form values are not redacted. | `false` |
353
+ | `LOG_TOOL_FAILURE_PAYLOAD_MAX_BYTES` | Maximum bytes per failed-call input or output record. | `16384` |
366
354
 
367
355
  See [`.env.example`](./.env.example) for the full list of optional overrides.
368
356
 
@@ -377,6 +365,14 @@ See [`.env.example`](./.env.example) for the full list of optional overrides.
377
365
  bun run start:http # or start:stdio
378
366
  ```
379
367
 
368
+ - **Build the bill search mirror** (with `CONGRESS_MIRROR_ENABLED=true`):
369
+
370
+ ```sh
371
+ bun run mirror:init # full build
372
+ bun run mirror:refresh # incremental refresh
373
+ bun run mirror:verify # readiness and integrity check
374
+ ```
375
+
380
376
  - **Run checks and tests:**
381
377
 
382
378
  ```sh
@@ -392,22 +388,23 @@ docker build -t congressgov-mcp-server .
392
388
  docker run --rm -e CONGRESS_API_KEY=your-api-key -p 3010:3010 congressgov-mcp-server
393
389
  ```
394
390
 
395
- The Dockerfile defaults to HTTP transport, stateless session mode, and logs to `/var/log/congressgov-mcp-server`. OpenTelemetry peer dependencies are installed by default — build with `--build-arg OTEL_ENABLED=false` to omit them.
391
+ The Dockerfile defaults to HTTP transport, stateless session mode, and logs to `/var/log/congressgov-mcp-server`. OpenTelemetry peer dependencies are installed by default; build with `--build-arg OTEL_ENABLED=false` to omit them. The image carries the mirror scripts, so `docker exec <container> bun run mirror:init` builds the index in place.
396
392
 
397
393
  ## Project structure
398
394
 
399
395
  | Directory | Purpose |
400
396
  |:---|:---|
401
- | `src/index.ts` | `createApp()` entry point — registers tools/resources/prompts and inits services. |
397
+ | `src/index.ts` | `createApp()` entry point: registers tools, resources, and prompts, inits services, and schedules the mirror refresh. |
402
398
  | `src/config/` | Server-specific environment variable parsing and validation with Zod. |
403
- | `src/mcp-server/tools/definitions/` | Tool definitions (`*.tool.ts`) — eleven Congress.gov tools. |
404
- | `src/mcp-server/resources/definitions/` | Resource definitions (`*.resource.ts`) — congress, bill, member, and committee resources. |
405
- | `src/mcp-server/prompts/definitions/` | Prompt definitions (`*.prompt.ts`) — bill analysis and legislative research. |
406
- | `src/services/congress-api/` | Congress.gov API client — auth, pagination, rate limiting. |
407
- | `src/services/congress-documents/` | Bounded document-text fetch — host allowlist, byte ceiling, character window. |
408
- | `src/services/congress-mirror/` | Local SQLite FTS5 bill-search mirror — ingest, normalize, schema. |
399
+ | `src/mcp-server/tools/` | Tool definitions (`definitions/*.tool.ts`) plus shared input, formatting, and summary-window helpers. |
400
+ | `src/mcp-server/resources/definitions/` | Resource definitions (`*.resource.ts`). |
401
+ | `src/mcp-server/prompts/definitions/` | Prompt definitions (`*.prompt.ts`). |
402
+ | `src/services/congress-api/` | Congress.gov API client: auth, pagination, rate limiting. |
403
+ | `src/services/congress-documents/` | Bounded document-text fetch: host allowlist, byte ceiling, character window. |
404
+ | `src/services/congress-mirror/` | Local SQLite FTS5 bill-search mirror: ingest, normalize, schema. |
409
405
  | `src/services/senate-lis/` | Senate LIS XML client for Senate roll call votes. |
410
- | `scripts/` | Mirror lifecycle CLI scripts (`mirror:init` / `mirror:refresh` / `mirror:verify`). |
406
+ | `src/utils/` | HTML/XML character-reference decoding. |
407
+ | `scripts/` | Build, devcheck, and release tooling, plus the `mirror:init` / `mirror:refresh` / `mirror:verify` CLIs. |
411
408
  | `tests/` | Unit and integration tests, mirroring the `src/` structure. |
412
409
 
413
410
  ## Development guide
@@ -0,0 +1,20 @@
1
+ ---
2
+ summary: "Character references now decode in a single pass, closing three CodeQL double-escaping alerts. This release also resolves Senate roll-call vote dates and bounds summary text windows."
3
+ breaking: false
4
+ security: true
5
+ ---
6
+
7
+ # 0.7.2 — 2026-09-22
8
+
9
+ ## Fixed
10
+
11
+ - **`congressgov_roll_votes` Senate list rows** now carry a resolved `voteDateIso` beside the menu's year-less `voteDate`, derived by walking the session's vote sequence across December→January rollovers. ([#67](https://github.com/cyanheads/congressgov-mcp-server/issues/67))
12
+ - **`congressgov_bill_summaries` and `congressgov_bill_lookup` `summaries`** now bound page size and per-row summary text — a windowed row carries `textTotalCharacters`/`textTruncated`/`textNextOffset`, and `summaries` gains a `versionCode` selector. ([#70](https://github.com/cyanheads/congressgov-mcp-server/issues/70))
13
+
14
+ ## Security
15
+
16
+ - **Character references** decode in a single pass through a shared decoder (`src/utils/character-references.ts`) — replacing the two `replace()` chains in tool formatting and the one in the search mirror, and taking over the single-pass decoder document extraction already used. A reference naming an inherited object member (`&constructor;`) now stays verbatim instead of resolving to it. Closes three CodeQL `js/double-escaping` alerts. ([#73](https://github.com/cyanheads/congressgov-mcp-server/issues/73))
17
+
18
+ ## Dependencies
19
+
20
+ - `@types/node` `^26.6.1` → `^26.6.2`
@@ -0,0 +1,36 @@
1
+ ---
2
+ summary: "Framework upkeep brings stricter HTTP validation, integer-to-string input repair, and optional telemetry logging."
3
+ breaking: true
4
+ security: false
5
+ ---
6
+
7
+ # 0.7.3 — 2026-09-26
8
+
9
+ ## Changed
10
+
11
+ - **HTTP clients** inherit MCP SDK 2.1.0 through framework 0.13.9: 2026-07-28 POSTs require `MCP-Protocol-Version` (otherwise `400` / `-32020`), and batches over 100 messages receive `400` / `-32600`. Clients relying on either previously accepted form must adapt.
12
+ - **Cancellation** inherits SDK 2.1.0 handling for `requestId: 0`; stdin EOF aborts in-flight stdio requests without answering them.
13
+ - **Error envelopes** inherit framework 0.13.7 stack removal and 0.13.8 request-context removal; output-contract violations now return `InternalError` (`-32603`) instead of `ValidationError` (`-32007`).
14
+ - **Telemetry** inherits framework 0.13.7 base OTLP endpoint resolution and 0.13.8 opt-in log export (`OTEL_EXPORTER_OTLP_LOGS_ENDPOINT`) and failed-call payload logging (`LOG_TOOL_FAILURE_PAYLOADS`, capped by `LOG_TOOL_FAILURE_PAYLOAD_MAX_BYTES`). Payload redaction matches keys, not secrets embedded in free-form values.
15
+ - **Docker** preserves the release-age gate and Socket scanner during production installs, resolves optional telemetry packages within framework peer ranges, includes OTLP log peers, and removes the unused `MCP_FORCE_CONSOLE_LOGGING` setting.
16
+ - **Packaging** excludes built `.mcpb` bundles from npm and excludes `docs/idea.md` and `logs/` from MCPB bundles.
17
+ - **Development checks** reject unloadable definitions and malformed `server.json`, enforce manifest version and Docker build-platform parity, and validate release annotations before GitHub publication.
18
+ - **Documentation** clarifies existing tool inputs, summary windows, pagination, and mirror commands; updates the VS Code install link, framework guidance, and synchronized development skills.
19
+
20
+ ## Fixed
21
+
22
+ - **String identifiers** inherit framework 0.13.9 safe-integer repair: an integer `nominationNumber`, for example `677`, reaches the handler as `"677"` when that string passes the schema. Argument rejection hints retain field paths and identify key rewrites.
23
+
24
+ ## Dependencies
25
+
26
+ - `@cyanheads/mcp-ts-core` ^0.13.6 → ^0.13.9 (locked to 0.13.9).
27
+ - `@socketsecurity/bun-security-scanner` ^1.1.2 → ^1.1.3 (development).
28
+ - `ignore` ^7.0.9 → ^7.0.10 (development).
29
+ - Bun 1.4.0 → 1.4.2 (`packageManager` and Docker base images).
30
+ - Transitive `@modelcontextprotocol/server` and `@modelcontextprotocol/core` 2.0.0 → 2.1.0; unused framework client, ext-apps, and dotenv dependencies leave the lockfile.
31
+ - Transitive `@babel/parser` 7.29.8 → 7.29.9.
32
+ - Transitive `@oxc-project/types` 0.150.0 → 0.151.0.
33
+ - Transitive `rolldown` and its platform bindings 1.2.9 → 1.2.10.
34
+ - Transitive `@vue/compiler-core`, `@vue/compiler-dom`, `@vue/compiler-sfc`, `@vue/compiler-ssr`, and `@vue/shared` 3.5.42 → 3.5.43.
35
+ - Transitive `is-core-module` 2.16.2 → 2.17.0.
36
+ - Transitive `magic-string` 1.4.1 → 1.4.2.
@@ -8,8 +8,6 @@ export declare const billLookupTool: import("@cyanheads/mcp-ts-core").ToolDefini
8
8
  text: "text";
9
9
  xml: "xml";
10
10
  }>>;
11
- characterOffset: z.ZodDefault<z.ZodNumber>;
12
- characterLimit: z.ZodDefault<z.ZodNumber>;
13
11
  operation: z.ZodEnum<{
14
12
  actions: "actions";
15
13
  amendments: "amendments";
@@ -45,6 +43,9 @@ export declare const billLookupTool: import("@cyanheads/mcp-ts-core").ToolDefini
45
43
  limit: z.ZodDefault<z.ZodNumber>;
46
44
  offset: z.ZodDefault<z.ZodNumber>;
47
45
  textVersionIndex: z.ZodDefault<z.ZodNumber>;
46
+ versionCode: z.ZodOptional<z.ZodString>;
47
+ characterOffset: z.ZodDefault<z.ZodNumber>;
48
+ characterLimit: z.ZodDefault<z.ZodNumber>;
48
49
  }, z.core.$strip>, z.ZodObject<{
49
50
  data: z.ZodOptional<z.ZodArray<z.ZodObject<{}, z.core.$loose>>>;
50
51
  pagination: z.ZodOptional<z.ZodObject<{
@@ -112,8 +113,8 @@ export declare const billLookupTool: import("@cyanheads/mcp-ts-core").ToolDefini
112
113
  readonly reason: 'offset_past_end';
113
114
  readonly thrownBy: 'service';
114
115
  readonly retryable: false;
115
- readonly when: 'characterOffset is at or beyond the last character of the document, so the window would be empty.';
116
- readonly recovery: 'Restart the walk at characterOffset 0 and follow nextOffset, which goes null once the document has been read to the end.';
116
+ readonly when: "characterOffset is at or beyond the last character of every text the call would window — the document on 'content', or every returned row's summary text on 'summaries' — so the window would be empty.";
117
+ readonly recovery: "Restart the walk at characterOffset 0 and follow the response's nextOffset (or a summary row's textNextOffset), which goes null once the text has been read to the end.";
117
118
  }], {
118
119
  effectiveQuery: z.ZodString;
119
120
  totalCount: z.ZodNumber;
@@ -1 +1 @@
1
- {"version":3,"file":"bill-lookup.tool.d.ts","sourceRoot":"","sources":["../../../../src/mcp-server/tools/definitions/bill-lookup.tool.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAQ,CAAC,EAAE,MAAM,wBAAwB,CAAC;AA+CjD,eAAO,MAAM,cAAc;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAmOzB,CAAC"}
1
+ {"version":3,"file":"bill-lookup.tool.d.ts","sourceRoot":"","sources":["../../../../src/mcp-server/tools/definitions/bill-lookup.tool.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAQ,CAAC,EAAE,MAAM,wBAAwB,CAAC;AAqDjD,eAAO,MAAM,cAAc;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAoWzB,CAAC"}