API Reference¶
Auto-generated reference documentation for all public API2MCP classes and functions.
Core¶
api2mcp.core.ir_schema¶
api2mcp.core.ir_schema
¶
Intermediate Representation (IR) schema for API2MCP.
The IR is the central data structure bridging ALL parsers to ALL generators. Every parser outputs IR; every generator consumes IR. Changes to the IR schema affect the entire pipeline.
Design decisions: - GraphQL queries/mutations map to Endpoint with method="QUERY"/"MUTATION" - GraphQL fragments resolved during parsing, not stored in IR - Postman variables substituted during parsing, not stored in IR - Pagination patterns detected and stored for smart tool generation
Classes¶
APISpec
dataclass
¶
Top-level Intermediate Representation for a parsed API.
This is the output of every parser and input to every generator.
Source code in src/api2mcp/core/ir_schema.py
Endpoint
dataclass
¶
Single API operation.
Source code in src/api2mcp/core/ir_schema.py
Parameter
dataclass
¶
API parameter with location and schema.
Source code in src/api2mcp/core/ir_schema.py
RequestBody
dataclass
¶
Response
dataclass
¶
SchemaRef
dataclass
¶
Unified JSON Schema type reference.
Maps to JSON Schema for MCP tool input_schema generation.
Source code in src/api2mcp/core/ir_schema.py
71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 | |
Functions¶
to_json_schema()
¶
Convert to standard JSON Schema dict.
Source code in src/api2mcp/core/ir_schema.py
AuthScheme
dataclass
¶
Authentication scheme definition.
Source code in src/api2mcp/core/ir_schema.py
HttpMethod
¶
Bases: str, Enum
HTTP methods + GraphQL virtual methods.
Source code in src/api2mcp/core/ir_schema.py
ParameterLocation
¶
Bases: str, Enum
Where in the request a parameter is sent.
Source code in src/api2mcp/core/ir_schema.py
Parsers¶
api2mcp.parsers.openapi¶
api2mcp.parsers.openapi.OpenAPIParser
¶
Bases: BaseParser
Parser for OpenAPI 3.0.x and 3.1.x specifications.
Source code in src/api2mcp/parsers/openapi.py
505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 720 721 722 723 724 725 726 727 728 729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 748 749 750 751 752 753 754 755 756 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 823 824 825 826 827 828 829 830 831 832 833 834 835 836 837 838 839 840 841 842 843 844 845 846 847 848 849 850 851 852 853 854 855 856 857 858 859 860 861 862 863 864 865 866 867 868 869 870 871 872 873 874 875 876 877 878 879 880 881 882 883 884 885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 900 901 902 903 904 905 906 907 908 909 910 911 912 913 914 915 916 917 918 919 920 921 922 923 924 925 926 927 928 929 930 931 932 933 934 935 936 937 938 939 940 941 942 943 944 945 946 947 948 949 | |
Functions¶
detect(content)
¶
Return True if content looks like an OpenAPI 3.x document.
validate(source, **kwargs)
async
¶
Validate an OpenAPI spec without producing full IR.
Source code in src/api2mcp/parsers/openapi.py
parse(source, **kwargs)
async
¶
Parse an OpenAPI 3.0/3.1 spec into an IR APISpec.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
source
|
str | Path
|
Path to the spec file, or a URL. |
required |
**kwargs
|
Any
|
Options: - resolve_external_refs (bool): Whether to resolve external $refs. Defaults to True. |
{}
|
Returns:
| Type | Description |
|---|---|
APISpec
|
Parsed APISpec. |
Raises:
| Type | Description |
|---|---|
ParseException
|
On invalid input. |
ValidationException
|
On structural validation failure. |
Source code in src/api2mcp/parsers/openapi.py
535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 | |
api2mcp.parsers.graphql¶
api2mcp.parsers.graphql.GraphQLParser
¶
Bases: BaseParser
Parser for GraphQL schemas (SDL and introspection JSON).
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
graphql_endpoint
|
str
|
The HTTP path of the GraphQL endpoint that will be
stored in the IR. Defaults to |
'/graphql'
|
Example::
parser = GraphQLParser()
spec = await parser.parse("schema.graphql")
# or
spec = await parser.parse("introspection.json")
Source code in src/api2mcp/parsers/graphql.py
770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 823 824 825 826 827 828 829 830 831 832 833 834 835 836 837 838 839 840 841 842 843 844 845 846 847 848 849 850 851 852 853 854 855 856 857 858 859 860 861 862 863 864 865 866 867 868 869 870 871 872 873 874 875 876 877 878 879 880 881 882 883 884 885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 900 901 902 903 904 905 906 907 908 909 910 911 912 913 914 915 916 | |
Functions¶
detect(content)
¶
Return True if content looks like a GraphQL introspection result.
Source code in src/api2mcp/parsers/graphql.py
validate(source, **_kwargs)
async
¶
Validate a GraphQL schema without producing full IR.
Source code in src/api2mcp/parsers/graphql.py
parse(source, **kwargs)
async
¶
Parse a GraphQL schema into an IR :class:APISpec.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
source
|
str | Path
|
File path, URL, or raw SDL/JSON string. |
required |
**kwargs
|
Any
|
Optional:
|
{}
|
Returns:
| Name | Type | Description |
|---|---|---|
Parsed |
APISpec
|
class: |
Raises:
| Type | Description |
|---|---|
|
class: |
|
|
class: |
Source code in src/api2mcp/parsers/graphql.py
api2mcp.parsers.postman¶
api2mcp.parsers.postman.PostmanParser
¶
Bases: BaseParser
Parse Postman Collection v2.1 files into an :class:APISpec.
Supports:
- Collection v2.1 (and v2.0 with a best-effort mapping)
- Variable substitution ({{varName}})
- Folder hierarchy → endpoint tags
- Collection / folder / request-level auth
Source code in src/api2mcp/parsers/postman.py
574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 720 721 722 723 724 725 726 727 728 729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 748 749 750 751 752 753 754 755 756 757 758 759 760 761 762 763 | |
Functions¶
detect(content)
¶
Return True if content looks like a Postman Collection.
Source code in src/api2mcp/parsers/postman.py
validate(source, **_kwargs)
async
¶
Validate a Postman Collection document.
Returns a list of :class:ParseError; empty means valid.
Source code in src/api2mcp/parsers/postman.py
parse(source, *, title=None, **_kwargs)
async
¶
Parse a Postman Collection and return an :class:APISpec.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
source
|
str | Path
|
File path or raw JSON string. |
required |
title
|
str | None
|
Override the collection name as the API title. |
None
|
Returns:
| Name | Type | Description |
|---|---|---|
Parsed |
APISpec
|
class: |
Raises:
| Type | Description |
|---|---|
ParseException
|
If the document cannot be parsed or is not a Postman Collection. |
Source code in src/api2mcp/parsers/postman.py
629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 | |
Generators¶
api2mcp.generators.tool¶
api2mcp.generators.tool
¶
MCP Tool Generator — IR to MCP tool definitions (TASK-016, TASK-017).
Consumes IR (APISpec) and produces MCP-compliant tool definitions. Supports: - JSON Schema input_schema generation - Jinja2 template-based server code generation - Edge cases: no parameters, file uploads, multipart, empty responses
Classes¶
ToolGenerator
¶
Generates MCP tool definitions and server code from IR.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
max_depth
|
int
|
Maximum nesting depth for schema simplification. |
5
|
template_dir
|
Path | None
|
Override the Jinja2 template directory. |
None
|
Source code in src/api2mcp/generators/tool.py
59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 | |
Attributes¶
jinja_env
property
¶
Lazily create Jinja2 environment.
Functions¶
generate(api_spec)
¶
Generate MCP tool definitions from an IR APISpec.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
api_spec
|
APISpec
|
Parsed API specification (IR). |
required |
Returns:
| Type | Description |
|---|---|
list[MCPToolDef]
|
List of MCPToolDef objects, one per endpoint. |
Raises:
| Type | Description |
|---|---|
GeneratorException
|
If generation fails for any endpoint. |
Source code in src/api2mcp/generators/tool.py
generate_server_code(api_spec, output_dir, server_name=None)
¶
Generate Python MCP server code from IR using Jinja2 templates.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
api_spec
|
APISpec
|
Parsed API specification. |
required |
output_dir
|
Path
|
Directory to write generated files. |
required |
server_name
|
str | None
|
Override the server name (defaults to sanitized API title). |
None
|
Returns:
| Type | Description |
|---|---|
list[Path]
|
List of generated file paths. |
Source code in src/api2mcp/generators/tool.py
MCPToolDef
dataclass
¶
A generated MCP tool definition.
Represents a single tool in the MCP tools/list response.
Source code in src/api2mcp/generators/tool.py
Testing¶
api2mcp.testing¶
api2mcp.testing
¶
API2MCP Testing Framework — F6.3.
Built-in testing utilities for generated MCP servers:
- :class:
MCPTestClient— in-process tool execution testing - :class:
MockResponseGenerator— mock API responses from spec - :class:
MockScenario— single mock scenario definition - :class:
SnapshotStore— snapshot testing for generated output - :class:
CoverageReporter— tool execution coverage tracking - :class:
CoverageReport— coverage report snapshot - :class:
ToolResult— result of a tool call
Classes¶
MCPTestClient
¶
In-process MCP test client backed by mock API responses.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
server_dir
|
str | Path
|
Directory containing |
'.'
|
scenario
|
str
|
Default mock scenario name to use ( |
'success'
|
seed
|
int | None
|
Random seed forwarded to :class: |
None
|
The client tracks which tools are called; use :attr:call_log for
assertions and integrate with :class:~api2mcp.testing.coverage.CoverageReporter.
Source code in src/api2mcp/testing/client.py
60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 | |
Attributes¶
call_log
property
¶
All :class:ToolResult objects produced since the client was created.
api_spec
property
¶
The loaded :class:~api2mcp.core.ir_schema.APISpec.
tools
property
¶
All generated :class:~api2mcp.generators.tool.MCPToolDef objects.
Functions¶
list_tools()
async
¶
Return all MCP tool definitions (name + description + inputSchema).
Returns:
| Type | Description |
|---|---|
list[dict[str, Any]]
|
List of dicts in MCP |
Source code in src/api2mcp/testing/client.py
call_tool(tool_name, arguments=None, *, scenario=None)
async
¶
Execute a tool against a mock API response.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
tool_name
|
str
|
Name of the MCP tool to call. |
required |
arguments
|
dict[str, Any] | None
|
Input arguments (validated against the tool's schema). |
None
|
scenario
|
str | None
|
Override the default mock scenario for this call. |
None
|
Returns:
| Type | Description |
|---|---|
ToolResult
|
class: |
Raises:
| Type | Description |
|---|---|
KeyError
|
If tool_name is not found in the loaded tools. |
ValueError
|
If required arguments are missing. |
Source code in src/api2mcp/testing/client.py
called_tool_names()
¶
ToolResult
dataclass
¶
Result of a :meth:MCPTestClient.call_tool invocation.
Attributes:
| Name | Type | Description |
|---|---|---|
tool_name |
str
|
Name of the called tool. |
status |
str
|
|
content |
dict[str, Any] | list[Any]
|
Parsed response body (dict or list). |
status_code |
int
|
HTTP status code from the mock scenario. |
scenario |
MockScenario
|
The :class: |
Source code in src/api2mcp/testing/client.py
CoverageReporter
¶
Tracks and reports tool execution coverage.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
tools
|
list[MCPToolDef]
|
List of :class: |
required |
Source code in src/api2mcp/testing/coverage.py
Functions¶
record_call(tool_name)
¶
Record a single call to tool_name.
Unknown tool names are silently ignored so the reporter can be used with partial tool sets.
Source code in src/api2mcp/testing/coverage.py
record_results(results)
¶
Bulk-record calls from a :attr:~api2mcp.testing.client.MCPTestClient.call_log.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
results
|
list[ToolResult]
|
List of :class: |
required |
Source code in src/api2mcp/testing/coverage.py
reset()
¶
report()
¶
Build and return a :class:CoverageReport.
Returns:
| Type | Description |
|---|---|
CoverageReport
|
Snapshot of coverage at the time of the call. |
Source code in src/api2mcp/testing/coverage.py
from_client(client)
classmethod
¶
Create a reporter pre-populated from a :class:~api2mcp.testing.client.MCPTestClient.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
client
|
Any
|
A loaded :class: |
required |
Returns:
| Type | Description |
|---|---|
CoverageReporter
|
class: |
Source code in src/api2mcp/testing/coverage.py
CoverageReport
dataclass
¶
Immutable snapshot of coverage at a point in time.
Attributes:
| Name | Type | Description |
|---|---|---|
total_tools |
int
|
Total number of tools in the server. |
called_tools |
set[str]
|
Set of tool names that were called at least once. |
uncalled_tools |
set[str]
|
Tools not yet covered. |
call_counts |
dict[str, int]
|
How many times each tool was called. |
percentage |
float
|
Coverage percentage (0–100). |
Source code in src/api2mcp/testing/coverage.py
Functions¶
summary()
¶
to_dict()
¶
Serialise to a plain dict (suitable for JSON output).
Source code in src/api2mcp/testing/coverage.py
assert_minimum(minimum)
¶
Assert that coverage meets a minimum threshold.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
minimum
|
float
|
Minimum required percentage (0–100). |
required |
Raises:
| Type | Description |
|---|---|
AssertionError
|
If coverage is below minimum. |
Source code in src/api2mcp/testing/coverage.py
SnapshotStore
¶
Manages snapshot files for generated MCP server output.
Each snapshot is stored as a <name>.json file inside snapshot_dir.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
snapshot_dir
|
str | Path
|
Directory to read/write snapshot files. Created automatically if it does not exist. |
'tests/snapshots/data'
|
update
|
bool
|
When |
False
|
Source code in src/api2mcp/testing/snapshot.py
112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 | |
Functions¶
assert_match(name, tools, *, update=None)
¶
Assert that tools matches the stored snapshot named name.
If no snapshot exists yet (first run), it is created automatically and the assertion passes.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
name
|
str
|
Snapshot identifier (used as filename stem). |
required |
tools
|
list[MCPToolDef]
|
Tool definitions to snapshot. |
required |
update
|
bool | None
|
Override :attr: |
None
|
Raises:
| Type | Description |
|---|---|
|
class: |
Source code in src/api2mcp/testing/snapshot.py
save(name, tools)
¶
Unconditionally overwrite the snapshot for name.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
name
|
str
|
Snapshot identifier. |
required |
tools
|
list[MCPToolDef]
|
Tool definitions to snapshot. |
required |
Source code in src/api2mcp/testing/snapshot.py
load(name)
¶
Load and return the stored snapshot dict for name.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
name
|
str
|
Snapshot identifier. |
required |
Returns:
| Type | Description |
|---|---|
dict[str, Any]
|
Parsed snapshot dict. |
Raises:
| Type | Description |
|---|---|
FileNotFoundError
|
If the snapshot does not exist. |
Source code in src/api2mcp/testing/snapshot.py
exists(name)
¶
delete(name)
¶
list_snapshots()
¶
Return the names of all snapshots stored in :attr:snapshot_dir.
MockResponseGenerator
¶
Generate mock responses from an :class:~api2mcp.core.ir_schema.APISpec.
Given an API spec, this class produces per-endpoint mock scenarios that
can be used by :class:~api2mcp.testing.client.MCPTestClient to simulate
API responses without making real HTTP calls.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
api_spec
|
APISpec
|
The parsed API specification. |
required |
seed
|
int | None
|
Optional random seed for deterministic generation. |
None
|
Usage::
generator = MockResponseGenerator(api_spec)
scenarios = generator.scenarios_for("list_issues")
# → [MockScenario("success", 200, ...), MockScenario("not_found", 404, ...)]
Source code in src/api2mcp/testing/mock_generator.py
57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 | |
Functions¶
scenarios_for(tool_name)
¶
Return mock scenarios for the endpoint matching tool_name.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
tool_name
|
str
|
The MCP tool name (e.g. |
required |
Returns:
| Type | Description |
|---|---|
list[MockScenario]
|
List of :class: |
Raises:
| Type | Description |
|---|---|
KeyError
|
If no endpoint matches tool_name. |
Source code in src/api2mcp/testing/mock_generator.py
all_scenarios()
¶
Return scenarios for every endpoint in the spec.
Returns:
| Type | Description |
|---|---|
dict[str, list[MockScenario]]
|
Mapping of tool name → list of :class: |
Source code in src/api2mcp/testing/mock_generator.py
success_body(tool_name)
¶
Return just the success scenario body for tool_name.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
tool_name
|
str
|
MCP tool name. |
required |
Returns:
| Type | Description |
|---|---|
dict[str, Any] | list[Any]
|
Mock response body. |
Source code in src/api2mcp/testing/mock_generator.py
MockScenario
¶
Defines how to generate a mock response.
Attributes:
| Name | Type | Description |
|---|---|---|
name |
Human-readable scenario name. |
|
status_code |
HTTP status code to return. |
|
body |
Response body dict (or None for empty body). |
|
headers |
Extra response headers. |
Source code in src/api2mcp/testing/mock_generator.py
Plugins¶
api2mcp.plugins¶
api2mcp.plugins
¶
Plugin system for API2MCP (F7.2).
Exports the public API for plugin authors and host code.
Classes¶
BasePlugin
¶
Abstract base class for all API2MCP plugins.
Subclass this and define the class-level attributes below. The
framework will instantiate your class and call :meth:setup/:meth:teardown.
Class attributes¶
id : str
Unique slug identifier. Required.
name : str
Human-readable name. Required.
version : str
Semver version string (default "0.1.0").
description : str
One-line description.
author : str
Author name.
requires : list[str]
IDs of plugins that must be loaded before this one.
Source code in src/api2mcp/plugins/base.py
Functions¶
setup(hook_manager)
¶
Called when the plugin is loaded.
Override to register hooks and perform initialisation.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
hook_manager
|
HookManager
|
The application :class: |
required |
Source code in src/api2mcp/plugins/base.py
teardown()
¶
metadata()
classmethod
¶
Return :class:PluginMetadata derived from class attributes.
Source code in src/api2mcp/plugins/base.py
HookManager
¶
Manages plugin hooks throughout the API2MCP pipeline.
Thread-safety note: registration is not thread-safe; register all hooks before starting concurrent work.
Source code in src/api2mcp/plugins/hooks.py
97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 | |
Functions¶
register_hook(event, callback, *, plugin_id='', priority=100)
¶
Register callback to fire when event is emitted.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
event
|
str
|
Hook event name (see :data: |
required |
callback
|
Callable[..., Any]
|
Any callable (sync or async). |
required |
plugin_id
|
str
|
Identifier of the owning plugin. |
''
|
priority
|
int
|
Execution order — lower numbers run first. |
100
|
Returns:
| Name | Type | Description |
|---|---|---|
The |
HookRegistration
|
class: |
Source code in src/api2mcp/plugins/hooks.py
unregister_hook(registration)
¶
Remove a previously registered hook.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
registration
|
HookRegistration
|
The :class: |
required |
Returns:
| Type | Description |
|---|---|
bool
|
|
Source code in src/api2mcp/plugins/hooks.py
emit(event, **kwargs)
async
¶
Emit event, invoking all registered callbacks in priority order.
Async callbacks are awaited; sync callbacks are called directly. Exceptions in individual callbacks are logged but do NOT abort the remaining callbacks.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
event
|
str
|
Hook event name. |
required |
**kwargs
|
Any
|
Keyword arguments forwarded to every callback. |
{}
|
Returns:
| Type | Description |
|---|---|
list[Any]
|
List of return values from each callback ( |
Source code in src/api2mcp/plugins/hooks.py
emit_sync(event, **kwargs)
¶
Synchronous wrapper around :meth:emit for non-async contexts.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
event
|
str
|
Hook event name. |
required |
**kwargs
|
Any
|
Keyword arguments forwarded to every callback. |
{}
|
Returns:
| Type | Description |
|---|---|
list[Any]
|
List of return values from each callback. |
Source code in src/api2mcp/plugins/hooks.py
registered_hooks(event=None)
¶
Return all registrations, optionally filtered by event.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
event
|
str | None
|
If given, return only registrations for this event. |
None
|
Returns:
| Type | Description |
|---|---|
list[HookRegistration]
|
List of :class: |
Source code in src/api2mcp/plugins/hooks.py
clear(event=None)
¶
Remove all registrations, or only those for event.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
event
|
str | None
|
If given, clear only this event's registrations. |
None
|
Source code in src/api2mcp/plugins/hooks.py
PluginManager
¶
Orchestrates the full plugin lifecycle.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
plugin_dir
|
Path | None
|
Local directory for directory-based discovery. |
None
|
sandbox
|
PluginSandbox | None
|
:class: |
None
|
loader
|
PluginLoader | None
|
Custom :class: |
None
|
Source code in src/api2mcp/plugins/manager.py
27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 | |
Attributes¶
hooks
property
¶
The shared :class:~api2mcp.plugins.hooks.HookManager.
loaded_plugins
property
¶
List of currently loaded :class:~api2mcp.plugins.base.BasePlugin instances.
Functions¶
load_plugins(plugins)
¶
Load plugins in dependency-resolved order.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
plugins
|
list[BasePlugin]
|
Pre-discovered plugin instances to load. |
required |
Raises:
| Type | Description |
|---|---|
|
class: |
Source code in src/api2mcp/plugins/manager.py
load_all(directory=None)
¶
Discover and load all plugins (entry points + directory).
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
directory
|
Path | None
|
Override local plugin directory for this call. |
None
|
Source code in src/api2mcp/plugins/manager.py
unload_all()
¶
Call :meth:~api2mcp.plugins.base.BasePlugin.teardown on all plugins
and clear the hooks.
Source code in src/api2mcp/plugins/manager.py
get_plugin(plugin_id)
¶
Return the loaded plugin with plugin_id, or None.
PluginLoader
¶
Discovers and instantiates :class:~api2mcp.plugins.base.BasePlugin subclasses.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
plugin_dir
|
Path | None
|
Local directory to scan for |
None
|
Source code in src/api2mcp/plugins/discovery.py
44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 | |
Functions¶
discover_entry_points()
¶
Load plugins registered via the api2mcp.plugins entry-point group.
Returns:
| Type | Description |
|---|---|
list[BasePlugin]
|
List of instantiated :class: |
Source code in src/api2mcp/plugins/discovery.py
discover_directory(directory=None)
¶
Scan directory for .py files and load plugin classes.
Each .py file is imported as a module. All
:class:~api2mcp.plugins.base.BasePlugin subclasses with a non-empty
id attribute are instantiated.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
directory
|
Path | None
|
Directory to scan. Defaults to :attr: |
None
|
Returns:
| Type | Description |
|---|---|
list[BasePlugin]
|
List of instantiated :class: |
Source code in src/api2mcp/plugins/discovery.py
discover_all(directory=None)
¶
Combine entry-point and directory discovery.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
directory
|
Path | None
|
Override local plugin directory. |
None
|
Returns:
| Type | Description |
|---|---|
list[BasePlugin]
|
Deduplicated list of :class: |
Source code in src/api2mcp/plugins/discovery.py
PluginSandbox
¶
Runs plugin callbacks with timeout enforcement and exception isolation.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
timeout
|
float | None
|
Maximum seconds a single callback may run. |
10.0
|
reraise
|
bool
|
If |
False
|
Source code in src/api2mcp/plugins/sandbox.py
Functions¶
call(callback, **kwargs)
async
¶
Invoke callback safely with optional timeout.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
callback
|
Callable[..., Any]
|
Sync or async callable. |
required |
**kwargs
|
Any
|
Forwarded to callback. |
{}
|
Returns:
| Type | Description |
|---|---|
Any
|
The return value of callback, or |
Raises:
| Type | Description |
|---|---|
Exception
|
Only if :attr: |
Source code in src/api2mcp/plugins/sandbox.py
Templates¶
api2mcp.templates¶
api2mcp.templates
¶
Template registry and installer for F7.1.
Classes¶
TemplateManifest
dataclass
¶
Parsed contents of a template.yaml file.
Attributes:
| Name | Type | Description |
|---|---|---|
id |
str
|
Unique slug identifier (e.g. |
name |
str
|
Human-readable template name. |
description |
str
|
Short description of what the template does. |
author |
str
|
Author handle or organisation name. |
version |
str
|
Current version string (semver recommended). |
tags |
list[str]
|
Searchable keyword tags. |
spec_file |
str
|
Relative path to the OpenAPI/Swagger spec inside the template repo. |
repository |
str
|
URL of the template's git repository. |
versions |
list[VersionEntry]
|
Ordered list of :class: |
rating |
float
|
Average user rating (0.0–5.0). |
downloads |
int
|
Total install count. |
reviews |
list[ReviewEntry]
|
List of :class: |
Source code in src/api2mcp/templates/manifest.py
93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 | |
Functions¶
from_dict(data)
classmethod
¶
Build a :class:TemplateManifest from a raw parsed dict.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
data
|
dict[str, Any]
|
Dict loaded from |
required |
Returns:
| Type | Description |
|---|---|
TemplateManifest
|
A populated :class: |
Raises:
| Type | Description |
|---|---|
ValueError
|
If required fields ( |
Source code in src/api2mcp/templates/manifest.py
from_yaml(text)
classmethod
¶
Parse a template.yaml string.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
text
|
str
|
Raw YAML content. |
required |
Returns:
| Type | Description |
|---|---|
TemplateManifest
|
class: |
Raises:
| Type | Description |
|---|---|
ValueError
|
If the YAML is invalid or required fields are missing. |
Source code in src/api2mcp/templates/manifest.py
to_dict()
¶
Serialise to a plain dict (round-trippable via :meth:from_dict).
Source code in src/api2mcp/templates/manifest.py
latest_version_tag()
¶
resolve_version(requested)
¶
Resolve a requested version string to a git tag.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
requested
|
str | None
|
Version tag (e.g. |
required |
Returns:
| Type | Description |
|---|---|
str
|
The resolved git tag string. |
Raises:
| Type | Description |
|---|---|
ValueError
|
If requested does not match any known version. |
Source code in src/api2mcp/templates/manifest.py
matches_query(query)
¶
Return True if query appears in the id, name, description, or tags.
Source code in src/api2mcp/templates/manifest.py
TemplateRegistry
¶
Client for the remote template registry.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
index_url
|
str
|
URL of the remote |
_DEFAULT_INDEX_URL
|
cache_dir
|
Path | None
|
Local directory for caching the index and downloaded manifests. |
None
|
http_client
|
Any | None
|
Optional pre-built :class: |
None
|
Source code in src/api2mcp/templates/registry.py
101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 | |
Attributes¶
index
property
¶
The currently loaded :class:RegistryIndex, or None.
Functions¶
refresh(*, force=False)
async
¶
Fetch (or re-fetch) the registry index.
Uses local disk cache if the cached file is still fresh,
unless force is True.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
force
|
bool
|
Bypass cache and always fetch from remote. |
False
|
Returns:
| Type | Description |
|---|---|
RegistryIndex
|
The loaded :class: |
Source code in src/api2mcp/templates/registry.py
search(query='')
¶
Filter templates by query (case-insensitive substring match).
Searches template id, name, description, and tags.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
query
|
str
|
Search string. Empty string returns all templates. |
''
|
Returns:
| Type | Description |
|---|---|
list[TemplateManifest]
|
List of matching :class: |
Raises:
| Type | Description |
|---|---|
RuntimeError
|
If :meth: |
Source code in src/api2mcp/templates/registry.py
get(template_id)
¶
Look up a template by exact id.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
template_id
|
str
|
Exact template slug. |
required |
Returns:
| Type | Description |
|---|---|
TemplateManifest | None
|
class: |
Source code in src/api2mcp/templates/registry.py
fetch_manifest(template_id)
async
¶
Fetch the full template.yaml manifest from the template's repository.
The summary entry in the registry index only contains subset metadata. This method fetches the full manifest from the template's own repo.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
template_id
|
str
|
Exact template slug. |
required |
Returns:
| Name | Type | Description |
|---|---|---|
Full |
TemplateManifest
|
class: |
Raises:
| Type | Description |
|---|---|
KeyError
|
If template_id is not in the registry. |
ValueError
|
If the remote manifest YAML is malformed. |
Source code in src/api2mcp/templates/registry.py
TemplateInstaller
¶
Downloads and installs MCP server templates.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
registry
|
TemplateRegistry | None
|
:class: |
None
|
git_runner
|
Any | None
|
Callable |
None
|
Source code in src/api2mcp/templates/installer.py
57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 | |
Functions¶
install(template_id, *, dest, version=None)
async
¶
Install a template into dest.
Fetches the full manifest, resolves the version, clones the
repository at the requested tag into dest, and writes a
installed.yaml receipt.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
template_id
|
str
|
Template slug from the registry. |
required |
dest
|
Path
|
Directory to install into (created if missing). |
required |
version
|
str | None
|
Git tag to install. |
None
|
Returns:
| Type | Description |
|---|---|
InstalledTemplate
|
class: |
Raises:
| Type | Description |
|---|---|
KeyError
|
If template_id is not in the registry. |
ValueError
|
If version is unknown. |
RuntimeError
|
If git clone fails. |
Source code in src/api2mcp/templates/installer.py
update(template_id, *, dest, version=None)
async
¶
Update an existing installation to a newer version.
Equivalent to a fresh install that overwrites dest.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
template_id
|
str
|
Template slug. |
required |
dest
|
Path
|
Directory of the existing installation. |
required |
version
|
str | None
|
Target version tag. |
None
|
Returns:
| Type | Description |
|---|---|
InstalledTemplate
|
class: |
Source code in src/api2mcp/templates/installer.py
read_receipt(dest)
staticmethod
¶
Read the installed.yaml receipt from dest.
Returns:
| Type | Description |
|---|---|
dict[str, str] | None
|
Dict with |
dict[str, str] | None
|
if no receipt exists. |
Source code in src/api2mcp/templates/installer.py
Orchestration¶
api2mcp.orchestration.adapters¶
api2mcp.orchestration.adapters.base.MCPToolAdapter
¶
Adapts an MCP tool to LangChain's StructuredTool interface.
Do not instantiate directly — use :meth:from_mcp_tool instead.
The adapter tracks per-tool latency metrics and wraps execution with configurable retry (tenacity exponential backoff) and timeout.
Attributes:
| Name | Type | Description |
|---|---|---|
name |
Colon-namespaced tool name, e.g. |
|
description |
Human-readable tool description forwarded to the LLM. |
|
server_name |
MCP server identifier. |
|
timeout_seconds |
Per-call asyncio timeout. |
|
retry_count |
Maximum tenacity retry attempts. |
Source code in src/api2mcp/orchestration/adapters/base.py
123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 | |
Attributes¶
call_count
property
¶
Total number of calls attempted through this adapter.
avg_latency_ms
property
¶
Average call latency in milliseconds (0.0 if no calls made).
Functions¶
from_mcp_tool(session, tool, server_name, *, timeout_seconds=30.0, retry_count=3, response_transformer=None)
async
classmethod
¶
Convert an MCP :class:~mcp.types.Tool into a LangChain StructuredTool.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
session
|
Any
|
Active :class: |
required |
tool
|
Any
|
The :class: |
required |
server_name
|
str
|
Identifier for the MCP server (used in namespacing). |
required |
timeout_seconds
|
float
|
Per-call asyncio timeout in seconds. |
30.0
|
retry_count
|
int
|
Maximum retry attempts on transient errors. |
3
|
response_transformer
|
Callable[[str], str] | None
|
Optional callable applied to the raw result string before returning to the LLM. |
None
|
Returns:
| Name | Type | Description |
|---|---|---|
A |
StructuredTool
|
class: |
StructuredTool
|
LangGraph agents. |
Example::
tool = await MCPToolAdapter.from_mcp_tool(session, mcp_tool, "github")
result = await tool.ainvoke({"owner": "user", "repo": "project"})
Source code in src/api2mcp/orchestration/adapters/base.py
to_structured_tool()
¶
Return a :class:~langchain_core.tools.StructuredTool wrapping this adapter.
The returned tool uses the bound :meth:_execute coroutine and the
dynamically generated Pydantic :attr:args_schema.
Source code in src/api2mcp/orchestration/adapters/base.py
metrics()
¶
Return a snapshot of call metrics for this adapter.
Returns:
| Type | Description |
|---|---|
dict[str, Any]
|
Dict with |
dict[str, Any]
|
|
Source code in src/api2mcp/orchestration/adapters/base.py
api2mcp.orchestration.adapters.registry.MCPToolRegistry
¶
Central registry for MCP tools across multiple servers.
Supports two registration modes:
-
Session-based (eager): pass an already-active :class:
~mcp.client.session.ClientSessionto :meth:register_server. The caller owns session lifecycle. -
Config-based (lazy): pass a :class:
ServerConfigto :meth:register_server_config, then call :meth:connect_server/ :meth:connect_allto establish subprocess connections managed internally. Call :meth:closeto clean up.
Tool names use colon namespacing::
"github:list_issues"
"jira:create_ticket"
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
default_timeout
|
float
|
Per-call timeout forwarded to every adapter. |
30.0
|
default_retry_count
|
int
|
Retry count forwarded to every adapter. |
3
|
Source code in src/api2mcp/orchestration/adapters/registry.py
121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 | |
Functions¶
register_server_config(config)
async
¶
Register a :class:ServerConfig without connecting.
The actual subprocess connection is deferred to
:meth:connect_server or :meth:connect_all.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
config
|
ServerConfig
|
Server configuration to store. |
required |
Source code in src/api2mcp/orchestration/adapters/registry.py
connect_server(name)
async
¶
Establish a subprocess connection for a registered config.
Launches the subprocess described by the stored
:class:ServerConfig, creates a
:class:~mcp.client.session.ClientSession, initialises the
protocol, and calls :meth:register_server to discover tools.
If the server is already connected, returns the existing session.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
name
|
str
|
Server name matching a previously registered
:class: |
required |
Returns:
| Type | Description |
|---|---|
Any
|
The active :class: |
Raises:
| Type | Description |
|---|---|
ValueError
|
If no config is registered under name. |
ImportError
|
If the |
Source code in src/api2mcp/orchestration/adapters/registry.py
connect_all()
async
¶
Connect all registered :class:ServerConfig instances.
Skips servers that are already connected. Errors from individual servers are logged and re-raised immediately.
Source code in src/api2mcp/orchestration/adapters/registry.py
register_server(server_name, session, *, timeout_seconds=None, retry_count=None)
async
¶
Discover all tools from session and register them under server_name.
Calls session.list_tools() once and converts every returned tool
into a :class:~langchain_core.tools.StructuredTool.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
server_name
|
str
|
Logical server identifier (namespace prefix). |
required |
session
|
Any
|
Active MCP ClientSession. |
required |
timeout_seconds
|
float | None
|
Per-adapter timeout override (defaults to
:attr: |
None
|
retry_count
|
int | None
|
Per-adapter retry count override (defaults to
:attr: |
None
|
Returns:
| Type | Description |
|---|---|
list[str]
|
List of registered colon-namespaced tool names. |
Source code in src/api2mcp/orchestration/adapters/registry.py
register_tool(server_name, tool)
async
¶
Manually register a pre-built :class:~langchain_core.tools.StructuredTool.
Useful for testing or when the tool is built outside the registry.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
server_name
|
str
|
Logical server identifier (namespace prefix). |
required |
tool
|
StructuredTool
|
The StructuredTool to register. |
required |
Returns:
| Type | Description |
|---|---|
str
|
The colon-namespaced name used in the registry. |
Source code in src/api2mcp/orchestration/adapters/registry.py
unregister_server(server_name)
async
¶
Remove all tools, adapters, and the session for server_name.
Note: Subprocess connections established via :meth:connect_server
are only fully closed when :meth:close is called. This method
only removes the server from the registry's lookup tables.
Returns:
| Type | Description |
|---|---|
bool
|
|
Source code in src/api2mcp/orchestration/adapters/registry.py
get_tool(namespaced_name)
¶
Return the tool registered as namespaced_name, or None.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
namespaced_name
|
str
|
Colon-namespaced name, e.g. |
required |
Source code in src/api2mcp/orchestration/adapters/registry.py
get_tools(*, server=None, category=None, pattern=None)
¶
Return registered tools, optionally filtered.
Filters are combined (AND semantics).
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
server
|
str | None
|
If given, return only tools from this server. |
None
|
category
|
str | None
|
If given, filter by inferred category. Supported
values: |
None
|
pattern
|
str | None
|
If given, filter tool names using :mod: |
None
|
Returns:
| Type | Description |
|---|---|
list[StructuredTool]
|
Filtered list of :class: |
Source code in src/api2mcp/orchestration/adapters/registry.py
registered_servers()
¶
list_servers()
¶
list_categories()
¶
Return the distinct inferred categories present in the registry.
Returns:
| Type | Description |
|---|---|
list[str]
|
Sorted list of category strings (e.g. |
Source code in src/api2mcp/orchestration/adapters/registry.py
registered_tools()
¶
tools_for_server(server_name)
¶
Return colon-namespaced names for all tools from server_name.
Returns an empty list if the server is not registered.
Source code in src/api2mcp/orchestration/adapters/registry.py
get_usage_stats()
¶
Return usage statistics for all tools with registered adapters.
Tools registered manually via :meth:register_tool are excluded
(no adapter to track calls).
Returns:
| Type | Description |
|---|---|
dict[str, dict[str, Any]]
|
Mapping of namespaced tool name → metrics dict. Each metrics |
dict[str, dict[str, Any]]
|
dict contains |
dict[str, dict[str, Any]]
|
|
Source code in src/api2mcp/orchestration/adapters/registry.py
close()
async
¶
Close all subprocess connections managed by this registry.
Calls :meth:contextlib.AsyncExitStack.aclose which tears down
every :class:~mcp.client.session.ClientSession and subprocess
established via :meth:connect_server.
Sessions registered directly with :meth:register_server are
not closed here — their lifecycle is managed by the caller.
Source code in src/api2mcp/orchestration/adapters/registry.py
Graphs¶
api2mcp.orchestration.graphs.reactive.ReactiveGraph
¶
Bases: BaseAPIGraph
Single-API reactive (ReAct) agent graph.
Wraps langgraph.prebuilt.create_react_agent with an
API2MCP-specific system prompt and tool set sourced from
:class:~api2mcp.orchestration.adapters.registry.MCPToolRegistry.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
model
|
BaseChatModel
|
LangChain chat model for the agent node. |
required |
registry
|
MCPToolRegistry
|
Tool registry that provides the MCP-backed tools for api_name. |
required |
api_name
|
str
|
Logical MCP server name (e.g. |
required |
checkpointer
|
Any
|
Optional LangGraph checkpointer. When provided, the compiled graph supports multi-turn / persistent memory. |
None
|
max_iterations
|
int
|
Maximum agent iterations before the graph
terminates with a |
10
|
Source code in src/api2mcp/orchestration/graphs/reactive.py
54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 | |
Functions¶
build_graph()
¶
Compile the ReAct agent graph via create_react_agent.
Retrieves tools for :attr:api_name from the registry, builds
the system prompt, and delegates to
langgraph.prebuilt.create_react_agent.
Returns:
| Type | Description |
|---|---|
Any
|
Compiled LangGraph graph ( |
Raises:
| Type | Description |
|---|---|
ImportError
|
If |
Source code in src/api2mcp/orchestration/graphs/reactive.py
run(user_input, *, thread_id='default', **kwargs)
async
¶
Invoke the reactive agent and return the final state.
Delegates to :meth:BaseAPIGraph.run and catches residual
asyncio.TimeoutError, ConnectionError, and OSError
exceptions that may escape the adapter's retry logic (e.g. if
all retry attempts are exhausted).
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
user_input
|
str
|
The user's request / prompt. |
required |
thread_id
|
str
|
Checkpointer thread identifier. |
'default'
|
**kwargs
|
Any
|
Extra keys passed through to the graph input dict. |
{}
|
Returns:
| Type | Description |
|---|---|
Any
|
Final graph state dict from |
Raises:
| Type | Description |
|---|---|
TimeoutError
|
Re-raised after logging if the MCP server does not respond within the configured timeout after all retries. |
ConnectionError
|
Re-raised after logging on persistent connection failure. |
OSError
|
Re-raised after logging on OS-level I/O failure. |
Source code in src/api2mcp/orchestration/graphs/reactive.py
stream(user_input, *, thread_id='default', **kwargs)
async
¶
Stream events from the reactive agent.
Delegates to :meth:BaseAPIGraph.stream and propagates events
as an async generator. Residual MCP errors are logged before
re-raising.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
user_input
|
str
|
The user's request / prompt. |
required |
thread_id
|
str
|
Checkpointer thread identifier. |
'default'
|
**kwargs
|
Any
|
Extra keys passed through to the graph input dict. |
{}
|
Yields:
| Type | Description |
|---|---|
AsyncIterator[dict[str, Any]]
|
LangGraph event dicts ( |
Raises:
| Type | Description |
|---|---|
TimeoutError
|
Re-raised after logging. |
ConnectionError
|
Re-raised after logging. |
OSError
|
Re-raised after logging. |
Source code in src/api2mcp/orchestration/graphs/reactive.py
api2mcp.orchestration.graphs.planner.PlannerGraph
¶
Bases: BaseAPIGraph
Plan-and-execute graph for multi-API workflows.
Builds a :class:~langgraph.graph.StateGraph that:
- Calls an LLM to generate an :class:
ExecutionStepplan. - Validates the plan for dependency cycles.
- Executes steps respecting the configured execution mode.
- On failure, asks the LLM to revise the remaining plan.
- Synthesises a final human-readable result from all step outputs.
Inherits from :class:~api2mcp.orchestration.graphs.base.BaseAPIGraph.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
model
|
BaseChatModel
|
LangChain chat model used for planning, synthesis, and
replanning (must support |
required |
registry
|
MCPToolRegistry
|
Populated
:class: |
required |
api_names
|
list[str]
|
Names of MCP servers available for this workflow. |
required |
execution_mode
|
str
|
|
'sequential'
|
checkpointer
|
Any | None
|
LangGraph checkpointer for persistence (optional). |
None
|
max_iterations
|
int
|
Guard against infinite replan loops. |
20
|
Source code in src/api2mcp/orchestration/graphs/planner.py
295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 720 721 722 723 724 725 726 727 728 729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 748 749 750 751 752 753 754 755 756 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 823 824 825 826 827 828 829 830 831 832 833 834 835 836 837 838 839 840 841 842 843 844 845 846 847 848 849 850 851 852 853 854 855 856 857 858 859 860 861 862 863 864 865 866 867 868 869 870 871 872 873 874 875 876 877 878 879 880 881 882 883 884 885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 900 901 902 903 904 905 906 907 908 909 910 911 912 913 914 915 916 917 918 919 920 921 922 923 924 925 926 927 928 929 930 931 932 933 934 935 936 937 938 939 940 941 942 943 944 945 946 947 948 949 950 951 952 953 954 955 956 957 958 959 960 961 962 963 964 965 966 967 968 969 970 971 972 973 974 975 976 977 978 979 980 981 | |
Functions¶
build_graph()
¶
Construct and compile the LangGraph StateGraph.
Called automatically by :meth:BaseAPIGraph.__init__.
Returns:
| Type | Description |
|---|---|
Any
|
Compiled graph ( |
Source code in src/api2mcp/orchestration/graphs/planner.py
run(user_input, *, thread_id='default', **kwargs)
async
¶
Execute the planner workflow and return the final state.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
user_input
|
str
|
Natural-language request for the workflow to fulfil. |
required |
thread_id
|
str
|
Checkpointer thread identifier (defaults to
|
'default'
|
**kwargs
|
Any
|
Additional keys merged into the initial state. |
{}
|
Returns:
| Name | Type | Description |
|---|---|---|
Final |
MultiAPIState
|
class: |
Source code in src/api2mcp/orchestration/graphs/planner.py
stream(user_input, *, thread_id='default', **kwargs)
async
¶
Stream graph state updates as they are emitted by each node.
Yields one dict per node execution, keyed by node name.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
user_input
|
str
|
Natural-language request for the workflow to fulfil. |
required |
thread_id
|
str
|
Checkpointer thread identifier. |
'default'
|
**kwargs
|
Any
|
Additional keys merged into the initial state. |
{}
|
Yields:
| Type | Description |
|---|---|
AsyncIterator[dict[str, Any]]
|
Partial state update dicts emitted after each node completes. |
Source code in src/api2mcp/orchestration/graphs/planner.py
api2mcp.orchestration.graphs.conversational.ConversationalGraph
¶
Bases: BaseAPIGraph
Multi-turn conversational agent with human-in-the-loop support.
Builds a custom :class:~langgraph.graph.StateGraph over
:class:~api2mcp.orchestration.state.definitions.ConversationalState
with four nodes:
agent— calls the LLM with memory-filtered messages.tools— executes non-destructive tool calls from the agent.clarify— surfaces a clarification question to the caller.approve— pauses viainterrupt()for user approval before executing a destructive tool.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
model
|
BaseChatModel
|
LangChain chat model used by the agent node. |
required |
registry
|
MCPToolRegistry
|
Tool registry that provides MCP-backed
:class: |
required |
api_names
|
list[str] | None
|
Optional list of MCP server names to expose as tools.
When |
None
|
memory_strategy
|
str
|
One of |
'window'
|
max_history
|
int
|
Maximum number of non-system messages to keep when
the |
20
|
checkpointer
|
Any
|
LangGraph checkpointer required for session
persistence and human-in-the-loop interrupt/resume support.
Recommended: pass a |
None
|
max_iterations
|
int
|
Upper bound on agent iterations, forwarded as
|
50
|
Source code in src/api2mcp/orchestration/graphs/conversational.py
109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 | |
Functions¶
build_graph()
¶
Compile and return the conversational LangGraph graph.
Constructs a :class:~langgraph.graph.StateGraph over
:class:~api2mcp.orchestration.state.definitions.ConversationalState
with agent, tools, clarify, and approve nodes, then
compiles it with the configured checkpointer.
Returns:
| Type | Description |
|---|---|
Any
|
Compiled LangGraph |