Monitoring Plans
Monitoring plans track deployment risk for pull requests. When a PR is merged and deployed, Firetiger monitors the deployment for unintended effects based on a plan written by an agent during code review.
This page covers three services: MonitoringPlanService for plan lifecycle and status updates, ChangeMonitorNotificationsService for personal Change Monitor notification setup, and MonitoringRunService (legacy) for backward-compatible run access.
Services: firetiger.monitoring_plans.v1.MonitoringPlanService, firetiger.monitoring_plans.v1.ChangeMonitorNotificationsService, firetiger.monitoring_plans.v1.MonitoringRunService
Resource name patterns: monitoring-plans/{plan_id} and monitoring-plans/{plan_id}/runs/{run_id}
Access: Read-write for status updates, read-only for externally managed monitoring state
Resource types: Monitoring Plan, Monitoring Run
Example flow
List recent monitoring plans, then fetch details for a specific one.
1. List monitoring plans
curl -X POST "https://api.cloud.firetiger.com/firetiger.monitoring_plans.v1.MonitoringPlanService/ListMonitoringPlans" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{"page_size": 5, "order_by": "create_time desc"}'
{
"monitoringPlans": [
{
"name": "monitoring-plans/plan-abc123",
"origin": {
"repository": "acme-corp/backend",
"prNumber": 42,
"prTitle": "Fix auth service timeout handling",
"prAuthorGithubLogin": "engineer",
"prAuthorGithubUserId": "1234567"
},
"planSummary": "Fixes auth service timeout handling to prevent cascading failures during peak traffic.",
"intendedEffects": [
"Auth service p99 latency stays under 500ms at peak (24h baseline 480ms).",
"Cascading 503s attributed to auth timeouts drop to zero."
],
"risks": [
"Masked failures: watch auth 5xx rate; alert if > 1% sustained for 5m."
],
"createTime": "2024-06-15T14:30:00Z"
}
],
"nextPageToken": ""
}
2. Get plan details
curl -X POST "https://api.cloud.firetiger.com/firetiger.monitoring_plans.v1.MonitoringPlanService/GetMonitoringPlan" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{"name": "monitoring-plans/plan-abc123"}'
{
"monitoringPlan": {
"name": "monitoring-plans/plan-abc123",
"origin": {
"repository": "acme-corp/backend",
"prNumber": 42,
"prUrl": "https://github.com/acme-corp/backend/pull/42",
"headSha": "a1b2c3d4e5f6",
"prTitle": "Fix auth service timeout handling",
"prAuthorGithubLogin": "engineer",
"prAuthorGithubUserId": "1234567"
},
"activation": {
"mergeSha": "f6e5d4c3b2a1",
"environments": ["production"]
},
"planContent": "## Intended Effect\nFixes timeout handling in auth service...",
"planSummary": "Fixes auth service timeout handling to prevent cascading failures during peak traffic.",
"intendedEffects": [
"Auth service p99 latency stays under 500ms at peak (24h baseline 480ms).",
"Cascading 503s attributed to auth timeouts drop to zero."
],
"risks": [
"Masked failures: watch auth 5xx rate; alert if > 1% sustained for 5m."
],
"notificationChannel": "#deploy-alerts",
"authorSession": "agents/plan-author/sessions/sess-xyz",
"createTime": "2024-06-15T14:30:00Z",
"updateTime": "2024-06-15T15:00:00Z",
"deployments": [
{
"environment": "production",
"deployment": "deployments/dep-789",
"deployTime": "2024-06-15T16:00:00Z",
"intendedEffectConfirmed": true,
"outcome": "MONITORING_OUTCOME_NO_ISSUE",
"completeTime": "2024-06-15T17:30:00Z"
}
],
"lastCheckTime": "2024-06-15T17:30:00Z"
}
}
Methods
| Method | Service | Description |
|---|---|---|
| GetMonitoringPlan | MonitoringPlanService | Retrieve a monitoring plan by name |
| ListMonitoringPlans | MonitoringPlanService | List monitoring plans with filtering and pagination |
| PostPlanComment | MonitoringPlanService | Post a monitoring update to the originating pull request and configured user DMs |
| PostInProgressComment | MonitoringPlanService | Post the “working on a monitoring plan” placeholder comment and record it for in-place finalization |
| ActivateFromDeployment | MonitoringPlanService | Correlate a successful deployment to merged monitoring plans and activate the ones whose change shipped (deployment-hook driven) |
| ActivatePlanFromDeployments | MonitoringPlanService | Activate one already-merged plan against its repository’s current deployments (the dual of ActivateFromDeployment; plan-creation driven) |
| RecordPullRequestFixLink | MonitoringPlanService | Persist a PR-to-issue fix link and reconcile it against existing deployments |
| RecordPullRequestUpdated | MonitoringPlanService | Extract closing-keyword issue refs from current PR text and persist them as fix links |
| GetMyChangeMonitorSetup | ChangeMonitorNotificationsService | Read the current user’s Change Monitor notification setup |
| UpdateMyChangeMonitorNotificationPreference | ChangeMonitorNotificationsService | Update the current user’s Change Monitor Slack DM toggle and Impact Report email opt-out |
| VerifyMyChangeMonitorSlackDM | ChangeMonitorNotificationsService | Send a test Slack DM and store the verified Slack destination |
| GetMonitoringRun | MonitoringRunService | Retrieve a monitoring run by name |
| ListMonitoringRuns | MonitoringRunService | List monitoring runs for a plan |
GetMonitoringPlan
Retrieve a monitoring plan by name.
POST /firetiger.monitoring_plans.v1.MonitoringPlanService/GetMonitoringPlan
Request body
| Field | Type | Required | Description |
|---|---|---|---|
name |
string | Yes | Resource name of the monitoring plan |
Example
curl -X POST "https://api.cloud.firetiger.com/firetiger.monitoring_plans.v1.MonitoringPlanService/GetMonitoringPlan" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{"name": "monitoring-plans/plan-abc123"}'
Response
{
"monitoringPlan": {
"name": "monitoring-plans/plan-abc123",
"origin": {
"repository": "acme-corp/backend",
"prNumber": 42,
"prUrl": "https://github.com/acme-corp/backend/pull/42",
"headSha": "a1b2c3d4e5f6",
"prTitle": "Fix auth service timeout handling",
"prAuthorGithubLogin": "engineer",
"prAuthorGithubUserId": "1234567"
},
"activation": {
"mergeSha": "f6e5d4c3b2a1",
"environments": ["production"]
},
"planContent": "## Intended Effect\nFixes timeout handling in auth service...",
"planSummary": "Fixes auth service timeout handling to prevent cascading failures during peak traffic.",
"intendedEffects": [
"Auth service p99 latency stays under 500ms at peak (24h baseline 480ms).",
"Cascading 503s attributed to auth timeouts drop to zero."
],
"risks": [
"Masked failures: watch auth 5xx rate; alert if > 1% sustained for 5m."
],
"notificationChannel": "#deploy-alerts",
"authorSession": "agents/plan-author/sessions/sess-xyz",
"createTime": "2024-06-15T14:30:00Z",
"updateTime": "2024-06-15T15:00:00Z",
"deployments": [
{
"environment": "production",
"deployment": "deployments/dep-789",
"deployTime": "2024-06-15T16:00:00Z",
"intendedEffectConfirmed": true,
"outcome": "MONITORING_OUTCOME_NO_ISSUE",
"completeTime": "2024-06-15T17:30:00Z"
}
],
"lastCheckTime": "2024-06-15T17:30:00Z"
}
}
ListMonitoringPlans
List monitoring plans with optional filtering and pagination.
POST /firetiger.monitoring_plans.v1.MonitoringPlanService/ListMonitoringPlans
Request body
| Field | Type | Required | Description |
|---|---|---|---|
filter |
string | No | Filter expression |
order_by |
string | No | Field to sort by (e.g. create_time desc) |
page_size |
integer | No | Maximum results per page |
page_token |
string | No | Token for the next page of results |
show_deleted |
boolean | No | Include soft-deleted monitoring plans |
Example
curl -X POST "https://api.cloud.firetiger.com/firetiger.monitoring_plans.v1.MonitoringPlanService/ListMonitoringPlans" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{"page_size": 10, "order_by": "create_time desc"}'
Response
{
"monitoringPlans": [
{
"name": "monitoring-plans/plan-abc123",
"origin": {
"repository": "acme-corp/backend",
"prNumber": 42,
"prUrl": "https://github.com/acme-corp/backend/pull/42",
"prTitle": "Fix auth service timeout handling",
"prAuthorGithubLogin": "engineer",
"prAuthorGithubUserId": "1234567"
},
"planSummary": "Fixes auth service timeout handling to prevent cascading failures during peak traffic.",
"intendedEffects": [
"Auth service p99 latency stays under 500ms at peak (24h baseline 480ms).",
"Cascading 503s attributed to auth timeouts drop to zero."
],
"risks": [
"Masked failures: watch auth 5xx rate; alert if > 1% sustained for 5m."
],
"createTime": "2024-06-15T14:30:00Z",
"updateTime": "2024-06-15T15:00:00Z"
}
],
"nextPageToken": ""
}
PostPlanComment
Post a Markdown monitoring update to the pull request associated with a monitoring plan. If the PR author has linked GitHub and Slack and enabled Change Monitor DMs, Firetiger also sends the same update to their Slack DM. GitHub comment posting and Slack delivery are best-effort and independent.
POST /v1/monitoring-plans/{plan_id}:postComment
Path parameters
| Field | Type | Required | Description |
|---|---|---|---|
plan_id |
string | Yes | ID portion of the monitoring plan resource name |
Request body
| Field | Type | Required | Description |
|---|---|---|---|
comment_body |
string | Yes | Markdown body to post on the pull request |
Example
curl -X POST "https://api.cloud.firetiger.com/v1/monitoring-plans/plan-abc123:postComment" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{
"comment_body": "Post-deployment verification completed. No anomalies were detected."
}'
Response
{
"commentUrl": "https://github.com/acme-corp/backend/pull/42#issuecomment-1234567890"
}
PostInProgressComment
Post the initial “Firetiger is working on a monitoring plan for this PR” placeholder comment on the pull request associated with a monitoring plan, and record its comment ID on the plan (origin.pr_in_progress_comment_id). When the plan is later published, Firetiger edits that same comment in place into “Firetiger has created a monitoring plan for this PR” so the PR carries one comment that transitions state. The comment body and change-monitor link are generated server-side. Best-effort: returns an empty commentUrl (and records nothing) when GitHub posting is unavailable.
POST /v1/monitoring-plans/{plan_id}:postInProgressComment
Path parameters
| Field | Type | Required | Description |
|---|---|---|---|
plan_id |
string | Yes | ID portion of the monitoring plan resource name |
Example
curl -X POST "https://api.cloud.firetiger.com/v1/monitoring-plans/plan-abc123:postInProgressComment" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{}'
Response
{
"commentUrl": "https://github.com/acme-corp/backend/pull/42#issuecomment-1234567890"
}
ActivateFromDeployment
Correlate a successful deployment to the merged monitoring plans whose change shipped in it, and activate those plans (append a per-environment MonitoredDeployment). This RPC is driven by Firetiger’s deployment hook, not typically called by end users.
Activation resolves which plans shipped by comparing the deployment’s commit range: base_sha is the previous deployment’s processed SHA (the per-environment watermark) and deployed_sha is the new tip. Plans whose activation.merge_sha falls in that range are activated. When base_sha is empty (the first deployment of a repository/environment), Firetiger falls back to walking the deployed SHA’s commit history.
POST /firetiger.monitoring_plans.v1.MonitoringPlanService/ActivateFromDeployment
Request body
| Field | Type | Required | Description |
|---|---|---|---|
repository |
string | Yes | Repository in owner/repo format |
environment |
string | Yes | Deployment environment (e.g. production) |
deployed_sha |
string | Yes | The newly deployed commit SHA |
base_sha |
string | No | Previous processed deployment SHA for this (repository, environment) — the forward-delta watermark. Empty falls back to a history walk |
installation_id |
int64 | No | GitHub App installation ID used to authorize the commit comparison |
github_deployment_id |
int64 | No | GitHub deployment ID, used to look up the corresponding Deployment resource |
deployment_name |
string | No | Deployment resource name (e.g. deployments/dep-789) when the GitHub deployment ID is unavailable |
Response
{
"activatedPlans": [
{
"name": "monitoring-plans/plan-abc123",
"activation": { "mergeSha": "f6e5d4c3b2a1", "environments": ["production"] }
}
]
}
ActivatePlanFromDeployments
Activate a single already-merged monitoring plan against the current deployments of its repository — the dual of ActivateFromDeployment. This RPC is driven by plan-creation flows, not typically called by end users.
ActivateFromDeployment correlates a deployment to the plans whose change it shipped. But a plan can be created after its PR already merged and deployed (e.g. authoring a monitor for an already-merged PR); that merge is behind every later deployment’s commit range, so the deployment-driven path never sees it. This RPC closes that gap: for each environment with a recent successful deployment of the plan’s repository, if the plan’s merge_sha is an ancestor of that environment’s latest deployed SHA and the plan isn’t already activated there, it appends a MonitoredDeployment. Idempotent.
POST /firetiger.monitoring_plans.v1.MonitoringPlanService/ActivatePlanFromDeployments
Request body
| Field | Type | Required | Description |
|---|---|---|---|
name |
string | Yes | Resource name of the monitoring plan to activate (monitoring-plans/{plan}) |
Response
{
"activatedPlans": [
{
"name": "monitoring-plans/plan-abc123",
"activation": { "mergeSha": "f6e5d4c3b2a1", "environments": ["production"] }
}
]
}
RecordPullRequestFixLink
Persist that a pull request fixes a specific issue. Firetiger records the PR on the issue, ensures the PR has a monitoring plan, links the issue to that plan, and replays any deployments already recorded on the plan so the issue can move to ISSUE_WORKFLOW_STATE_VERIFYING_FIX immediately.
POST /v1/monitoring-plans:recordPullRequestFixLink
Request body
| Field | Type | Required | Description |
|---|---|---|---|
pr_url |
string | Yes | Full GitHub pull request URL |
issue_name |
string | Yes | Issue resource name, for example issues/FT-42 |
installation_id |
int64 | No | GitHub App installation ID to use if Firetiger must create a monitoring plan for the PR |
Example
curl -X POST "https://api.cloud.firetiger.com/v1/monitoring-plans:recordPullRequestFixLink" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{
"pr_url": "https://github.com/acme-corp/backend/pull/42",
"issue_name": "issues/FT-42"
}'
Response
{
"monitoringPlan": {
"name": "monitoring-plans/plan-abc123",
"origin": {
"repository": "acme-corp/backend",
"prNumber": 42,
"prUrl": "https://github.com/acme-corp/backend/pull/42"
},
"relatedResources": ["issues/FT-42"]
},
"linkedIssues": ["issues/FT-42"],
"promotedIssues": ["issues/FT-42"]
}
RecordPullRequestUpdated
Record the current pull request title and body and persist any issue refs introduced by a GitHub-style closing keyword, such as Fixes FT-42, Closes: FT-42, or Resolves https://app.example.com/issues/FT-42. Bare mentions like Related to FT-42 are ignored. This RPC is typically called from GitHub pull request webhooks.
For each extracted issue, Firetiger performs the same reconciliation as RecordPullRequestFixLink: it records the PR on the issue, ensures the PR has a monitoring plan, links the issue to the plan, and replays existing deployments for possible VERIFYING_FIX promotion.
POST /v1/monitoring-plans:recordPullRequestUpdated
Request body
| Field | Type | Required | Description |
|---|---|---|---|
pr_url |
string | Yes | Full GitHub pull request URL |
title |
string | No | Current PR title |
body |
string | No | Current PR body |
installation_id |
int64 | No | GitHub App installation ID to use if Firetiger must create a monitoring plan for the PR |
Example
curl -X POST "https://api.cloud.firetiger.com/v1/monitoring-plans:recordPullRequestUpdated" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{
"pr_url": "https://github.com/acme-corp/backend/pull/42",
"title": "Fix auth service timeout handling",
"body": "Fixes FT-42. Related to FT-7."
}'
Response
{
"monitoringPlan": {
"name": "monitoring-plans/plan-abc123",
"origin": {
"repository": "acme-corp/backend",
"prNumber": 42,
"prUrl": "https://github.com/acme-corp/backend/pull/42"
},
"relatedResources": ["issues/FT-42"]
},
"linkedIssues": ["issues/FT-42"],
"promotedIssues": ["issues/FT-42"]
}
GetMyChangeMonitorSetup
Read the current user’s personal Change Monitor notification setup. This includes their GitHub identity link, Slack identity link, installed Slack app connection, and notification preference.
GET /v1/users/me/change-monitor-setup
Example
curl "https://api.cloud.firetiger.com/v1/users/me/change-monitor-setup" \
-u "$USERNAME:$PASSWORD"
Response
{
"preference": {
"name": "change-monitor-notification-preferences/user-123",
"enabled": true,
"impactReportEmailsDisabled": false,
"slackDm": {
"slackConnection": "connections/slack-test",
"slackExternalIdentity": "external-identities/slack-123"
}
},
"status": {
"githubIdentityLinked": true,
"slackIdentityLinked": true,
"slackDmVerified": true
}
}
UpdateMyChangeMonitorNotificationPreference
Update the current user’s Change Monitor notification settings: the Slack DM toggle (enabled) and the weekly Impact Report email opt-out (impact_report_emails_disabled). When Slack DMs are enabled, every Change Monitor notification is delivered to the verified Slack DM destination. Impact Report emails are on by default for engineers with a change monitor; set impact_report_emails_disabled to true to opt out.
PATCH /v1/users/me/change-monitor-notification-preference
Request body
| Field | Type | Required | Description |
|---|---|---|---|
enabled |
boolean | No | Whether Change Monitor Slack DM notifications are enabled |
impact_report_emails_disabled |
boolean | No | Opt-out for weekly Impact Report emails |
update_mask |
string | No | Comma-separated field mask naming the fields to write. Supported paths: enabled, impact_report_emails_disabled. Defaults to enabled |
Example (opt out of weekly Impact Report emails)
curl -X PATCH "https://api.cloud.firetiger.com/v1/users/me/change-monitor-notification-preference" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{
"impact_report_emails_disabled": true,
"update_mask": "impact_report_emails_disabled"
}'
Response
{
"preference": {
"enabled": true,
"impactReportEmailsDisabled": true,
"slackDm": {
"slackConnection": "connections/slack-test",
"slackExternalIdentity": "external-identities/slack-123"
}
}
}
VerifyMyChangeMonitorSlackDM
Send a test DM to the current user’s linked Slack account and store that Slack connection as the verified destination for Change Monitor notifications.
POST /v1/users/me/change-monitor-notification-preference:verify-slack-dm
Request body
| Field | Type | Required | Description |
|---|---|---|---|
slack_connection |
string | Yes | Slack app connection resource name to verify |
Example
curl -X POST "https://api.cloud.firetiger.com/v1/users/me/change-monitor-notification-preference:verify-slack-dm" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{"slack_connection": "connections/slack-test"}'
Response
{
"preference": {
"enabled": true,
"slackDestination": {
"slackConnection": "connections/slack-test",
"slackExternalIdentity": "users/user-123/external-identities/slack"
}
}
}
GetMonitoringRun
MonitoringRunService is a legacy service. New monitoring state is stored directly on MonitoringPlan.deployments. The run endpoints are retained for backward compatibility.
Retrieve a monitoring run by name.
POST /firetiger.monitoring_plans.v1.MonitoringRunService/GetMonitoringRun
Request body
| Field | Type | Required | Description |
|---|---|---|---|
name |
string | Yes | Resource name of the monitoring run |
Example
curl -X POST "https://api.cloud.firetiger.com/firetiger.monitoring_plans.v1.MonitoringRunService/GetMonitoringRun" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{"name": "monitoring-plans/plan-abc123/runs/run-prod-001"}'
Response
{
"monitoringRun": {
"name": "monitoring-plans/plan-abc123/runs/run-prod-001",
"environment": "production",
"deployment": "deployments/dep-789",
"status": "MONITORING_RUN_STATUS_COMPLETED",
"outcome": "MONITORING_RUN_OUTCOME_NO_ISSUE",
"intendedEffectConfirmed": true,
"activateTime": "2024-06-15T16:00:00Z",
"completeTime": "2024-06-15T17:30:00Z",
"lastCheckTime": "2024-06-15T17:30:00Z",
"createTime": "2024-06-15T16:00:00Z",
"updateTime": "2024-06-15T17:30:00Z"
}
}
ListMonitoringRuns
MonitoringRunService is a legacy service. New monitoring state is stored directly on MonitoringPlan.deployments. The run endpoints are retained for backward compatibility.
List monitoring runs for a plan with optional filtering and pagination.
POST /firetiger.monitoring_plans.v1.MonitoringRunService/ListMonitoringRuns
Request body
| Field | Type | Required | Description |
|---|---|---|---|
parent |
string | Yes | Parent monitoring plan resource name |
filter |
string | No | Filter expression |
order_by |
string | No | Field to sort by (e.g. create_time desc) |
page_size |
integer | No | Maximum results per page |
page_token |
string | No | Token for the next page of results |
show_deleted |
boolean | No | Include soft-deleted monitoring runs |
Example
curl -X POST "https://api.cloud.firetiger.com/firetiger.monitoring_plans.v1.MonitoringRunService/ListMonitoringRuns" \
-u "$USERNAME:$PASSWORD" \
-H "Content-Type: application/json" \
-d '{"parent": "monitoring-plans/plan-abc123", "page_size": 10}'
Response
{
"monitoringRuns": [
{
"name": "monitoring-plans/plan-abc123/runs/run-prod-001",
"environment": "production",
"deployment": "deployments/dep-789",
"status": "MONITORING_RUN_STATUS_COMPLETED",
"outcome": "MONITORING_RUN_OUTCOME_NO_ISSUE",
"intendedEffectConfirmed": true,
"activateTime": "2024-06-15T16:00:00Z",
"completeTime": "2024-06-15T17:30:00Z",
"createTime": "2024-06-15T16:00:00Z",
"updateTime": "2024-06-15T17:30:00Z"
}
],
"nextPageToken": ""
}