Dashboards
Sourcegull's Grafana dashboards, one per service. They are generated from crates/monitoring into deploy/docker/grafana/dashboards/ (in the Compose bundle, to import into your Grafana) and the Helm chart's dashboard ConfigMaps (metrics.grafanaDashboards.enabled=true); README.md shows how to set them up. Panels with alerts link to alerts.md.
- Sourcegull: web
- Sourcegull: repo
- Sourcegull: worker
- Sourcegull: executor
- Sourcegull: blob
- Sourcegull: postgres
Sourcegull: web
The web role serves the UI, the GraphQL and HTTP APIs, streaming search, code host webhooks and the executor API.
Grafana uid: sourcegull-web.
web: HTTP requests
web_http_request_rate
Requests per second by route
Requests to the public listener by matched route pattern (fallback is the UI and raw files). Health checks and scrapes are left out.
sum by (route) (rate(sourcegull_http_requests_total{role=~"web|all",route!~"/metrics|/healthz|/readyz"}[5m]))
Owner: platform
web_http_5xx_ratio
Share of requests answered with 5xx
- Alert (warning): web: share of requests answered with 5xx above 2% for 5m
- Alert (critical): web: share of requests answered with 5xx above 10% for 10m
(sum(rate(sourcegull_http_requests_total{role=~"web|all",route!~"/metrics|/healthz|/readyz",status=~"5.."}[5m])) or 0 * sum(rate(sourcegull_http_requests_total{role=~"web|all",route!~"/metrics|/healthz|/readyz"}[5m])))
/ sum(rate(sourcegull_http_requests_total{role=~"web|all",route!~"/metrics|/healthz|/readyz"}[5m]))
Owner: platform
web_http_p90_latency
90th percentile request duration by route
- Alert (warning): web: 90th percentile request duration by route above 5s for 15m
histogram_quantile(0.9, sum by (le, route) (rate(sourcegull_http_request_duration_seconds_bucket{role=~"web|all",route!~"/metrics|/healthz|/readyz|/.api/search/stream|/.api/compute/stream|/.api/blame/.*|/.api/scip/upload|/.api/files/.*|/.executors/.*"}[5m])))
Owner: platform
web: Search and GraphQL
web_search_stream_p90_duration
90th percentile streaming search duration
Time from the request until the search stream ends, as users see it. Histogram buckets end at 60 s.
- Alert (warning): web: 90th percentile streaming search duration above 20s for 15m
histogram_quantile(0.9, sum by (le) (rate(sourcegull_http_request_duration_seconds_bucket{role=~"web|all",route="/.api/search/stream"}[5m])))
Owner: search
web_search_stream_requests
Streaming searches per second by status
Search requests from the UI, the API and gull. Errors inside a stream are sent as events and still count as 200.
sum by (status) (rate(sourcegull_http_requests_total{role=~"web|all",route="/.api/search/stream"}[5m]))
Owner: search
web_graphql_p90_duration
90th percentile GraphQL request duration
- Alert (warning): web: 90th percentile GraphQL request duration above 5s for 15m
histogram_quantile(0.9, sum by (le) (rate(sourcegull_http_request_duration_seconds_bucket{role=~"web|all",route="/.api/graphql"}[5m])))
Owner: platform
web: Code host webhooks
web_webhook_requests
Code host webhook deliveries per second by status
GitLab webhook deliveries (repository pushes, merge requests, pipelines) by response status.
sum by (route, status) (rate(sourcegull_http_requests_total{role=~"web|all",route=~"/.api/gitlab-webhooks|/.api/webhooks/.*"}[5m]))
Owner: source
web_webhook_rejection_ratio
Share of code host webhooks rejected
- Alert (warning): web: share of code host webhooks rejected above 50% for 30m
(sum(rate(sourcegull_http_requests_total{role=~"web|all",route=~"/.api/gitlab-webhooks|/.api/webhooks/.*",status!~"2.."}[30m])) or 0 * sum(rate(sourcegull_http_requests_total{role=~"web|all",route=~"/.api/gitlab-webhooks|/.api/webhooks/.*"}[30m])))
/ sum(rate(sourcegull_http_requests_total{role=~"web|all",route=~"/.api/gitlab-webhooks|/.api/webhooks/.*"}[30m]))
Owner: source
web: Instances
web_instance_up
Instances answering Prometheus scrapes
1 while Prometheus can scrape the instance's internal listener (:6060), 0 when it cannot.
- Alert (critical): web: instances answering Prometheus scrapes below 1 for 5m
up{role=~"web|all"}
Owner: platform
web_site_config_version
Site configuration version loaded by each instance
The site config version each process runs with. With the config in the database, all instances converge on the same version within seconds of a change; a lasting difference means an instance cannot reload it (its logs say why). With SOURCEGULL_SITE_CONFIG_FILE, versions count reloads per process and may differ.
max by (role, instance) (sourcegull_site_config_version)
Owner: platform
Sourcegull: repo
Repo nodes clone and fetch repositories from the code hosts, build the text search index and serve git data and searches to the other roles over gRPC.
Grafana uid: sourcegull-repo.
repo: Disk
repo_disk_free_ratio
Free disk space on the data volume
Measured by the repo node janitor (2 minutes after start, then hourly). The node pauses clones when free space is below both SOURCEGULL_REPO_PAUSE_CLONES_FREE_PERCENT (default 10%) of the volume and SOURCEGULL_REPO_PAUSE_CLONES_FREE_GIB (default 20 GiB); Site admin > Repo nodes shows the threshold.
- Alert (warning): repo: free disk space on the data volume below 15% for 10m
- Alert (critical): repo: free disk space on the data volume below 5% for 5m
min by (instance) (sourcegull_repo_disk_free_bytes{role=~"repo|all"} / sourcegull_repo_disk_total_bytes{role=~"repo|all"})
Owner: source
repo_disk_free_bytes
Free bytes on the data volume
Free space for clones, the search index and caches, measured hourly. A repo node needs about 1.5 times the size of its repositories.
min by (instance) (sourcegull_repo_disk_free_bytes{role=~"repo|all"})
Owner: source
repo: Clones and fetches
repo_repo_update_rate
Clones and fetches per second by kind and outcome
Repository updates finished by the repo nodes: clone (first copy), fetch (scheduled or webhook-triggered update) and reclone.
sum by (kind, outcome) (rate(sourcegull_repo_updates_total{role=~"repo|all"}[5m]))
Owner: source
repo_repo_update_error_ratio
Share of clones and fetches failing
- Alert (warning): repo: share of clones and fetches failing above 20% for 30m
- Alert (critical): repo: share of clones and fetches failing above 80% for 30m
(sum by (kind) (rate(sourcegull_repo_updates_total{role=~"repo|all",outcome="error"}[30m])) or 0 * sum by (kind) (rate(sourcegull_repo_updates_total{role=~"repo|all"}[30m])))
/ sum by (kind) (rate(sourcegull_repo_updates_total{role=~"repo|all"}[30m]))
Owner: source
repo_repo_update_p90_duration
90th percentile clone and fetch duration by kind
Histogram buckets end at 60 s, so long clones show as 60 s.
histogram_quantile(0.9, sum by (le, kind) (rate(sourcegull_repo_update_duration_seconds_bucket{role=~"repo|all"}[15m])))
Owner: source
repo_update_queue_oldest
Age of the oldest queued clone or fetch
- Alert (warning): repo: age of the oldest queued clone or fetch above 2h for 30m
max(sourcegull_queue_oldest_queued_seconds{queue="repo_update_jobs"})
Owner: source
repo_update_queue_depth
Queued and running clones and fetches
Jobs in the repo_update_jobs queue. Scheduled fetches and webhook pushes add jobs; one queued job per repository at most.
max by (state) (sourcegull_queue_jobs{queue="repo_update_jobs",state=~"queued|processing"})
Owner: source
repo: Repositories
repo_repos_by_clone_status
Repositories by clone status
Repositories known to Sourcegull (not deleted). not_cloned falls as the repo nodes clone new repositories.
max by (clone_status) (sourcegull_repos)
Owner: source
repo_repos_fetch_errors
Repositories whose last update failed
Repositories with a last error recorded by their repo node; Site admin > Repositories lists them (filter: Failed fetch).
max(sourcegull_repos_fetch_errors)
Owner: source
repo_repos_corrupted
Repositories marked corrupt
- Alert (warning): repo: repositories marked corrupt above 0 for 5m
max(sourcegull_repos_corrupted)
Owner: source
repo: Search index
repo_index_queue_length
Repositories waiting to be indexed
- Alert (warning): repo: repositories waiting to be indexed above 500 for 1h
max by (instance) (sourcegull_index_queue_length{role=~"repo|all"})
Owner: search
repo_index_update_rate
Index updates per second by outcome
built: new shards written; unchanged: nothing to do; removed: index dropped; error: the build failed.
sum by (outcome) (rate(sourcegull_index_updates_total{role=~"repo|all"}[5m]))
Owner: search
repo_index_error_ratio
Share of index builds failing
- Alert (warning): repo: share of index builds failing above 20% for 30m
(sum(rate(sourcegull_index_updates_total{role=~"repo|all",outcome="error"}[30m])) or 0 * sum(rate(sourcegull_index_updates_total{role=~"repo|all"}[30m])))
/ sum(rate(sourcegull_index_updates_total{role=~"repo|all"}[30m]))
Owner: search
repo_index_build_p90_duration
90th percentile index build duration
Time to build one repository's shards. Histogram buckets end at 60 s.
histogram_quantile(0.9, sum by (le) (rate(sourcegull_index_build_duration_seconds_bucket{role=~"repo|all"}[30m])))
Owner: search
repo_index_repos
Repositories by index status
Repositories with a text index (indexed) and without one yet (not_indexed).
max by (status) (sourcegull_index_repos)
Owner: search
repo_index_repos_errored
Repositories whose last index build failed
Cleared by the next successful build. Site admin > Repositories shows the error per repository.
max(sourcegull_index_repos_errored)
Owner: search
repo: Rebalancing
repo_repo_moves
Repository moves between repo nodes by state
After repo nodes are added or removed, the repositories whose node changes are copied to their new node (queued, copying), switched over (flipped, the old copy is kept for a few minutes) and then removed from the old node. Nothing moves until every repo node runs with the same node list.
max by (state) (sourcegull_repo_moves)
Owner: source
repo_repo_move_rate
Repository moves finished per second by outcome
flipped: copied and switched over; reassigned: the old node was gone, cloned from the code host instead; retry: an attempt failed and is retried; failed: gave up; cancelled: no longer needed.
sum by (outcome) (rate(sourcegull_repo_moves_total{role=~"repo|all"}[5m]))
Owner: source
repo_repo_move_throughput
Bytes copied between repo nodes per second
Pack data received by the repositories' new nodes.
sum by (instance) (rate(sourcegull_repo_move_bytes_total{role=~"repo|all"}[5m]))
Owner: source
repo_repo_moves_failed
Repository moves that gave up
- Alert (warning): repo: repository moves that gave up above 0 for 30m
max(sourcegull_repo_moves{state="failed"})
Owner: source
repo: Instances
repo_instance_up
Instances answering Prometheus scrapes
1 while Prometheus can scrape the instance's internal listener (:6060), 0 when it cannot.
- Alert (critical): repo: instances answering Prometheus scrapes below 1 for 5m
up{role=~"repo|all"}
Owner: platform
Sourcegull: worker
Workers run the job queues (code host and permission syncs, SCIP uploads, bulk changes, search jobs, watches, trends, outbound webhooks) and the singleton background jobs.
Grafana uid: sourcegull-worker.
worker: Job queues
worker_queue_depth
Queued jobs by queue
Jobs waiting for a worker, per queue table. Site admin > Background jobs shows the same counts with the newest failures.
max by (queue) (sourcegull_queue_jobs{state="queued",queue!~"codeintel_index_jobs|batch_spec_workspace_execution_jobs|repo_update_jobs"})
Owner: platform
worker_queue_processing
Running jobs by queue
Jobs a worker holds right now. Stalled jobs (no heartbeat) are returned to the queue by the resetters.
max by (queue) (sourcegull_queue_jobs{state="processing",queue!~"codeintel_index_jobs|batch_spec_workspace_execution_jobs|repo_update_jobs"})
Owner: platform
worker_queue_oldest_queued
Age of the oldest queued job by queue
- Alert (warning): worker: age of the oldest queued job by queue above 6h for 30m
max by (queue) (sourcegull_queue_oldest_queued_seconds{queue!~"codeintel_index_jobs|batch_spec_workspace_execution_jobs|repo_update_jobs"})
Owner: platform
worker_queue_failed
Failed and errored jobs kept by queue
errored jobs are retried, failed ones are not. Growth means a job type keeps failing; Site admin > Background jobs lists the messages and can retry them.
max by (queue) (sourcegull_queue_jobs{state=~"failed|errored",queue!~"codeintel_index_jobs|batch_spec_workspace_execution_jobs|repo_update_jobs"})
Owner: platform
worker: Code intelligence
worker_upload_processing_rate
SCIP uploads processed per second by outcome
completed, errored (retried) and failed (given up) upload processing runs.
sum by (outcome) (rate(sourcegull_codeintel_upload_processing_seconds_count[5m]))
Owner: code-intel
worker_upload_processing_failure_ratio
Share of SCIP upload processing runs failing
(sum(rate(sourcegull_codeintel_upload_processing_seconds_count{outcome!="completed"}[1h])) or 0 * sum(rate(sourcegull_codeintel_upload_processing_seconds_count[1h])))
/ sum(rate(sourcegull_codeintel_upload_processing_seconds_count[1h]))
Owner: code-intel
worker_upload_processing_p90_duration
90th percentile SCIP upload processing duration
Histogram buckets end at 60 s, so larger uploads show as 60 s.
histogram_quantile(0.9, sum by (le) (rate(sourcegull_codeintel_upload_processing_seconds_bucket[30m])))
Owner: code-intel
worker_upload_processed_bytes
SCIP upload bytes processed per second
Size of the SCIP indexes turned into code graph data.
sum(rate(sourcegull_codeintel_upload_processed_bytes_total[5m]))
Owner: code-intel
worker_autoindex_commits_considered
Commits considered for auto-indexing per second
Commits the auto-indexing scheduler looked at, on ref updates (event) and in its sweep.
sum by (trigger) (rate(sourcegull_autoindex_commits_considered_total[5m]))
Owner: code-intel
worker_autoindex_jobs_queued
Auto-indexing jobs queued per second
Index jobs added to the codeintel_index_jobs executor queue (see the executor dashboard).
sum(rate(sourcegull_autoindex_jobs_queued_total[5m]))
Owner: code-intel
worker_autoindex_rate_limited
Auto-indexing passes skipped by the rate limit per second
Repositories skipped because they were indexed too recently.
sum(rate(sourcegull_autoindex_rate_limited_total[5m]))
Owner: code-intel
worker_codeintel_coverage_repos
Repositories by precise index coverage
up_to_date: a completed index serves the default branch; stale: the newest index is not at the default branch tip and older than 7 days; failing: the latest index job or upload failed; none: an indexing policy applies but nothing is indexed; not_targeted: no indexing policy applies. Site admin > Index coverage lists the repositories. Refreshed every 5 minutes.
max by (state) (sourcegull_codeintel_coverage_repos)
Owner: code-intel
worker_codeintel_failing_repos_growth
Growth in repositories whose precise indexing fails, over 6 hours
- Alert (warning): worker: growth in repositories whose precise indexing fails, over 6 hours above 0 for 1h
max(sourcegull_codeintel_coverage_repos{state="failing"}) - max(sourcegull_codeintel_coverage_repos{state="failing"} offset 6h)
Owner: code-intel
worker_codeintel_failing_repos_by_source
Failing repositories by where the latest failure happened
index_job: an auto-indexing job failed on an executor; upload: processing an uploaded index failed.
max by (source) (sourcegull_codeintel_coverage_failing_repos)
Owner: code-intel
worker: Code intelligence data retention (collapsed)
worker_codeintel_uploads_deleted
SCIP uploads deleted per hour by reason
Uploads removed by the janitor: expired by data retention policies, abandoned (never finished uploading) and repository deleted.
sum by (reason) (increase(sourcegull_codeintel_janitor_uploads_deleted_total[1h]))
Owner: code-intel
worker_codeintel_orphaned_blobs_deleted
Orphaned upload files deleted per hour
Blob store files without an upload, removed by the janitor.
sum(increase(sourcegull_codeintel_janitor_orphaned_blobs_deleted_total[1h]))
Owner: code-intel
worker_codeintel_retention_expired
Uploads expired by data retention policies per hour
Uploads the expirer marked expired; the janitor deletes them later. Uploads on commits the repo node does not know are skipped until it does.
sum(increase(sourcegull_codeintel_retention_uploads_expired_total[1h]))
Owner: code-intel
worker_codeintel_ranking_duration
Duration of the last ranking run
How long the last PageRank run over the code graph took.
max(sourcegull_codeintel_ranking_duration_seconds)
Owner: code-intel
worker: Bulk changes
worker_reconciler_outcomes
Changesets reconciled per second by outcome
ok: the changeset matches its spec on the code host; scheduled: waiting for the rollout window; retry/failed: an error.
sum by (outcome) (rate(sourcegull_batches_changesets_reconciled_total[5m]))
Owner: batches
worker_reconciler_failure_ratio
Share of changeset reconciliations failing
- Alert (warning): worker: share of changeset reconciliations failing above 20% for 30m
(sum(rate(sourcegull_batches_changesets_reconciled_total{outcome="failed"}[30m])) or 0 * sum(rate(sourcegull_batches_changesets_reconciled_total[30m])))
/ sum(rate(sourcegull_batches_changesets_reconciled_total[30m]))
Owner: batches
worker_changeset_sync_error_ratio
Share of changeset syncs failing
- Alert (warning): worker: share of changeset syncs failing above 50% for 1h
(sum(rate(sourcegull_batches_changeset_syncs_total{outcome="error"}[1h])) or 0 * sum(rate(sourcegull_batches_changeset_syncs_total[1h])))
/ sum(rate(sourcegull_batches_changeset_syncs_total[1h]))
Owner: batches
worker_bulk_operations
Bulk operations per second by type and outcome
Bulk actions on changesets: comment, detach, reenqueue, merge, close, publish.
sum by (type, outcome) (rate(sourcegull_batches_bulk_jobs_total[5m]))
Owner: batches
worker: Watches, Trends and outbound webhooks
worker_code_monitor_triggers
Watch searches queued per second
Trigger searches queued on pushes and by the evaluator's sweep.
sum by (trigger) (rate(sourcegull_code_monitor_triggers_total[5m]))
Owner: code-insights
worker_code_monitor_delivery_error_ratio
Share of watch notifications failing by kind
(sum by (kind) (rate(sourcegull_code_monitor_deliveries_total{outcome="error"}[1h])) or 0 * sum by (kind) (rate(sourcegull_code_monitor_deliveries_total[1h])))
/ sum by (kind) (rate(sourcegull_code_monitor_deliveries_total[1h]))
Owner: code-insights
worker_insights_search_calls
Trend searches per second by job
Searches run by trend backfills and recordings; limited by insights.query.worker.rateLimit.
sum by (job) (rate(sourcegull_insights_count_calls_total[5m]))
Owner: code-insights
worker_outbound_webhook_error_ratio
Share of outbound webhook deliveries failing
(sum(rate(sourcegull_outbound_webhook_deliveries_total{outcome="error"}[1h])) or 0 * sum(rate(sourcegull_outbound_webhook_deliveries_total[1h])))
/ sum(rate(sourcegull_outbound_webhook_deliveries_total[1h]))
Owner: platform
worker: Out-of-band migrations
worker_oob_migration_progress
Out-of-band migration progress
Progress of background data migrations, e.g. re-encryption after a key rotation. Site admin > Migrations shows the same.
max by (id) (sourcegull_oob_migration_progress)
Owner: platform
worker_oob_migration_errors
Out-of-band migration errors in the last hour
- Alert (warning): worker: out-of-band migration errors in the last hour above 0
sum by (id) (increase(sourcegull_oob_migration_errors_total[1h]))
Owner: platform
worker: Housekeeping (collapsed)
worker_sessions_expired_deleted
Expired sessions deleted per hour
Removed by the session janitor every 10 minutes.
sum(increase(sourcegull_sessions_expired_deleted_total[1h]))
Owner: platform
worker_changesets_purged
Changesets deleted by retention per hour
Detached changesets older than batchChanges.changesetsRetention.
sum(increase(sourcegull_batches_changesets_purged_total[1h]))
Owner: batches
worker_changesets_released
Changesets released by the rollout window scheduler per hour
Changesets published as batchChanges.rolloutWindows allows.
sum(increase(sourcegull_batches_changesets_released_total[1h]))
Owner: batches
worker_outbound_webhook_logs_deleted
Outbound webhook logs deleted per hour
Delivery logs past their retention, removed by the janitor.
sum(increase(sourcegull_outbound_webhook_logs_deleted_total[1h]))
Owner: platform
worker: Instances
worker_instance_up
Instances answering Prometheus scrapes
1 while Prometheus can scrape the instance's internal listener (:6060), 0 when it cannot.
- Alert (critical): worker: instances answering Prometheus scrapes below 1 for 5m
up{role=~"worker|all"}
Owner: platform
Sourcegull: executor
Executors take auto-indexing jobs (codeintel_index_jobs) and server-side bulk change spec executions (batch_spec_workspace_execution_jobs) from the web role's executor API and run them in containers or Kubernetes jobs. Executor processes expose no metrics; this dashboard shows their queues, heartbeats and API traffic.
Grafana uid: sourcegull-executor.
executor: Executors
executor_executors_active
Executors sending heartbeats
Executors that sent a heartbeat in the last minute (they send one every 5 s). Site admin > Executors lists them.
max(sourcegull_executors_active)
Owner: platform
executor_running_jobs
Jobs running on executors
Jobs the active executors report running, across both queues.
max(sourcegull_executor_running_jobs)
Owner: platform
executor_jobs_without_executors
Queued executor jobs while no executor is active
The number of queued executor jobs when no executor has sent a heartbeat for a minute, else 0.
sum(max by (queue) (sourcegull_queue_jobs{queue=~"codeintel_index_jobs|batch_spec_workspace_execution_jobs",state="queued"}))
* on() (max(sourcegull_executors_active) == bool 0)
Owner: platform
executor: Executor queues
executor_queue_depth
Queued and running executor jobs by queue
Jobs waiting for and held by executors.
max by (queue, state) (sourcegull_queue_jobs{queue=~"codeintel_index_jobs|batch_spec_workspace_execution_jobs",state=~"queued|processing"})
Owner: platform
executor_queue_oldest_queued
Age of the oldest queued executor job by queue
max by (queue) (sourcegull_queue_oldest_queued_seconds{queue=~"codeintel_index_jobs|batch_spec_workspace_execution_jobs"})
Owner: platform
executor_queue_failed
Failed and errored executor jobs kept by queue
Failed auto-indexing jobs are shown per repository under Code graph > Index jobs; failed bulk change spec workspaces on the bulk change spec's execution page.
max by (queue, state) (sourcegull_queue_jobs{queue=~"codeintel_index_jobs|batch_spec_workspace_execution_jobs",state=~"failed|errored"})
Owner: platform
executor: Executor API
executor_api_requests
Executor API requests per second by route
Heartbeats, dequeues, log updates, git and file downloads from executors.
sum by (route) (rate(sourcegull_http_requests_total{role=~"web|all",route=~"/.executors/.*"}[5m]))
Owner: platform
executor_api_5xx_ratio
Share of executor API requests answered with 5xx
(sum(rate(sourcegull_http_requests_total{role=~"web|all",route=~"/.executors/.*",status=~"5.."}[15m])) or 0 * sum(rate(sourcegull_http_requests_total{role=~"web|all",route=~"/.executors/.*"}[15m])))
/ sum(rate(sourcegull_http_requests_total{role=~"web|all",route=~"/.executors/.*"}[15m]))
Owner: platform
Sourcegull: blob
The blob role stores SCIP uploads, bulk change workspace files and search job results on its volume and serves them to the other roles. With an S3-compatible store (blobstore.mode=s3) there is no blob role and this dashboard stays empty.
Grafana uid: sourcegull-blob.
blob: Requests
blob_request_rate
Blob requests per second by method and status
PUT writes, GET/HEAD reads, DELETE removals. 404 on reads is normal for missing keys.
sum by (method, status) (rate(sourcegull_blob_requests_total{role=~"blob|all"}[5m]))
Owner: platform
blob_error_ratio
Share of blob requests answered with 5xx
- Alert (warning): blob: share of blob requests answered with 5xx above 1% for 10m
- Alert (critical): blob: share of blob requests answered with 5xx above 10% for 10m
(sum(rate(sourcegull_blob_requests_total{role=~"blob|all",status=~"5.."}[10m])) or 0 * sum(rate(sourcegull_blob_requests_total{role=~"blob|all"}[10m])))
/ sum(rate(sourcegull_blob_requests_total{role=~"blob|all"}[10m]))
Owner: platform
blob_p90_latency
90th percentile blob request duration by method
Until the response starts: reads stream their body afterwards, writes include receiving the upload.
histogram_quantile(0.9, sum by (le, method) (rate(sourcegull_blob_request_duration_seconds_bucket{role=~"blob|all"}[5m])))
Owner: platform
blob: Instances
blob_instance_up
Instances answering Prometheus scrapes
1 while Prometheus can scrape the instance's internal listener (:6060), 0 when it cannot.
- Alert (critical): blob: instances answering Prometheus scrapes below 1 for 5m
up{role=~"blob|all"}
Owner: platform
Sourcegull: postgres
Sourcegull's database, measured by the workers (pg_stat_activity, database size) and by every process (its connection pool). For server-level metrics (replication, I/O, vacuum), run a Postgres exporter next to it.
Grafana uid: sourcegull-postgres.
postgres: Database
postgres_postgres_up
Workers reaching Postgres
1 when the last metrics collection by a worker (every 30 s) reached Postgres, else 0.
- Alert (critical): postgres: workers reaching Postgres below 1 for 5m
max(sourcegull_postgres_up)
Owner: platform
postgres_connections
Connections to Sourcegull's database by state
From pg_stat_activity. Many idle in transaction connections point to transactions left open by a client.
max by (state) (sourcegull_postgres_connections)
Owner: platform
postgres_connection_saturation
Share of max_connections in use by Sourcegull's database
- Alert (warning): postgres: share of max_connections in use by Sourcegull's database above 80% for 5m
- Alert (critical): postgres: share of max_connections in use by Sourcegull's database above 95% for 5m
sum(max by (state) (sourcegull_postgres_connections))
/ max(sourcegull_postgres_max_connections)
Owner: platform
postgres_oldest_transaction
Age of the oldest open transaction
- Alert (warning): postgres: age of the oldest open transaction above 30m for 5m
max(sourcegull_postgres_oldest_transaction_seconds)
Owner: platform
postgres_database_size
Size of Sourcegull's database
Grows with repositories, code graph data and job history. Watch the free space of the Postgres volume.
max(sourcegull_postgres_database_size_bytes)
Owner: platform
postgres: Connection pools
postgres_pool_in_use
Pool connections in use by process
Connections each process has checked out of its pool. Workers next to other roles get a separate worker pool.
max by (role, instance, pool) (sourcegull_db_pool_connections{state="in_use"})
Owner: platform
postgres_pool_saturation
Share of the connection pool in use by process
max by (role, instance, pool) (sourcegull_db_pool_connections{state="in_use"} / ignoring(state) sourcegull_db_pool_connections{state="max"})
Owner: platform