Skip to content

Commit c79f5a5

Browse files
Python: improved MCP connect and additional samples (#12696)
### Motivation and Context <!-- Thank you for your contribution to the semantic-kernel repo! Please help reviewers and future users, providing the following information: 1. Why is this change required? 2. What problem does it solve? 3. What scenario does it contribute to? 4. If it fixes an open issue, please link to the issue here. --> Adding a sample using StreamableHTTPServer towards Github. Added a demo showing how to connect to a OAuth protected MCP server. Also some improvements in the connect logic for MCP. ### Description <!-- Describe your changes, the overall approach, the underlying design. These notes will help understanding how your code works. Thanks! --> ### Contribution Checklist <!-- Before submitting this PR, please make sure: --> - [x] The code builds clean without any errors or warnings - [x] The PR follows the [SK Contribution Guidelines](https://github.com/microsoft/semantic-kernel/blob/main/CONTRIBUTING.md) and the [pre-submission formatting script](https://github.com/microsoft/semantic-kernel/blob/main/CONTRIBUTING.md#development-scripts) raises no violations - [x] All unit tests pass, and I have added new tests where possible - [x] I didn't break anyone 😄
1 parent 9452cfe commit c79f5a5

File tree

19 files changed

+5809
-930
lines changed

19 files changed

+5809
-930
lines changed

python/pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -240,7 +240,7 @@ min-file-size = 1
240240

241241
[tool.bandit]
242242
targets = ["semantic_kernel"]
243-
exclude_dirs = ["tests"]
243+
exclude_dirs = ["tests", "samples/demos/mcp_with_oauth"]
244244

245245
[tool.flit.module]
246246
name = "semantic_kernel"
Lines changed: 126 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,126 @@
1+
# Copyright (c) Microsoft. All rights reserved.
2+
3+
import asyncio
4+
import os
5+
6+
from semantic_kernel.agents import ChatCompletionAgent, ChatHistoryAgentThread
7+
from semantic_kernel.connectors.ai.open_ai import AzureChatCompletion
8+
from semantic_kernel.connectors.mcp import MCPStreamableHttpPlugin
9+
10+
"""
11+
The following sample demonstrates how to create a chat completion agent that
12+
answers questions about Github using a Semantic Kernel Plugin from a MCP server.
13+
14+
It uses the Azure OpenAI service to create a agent, so make sure to
15+
set the required environment variables for the Azure AI Foundry service:
16+
- AZURE_OPENAI_CHAT_DEPLOYMENT_NAME
17+
- Optionally: AZURE_OPENAI_API_KEY
18+
If this is not set, it will try to use DefaultAzureCredential.
19+
20+
"""
21+
22+
23+
# Simulate a conversation with the agent
24+
USER_INPUTS = [
25+
"What are the latest 5 python issues in Microsoft/semantic-kernel?",
26+
"Are there any untriaged python issues?",
27+
"What is the status of issue #10785?",
28+
]
29+
30+
31+
async def main():
32+
# 1. Create the agent
33+
async with MCPStreamableHttpPlugin(
34+
name="Github",
35+
description="Github Plugin",
36+
url="https://api.githubcopilot.com/mcp/",
37+
headers={"Authorization": f"Bearer {os.getenv('GITHUB_PERSONAL_ACCESS_TOKEN')}"},
38+
) as github_plugin:
39+
agent = ChatCompletionAgent(
40+
service=AzureChatCompletion(),
41+
name="IssueAgent",
42+
instructions="Answer questions about the Microsoft semantic-kernel github project.",
43+
plugins=[github_plugin],
44+
)
45+
46+
for user_input in USER_INPUTS:
47+
# 2. Create a thread to hold the conversation
48+
# If no thread is provided, a new thread will be
49+
# created and returned with the initial response
50+
thread: ChatHistoryAgentThread | None = None
51+
52+
print(f"# User: {user_input}")
53+
# 3. Invoke the agent for a response
54+
response = await agent.get_response(messages=user_input, thread=thread)
55+
print(f"# {response.name}: {response} ")
56+
thread = response.thread
57+
58+
# 4. Cleanup: Clear the thread
59+
await thread.delete() if thread else None
60+
61+
62+
"""
63+
Sample output:
64+
GitHub MCP Server running on stdio
65+
# User: What are the latest 5 python issues in Microsoft/semantic-kernel?
66+
# IssueAgent: Here are the latest 5 Python issues in the
67+
[Microsoft/semantic-kernel](https://github.com/microsoft/semantic-kernel) repository:
68+
69+
1. **[Issue #11358](https://github.com/microsoft/semantic-kernel/pull/11358)**
70+
**Title:** Python: Bump Python version to 1.27.0 for a release.
71+
**Created by:** [moonbox3](https://github.com/moonbox3)
72+
**Created at:** April 3, 2025
73+
**State:** Open
74+
**Comments:** 1
75+
**Description:** Bump Python version to 1.27.0 for a release.
76+
77+
2. **[Issue #11357](https://github.com/microsoft/semantic-kernel/pull/11357)**
78+
**Title:** .Net: Version 1.45.0
79+
**Created by:** [markwallace-microsoft](https://github.com/markwallace-microsoft)
80+
**Created at:** April 3, 2025
81+
**State:** Open
82+
**Comments:** 0
83+
**Description:** Version bump for release 1.45.0.
84+
85+
3. **[Issue #11356](https://github.com/microsoft/semantic-kernel/pull/11356)**
86+
**Title:** .Net: Fix bug in sqlite filter logic
87+
**Created by:** [westey-m](https://github.com/westey-m)
88+
**Created at:** April 3, 2025
89+
**State:** Open
90+
**Comments:** 0
91+
**Description:** Fix bug in sqlite filter logic.
92+
93+
4. **[Issue #11355](https://github.com/microsoft/semantic-kernel/issues/11355)**
94+
**Title:** .Net: [MEVD] Validate that the collection generic key parameter corresponds to the model
95+
**Created by:** [roji](https://github.com/roji)
96+
**Created at:** April 3, 2025
97+
**State:** Open
98+
**Comments:** 0
99+
**Description:** We currently have validation for the TKey generic type parameter passed to the collection type,
100+
and we have validation for the key property type on the model.
101+
102+
5. **[Issue #11354](https://github.com/microsoft/semantic-kernel/issues/11354)**
103+
**Title:** .Net: How to add custom JsonSerializer on a builder level
104+
**Created by:** [PawelStadnicki](https://github.com/PawelStadnicki)
105+
**Created at:** April 3, 2025
106+
**State:** Open
107+
**Comments:** 0
108+
**Description:** Inquiry about adding a custom JsonSerializer for handling F# types within the SDK.
109+
110+
If you need more details about a specific issue, let me know!
111+
# User: Are there any untriaged python issues?
112+
# IssueAgent: There are no untriaged Python issues in the Microsoft semantic-kernel repository.
113+
# User: What is the status of issue #10785?
114+
# IssueAgent: The status of issue #10785 in the Microsoft Semantic Kernel repository is **open**.
115+
116+
- **Title**: Port dotnet feature: Create MCP Sample
117+
- **Created at**: March 4, 2025
118+
- **Comments**: 0
119+
- **Labels**: python
120+
121+
You can view the issue [here](https://github.com/microsoft/semantic-kernel/issues/10785).
122+
"""
123+
124+
125+
if __name__ == "__main__":
126+
asyncio.run(main())
Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
The server code and some of the agent code for this samples comes from: https://github.com/modelcontextprotocol/python-sdk/tree/main/examples/servers/simple-auth
2+
in order to demonstrate connecting with OAuth to a MCP server with SK.
3+
4+
# MCP OAuth Authentication Demo
5+
6+
This example demonstrates OAuth 2.0 authentication with the Model Context Protocol using **separate Authorization Server (AS) and Resource Server (RS)** to comply with the new RFC 9728 specification.
7+
8+
---
9+
10+
## Running the Servers
11+
12+
### Step 1: Start Authorization Server
13+
14+
```bash
15+
# Navigate to the simple-auth directory
16+
cd samples/demos/mcp_with_oauth/server
17+
18+
# Start Authorization Server on port 9000
19+
uv run mcp-simple-auth-as --port=9000
20+
```
21+
22+
**What it provides:**
23+
24+
- OAuth 2.0 flows (registration, authorization, token exchange)
25+
- Simple credential-based authentication (no external provider needed)
26+
- Token introspection endpoint for Resource Servers (`/introspect`)
27+
28+
---
29+
30+
### Step 2: Start Resource Server (MCP Server)
31+
32+
```bash
33+
# In another terminal, navigate to the simple-auth directory
34+
cd samples/demos/mcp_with_oauth/server
35+
36+
# Start Resource Server on port 8001, connected to Authorization Server
37+
uv run mcp-simple-auth-rs --port=8001 --auth-server=http://localhost:9000 --transport=streamable-http
38+
39+
# With RFC 8707 strict resource validation (recommended for production)
40+
uv run mcp-simple-auth-rs --port=8001 --auth-server=http://localhost:9000 --transport=streamable-http --oauth-strict
41+
42+
```
43+
44+
### Step 3: Test with Client
45+
46+
Either have Azure settings setup in your global venv, or add a `.env` file in `samples/demos/mcp_with_oauth/agent` with the following content:
47+
```bash
48+
AZURE_OPENAI_ENDPOINT=
49+
AZURE_OPENAI_CHAT_DEPLOYMENT_NAME=
50+
```
51+
52+
and then:
53+
54+
```bash
55+
cd samples/demos/mcp_with_oauth
56+
# Start agent with streamable HTTP plugin
57+
uv --env-file .env run agent
58+
```
59+
60+
or open file main.py in samples/demos/mcp_with_oauth/agent and run it in your IDE.
61+
62+
For more details on how the server and auth flows work, see https://github.com/modelcontextprotocol/python-sdk/tree/main/examples/servers/simple-auth

python/samples/demos/mcp_with_oauth/agent/__init__.py

Whitespace-only changes.

0 commit comments

Comments
 (0)