Jeremiah Lowin commited on
Commit
35f12d2
·
unverified ·
2 Parent(s): 697de8d016486c

Merge pull request #185 from jlowin/docs

Browse files
docs/clients/{overview.mdx → client.mdx} RENAMED
@@ -5,6 +5,10 @@ description: Learn how to use the FastMCP Client to interact with MCP servers.
5
  icon: user-robot
6
  ---
7
 
 
 
 
 
8
  The `fastmcp.Client` provides a high-level, asynchronous interface for interacting with any Model Context Protocol (MCP) server, whether it's built with FastMCP or another implementation. It simplifies communication by handling protocol details and connection management.
9
 
10
  ## FastMCP Client
 
5
  icon: user-robot
6
  ---
7
 
8
+ import { VersionBadge } from '/snippets/version-badge.mdx'
9
+
10
+ <VersionBadge version="2.0.0" />
11
+
12
  The `fastmcp.Client` provides a high-level, asynchronous interface for interacting with any Model Context Protocol (MCP) server, whether it's built with FastMCP or another implementation. It simplifies communication by handling protocol details and connection management.
13
 
14
  ## FastMCP Client
docs/clients/transports.mdx CHANGED
@@ -7,7 +7,7 @@ icon: link
7
 
8
  The FastMCP `Client` relies on a `ClientTransport` object to handle the specifics of connecting to and communicating with an MCP server. FastMCP provides several built-in transport implementations for common connection methods.
9
 
10
- While the `Client` often infers the correct transport automatically (see [Client Overview](/clients/overview#transport-inference)), you can also instantiate transports explicitly for more control.
11
 
12
 
13
  ## Stdio Transports
 
7
 
8
  The FastMCP `Client` relies on a `ClientTransport` object to handle the specifics of connecting to and communicating with an MCP server. FastMCP provides several built-in transport implementations for common connection methods.
9
 
10
+ While the `Client` often infers the correct transport automatically (see [Client Overview](/clients/client#transport-inference)), you can also instantiate transports explicitly for more control.
11
 
12
 
13
  ## Stdio Transports
docs/docs.json CHANGED
@@ -50,14 +50,14 @@
50
  {
51
  "group": "Clients",
52
  "pages": [
53
- "clients/overview",
54
  "clients/transports"
55
  ]
56
  },
57
  {
58
  "group": "Patterns",
59
  "pages": [
60
- "patterns/proxying",
61
  "patterns/composition",
62
  "patterns/decorating-methods",
63
  "patterns/openapi",
 
50
  {
51
  "group": "Clients",
52
  "pages": [
53
+ "clients/client",
54
  "clients/transports"
55
  ]
56
  },
57
  {
58
  "group": "Patterns",
59
  "pages": [
60
+ "patterns/proxy",
61
  "patterns/composition",
62
  "patterns/decorating-methods",
63
  "patterns/openapi",
docs/patterns/composition.mdx CHANGED
@@ -4,6 +4,9 @@ sidebarTitle: Composition
4
  description: Combine multiple FastMCP servers into a single, larger application using mounting and importing.
5
  icon: puzzle-piece
6
  ---
 
 
 
7
 
8
  As your MCP applications grow, you might want to organize your tools, resources, and prompts into logical modules or reuse existing server components. FastMCP supports composition through two methods:
9
 
@@ -17,13 +20,31 @@ As your MCP applications grow, you might want to organize your tools, resources,
17
  - **Teamwork**: Different teams can work on separate FastMCP servers that are later combined.
18
  - **Organization**: Keep related functionality grouped together logically.
19
 
20
- ## Importing Subservers (Static Composition)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
21
 
22
  The `import_server()` method copies all components (tools, resources, templates, prompts) from one `FastMCP` instance (the *subserver*) into another (the *main server*). A `prefix` is added to avoid naming conflicts.
23
 
24
  ```python
25
  from fastmcp import FastMCP
26
- from typing import dict, list
27
  import asyncio
28
 
29
  # --- Define Subservers ---
@@ -114,7 +135,7 @@ await main_mcp.import_server(
114
  Be cautious when choosing separators. Some MCP clients (like Claude Desktop) might have restrictions on characters allowed in tool names (e.g., `/` might not be supported). The defaults (`_` for names, `+` for URIs) are generally safe.
115
  </Warning>
116
 
117
- ## Mounting Subservers (Live Linking)
118
 
119
  The `mount()` method creates a **live link** between the `main_mcp` server and the `subserver`. Instead of copying components, requests for components matching the `prefix` are **delegated** to the `subserver` at runtime.
120
 
@@ -186,61 +207,19 @@ main_mcp.mount(
186
  )
187
  ```
188
 
189
- ## Comparing Import and Mount
190
-
191
- | Feature | `import_server` | `mount` |
192
- |---------|----------------|---------|
193
- | **Synchronicity** | Async (must be awaited) | Sync |
194
- | **Composition Type** | One-time copy (static) | Live link (dynamic) |
195
- | **Updates** | Changes to subserver NOT reflected | Changes to subserver immediately reflected |
196
- | **Lifespan** | Not managed | Automatically managed |
197
- | **Best For** | Bundling finalized components | Modular runtime composition |
198
 
199
  ## Example: Modular Application
200
 
201
  Here's how a modular application might use `import_server`:
202
 
203
- ```python
204
- # modules/text_utils.py
205
- from fastmcp import FastMCP
206
- from typing import list
207
-
208
- text_mcp = FastMCP(name="TextUtilities")
209
-
210
- @text_mcp.tool()
211
- def count_words(text: str) -> int:
212
- """Counts words in a text."""
213
- return len(text.split())
214
-
215
- @text_mcp.resource("resource://stopwords")
216
- def get_stopwords() -> list[str]:
217
- """Return a list of common stopwords."""
218
- return ["the", "a", "is", "in"]
219
-
220
- # ------------------------------
221
- # modules/data_api.py
222
- from fastmcp import FastMCP
223
- import random
224
- from typing import dict
225
-
226
- data_mcp = FastMCP(name="DataAPI")
227
-
228
- @data_mcp.tool()
229
- def fetch_record(record_id: int) -> dict:
230
- """Fetches a dummy data record."""
231
- return {"id": record_id, "value": random.random()}
232
-
233
- @data_mcp.resource("data://schema/{table}")
234
- def get_table_schema(table: str) -> dict:
235
- """Provides a dummy schema for a table."""
236
- return {"table": table, "columns": ["id", "value"]}
237
-
238
- # ------------------------------
239
- # main_app.py
240
  from fastmcp import FastMCP
241
  import asyncio
242
- from modules.text_utils import text_mcp # Import server instances
243
- from modules.data_api import data_mcp
 
 
244
 
245
  app = FastMCP(name="MainApplication")
246
 
@@ -273,8 +252,42 @@ if __name__ == "__main__":
273
  # Run the server
274
  app.run()
275
  ```
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
276
 
277
- Now, running `main_app.py` starts a server that exposes:
 
278
  - `text_count_words`
279
  - `data_fetch_record`
280
  - `process_and_analyze`
 
4
  description: Combine multiple FastMCP servers into a single, larger application using mounting and importing.
5
  icon: puzzle-piece
6
  ---
7
+ import { VersionBadge } from '/snippets/version-badge.mdx'
8
+
9
+ <VersionBadge version="2.2.0" />
10
 
11
  As your MCP applications grow, you might want to organize your tools, resources, and prompts into logical modules or reuse existing server components. FastMCP supports composition through two methods:
12
 
 
20
  - **Teamwork**: Different teams can work on separate FastMCP servers that are later combined.
21
  - **Organization**: Keep related functionality grouped together logically.
22
 
23
+ ### Importing vs Mounting
24
+
25
+ The choice of importing or mounting depends on your use case and requirements. In general, importing is best for simpler cases because it copies the imported server's components into the main server, treating them as native integrations. Mounting is best for more complex cases where you need to delegate requests to the subserver at runtime.
26
+
27
+
28
+ | Feature | Importing | Mounting |
29
+ |---------|----------------|---------|
30
+ | **Method** | `FastMCP.import_server()` | `FastMCP.mount()` |
31
+ | **Composition Type** | One-time copy (static) | Live link (dynamic) |
32
+ | **Updates** | Changes to subserver NOT reflected | Changes to subserver immediately reflected |
33
+ | **Lifespan** | Not managed | Automatically managed |
34
+ | **Synchronicity** | Async (must be awaited) | Sync |
35
+ | **Best For** | Bundling finalized components | Modular runtime composition |
36
+
37
+ ### Proxy Servers
38
+
39
+ FastMCP supports [MCP proxying](/patterns/proxy), which allows you to mirror a local or remote server in a local FastMCP instance. Proxies are fully compatible with both importing and mounting.
40
+
41
+
42
+ ## Importing (Static Composition)
43
 
44
  The `import_server()` method copies all components (tools, resources, templates, prompts) from one `FastMCP` instance (the *subserver*) into another (the *main server*). A `prefix` is added to avoid naming conflicts.
45
 
46
  ```python
47
  from fastmcp import FastMCP
 
48
  import asyncio
49
 
50
  # --- Define Subservers ---
 
135
  Be cautious when choosing separators. Some MCP clients (like Claude Desktop) might have restrictions on characters allowed in tool names (e.g., `/` might not be supported). The defaults (`_` for names, `+` for URIs) are generally safe.
136
  </Warning>
137
 
138
+ ## Mounting (Live Linking)
139
 
140
  The `mount()` method creates a **live link** between the `main_mcp` server and the `subserver`. Instead of copying components, requests for components matching the `prefix` are **delegated** to the `subserver` at runtime.
141
 
 
207
  )
208
  ```
209
 
 
 
 
 
 
 
 
 
 
210
 
211
  ## Example: Modular Application
212
 
213
  Here's how a modular application might use `import_server`:
214
 
215
+ <CodeGroup>
216
+ ```python main.py
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
217
  from fastmcp import FastMCP
218
  import asyncio
219
+
220
+ # Import the servers (see other files)
221
+ from modules.text_server import text_mcp
222
+ from modules.data_server import data_mcp
223
 
224
  app = FastMCP(name="MainApplication")
225
 
 
252
  # Run the server
253
  app.run()
254
  ```
255
+ ```python modules/text_server.py
256
+ from fastmcp import FastMCP
257
+
258
+ text_mcp = FastMCP(name="TextUtilities")
259
+
260
+ @text_mcp.tool()
261
+ def count_words(text: str) -> int:
262
+ """Counts words in a text."""
263
+ return len(text.split())
264
+
265
+ @text_mcp.resource("resource://stopwords")
266
+ def get_stopwords() -> list[str]:
267
+ """Return a list of common stopwords."""
268
+ return ["the", "a", "is", "in"]
269
+ ```
270
+
271
+ ```python modules/data_server.py
272
+ from fastmcp import FastMCP
273
+ import random
274
+ from typing import dict
275
+
276
+ data_mcp = FastMCP(name="DataAPI")
277
+
278
+ @data_mcp.tool()
279
+ def fetch_record(record_id: int) -> dict:
280
+ """Fetches a dummy data record."""
281
+ return {"id": record_id, "value": random.random()}
282
+
283
+ @data_mcp.resource("data://schema/{table}")
284
+ def get_table_schema(table: str) -> dict:
285
+ """Provides a dummy schema for a table."""
286
+ return {"table": table, "columns": ["id", "value"]}
287
+ ```
288
 
289
+ </CodeGroup>
290
+ Now, running `main.py` starts a server that exposes:
291
  - `text_count_words`
292
  - `data_fetch_record`
293
  - `process_and_analyze`
docs/patterns/fastapi.mdx CHANGED
@@ -4,6 +4,9 @@ sidebarTitle: FastAPI
4
  description: Generate MCP servers from FastAPI apps
5
  icon: square-bolt
6
  ---
 
 
 
7
 
8
 
9
  FastMCP can automatically convert FastAPI applications into MCP servers.
 
4
  description: Generate MCP servers from FastAPI apps
5
  icon: square-bolt
6
  ---
7
+ import { VersionBadge } from '/snippets/version-badge.mdx'
8
+
9
+ <VersionBadge version="2.0.0" />
10
 
11
 
12
  FastMCP can automatically convert FastAPI applications into MCP servers.
docs/patterns/openapi.mdx CHANGED
@@ -4,6 +4,9 @@ sidebarTitle: OpenAPI
4
  description: Generate MCP servers from OpenAPI specs
5
  icon: code-branch
6
  ---
 
 
 
7
 
8
  FastMCP can automatically generate an MCP server from an OpenAPI specification. Users only need to provide an OpenAPI specification (3.0 or 3.1) and an API client.
9
 
 
4
  description: Generate MCP servers from OpenAPI specs
5
  icon: code-branch
6
  ---
7
+ import { VersionBadge } from '/snippets/version-badge.mdx'
8
+
9
+ <VersionBadge version="2.0.0" />
10
 
11
  FastMCP can automatically generate an MCP server from an OpenAPI specification. Users only need to provide an OpenAPI specification (3.0 or 3.1) and an API client.
12
 
docs/patterns/{proxying.mdx → proxy.mdx} RENAMED
@@ -4,6 +4,9 @@ sidebarTitle: Proxying
4
  description: Use FastMCP to act as an intermediary or change transport for other MCP servers.
5
  icon: arrows-retweet
6
  ---
 
 
 
7
 
8
  FastMCP provides a powerful proxying capability that allows one FastMCP server instance to act as a frontend for another MCP server (which could be remote, running on a different transport, or even another FastMCP instance). This is achieved using the `FastMCP.from_client()` class method.
9
 
 
4
  description: Use FastMCP to act as an intermediary or change transport for other MCP servers.
5
  icon: arrows-retweet
6
  ---
7
+ import { VersionBadge } from '/snippets/version-badge.mdx'
8
+
9
+ <VersionBadge version="2.0.0" />
10
 
11
  FastMCP provides a powerful proxying capability that allows one FastMCP server instance to act as a frontend for another MCP server (which could be remote, running on a different transport, or even another FastMCP instance). This is achieved using the `FastMCP.from_client()` class method.
12
 
docs/servers/context.mdx CHANGED
@@ -4,6 +4,7 @@ sidebarTitle: Context
4
  description: Access MCP capabilities like logging, progress, and resources within your tools.
5
  icon: rectangle-code
6
  ---
 
7
 
8
  When defining FastMCP [tools](/servers/tools), your functions might need to interact with the underlying MCP session or access server capabilities. FastMCP provides the `Context` object for this purpose.
9
 
@@ -174,6 +175,8 @@ The returned content is typically accessed via `content_list[0].content` and can
174
 
175
  ### LLM Sampling
176
 
 
 
177
  Request the client's LLM to generate text based on provided messages. This is useful when your tool needs to leverage the LLM's capabilities to process data or generate responses.
178
 
179
  ```python
@@ -227,7 +230,7 @@ async def generate_example(concept: str, ctx: Context) -> str:
227
  return f"```python\n{code_example}\n```"
228
  ```
229
 
230
- See [Client Sampling](/clients/overview#llm-sampling) for more details on how clients handle these requests.
231
 
232
  ### Request Information
233
 
 
4
  description: Access MCP capabilities like logging, progress, and resources within your tools.
5
  icon: rectangle-code
6
  ---
7
+ import { VersionBadge } from '/snippets/version-badge.mdx'
8
 
9
  When defining FastMCP [tools](/servers/tools), your functions might need to interact with the underlying MCP session or access server capabilities. FastMCP provides the `Context` object for this purpose.
10
 
 
175
 
176
  ### LLM Sampling
177
 
178
+ <VersionBadge version="2.0.0" />
179
+
180
  Request the client's LLM to generate text based on provided messages. This is useful when your tool needs to leverage the LLM's capabilities to process data or generate responses.
181
 
182
  ```python
 
230
  return f"```python\n{code_example}\n```"
231
  ```
232
 
233
+ See [Client Sampling](/clients/client#llm-sampling) for more details on how clients handle these requests.
234
 
235
  ### Request Information
236
 
docs/servers/fastmcp.mdx CHANGED
@@ -225,159 +225,39 @@ The CLI can dynamically find and run FastMCP server objects in your files, but i
225
 
226
  ## Composing Servers
227
 
228
- FastMCP provides two methods for composing multiple servers together:
229
 
230
- 1. `import_server()`: One-time static import of components (async)
231
- 2. `mount()`: Live link delegating to subservers (sync)
232
-
233
- This allows you to organize large applications into logical components, reuse existing FastMCP servers, and create domain-specific servers that can be used independently or composed.
234
-
235
- ### Importing Subservers (Static Composition)
236
-
237
- The `import_server()` method performs a one-time copy of all components from a subserver into the main server with prefixed names:
238
 
239
  ```python
 
240
  from fastmcp import FastMCP
241
  import asyncio
242
 
243
- # Create the main server
244
- main_mcp = FastMCP(name="MainServer")
245
-
246
- # Create a domain-specific subserver
247
- weather_mcp = FastMCP(name="WeatherService")
248
-
249
- @weather_mcp.tool()
250
- def get_forecast(city: str) -> dict:
251
- """Get the weather forecast for a city."""
252
- return {"city": city, "forecast": "Sunny", "temperature": 72}
253
-
254
- # Create another domain-specific subserver
255
- calculator_mcp = FastMCP(name="CalculatorService")
256
-
257
- @calculator_mcp.tool()
258
- def add(a: float, b: float) -> float:
259
- """Add two numbers."""
260
- return a + b
261
-
262
- # Import the subservers with prefixes
263
- async def setup():
264
- await main_mcp.import_server("weather", weather_mcp)
265
- await main_mcp.import_server("calc", calculator_mcp)
266
-
267
- # Now main_mcp has access to both subservers' tools:
268
- # - "weather_get_forecast" (from weather_mcp)
269
- # - "calc_add" (from calculator_mcp)
270
-
271
- if __name__ == "__main__":
272
- # Run async setup
273
- asyncio.run(setup())
274
- # Then run the server
275
- main_mcp.run()
276
- ```
277
-
278
- #### How Import Works
279
-
280
- When you import a server with `await main_mcp.import_server(prefix, subserver)`:
281
-
282
- 1. All tools from the subserver are copied with prefixed names:
283
- - `tool_name` becomes `{prefix}_tool_name`
284
- - Default separator is `_`, but can be customized
285
-
286
- 2. All resources and resource templates are copied with prefixed URIs:
287
- - `resource://data` becomes `{prefix}+resource://data`
288
- - Default separator is `+`, but can be customized
289
-
290
- 3. All prompts are copied with prefixed names:
291
- - `prompt_name` becomes `{prefix}_prompt_name`
292
- - Default separator is `_`, but can be customized
293
-
294
- 4. This is a **one-time copy** - changes to the subserver after importing won't be reflected in the main server
295
-
296
- 5. The subserver's lifespan is **not** managed by the main server
297
 
298
- ### Mounting Subservers (Live Linking)
 
 
299
 
300
- The `mount()` method creates a live link between servers, delegating requests to the appropriate subserver:
301
-
302
- ```python
303
- from fastmcp import FastMCP
304
-
305
- # Create the main server
306
- main_mcp = FastMCP(name="MainServer")
307
-
308
- # Create a domain-specific subserver
309
- weather_mcp = FastMCP(name="WeatherService")
310
-
311
- @weather_mcp.tool()
312
- def get_forecast(city: str) -> dict:
313
- """Get the weather forecast for a city."""
314
- return {"city": city, "forecast": "Sunny", "temperature": 72}
315
-
316
- # Mount the subserver (sync operation)
317
- main_mcp.mount("weather", weather_mcp)
318
-
319
- # Later, add another tool to the subserver
320
- @weather_mcp.tool()
321
- def get_temperature(city: str) -> float:
322
- """Get the current temperature for a city."""
323
- return 72.5 # Example value
324
-
325
- # The new tool is automatically available through the main server
326
- # as "weather_get_temperature"
327
-
328
- if __name__ == "__main__":
329
- main_mcp.run()
330
  ```
331
 
332
- #### How Mounting Works
333
-
334
- When you mount a server with `main_mcp.mount(prefix, subserver)`:
335
-
336
- 1. A live link is created between the main server and the subserver
337
- 2. Requests for components matching the prefix are delegated to the subserver
338
- 3. Changes to the subserver are **immediately reflected** when accessing through the main server
339
- 4. The subserver's lifespan **is automatically managed** by the main server
340
 
341
- ### Customizing Separators
342
 
343
- For both `import_server()` and `mount()`, you can customize the separators used for naming:
344
 
345
  ```python
346
- # For import_server (async)
347
- await main_mcp.import_server(
348
- "weather",
349
- weather_mcp,
350
- tool_separator="-", # Use "weather-get_forecast" instead of "weather_get_forecast"
351
- resource_separator=".", # Use "weather.resource://data" instead of "weather+resource://data"
352
- prompt_separator=":" # Use "weather:prompt_name" instead of "weather_prompt_name"
353
- )
354
 
355
- # For mount (sync)
356
- main_mcp.mount(
357
- "weather",
358
- weather_mcp,
359
- tool_separator="-",
360
- resource_separator=".",
361
- prompt_separator=":"
362
- )
363
  ```
364
 
365
- <Warning>
366
- Some MCP clients may reject certain separators as invalid. For example, Claude Desktop does not support `/` in tool names.
367
- </Warning>
368
-
369
- ### Comparison
370
-
371
- | Feature | `import_server()` | `mount()` |
372
- |---------|------------------|-----------|
373
- | **Synchronicity** | Async (must be awaited) | Sync |
374
- | **Composition Type** | One-time copy (static) | Live link (dynamic) |
375
- | **Updates** | Changes to subserver NOT reflected | Changes immediately reflected |
376
- | **Lifespan** | Not managed | Automatically managed |
377
- | **Best For** | Bundling finalized components | Modular runtime composition |
378
-
379
- For more detailed examples, see the [Server Composition](/patterns/composition) guide.
380
-
381
  ## Server Configuration
382
 
383
  Server behavior, like transport settings (host, port for SSE) and how duplicate components are handled, can be configured via `ServerSettings`. These settings can be passed during `FastMCP` initialization, set via environment variables (prefixed with `FASTMCP_SERVER_`), or loaded from a `.env` file.
 
225
 
226
  ## Composing Servers
227
 
228
+ FastMCP supports composing multiple servers together using `import_server` (static copy) and `mount` (live link). This allows you to organize large applications into modular components or reuse existing servers.
229
 
230
+ See the [Server Composition](/patterns/composition) guide for full details, best practices, and examples.
 
 
 
 
 
 
 
231
 
232
  ```python
233
+ # Example: Importing a subserver
234
  from fastmcp import FastMCP
235
  import asyncio
236
 
237
+ main = FastMCP(name="Main")
238
+ sub = FastMCP(name="Sub")
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
239
 
240
+ @sub.tool()
241
+ def hello():
242
+ return "hi"
243
 
244
+ main.mount("sub", sub)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
245
  ```
246
 
247
+ ## Proxying Servers
 
 
 
 
 
 
 
248
 
249
+ FastMCP can act as a proxy for any MCP server (local or remote) using `FastMCP.from_client`, letting you bridge transports or add a frontend to existing servers. For example, you can expose a remote SSE server locally via stdio, or vice versa.
250
 
251
+ See the [Proxying Servers](/patterns/proxy) guide for details and advanced usage.
252
 
253
  ```python
254
+ from fastmcp import FastMCP, Client
 
 
 
 
 
 
 
255
 
256
+ backend = Client("http://example.com/mcp/sse")
257
+ proxy = FastMCP.from_client(backend, name="ProxyServer")
258
+ # Now use the proxy like any FastMCP server
 
 
 
 
 
259
  ```
260
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
261
  ## Server Configuration
262
 
263
  Server behavior, like transport settings (host, port for SSE) and how duplicate components are handled, can be configured via `ServerSettings`. These settings can be passed during `FastMCP` initialization, set via environment variables (prefixed with `FASTMCP_SERVER_`), or loaded from a `.env` file.
docs/snippets/version-badge.mdx ADDED
@@ -0,0 +1,8 @@
 
 
 
 
 
 
 
 
 
1
+ export const VersionBadge = ({ version }) => {
2
+ return (
3
+ <span className="version-badge">
4
+ <span className="badge-emoji" aria-hidden="true" style={{ marginRight: '0.3em', verticalAlign: 'middle' }}>✨</span>
5
+ New in version {version}
6
+ </span>
7
+ );
8
+ };
docs/style.css CHANGED
@@ -1,4 +1,4 @@
1
- /* Target only inline code elements, not code blocks */
2
  p code:not(pre code),
3
  table code:not(pre code),
4
  li code:not(pre code),
@@ -9,5 +9,45 @@ h4 code:not(pre code),
9
  h5 code:not(pre code),
10
  h6 code:not(pre code) {
11
  color: #f72585 !important;
12
- background-color: #ea54551a !important;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
13
  }
 
1
+ /* Code highlighting -- target only inline code elements, not code blocks */
2
  p code:not(pre code),
3
  table code:not(pre code),
4
  li code:not(pre code),
 
9
  h5 code:not(pre code),
10
  h6 code:not(pre code) {
11
  color: #f72585 !important;
12
+ background-color: rgba(247, 37, 133, 0.09);
13
+ }
14
+
15
+ /* Version badge -- display a badge with the current version of the documentation */
16
+ .version-badge {
17
+ display: inline-flex;
18
+ align-items: center;
19
+ gap: 0.3em;
20
+ padding: 0.32em 1em;
21
+ font-size: 0.92em;
22
+ font-weight: 600;
23
+ letter-spacing: 0.01em;
24
+ color: #7417e5;
25
+ background: #f3e8ff;
26
+ border: 1.5px solid #c084fc;
27
+ border-radius: 6px;
28
+ box-shadow: none;
29
+ vertical-align: middle;
30
+ position: relative;
31
+ transition: box-shadow 0.2s, transform 0.15s;
32
+ }
33
+
34
+ .version-badge:hover {
35
+ box-shadow: 0 2px 8px 0 rgba(160, 132, 252, 0.1);
36
+ transform: translateY(-1px) scale(1.03);
37
+ }
38
+
39
+ .dark .version-badge {
40
+ color: #fff;
41
+ background: #312e81;
42
+ border: 1.5px solid #a78bfa;
43
+ }
44
+
45
+ .badge-emoji {
46
+ font-size: 1.15em;
47
+ line-height: 1;
48
+ text-shadow: 0 1px 2px #fff, 0 0px 2px #c084fc;
49
+ }
50
+
51
+ .dark .badge-emoji {
52
+ text-shadow: 0 1px 2px #312e81, 0 0px 2px #a78bfa;
53
  }