fast-agent-mcp 0.3.0__py3-none-any.whl → 0.3.2__py3-none-any.whl

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.

Potentially problematic release.


This version of fast-agent-mcp might be problematic. Click here for more details.

fast_agent/__init__.py CHANGED
@@ -1,4 +1,5 @@
1
1
  """fast-agent - An MCP native agent application framework"""
2
+ from typing import TYPE_CHECKING as _TYPE_CHECKING
2
3
 
3
4
  # Configuration and settings (safe - pure Pydantic models)
4
5
  from fast_agent.config import (
@@ -83,6 +84,11 @@ def __getattr__(name: str):
83
84
  raise AttributeError(f"module '{__name__}' has no attribute '{name}'")
84
85
 
85
86
 
87
+ # Help static analyzers/IDEs resolve symbols and signatures without importing at runtime.
88
+ if _TYPE_CHECKING: # pragma: no cover - typing aid only
89
+ from fast_agent.core.fastagent import FastAgent as FastAgent # noqa: F401
90
+
91
+
86
92
  __all__ = [
87
93
  # Core fast-agent components (lazy loaded)
88
94
  "Core",
@@ -43,7 +43,6 @@ from fast_agent.constants import HUMAN_INPUT_TOOL_NAME
43
43
  from fast_agent.core.exceptions import PromptExitError
44
44
  from fast_agent.core.logging.logger import get_logger
45
45
  from fast_agent.interfaces import FastAgentLLMProtocol
46
- from fast_agent.mcp.helpers.content_helpers import normalize_to_extended_list
47
46
  from fast_agent.mcp.mcp_aggregator import MCPAggregator
48
47
  from fast_agent.tools.elicitation import (
49
48
  get_elicitation_tool,
@@ -624,12 +623,9 @@ class McpAgent(ABC, ToolAgent):
624
623
  Returns:
625
624
  An instance of the specified model, or None if coercion fails
626
625
  """
627
- assert self._llm
628
- # Normalize all input types to a list of PromptMessageExtended
629
- normalized_messages = normalize_to_extended_list(messages)
630
626
 
631
627
  with self._tracer.start_as_current_span(f"Agent: '{self._name}' structured"):
632
- return await self._llm.structured(normalized_messages, model, request_params)
628
+ return await super().structured(messages, model, request_params)
633
629
 
634
630
  async def apply_prompt_messages(
635
631
  self, prompts: List[PromptMessageExtended], request_params: RequestParams | None = None
@@ -9,50 +9,33 @@ console = Console()
9
9
 
10
10
 
11
11
  def load_template_text(filename: str) -> str:
12
- """Load template text from packaged resources with a development fallback.
12
+ """Load template text from packaged resources only.
13
13
 
14
14
  Special-case: when requesting 'fastagent.secrets.yaml', read the
15
15
  'fastagent.secrets.yaml.example' template from resources, but still
16
16
  return its contents so we can write out the real secrets file name
17
17
  in the destination project.
18
18
  """
19
- try:
20
- # Prefer reading from installed package resources
21
- from importlib.resources import files
19
+ from importlib.resources import files
22
20
 
23
- # Map secrets filename to its '.example' template in resources
24
- res_name = (
25
- "fastagent.secrets.yaml.example" if filename == "fastagent.secrets.yaml" else filename
26
- )
27
- resource_path = files("fast_agent").joinpath("resources").joinpath("setup").joinpath(res_name)
28
- if resource_path.is_file():
29
- return resource_path.read_text()
30
- # If the path exists but isn't a file, fall back to dev
31
- raise FileNotFoundError
32
- except (ImportError, ModuleNotFoundError, FileNotFoundError):
33
- # Development environment fallback to repo path (project root/examples/setup)
34
- try:
35
- repo_root = Path(__file__).resolve().parents[4]
36
- except IndexError:
37
- repo_root = Path(__file__).resolve().parent
38
- # Apply the same secrets mapping for the dev path
39
- dev_name = (
40
- "fastagent.secrets.yaml.example" if filename == "fastagent.secrets.yaml" else filename
41
- )
42
- dev_path = repo_root / "examples" / "setup" / dev_name
43
- if dev_path.exists():
44
- return dev_path.read_text()
45
- raise RuntimeError(
46
- "Setup template missing: '"
47
- + filename
48
- + "'.\n"
49
- + "Expected at: "
50
- + str(resource_path)
51
- + " (package) or "
52
- + str(dev_path)
53
- + " (dev).\n"
54
- + "This indicates a packaging issue. Please rebuild/reinstall fast-agent."
55
- )
21
+ # Map requested filenames to resource templates
22
+ if filename == "fastagent.secrets.yaml":
23
+ res_name = "fastagent.secrets.yaml.example"
24
+ elif filename == "pyproject.toml":
25
+ res_name = "pyproject.toml.tmpl"
26
+ else:
27
+ res_name = filename
28
+ resource_path = (
29
+ files("fast_agent").joinpath("resources").joinpath("setup").joinpath(res_name)
30
+ )
31
+ if resource_path.is_file():
32
+ return resource_path.read_text()
33
+
34
+ raise RuntimeError(
35
+ f"Setup template missing: '{filename}'.\n"
36
+ f"Expected packaged resource at: {resource_path}.\n"
37
+ "This indicates a packaging issue. Please rebuild/reinstall fast-agent."
38
+ )
56
39
 
57
40
 
58
41
  # (No embedded template defaults; templates are the single source of truth.)
@@ -114,6 +97,7 @@ def init(
114
97
  console.print(f" - {config_path}/fastagent.config.yaml")
115
98
  console.print(f" - {config_path}/fastagent.secrets.yaml")
116
99
  console.print(f" - {config_path}/agent.py")
100
+ console.print(f" - {config_path}/pyproject.toml")
117
101
  if needs_gitignore:
118
102
  console.print(f" - {config_path}/.gitignore")
119
103
 
@@ -135,6 +119,33 @@ def init(
135
119
  if create_file(config_path / "agent.py", load_template_text("agent.py"), force):
136
120
  created.append("agent.py")
137
121
 
122
+ # Create a minimal pyproject.toml so `uv run` installs dependencies
123
+ def _render_pyproject(template_text: str) -> str:
124
+ # Determine Python requirement from installed fast-agent-mcp metadata, fall back if missing
125
+ py_req = ">=3.13.7"
126
+ try:
127
+ from importlib.metadata import metadata
128
+
129
+ md = metadata("fast-agent-mcp")
130
+ req = md.get("Requires-Python")
131
+ if req:
132
+ py_req = req
133
+ except Exception:
134
+ pass
135
+
136
+ # Always use latest fast-agent-mcp (no version pin)
137
+ fast_agent_dep = '"fast-agent-mcp"'
138
+
139
+ return (
140
+ template_text.replace("{{python_requires}}", py_req)
141
+ .replace("{{fast_agent_dep}}", fast_agent_dep)
142
+ )
143
+
144
+ pyproject_template = load_template_text("pyproject.toml")
145
+ pyproject_text = _render_pyproject(pyproject_template)
146
+ if create_file(config_path / "pyproject.toml", pyproject_text, force):
147
+ created.append("pyproject.toml")
148
+
138
149
  # Only create .gitignore if none exists in parent directories
139
150
  if needs_gitignore and create_file(
140
151
  config_path / ".gitignore", load_template_text(".gitignore"), force
@@ -1,17 +1,52 @@
1
1
  """
2
- fast_agent.core package
2
+ Core interfaces and decorators for fast-agent.
3
3
 
4
- Provides core subpackages (executor, logging) and lazily exposes the `Core`
5
- class to avoid circular imports during initialization.
4
+ Public API:
5
+ - `Core`: The core application container (lazy-loaded)
6
+ - `FastAgent`: High-level, decorator-driven application class (lazy-loaded)
7
+ - Decorators: `agent`, `custom`, `orchestrator`, `iterative_planner`,
8
+ `router`, `chain`, `parallel`, `evaluator_optimizer` (lazy-loaded)
6
9
  """
7
10
 
8
- __all__ = ["Core"]
11
+ __all__ = [
12
+ "Core",
13
+ "FastAgent",
14
+ # Decorators
15
+ "agent",
16
+ "custom",
17
+ "orchestrator",
18
+ "iterative_planner",
19
+ "router",
20
+ "chain",
21
+ "parallel",
22
+ "evaluator_optimizer",
23
+ ]
9
24
 
10
25
 
11
26
  def __getattr__(name: str):
27
+ # Lazy imports to avoid heavy dependencies and circular imports at init time
12
28
  if name == "Core":
13
- # Lazy import to avoid importing heavy dependencies during package init
14
29
  from .core_app import Core
15
30
 
16
31
  return Core
32
+ if name == "FastAgent":
33
+ from .fastagent import FastAgent
34
+
35
+ return FastAgent
36
+
37
+ # Decorators from direct_decorators
38
+ if name in {
39
+ "agent",
40
+ "custom",
41
+ "orchestrator",
42
+ "iterative_planner",
43
+ "router",
44
+ "chain",
45
+ "parallel",
46
+ "evaluator_optimizer",
47
+ }:
48
+ from . import direct_decorators as _dd
49
+
50
+ return getattr(_dd, name)
51
+
17
52
  raise AttributeError(f"module '{__name__}' has no attribute '{name}'")
@@ -251,6 +251,33 @@ class FastAgent:
251
251
  return self.app.context
252
252
 
253
253
  # Decorator methods with type-safe implementations
254
+ # Provide annotations so IDEs can discover these attributes on instances
255
+ if TYPE_CHECKING: # pragma: no cover - typing aid only
256
+ from typing import Awaitable, ParamSpec, Protocol, TypeVar # re-import for type block
257
+
258
+ from fast_agent.core.direct_decorators import (
259
+ DecoratedAgentProtocol,
260
+ DecoratedChainProtocol,
261
+ DecoratedEvaluatorOptimizerProtocol,
262
+ DecoratedOrchestratorProtocol,
263
+ DecoratedParallelProtocol,
264
+ DecoratedRouterProtocol,
265
+ )
266
+
267
+ P = ParamSpec("P")
268
+ R = TypeVar("R")
269
+
270
+ # These are declared as attributes so IDEs show autocomplete on `fast.agent` etc.
271
+ def agent(self, *args, **kwargs) -> "DecoratedAgentProtocol[P, R]": ...
272
+ def custom(self, *args, **kwargs) -> "DecoratedAgentProtocol[P, R]": ...
273
+ def orchestrator(self, *args, **kwargs) -> "DecoratedOrchestratorProtocol[P, R]": ...
274
+ def iterative_planner(self, *args, **kwargs) -> "DecoratedOrchestratorProtocol[P, R]": ...
275
+ def router(self, *args, **kwargs) -> "DecoratedRouterProtocol[P, R]": ...
276
+ def chain(self, *args, **kwargs) -> "DecoratedChainProtocol[P, R]": ...
277
+ def parallel(self, *args, **kwargs) -> "DecoratedParallelProtocol[P, R]": ...
278
+ def evaluator_optimizer(self, *args, **kwargs) -> "DecoratedEvaluatorOptimizerProtocol[P, R]": ...
279
+
280
+ # Runtime bindings (actual implementations)
254
281
  agent = agent_decorator
255
282
  custom = custom_decorator
256
283
  orchestrator = orchestrator_decorator
@@ -1,7 +1,8 @@
1
1
  """
2
- MCP utilities and types for Fast Agent.
2
+ MCP utilities and types for fast-agent.
3
3
 
4
4
  Public API:
5
+ - `Prompt`: helper for constructing MCP prompts/messages.
5
6
  - `PromptMessageExtended`: canonical message container used internally by providers.
6
7
  - Helpers from `fast_agent.mcp.helpers` (re-exported for convenience).
7
8
 
@@ -26,6 +27,7 @@ from .helpers import (
26
27
  from .prompt_message_extended import PromptMessageExtended
27
28
 
28
29
  __all__ = [
30
+ "Prompt",
29
31
  "PromptMessageExtended",
30
32
  # Helpers
31
33
  "get_text",
@@ -41,3 +43,12 @@ __all__ = [
41
43
  "split_thinking_content",
42
44
  "text_content",
43
45
  ]
46
+
47
+
48
+ def __getattr__(name: str):
49
+ # Lazily import to avoid circular imports with fast_agent.types
50
+ if name == "Prompt":
51
+ from .prompt import Prompt # local import
52
+
53
+ return Prompt
54
+ raise AttributeError(f"module '{__name__}' has no attribute '{name}'")
@@ -0,0 +1,17 @@
1
+ [project]
2
+ name = "fast-agent-app"
3
+ version = "0.1.0"
4
+ description = "a simple fast-agent application"
5
+ readme = "README.md"
6
+ requires-python = "{{python_requires}}"
7
+ dependencies = [
8
+ {{fast_agent_dep}}
9
+ ]
10
+
11
+ [tool.uv]
12
+ package = true
13
+
14
+ # Optional convenience entry point if you later package this app:
15
+ [project.scripts]
16
+ fast-agent-app = "agent:main"
17
+
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: fast-agent-mcp
3
- Version: 0.3.0
3
+ Version: 0.3.2
4
4
  Summary: Define, Prompt and Test MCP enabled Agents and Workflows
5
5
  Author-email: Shaun Smith <fastagent@llmindset.co.uk>
6
6
  License: Apache License
@@ -1,4 +1,4 @@
1
- fast_agent/__init__.py,sha256=bmws6wJQefvfO0Cd5x9VLTI7RCdjF6NqZtWSj_14tv0,3349
1
+ fast_agent/__init__.py,sha256=sljPsYHqDmv5v0fBpQdhtwBm5IDyu37lwdSQA0IPEwQ,3628
2
2
  fast_agent/config.py,sha256=8CPbTctXGdSneAkMory5ZRXkUsUj4AyKnaf_nmEamQA,19886
3
3
  fast_agent/constants.py,sha256=d5EMSO2msRkjRFz8MgnnhpMnO3woqKP0EcQ4b_yI60w,235
4
4
  fast_agent/context.py,sha256=nBelOqehSH91z3aG2nYhwETP-biRzz-iuA2fqmKdHP8,7700
@@ -11,7 +11,7 @@ fast_agent/agents/__init__.py,sha256=kBI2VWTitLyWf8K3dFMyuE-K7Ufp7mkHBomM2K3I8H8
11
11
  fast_agent/agents/agent_types.py,sha256=ugolD3lC2KxSfBYjjRf9HjNATZaFx1o4Fhjb15huSgk,1776
12
12
  fast_agent/agents/llm_agent.py,sha256=iuy3kO5Q-f9bm3tjYLG2Wurd0gK2sLhTfTkSnfVWzSw,8311
13
13
  fast_agent/agents/llm_decorator.py,sha256=yzaYqsT8lqey4dbZrv1oK9qUqf8I2RMPYiWOy0uVHqA,16443
14
- fast_agent/agents/mcp_agent.py,sha256=R-OeHu0dO61z0vQwtCqKL2WLs1o9kHdsu74Fu4ALaCM,35494
14
+ fast_agent/agents/mcp_agent.py,sha256=BMSTcGd9_SdoyEGNGVAWXu8ubaE1TAeAMl-2c_wymQU,35240
15
15
  fast_agent/agents/tool_agent.py,sha256=zSaVQH-mBICgE3ildeZx24i00u_KMOk5P4OuJBTiQ3g,6571
16
16
  fast_agent/agents/workflow/chain_agent.py,sha256=Pd8dOH_YdKu3LXsKa4fwqzY_B2qVuhzdfCUiKi5v17s,6293
17
17
  fast_agent/agents/workflow/evaluator_optimizer.py,sha256=rhzazy8Aj-ydId6kmBC77TmtYZ5mirSe7eV6PPMWkBA,12040
@@ -29,16 +29,16 @@ fast_agent/cli/commands/check_config.py,sha256=nMiOBs-Sc7XqUU6tLReLn1JPXHqjR0Kuz
29
29
  fast_agent/cli/commands/go.py,sha256=VRiHq9h1UGIndLdQJMAwEM6bwTGy-h5n6w__bYCGaHM,15094
30
30
  fast_agent/cli/commands/quickstart.py,sha256=hQZYlvktPdDNdaZOZkBgcvi8u0bMW5yFhz4BLBZ251I,21175
31
31
  fast_agent/cli/commands/server_helpers.py,sha256=BmljUNLIcZdFpffYxEPfJf8rrX3JhTzMA7VONoZLAjM,3650
32
- fast_agent/cli/commands/setup.py,sha256=nPo9sI1BZTM_7P97De_nzmX61JUlIt9Mti8c2K7D9aw,6208
32
+ fast_agent/cli/commands/setup.py,sha256=rCp5wUs5kjbHJqi3Jz9ByCpOSvJ7L4KB0hpcKB8qpCM,6377
33
33
  fast_agent/cli/commands/url_parser.py,sha256=ivWrsODeVO9GGERkaTawYIxZuf57uRga1gubwT3n3vU,5907
34
- fast_agent/core/__init__.py,sha256=hlVPmPYKnR88k8awP3aEn5V3DhNK4UwaLA1DmUDNIfQ,448
34
+ fast_agent/core/__init__.py,sha256=RsHaeZTQmmNC6cd--kGsnu-jp053cr7h0TUMEnBcMQ0,1223
35
35
  fast_agent/core/agent_app.py,sha256=cdzNwpb--SUNYbhkUX6RolqVnxJ5WSchxw5I4gFrvpk,16836
36
36
  fast_agent/core/core_app.py,sha256=_8Di00HD2BzWhCAaopAUS0Hzc7pg0249QUUfPuLZ36A,4266
37
37
  fast_agent/core/direct_decorators.py,sha256=eHhQfKLbeaoH-W0snzAVJRxga7wTNGXBk5DEJTAbZB8,23642
38
38
  fast_agent/core/direct_factory.py,sha256=HGGnnF4Z9k_N3r0Iin_sp2Ch308To1oKX8JTKHjuUq0,21350
39
39
  fast_agent/core/error_handling.py,sha256=xoyS2kLe0eG0bj2eSJCJ2odIhGUve2SbDR7jP-A-uRw,624
40
40
  fast_agent/core/exceptions.py,sha256=ENAD_qGG67foxy6vDkIvc-lgopIUQy6O7zvNPpPXaQg,2289
41
- fast_agent/core/fastagent.py,sha256=duxLEQMXdKqvKXAxbbe86_V7ZQR-etR-OMt-XfvLB1I,25351
41
+ fast_agent/core/fastagent.py,sha256=PJPeRREuQqlqdVub7RqamfsArpoZ1D50B8Hz-CsDenA,26792
42
42
  fast_agent/core/prompt.py,sha256=qNUFlK3KtU7leYysYUglzBYQnEYiXu__iR_T8189zc0,203
43
43
  fast_agent/core/validation.py,sha256=GZ0hUTxkr5KMY1wr6_ifDy91Ycvcx384gZEMOwdie9w,12681
44
44
  fast_agent/core/executor/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -94,7 +94,7 @@ fast_agent/llm/provider/openai/llm_xai.py,sha256=fEyO9XlU3Ef1a-cXdJl0Qe-FmE562cA
94
94
  fast_agent/llm/provider/openai/multipart_converter_openai.py,sha256=M7cbM4F8_xycPtVHJv1kBYYBX7KRXyYPCDb1YKQEgo0,20925
95
95
  fast_agent/llm/provider/openai/openai_multipart.py,sha256=uuoRMYWiznYksBODbknBuqe65UxEHE1h7AphHpdnCCM,6864
96
96
  fast_agent/llm/provider/openai/openai_utils.py,sha256=RI9UgF7SGkZ02bAep7glvLy3erbismmZp7wXDsRoJPQ,2034
97
- fast_agent/mcp/__init__.py,sha256=447bAeavOiy_Y8hKSs1XBfmfIKTcleYtdDb-sLFEkac,1114
97
+ fast_agent/mcp/__init__.py,sha256=fS322k3GsnZ8LcPImoAy_TtiqgiJgDmMlbgCc7AvVdQ,1458
98
98
  fast_agent/mcp/common.py,sha256=MpSC0fLO21RcDz4VApah4C8_LisVGz7OXkR17Xw-9mY,431
99
99
  fast_agent/mcp/elicitation_factory.py,sha256=p9tSTcs1KSCXkFcFv1cG7vJBpS1PedOJ5bcBJp0qKw4,3172
100
100
  fast_agent/mcp/elicitation_handlers.py,sha256=LWNKn850Ht9V1SGTfAZDptlsgzrycNhOPNsCcqzsuUY,6884
@@ -180,6 +180,7 @@ fast_agent/resources/setup/.gitignore,sha256=UQKYvhK6samGg5JZg613XiuGUkUAz2qzE1W
180
180
  fast_agent/resources/setup/agent.py,sha256=co2lm190iQqOlRhup78X5BKHSB-RqLn3tZdxh2yaGhA,422
181
181
  fast_agent/resources/setup/fastagent.config.yaml,sha256=JpezZSP5-ybUlZJaeQG1EoUONXmzmDhdAR6JIpbb-jA,1356
182
182
  fast_agent/resources/setup/fastagent.secrets.yaml.example,sha256=ht-i2_SpAyeXG2OnG_vOA1n7gRsGIInxp9g5Nio-jpI,1038
183
+ fast_agent/resources/setup/pyproject.toml.tmpl,sha256=b_dL9TBAzA4sPOkVZd3psMKFT-g_gef0n2NcANojEqs,343
183
184
  fast_agent/tools/elicitation.py,sha256=8FaNvuN__LAM328VSJ5T4Bg3m8auHraqYvIYv6Eh4KU,13464
184
185
  fast_agent/types/__init__.py,sha256=IpUWlzx3u_3h99F2IKJ8aPjyGZXguOwkOVJKGrst6hg,951
185
186
  fast_agent/types/llm_stop_reason.py,sha256=bWe97OfhALUe8uQeAQOnTdPlYzJiabIfo8u38kPgj3Q,2293
@@ -195,8 +196,8 @@ fast_agent/ui/mermaid_utils.py,sha256=MpcRyVCPMTwU1XeIxnyFg0fQLjcyXZduWRF8NhEqvX
195
196
  fast_agent/ui/progress_display.py,sha256=hajDob65PttiJ2mPS6FsCtnmTcnyvDWGn-UqQboXqkQ,361
196
197
  fast_agent/ui/rich_progress.py,sha256=vMeDD5cybsPf_0IjOM98U8TVaE_yYIOKZa8JnRgTYUo,7451
197
198
  fast_agent/ui/usage_display.py,sha256=ltJpn_sDzo8PDNSXWx-QdEUbQWUnhmajCItNt5mA5rM,7285
198
- fast_agent_mcp-0.3.0.dist-info/METADATA,sha256=Vff6l-8Pb92peB_JNSm5Z-qYTbx9px2Q-jOY59KT-F0,30462
199
- fast_agent_mcp-0.3.0.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
200
- fast_agent_mcp-0.3.0.dist-info/entry_points.txt,sha256=i6Ujja9J-hRxttOKqTYdbYP_tyaS4gLHg53vupoCSsg,199
201
- fast_agent_mcp-0.3.0.dist-info/licenses/LICENSE,sha256=Gx1L3axA4PnuK4FxsbX87jQ1opoOkSFfHHSytW6wLUU,10935
202
- fast_agent_mcp-0.3.0.dist-info/RECORD,,
199
+ fast_agent_mcp-0.3.2.dist-info/METADATA,sha256=iaD5FYCGdDqTIAnGvq32PatCS2P-SbVzy-x79bmfIUA,30462
200
+ fast_agent_mcp-0.3.2.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
201
+ fast_agent_mcp-0.3.2.dist-info/entry_points.txt,sha256=i6Ujja9J-hRxttOKqTYdbYP_tyaS4gLHg53vupoCSsg,199
202
+ fast_agent_mcp-0.3.2.dist-info/licenses/LICENSE,sha256=Gx1L3axA4PnuK4FxsbX87jQ1opoOkSFfHHSytW6wLUU,10935
203
+ fast_agent_mcp-0.3.2.dist-info/RECORD,,