Repository navigation
Conversation
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
🤖 CI report
|
| File | Patch | Uncovered changed lines |
|---|---|---|
posthog/api/integration.py |
33.3% | 3016–3017, 3019, 3022 |
posthog/api/team/team_config.py |
33.3% | 443–444 |
products/workflows/backend/services/transactional_email_workflows.py |
72.2% | 165–166, 171, 181, 193 |
posthog/models/integration/email.py |
81.2% | 76, 95, 240 |
products/messaging/backend/services/transactional_email.py |
85.7% | 604 |
🤖 Agents: add a test only if an uncovered line exposes a realistic regression that existing tests miss. Otherwise explain why no new test is needed under "How did you test this code?". Gap list: the patch-coverage artifact on this run (gh run download 231709626052783 -n patch-coverage), or the coverage-data block at the end of this comment.
Per-product line coverage (touched products)
| Product | Coverage | Lines |
|---|---|---|
platform_features |
██░░░░░░░░░░░░░░░░░░ 12.1% |
7 / 58 |
data_tools |
████████████░░░░░░░░ 60.9% |
95 / 156 |
warehouse_sources_queue |
█████████████░░░░░░░ 65.2% |
2,161 / 3,314 |
demo |
██████████████░░░░░░ 71.2% |
1,982 / 2,783 |
knowledge_writer |
███████████████░░░░░ 76.5% |
1,289 / 1,685 |
batch_exports |
█████████████████░░░ 82.6% |
24,173 / 29,278 |
engineering_analytics |
█████████████████░░░ 85.5% |
12,384 / 14,482 |
ml_inference |
█████████████████░░░ 86.3% |
524 / 607 |
commands |
█████████████████░░░ 86.5% |
1,645 / 1,901 |
mcp_analytics |
█████████████████░░░ 86.8% |
6,235 / 7,180 |
posthog_ai |
██████████████████░░ 88.2% |
4,502 / 5,104 |
apm |
██████████████████░░ 88.2% |
1,973 / 2,236 |
notebooks |
██████████████████░░ 88.8% |
15,454 / 17,409 |
mcp_registry |
██████████████████░░ 89.0% |
1,596 / 1,794 |
dashboards |
██████████████████░░ 89.5% |
8,130 / 9,087 |
product_tours |
██████████████████░░ 89.6% |
1,355 / 1,512 |
warehouse_suggestions |
██████████████████░░ 90.2% |
3,879 / 4,300 |
ai_gateway |
██████████████████░░ 90.3% |
971 / 1,075 |
cohorts |
██████████████████░░ 90.5% |
9,621 / 10,633 |
visual_review |
██████████████████░░ 90.7% |
9,870 / 10,883 |
signals |
██████████████████░░ 90.8% |
105,661 / 116,317 |
data_warehouse |
██████████████████░░ 91.1% |
15,703 / 17,236 |
canvas |
██████████████████░░ 91.2% |
8,205 / 8,996 |
cdp |
██████████████████░░ 91.4% |
10,806 / 11,817 |
today |
██████████████████░░ 91.5% |
3,975 / 4,346 |
tasks |
██████████████████░░ 91.5% |
85,362 / 93,291 |
autoresearch |
██████████████████░░ 91.6% |
12,047 / 13,151 |
metrics |
██████████████████░░ 91.9% |
11,564 / 12,581 |
streamlit_apps |
██████████████████░░ 91.9% |
3,170 / 3,448 |
data_modeling |
██████████████████░░ 92.0% |
12,440 / 13,526 |
business_knowledge |
██████████████████░░ 92.1% |
10,871 / 11,801 |
managed_warehouse |
██████████████████░░ 92.3% |
14,337 / 15,533 |
wizard |
██████████████████░░ 92.3% |
7,031 / 7,616 |
conversations |
██████████████████░░ 92.3% |
31,407 / 34,013 |
review_hog |
██████████████████░░ 92.4% |
18,136 / 19,636 |
early_access_features |
██████████████████░░ 92.5% |
1,339 / 1,448 |
error_tracking |
███████████████████░ 92.5% |
20,776 / 22,453 |
actions |
███████████████████░ 92.8% |
1,360 / 1,466 |
notifications |
███████████████████░ 92.8% |
1,219 / 1,313 |
slack_app |
███████████████████░ 92.9% |
24,198 / 26,051 |
alerts_platform |
███████████████████░ 92.9% |
9,006 / 9,695 |
alerts |
███████████████████░ 93.2% |
12,009 / 12,885 |
stamphog |
███████████████████░ 93.2% |
10,903 / 11,697 |
webmcp |
███████████████████░ 93.3% |
277 / 297 |
ai_training |
███████████████████░ 93.3% |
598 / 641 |
web_analytics |
███████████████████░ 93.5% |
27,004 / 28,886 |
surveys |
███████████████████░ 93.5% |
7,456 / 7,973 |
exports |
███████████████████░ 93.6% |
4,394 / 4,696 |
approvals |
███████████████████░ 93.7% |
5,004 / 5,343 |
cross_project_dashboards |
███████████████████░ 93.7% |
858 / 916 |
workflows |
███████████████████░ 93.8% |
28,971 / 30,897 |
context_layer |
███████████████████░ 93.8% |
4,066 / 4,333 |
marketing_analytics |
███████████████████░ 93.9% |
22,170 / 23,617 |
authorization |
███████████████████░ 94.0% |
671 / 714 |
mcp_store |
███████████████████░ 94.0% |
9,324 / 9,920 |
billing_alerts |
███████████████████░ 94.0% |
2,322 / 2,470 |
messaging |
███████████████████░ 94.1% |
8,884 / 9,445 |
ai_observability |
███████████████████░ 94.1% |
34,380 / 36,546 |
customer_analytics |
███████████████████░ 94.1% |
30,872 / 32,803 |
managed_migrations |
███████████████████░ 94.1% |
1,877 / 1,994 |
legal_documents |
███████████████████░ 94.3% |
2,313 / 2,453 |
replay_vision |
███████████████████░ 94.4% |
33,357 / 35,351 |
logs |
███████████████████░ 94.4% |
19,543 / 20,692 |
aeo |
███████████████████░ 94.6% |
3,138 / 3,318 |
access_control |
███████████████████░ 94.7% |
8,515 / 8,991 |
reminders |
███████████████████░ 94.8% |
782 / 825 |
experiments |
███████████████████░ 94.8% |
45,809 / 48,311 |
warehouse_sources |
███████████████████░ 95.0% |
141,344 / 148,847 |
growth |
███████████████████░ 95.0% |
11,589 / 12,202 |
endpoints |
███████████████████░ 95.0% |
9,720 / 10,234 |
annotations |
███████████████████░ 95.0% |
1,097 / 1,155 |
skills |
███████████████████░ 95.2% |
7,656 / 8,043 |
uptime_monitoring |
███████████████████░ 95.3% |
306 / 321 |
data_catalog |
███████████████████░ 95.6% |
4,740 / 4,956 |
subscriptions |
███████████████████░ 95.7% |
14,021 / 14,654 |
ui_customization |
███████████████████░ 95.7% |
714 / 746 |
product_analytics |
███████████████████░ 95.8% |
31,105 / 32,468 |
feature_flags |
███████████████████░ 95.8% |
30,674 / 32,018 |
revenue_analytics |
███████████████████░ 95.9% |
1,877 / 1,958 |
data_quality |
███████████████████░ 96.0% |
8,564 / 8,918 |
tracing |
███████████████████░ 96.5% |
4,572 / 4,739 |
account_audits |
███████████████████░ 96.8% |
783 / 809 |
security |
███████████████████░ 96.8% |
1,597 / 1,650 |
pulse |
███████████████████░ 97.3% |
2,036 / 2,093 |
analytics_platform |
████████████████████ 98.0% |
2,953 / 3,013 |
groups |
████████████████████ 98.1% |
1,623 / 1,655 |
field_notes |
████████████████████ 98.3% |
172 / 175 |
Report-only. Patch coverage = changed backend lines covered vs origin/master. Sorted lowest first.
Known gaps: lines covered only by Temporal tests show as uncovered; core line numbers may drift if master changed the same file.
❌ Hogbox preview — build failed
The preview didn't come up for commit c0e60dd. See the build log for the failing step. It'll retry on the next push.
Previews are optional and never block merging. A failure here is often a hogland or tailnet hiccup rather than anything in your PR, so the check stays green and this section is the status.
…split/managed-sender-guards
…split/managed-sender-guards Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…rors A transactional email that names the sandbox sender now says the sandbox sender can't send transactional email, instead of asking for a verified domain. The setup guide's Channel step no longer counts the sandbox sender as the team's own channel. The docs name WORKFLOWS_SANDBOX_SENDER_DOMAIN. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… update Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Master added sends from code (#127123), which pick any verified sender. The sandbox row is stored as verified, so the code-send choice now skips it like the template path does. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…split/managed-sender-guards
|
Risk: No findings This delta replaces the upsert in EmailIntegration.create_native_integration with a domain-scoped advisory lock, an explicit duplicate-sender rejection, and a plain insert with an IntegrityError backstop, so a re-submitted sender can no longer silently overwrite an existing row (resetting verified and created_by) and concurrent cross-organization domain claims now serialize. I traced the locking, the duplicate-check/insert value flow, the sandbox-sender interplay, and the error messages, and found no new security issue. Sentinel reviewed |
There was a problem hiding this comment.
Not approved yet — waiting on the conditions below.
PostHog Review is still reviewing this commit, so stamphog does not approve yet. The review runs again on the next push, or you can re-request it once that review finishes.
Gate mechanics and policy version
| Gate | Result | |
|---|---|---|
| prerequisites | ✓ | all clear |
| deny-list | ✓ | no deny categories matched |
| size | ✓ | 129L, 12F substantive, 424L/21F incl. docs/generated/snapshots — within ceiling |
| tier | ✓ | T1-agent / T1d-complex (424L, 21F, cross-cutting, feat) |
| stamphog 2.7.0 | .stamphog/policy.yml @ e3dc001 · reviewed head e3dc001 |
…split/managed-sender-guards
…split/managed-sender-guards
Covers the sandbox-sender message on make-transactional and template updates, runs the real tenant-state sync in the sweep test with only SES mocked, and drops the forwarding is_sandbox_sender property. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…split/managed-sender-guards Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…split/managed-sender-guards Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
New commits were pushed — dismissing the stamphog approval from an earlier head. Re-add the trigger label to request a fresh review.
…split/managed-sender-guards
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…t state The mocked SES client returned a MagicMock for the tenant lookup, so the sweep went on to apply mock values to the own sender's team. Return None so the test only checks which teams the sweep looks up. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…split/managed-sender-guards # Conflicts: # products/workflows/backend/services/data_suggestions/team_context.py
…split/managed-sender-guards
New commits were pushed — dismissing the stamphog approval from an earlier head. Re-add the trigger label to request a fresh review.
…split/managed-sender-guards Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
New commits were pushed — dismissing the stamphog approval from an earlier head. Re-add the trigger label to request a fresh review.
|
Note 🤖 Claude Opus 5.5 responding on behalf of Michael Replaced by #131840 in the isolated sandbox rebuild. |

Problem
Merge danger
Warning
🟡 Merge risk: medium · two-way door (merge-risk rubric)
sandbox, which no row has until #128949. The domain block is off while its setting is empty. Tests pair each refusal with the own-sender path.git revertthe merge commit. Nothing to clean up: this PR creates no rows.Changes
provider == "ses"filters. New tests pin that.WORKFLOWS_SANDBOX_SENDER_DOMAINjoinsposthog/settings/ses.py, because the domain check reads it.How did you test this code?
Test rationale: each group catches a managed row that a team can change, or that leaks into a feature built for own senders. The tests create the sandbox row directly, before #128949 adds the endpoint.
test_sandbox_sender.py: every refused action, and the reserved domain with its subdomains.test_sandbox_sender_lifecycle.py: the sweep runs the real synchronizer with only SES mocked, and looks up only the team with an ownsessender.Earlier local run, at 3aa6850 to e92a320 (not saved as proof)
sender_not_verifiedCI report findings
test_sandbox_sender.py(PATCHemail/, verify, status, delete) andtest_team_workflows_config.py(sandbox sender as the default). The coverage run does not attribute theseproducts/workflowstests to theposthog/lines.Release status
Docs update
docs/internal/workflows-email-sending-tiers.mdgains a "Sandbox sender" section with the guards andWORKFLOWS_SANDBOX_SENDER_DOMAIN.🤖 Agent context
Autonomy: Human-driven (agent-assisted)
Agent: Claude Code, Claude Opus 5.5
Skills:
/improving-drf-endpoints,/writing-tests,/stacking-prs,/writing-pr-descriptions,/qa-swarmDecisions for the whole sandbox sender stack
sandbox, created only by PostHog codeWORKFLOWS_SANDBOX_SENDER_ENABLED, no feature flag in CDP Node codeNo open questions.
More context for AI agents
SANDBOX_EMAIL_INTEGRATION_IDand the domain setting live here, so the guards stand without the endpoint.ensure_user_managed()calls at each management entry point, not a throwingEmailIntegrationconstructor, so read-only uses of the adapter keep working.is_sandbox_senderproperty and made the sweep test real (4742c86, ba1b846, e2a237c).perform_destroyandemail_updateinposthog/api/integration.py, andposthog/models/integration/email.py.🤖 Generated with Claude Code