Skip to content

Python: [Bug]: M365 agent sample fails at startup and in anonymous mode #9595

Description

Description

python/samples/05-end-to-end/m365-agent/m365_agent_demo/app.py does not start. Fixing each error only reveals the next one:

  1. aiohttp keyword. web.Application(middleware=[middleware_fn]) raises immediately. aiohttp's parameter is middlewares. The bulk middlewares → middleware rename in Python: [BREAKING]: removed display_name, renamed context_providers, middleware and AggregateContextProvider #3139 appears to have caught this third-party call.
    TypeError: Application.__init__() got an unexpected keyword argument 'middleware'. Did you mean 'middlewares'?
    
  2. No credential. build_agent() calls FoundryChatClient() with no credential:
    ValueError: Azure credential is required when using project_endpoint without a project_client.
    
    The README still documents OPENAI_API_KEY / OPENAI_CHAT_COMPLETION_MODEL from before the sample moved to FoundryChatClient.
  3. Anonymous mode with the current M365 Agents SDK (microsoft-agents-hosting-core 1.9.0; the PEP 723 header does not pin it):
    • CloudAdapter(connection_manager=None) raises HttpAdapterBase.__init__: Either channel_service_client_factory or connection_manager must be provided.
    • With authorization=None, AgentApplication raises The AgentApplication requires a connection_manager to initialize the Authorization instance.
    • ClaimsIdentity's signature is now (claims, authentication_type, security_token), so ClaimsIdentity({...}, False, "Anonymous") builds a non-anonymous identity. The adapter then tries to get an MSAL token and fails with TENANT_ID is not set in the configuration. (HTTP 500 on /api/messages).

05-end-to-end is in SAMPLE_TYPING_EXCLUDES. Pyright on the file reports (1) and the ClaimsIdentity argument mismatch.

Reproduction

I loaded the sample module and called create_app(load_app_config()) with USE_ANONYMOUS_MODE=true, using aiohttp's test client. The agent was replaced by an echo stub so no model call is made, and a local endpoint captured the bot's reply:

result
main TypeError from web.Application(middleware=...) at startup
with all fixes below GET /api/health 200, GET /api/messages 200, POST /api/messages 202, and the reply activity reaches the channel

Expected behavior

The sample starts locally in anonymous mode, as the README describes, and answers messages.

Proposed fix

  • web.Application(middlewares=[...]).
  • FoundryChatClient(credential=AzureCliCredential()), and README configuration for FOUNDRY_PROJECT_ENDPOINT / FOUNDRY_MODEL plus az login.
  • In anonymous mode, give the adapter a connection manager with an empty SERVICE_CONNECTION, and always build Authorization. Anonymous requests never request tokens.
  • Inject a claim-less ClaimsIdentity(authentication_type="Anonymous"), which the adapter treats as anonymous.

I have a PR ready. Authenticated (non-anonymous) mode keeps its existing configuration path. I could not test it without an Azure Bot registration.

Package Versions

agent-framework-core / agent-framework-foundry from main at 8be57da, aiohttp 3.14.3, microsoft-agents-hosting-core / -hosting-aiohttp / -authentication-msal 1.9.0.

Python Version

3.13

AI Assistance

Claude Code helped find the breakages, build the aiohttp test-client reproduction, and draft this report. I verified the reproduction locally.

Activity

  1. added
    pythonUsage: [Issues, PRs], Target: Python
    triageUsage: [Issues], Target: All issues that still need to be triaged
    on Oct 22, 2026
  2. added
    reproducedUsage: [Issues], Target: all issues that can be reproduced by the triage workflow
    on Oct 22, 2026
  3. github-actions commented on Oct 22, 2026

    @github-actions
    Contributor

    🤖 Automated triage reproduction notes (agent-authored — trust but verify)

    Agent analysis

    The primary failure is in python/samples/05-end-to-end/m365-agent/m365_agent_demo/app.py::create_app at line 201 when any configuration reaches web.Application(middleware=[...]); anonymous mode additionally fails in build_adapter when build_connection_manager returns None, and its middleware assigns False to ClaimsIdentity.authentication_type. Minimal repro: run the sample with USE_ANONYMOUS_MODE=true, or run uv run python/samples/05-end-to-end/m365-agent/test_issue_9595.py -q.

    • Failing test: python/samples/05-end-to-end/m365-agent/test_issue_9595.py
    • Files examined: python/samples/05-end-to-end/m365-agent/m365_agent_demo/app.py, python/samples/05-end-to-end/m365-agent/README.md, python/samples/05-end-to-end/m365-agent/test_issue_9595.py, python/packages/core/pyproject.toml, python/packages/foundry/pyproject.toml
    • Tests run: anonymous sample startup, test_create_app_accepts_anonymous_configuration, test_anonymous_mode_builds_adapter, test_anonymous_middleware_injects_anonymous_identity
    • Reported version: agent-framework-core/agent-framework-foundry main@8be57da33; aiohttp 3.14.3; microsoft-agents-* 1.9.0
    • Current version: agent-framework-core 1.22.0; agent-framework-foundry 1.15.0
  4. removed
    triageUsage: [Issues], Target: All issues that still need to be triaged
    on Oct 22, 2026
  5. eavanvalkenburg commented on Oct 26, 2026

    @eavanvalkenburg
    Member

    /plan Coordinate with existing PR #9598 to establish the smallest correct repair for the maintained M365 agent sample. Current main fails at aiohttp Application(middleware=...), omits the Foundry credential, and has incompatible connection-manager/Authorization/ClaimsIdentity setup for the documented anonymous mode. Validate the supported M365 Agents SDK contracts before choosing anonymous-mode construction; explicitly decide whether an empty SERVICE_CONNECTION is supported rather than treating the proposed placeholder as accepted design. Preserve authenticated behavior and require anonymous message handling to avoid token acquisition. Include offline startup/health/messages/reply tests with a stub agent, authenticated-path mocks, Foundry credential/configuration and README alignment. The work spans linked startup/authentication contracts, so do not mark it ready based only on zero SDK production changes. Keep #9601 run-command cleanup coordinated but separately scoped; this planning request is not implementation agreement or PR approval.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

pythonUsage: [Issues, PRs], Target: PythonreproducedUsage: [Issues], Target: all issues that can be reproduced by the triage workflow

Type

Projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions