installed-api
Inspects installed Node.js packages from node_modules, returning package versions, export lists, and declaration information for requested symbols.
Inspects installed Python packages using the project's interpreter, returning signatures, docstrings, class/module members, source code, defining file locations, and installed versions.
Retrieves TypeScript declarations and JSDoc for symbols from installed packages' .d.ts files, with fallback to @types packages.
.---------------------------------------.
| |
| _ _ |
| / ) ( \ |
| | | | | |
| _| | __ | |_ |
| (_ | (__) | _) |
| | | | | |
| | |_ _| | |
| \\ \__) (__/ // |
| \\ // |
| \\__ __// |
| | ''--.. ..--'' | |
| | ''--'' | |
| | || | |
| | || | |
| | || | |
| '--.. || ..--' |
| ''--.. || ..--'' |
| ''--'' |
| |
'---------------------------------------'installed-api
Stop letting your agent guess at APIs. Ask the code you actually installed.
installed-api is a Claude Code plugin (an MCP server, Python standard library only) that answers
"what's the signature of X?", "does Y take that argument?" and "which version do we have?" from the
packages installed in this project: your .venv, your node_modules. It doesn't answer from
training data or from web docs written for some other version.
Why your Claude Code install needs this
The model's memory doesn't know your lockfile. Training data is a blend of many versions of every
library, and web docs describe latest. Your project pins one specific version. That gap produces
invented keyword arguments, calls to methods that were renamed two releases ago, wrong defaults, and
then a round of run, read the traceback, fix, run again.
Looking it up the hard way burns tokens. When Claude isn't sure, it falls back to grepping
site-packages or node_modules, cat-ing whole modules or bundled .d.ts files, or fetching doc
pages. All of that text goes into your context window, and you pay for it on every turn after that.
installed-api replaces it with one call that returns only the parts that matter.
To be clear about what it doesn't do: it doesn't search or index your own working directory. It saves tokens on looking up dependencies, the code your project calls but didn't write.
Without installed-api | With installed-api |
|
|
Fetch a docs page for whatever version the site documents | The declaration from the package your project resolves |
|
|
Guess, run, read the traceback, retry | Correct the first time |
The sizes in the first row were measured on one machine. Your savings depend on the library, but the
output is always bounded: up to 80 members per inspect, 12,000 characters of source, 80-line
declaration blocks, and at most 400 .d.ts files scanned per lookup.
For humans
Code that runs against the versions you pinned, not the ones the model remembers.
Smaller context, cheaper sessions. Targeted answers instead of whole files dumped into the conversation.
Nothing to install or configure. Python 3.11+ standard library only. It finds
.venv/venv,$VIRTUAL_ENV, poetry and pdm environments,node_modulesand@types/*on its own.Private and read-only. It makes no network requests, sends nothing anywhere, and writes nothing.
Tested on Python 3.11 through 3.15 in CI on every push and PR.
For LLM agents reading this
If these tools are available to you, use them in preference to your memory for any third-party API:
Before you write a call to a library function or class, call
py_inspect(Python) ornode_types(JS/TS) on it. Use the returned signature and the installed version. Trust them over what you recall.When the user asks "which version" or you're about to suggest version-specific code, call
py_versions/node_versions.When the docstring doesn't settle how something behaves, call
py_sourceinstead of greppingsite-packagesor reading whole files.For the user's own package (
./srclayouts), passinclude_project: true.
One call usually answers the question. Results include defined_at / file paths, so you can cite
exactly where the answer came from.
Related MCP server: FastAPI Architect MCP
Tools
Tool | What it returns |
| Signature, docstring, members (for classes and modules), MRO, defining |
| The source of an installed function, class or module |
|
|
| A symbol's TypeScript declaration with its JSDoc, from |
|
|
The interpreter is chosen in this order: .venv / venv (searched upward to the repo root), then
$VIRTUAL_ENV, the poetry or pdm env, and finally python3. Python lookups import the target module in
a subprocess (python -I), so they run that package's import-time code, as using it would.
include_project: true also imports from ./src and ./.
Example (py_inspect with target: "pytest.approx", output trimmed):
{
"target": "pytest.approx",
"kind": "function",
"version": "pytest 9.1.1",
"defined_at": ".../site-packages/_pytest/python_api.py:646",
"signature": "(expected: 'Any', rel: 'float | Decimal | timedelta | None' = None, abs: 'float | Decimal | timedelta | None' = None, nan_ok: 'bool' = False) -> 'ApproxBase'",
"doc": "Assert that two numbers (or two ordered sequences of numbers) are equal to each other\nwithin some tolerance. ..."
}Supported versions
installed-api supports the Python and Node.js release lines that still receive at least security
updates; a line is dropped once it reaches end of life. As of October 2026 that is Python 3.11–3.15
and Node.js 22, 24 and 26. Node.js is never executed: node_types and node_versions read
package.json and .d.ts files from node_modules.
Install
In Claude Code:
/plugin install installed-api --marketplace ajwann/installed-apiFrom Anthropic's plugin directory, once listed: search for installed-api in /plugin directory in Claude Code, or under Customize > Plugins on claude.ai.
To try it from a clone for one session: claude --plugin-dir /path/to/installed-api.
What it runs and stores
It is Python 3.11+ standard library only, makes no network requests, and sends nothing anywhere.
Runs the project's Python interpreter (
python -I) to import and inspect the module you ask about, which runs that package's import-time code.Reads
.d.tsfiles andpackage.jsonundernode_modules. It writes nothing.
Development
python3 -m pytest -q
claude plugin validate --strict .License
MIT. See LICENSE.
Available Tools
5 toolsnode_typesA
Read TypeScript declarations of a package installed in node_modules (falls back to @types/*). With symbol: the declaration(s) of that function/class/interface/type with JSDoc and file:line. Without: the package version and its exported names.
| Name | Required | Description | Default |
|---|---|---|---|
| symbol | No | ||
| package | Yes | ||
| project_dir | No |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With no annotations, the description carries the full burden and does substantial work: it discloses the @types/* fallback and the two distinct return shapes (declarations with JSDoc and file:line vs. version plus exported names). Still missing: read-only confirmation, error behavior when a package is not installed, and any size/truncation limits.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two dense sentences, front-loaded with the core action, then branching cleanly on the optional symbol parameter. No filler text.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
There is no output schema, and the description does describe both return shapes reasonably. It falls short on project_dir and on failure modes for a 3-parameter tool, but the essentials needed to call it are present.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 0%, so the description must explain parameters. It defines the symbol parameter's effect well and implies that package refers to an installed package, but project_dir is completely unexplained and its purpose (monorepo root? alternate install dir?) is left to guesswork.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource: reading TypeScript declarations of a package installed in node_modules, with the @types fallback named. It is clearly different from py_* siblings and from node_versions, though it never names those siblings explicitly.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The with/without-symbol branches imply what each mode is for, but there is no explicit when-to-use or when-not-to-use guidance, and no routing to node_versions or py_inspect. The agent must infer the choice.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
node_versionsB
List packages installed in the nearest node_modules (name@version) whose name contains pattern.
| Name | Required | Description | Default |
|---|---|---|---|
| pattern | No | ||
| project_dir | No |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With no annotations, the description carries the full burden; it usefully discloses two behavioral facts beyond the name: the search starts at the *nearest* node_modules (upward resolution) and results are rendered as name@version. It does not say what happens when no node_modules is found, whether matching is case-sensitive or regex, or how an absent pattern behaves.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single sentence with zero waste, front-loading the verb and resource and packing output format and filter semantics in the same clause.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a two-parameter read tool with no annotations and no output schema, the description covers purpose, output format, and filter semantics reasonably. The unexplained project_dir and undefined empty-pattern/no-install behaviors leave meaningful gaps an agent would need to guess at.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 0%, so the description must compensate. It does clarify that 'pattern' is a substring match on the package name, but 'project_dir' is left completely undefined — no hint whether it is a start directory, a path to a node_modules, or an absolute vs relative path.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Clear verb ('List') plus resource ('packages installed in the nearest node_modules') and even the output shape ('name@version'). It implicitly distinguishes itself from the py_* siblings by naming node_modules, though it never explicitly contrasts with py_versions or node_types.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
No statement of when to use this versus py_versions/node_types, and no prerequisites or exclusions. The only usable signal is the implicit ecosystem cue from 'node_modules', leaving the agent to infer the rest.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
py_inspectA
Inspect a Python object as installed in the project's own interpreter: signature, docstring, members (for modules/classes), defining file:line and the installed distribution version. target is a dotted path such as 'requests.Session.request' or 'pandas.DataFrame.merge'.
| Name | Required | Description | Default |
|---|---|---|---|
| target | Yes | ||
| max_members | No | ||
| project_dir | No | ||
| include_project | No | also import from the project's ./src and ./ |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With no annotations, the description carries the full burden. It usefully discloses that inspection happens in the project's live interpreter and reports the defining file:line and installed distribution version, but it says nothing about import side effects, failure behavior for unresolvable targets, or the effect of max_members truncation on results.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two tight sentences, zero filler, with the scope constraint and return contents front-loaded and the parameter format example trailing as supporting detail.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
No output schema exists, and the description does the required work by enumerating the returned fields (signature, docstring, members, file:line, distribution version). It falls short only on error/truncation behavior for a 4-parameter introspection tool.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is only 25% (only include_project is documented), so the description must compensate. It does add real value for `target` by giving dotted-path examples like 'requests.Session.request' and 'pandas.DataFrame.merge', but `max_members` (default 80, truncation semantics) and `project_dir` are left undocumented in both places.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Specific verb (inspect) plus a precise scope: 'a Python object as installed in the project's own interpreter', with an explicit enumeration of what is retrieved (signature, docstring, members, file:line, distribution version). That enumeration implicitly separates it from py_source (source bodies) and py_versions (version listing), but no sibling is named explicitly.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The phrase 'as installed in the project's own interpreter' implies when to use it (runtime introspection of the actually-installed package rather than other environments or source files), but the description never states when not to use it or names py_source/py_versions as the alternative for source-reading or version-listing tasks.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
py_sourceC
Return the source code of an installed Python function/class/module (truncated to max_chars).
| Name | Required | Description | Default |
|---|---|---|---|
| target | Yes | ||
| max_chars | No | ||
| project_dir | No | ||
| include_project | No |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With no annotations, the description carries the full burden. It mentions truncation (max_chars) and that the target must be installed, but omits whether the operation is read-only (implied), what happens if the target is not found, and other behavioral traits like error handling or return format.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is a single, front-loaded sentence with zero waste. It starts with the core action and includes the truncation note without unnecessary detail.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Given no annotations, no output schema, and zero schema description coverage for four parameters, the description is far too sparse. It lacks usage guidance and fails to explain two of the four parameters, leaving significant gaps for an agent to invoke it correctly.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 0%, so the description must compensate. It only explains max_chars via '(truncated to max_chars)' and indirectly describes 'target' as an installed Python function/class/module, but leaves project_dir and include_project completely unexplained.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a specific verb (Return) and resource (source code) with a clear scope (installed Python function/class/module). It does not explicitly differentiate from siblings like py_inspect, but an agent can infer the distinction without opening schemas.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
There is no guidance on when to use this tool versus alternatives such as py_inspect or py_versions. The description only states what it does, leaving the agent to infer usage context.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
py_versionsA
List installed Python distributions (name==version) in the project's interpreter whose name contains pattern (empty pattern lists all).
| Name | Required | Description | Default |
|---|---|---|---|
| pattern | No | ||
| project_dir | No |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
No annotations are supplied, so the description carries the full burden. It discloses the important behavioral scope (reads the project's interpreter, not the ambient environment) and the "name==version" output form, but says nothing about failure modes (missing interpreter), cost, or whether output is ordered/filtered further.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single dense sentence: verb first, parenthetical output format, then the parameter caveat. Nothing wasted and no postamble.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a 2-param read-only listing tool with no output schema, the description covers the core behavior adequately, but leaves one of two parameters (project_dir) and the return shape (list of strings? structure?) undocumented.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 0%, so the description must compensate: it fully specifies `pattern` (substring match, empty means all). `project_dir` is only obliquely implied by "the project's interpreter" — its purpose, default, and accepted format are never stated.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Specific verb ("List") plus a precise resource ("installed Python distributions") and scope ("in the project's interpreter"). The Python-specific framing clearly separates it from node_versions/node_types siblings, though no sibling is named explicitly.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
"empty pattern lists all" is useful call-time guidance for the optional pattern, but there is no when-to-use/when-not guidance and no reference to the sibling tools (py_inspect, py_source, node_versions) that an agent could confuse it with.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
Tool Schema Changelog
Recent tool additions, removals, and schema changes observed during successful MCP inspections.
5 tool updates
v0.1.0- First observed
node_types - First observed
node_versions - First observed
py_inspect - First observed
py_source - First observed
py_versions
TDQS
Scored across 5 tools
Each tool targets a distinct resource+action: metadata inspection (py_inspect), raw source (py_source), and version listing (py_versions) for Python; declarations (node_types) and version listing (node_versions) for Node. The py_/node_ split makes cross-language selection unambiguous, and the inspect-vs-source boundary is clear from the descriptions.
All five tools follow a strict <lang>_<noun/verb> pattern (py_inspect, py_source, py_versions, node_types, node_versions). Prefixes group by ecosystem and suffixes consistently denote the operation, making the set highly predictable.
Five tools is well-scoped for a dual-ecosystem introspection server: three for Python, two for Node, each earning its place with no redundant members. Nothing feels padded or thin for the stated purpose.
The Python side has both metadata inspection and source retrieval, but the Node side only offers type declarations and versions — there is no equivalent of py_source for reading installed JS implementation code. This asymmetry leaves a notable gap for agents debugging Node packages, though version and type coverage is solid.
Maintenance
Related MCP Connectors
The official Model Context Protocol server for Ambee. It gives any MCP-compatible AI assistant — Claude, ChatGPT, Cursor, VS Code, Ollama, and more direct access to live air quality, pollen, and weather data. To get started, including information on signing up and obtaining your Ambee key, check out the Ambee documentation on https://docs.ambeedata.com
Model Context Protocol server for the Apideck Unified API. Connect any MCP-compatible agent framework to 100+ accounting systems, HRIS platforms, file storage providers, and more through one integration. More information https://www.apideck.com/mcp-server
Nifra docs, runnable examples, and API types as an MCP server for any AI assistant.
Zotero MCP server for Claude and ChatGPT: search, citations, safe writes, PDF passages and pages.
Related MCP Servers
- AlicenseNot gradedqualityDmaintenanceAn MCP server that publishes CLI tools on your machine for discoverability by LLMs5 npm1MIT
- AlicenseAqualityAmaintenanceAn MCP server that gives Claude Code IDE-level intelligence for FastAPI projects — semantic code navigation, safe renaming, route inspection, dependency trees, and Pydantic model analysis. Instead of Claude reading files blindly, it calls structured tools backed by Jedi (Python language server) and Python's AST.191MIT
- AlicenseBqualityDmaintenanceMCP server for accessing Claude Code plugins. Enables retrieving plugin lists and detailed information via MCP clients like Claude Desktop, Cursor.229 PyPIMIT
- AlicenseNot gradedqualityDmaintenanceA dead simple MCP server for exposing your app functions to AI agents like Claude Desktop.5 npm6MIT