Skip to content

Conversation

@dav-rob
Copy link

@dav-rob dav-rob commented Jun 19, 2025

Summary

The initial codebase had no Weave tracing applied to the async chat_completions() function as would be expected for monitoring LLM interactions. When implementing @weave.op() decorators to enable tracing, we discovered significant issues with Weave context propagation in FastAPI async environments that prevented proper trace generation.

This PR resolves these issues by implementing a robust FastAPI middleware solution that enables proper Weave tracing of async chat completions.

Key Changes

  • WeaveContextMiddleware: New FastAPI middleware that copies synchronous Weave context into asynchronous FastAPI request contexts using contextvars.copy_context()
  • Single initialization: Weave now initializes once at server startup in the lifespan function
  • Environment loading: Automatic .env file loading on startup (no manual source .env needed)
  • Performance optimization: Removed per-request weave.init() overhead from generate_ui_completion
  • Documentation: Comprehensive testing guide and technical implementation details

Technical Details

Problem Discovered: FastAPI request handlers run in isolated async contexts where context variables set by the original weave.init() at server startup are not available, causing @weave.op() decorators to fail silently.

Solution: The middleware copies the synchronous Weave context (established at startup) into each asynchronous FastAPI request context, ensuring proper trace propagation.

class WeaveContextMiddleware:
    async def __call__(self, scope, receive, send):
        if scope["type"] == "http":
            # Copy synchronous context into async request context
            context = copy_context()
            return await context.run(self._handle_request, scope, receive, send)
        return await self.app(scope, receive, send)

Benefits

  • Single Weave initialization at server startup (efficient)
  • No performance overhead from repeated weave.init() calls
  • Proper async context propagation via FastAPI middleware
  • Full tracing functionality maintained for all @weave.op() decorated functions
  • Automatic environment loading - no manual source .env required

Verification

Successfully tested with evidence of proper trace generation:

weave: View Weave data at https://wandb.ai/[entity]/[project]/weave  # Single init
weave: 🍩 https://wandb.ai/[entity]/[project]/r/call/[call-id]      # Per-request traces

Files Changed

  • openui/server.py: Added WeaveContextMiddleware and lifespan Weave initialization
  • openui/__main__.py: Enhanced dev mode Weave initialization
  • CLAUDE.md: Comprehensive testing documentation and technical notes
  • .env.example: Template for environment configuration
  • async_issues.md: Detailed problem analysis and solution architecture

This addresses a sophisticated async context issue common to FastAPI + tracing library combinations and provides the proper architectural solution for robust Weave tracing of chat completions.

🤖 Generated with Claude Code

David Roberts and others added 5 commits June 19, 2025 23:05
Add comprehensive Weave integration to track AI-powered UI generation:

Key changes:
- Extract LLM logic into @weave.op() decorated function for proper tracing
- Set WEAVE_PRINT_CALL_LINK=true to enable console trace output
- Initialize Weave context within traced function for FastAPI compatibility
- Add development documentation and POC example

Technical details:
1. FastAPI decorator conflict: Separated AI logic from route handler
2. Missing environment variable: Set WEAVE_PRINT_CALL_LINK for console output
3. Context initialization: Call weave.init() within function for proper async/FastAPI tracing

This enables full observability of UI generation requests with clickable
trace links (🍩) in dev mode logs, matching weave_poc.py behavior.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
…tion

- Add WeaveContextMiddleware to propagate Weave context across async requests
- Remove weave.init() overhead from generate_ui_completion function
- Update lifespan to initialize Weave once at server startup
- Add comprehensive Playwright testing guide to CLAUDE.md
- Document the implemented solution and remove outdated workaround notes
- Create async_issues.md with detailed problem analysis and solution architecture

Tested successfully: Weave trace URLs now generate without per-request initialization overhead.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
- Document complete test procedure to verify middleware works
- Include success/failure indicators with exact log patterns
- Add debugging steps for troubleshooting trace issues
- Provide clear verification that context propagation is working

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
@socket-security
Copy link

socket-security bot commented Jun 20, 2025

Caution

Review the following alerts detected in dependencies.

According to your organization's Security Policy, you must resolve all "Block" alerts before proceeding. It is recommended to resolve "Warn" alerts too. Learn more about Socket for GitHub.

Action Severity Alert (click for details)
Block Critical
npm/openui@1.0.0 is a Possible typosquat attack.

Did you mean: openuai

From: frontend/package-lock.jsonnpm/openui@1.0.0

ℹ Read more on: This package | This alert | What is a typosquat?

Next steps: Take a moment to review the security alert above. Review the linked package source code to understand the potential risk. Ensure the package is not malicious before proceeding. If you're unsure how to proceed, reach out to your security team or ask the Socket team for help at support@socket.dev.

Suggestion: Use care when consuming similarly named packages and ensure that you did not intend to consume a different package. Malicious packages often publish using similar names as existing popular packages.

Mark the package as acceptable risk. To ignore this alert only in this pull request, reply with the comment @SocketSecurity ignore npm/openui@1.0.0. You can also ignore all packages with @SocketSecurity ignore-all. To ignore an alert for all future pull requests, use Socket's Dashboard to change the triage state of this alert.

Warn High
npm/caniuse-lite@1.0.30001723 has a License Policy Violation.

License: CC-BY-4.0 (npm metadata)

License: CC-BY-4.0 (package/LICENSE)

License: CC-BY-4.0 (package/package.json)

From: frontend/package-lock.jsonnpm/caniuse-lite@1.0.30001723

ℹ Read more on: This package | This alert | What is a license policy violation?

Next steps: Take a moment to review the security alert above. Review the linked package source code to understand the potential risk. Ensure the package is not malicious before proceeding. If you're unsure how to proceed, reach out to your security team or ask the Socket team for help at support@socket.dev.

Suggestion: Find a package that does not violate your license policy or adjust your policy to allow this package's license.

Mark the package as acceptable risk. To ignore this alert only in this pull request, reply with the comment @SocketSecurity ignore npm/caniuse-lite@1.0.30001723. You can also ignore all packages with @SocketSecurity ignore-all. To ignore an alert for all future pull requests, use Socket's Dashboard to change the triage state of this alert.

Warn High
npm/playwright@1.53.0 has a License Policy Violation.

License: CC-BY-4.0 (package/ThirdPartyNotices.txt)

License: CC-BY-4.0 (package/ThirdPartyNotices.txt)

License: CC-BY-4.0 (package/ThirdPartyNotices.txt)

License: CC-BY-4.0 (package/ThirdPartyNotices.txt)

License: CC-BY-4.0 (package/ThirdPartyNotices.txt)

From: frontend/package-lock.jsonnpm/playwright@1.53.0

ℹ Read more on: This package | This alert | What is a license policy violation?

Next steps: Take a moment to review the security alert above. Review the linked package source code to understand the potential risk. Ensure the package is not malicious before proceeding. If you're unsure how to proceed, reach out to your security team or ask the Socket team for help at support@socket.dev.

Suggestion: Find a package that does not violate your license policy or adjust your policy to allow this package's license.

Mark the package as acceptable risk. To ignore this alert only in this pull request, reply with the comment @SocketSecurity ignore npm/playwright@1.53.0. You can also ignore all packages with @SocketSecurity ignore-all. To ignore an alert for all future pull requests, use Socket's Dashboard to change the triage state of this alert.

Warn Medium
npm/unrs-resolver@1.9.0 has Install scripts.

Install script: postinstall

Source: napi-postinstall unrs-resolver 1.9.0 check

From: frontend/package-lock.jsonnpm/unrs-resolver@1.9.0

ℹ Read more on: This package | This alert | What is an install script?

Next steps: Take a moment to review the security alert above. Review the linked package source code to understand the potential risk. Ensure the package is not malicious before proceeding. If you're unsure how to proceed, reach out to your security team or ask the Socket team for help at support@socket.dev.

Suggestion: Packages should not be running non-essential scripts during install and there are often solutions to problems people solve with install scripts that can be run at publish time instead.

Mark the package as acceptable risk. To ignore this alert only in this pull request, reply with the comment @SocketSecurity ignore npm/unrs-resolver@1.9.0. You can also ignore all packages with @SocketSecurity ignore-all. To ignore an alert for all future pull requests, use Socket's Dashboard to change the triage state of this alert.

View full report

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant