railwatch 0.9.4 → 1.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/AGENTS.md +37 -33
- data/CHANGELOG.md +63 -0
- data/README.md +51 -60
- data/config/routes.rb +0 -59
- data/docs/ai-and-mcp.md +9 -8
- data/docs/configuration.md +35 -66
- data/docs/faq.md +17 -25
- data/docs/getting-started.md +105 -117
- data/docs/replacing-nightwatch.md +8 -7
- data/docs/replacing-sentry.md +12 -16
- data/docs/security.md +14 -20
- data/docs/self-hosting.md +24 -22
- data/docs/testing.md +6 -14
- data/docs/troubleshooting.md +12 -46
- data/lib/generators/railwatch/install/install_generator.rb +12 -240
- data/lib/generators/railwatch/install/templates/initializer.rb.tt +10 -40
- data/lib/generators/railwatch/install/templates/post-deploy +0 -7
- data/lib/railwatch/authentication.rb +6 -5
- data/lib/railwatch/configuration.rb +18 -152
- data/lib/railwatch/engine.rb +9 -118
- data/lib/railwatch/patches.rb +0 -11
- data/lib/railwatch/reporter.rb +13 -20
- data/lib/railwatch/subscribers/process_info.rb +1 -2
- data/lib/railwatch/version.rb +1 -1
- data/lib/railwatch.rb +4 -62
- data/lib/tasks/railwatch_tasks.rake +3 -325
- data/llms.txt +23 -25
- metadata +3 -453
- data/app/channels/railwatch/environment_channel.rb +0 -62
- data/app/controllers/concerns/railwatch/telemetry_identity.rb +0 -25
- data/app/controllers/railwatch/alerts_controller.rb +0 -48
- data/app/controllers/railwatch/anomaly_rules_controller.rb +0 -31
- data/app/controllers/railwatch/attachments_controller.rb +0 -22
- data/app/controllers/railwatch/broadcasts_controller.rb +0 -15
- data/app/controllers/railwatch/cache_events_controller.rb +0 -30
- data/app/controllers/railwatch/commands_controller.rb +0 -16
- data/app/controllers/railwatch/comments_controller.rb +0 -11
- data/app/controllers/railwatch/dashboard_controller.rb +0 -70
- data/app/controllers/railwatch/deploys_controller.rb +0 -34
- data/app/controllers/railwatch/deprecations_controller.rb +0 -54
- data/app/controllers/railwatch/environment_scoped.rb +0 -81
- data/app/controllers/railwatch/exceptions_controller.rb +0 -52
- data/app/controllers/railwatch/executions_controller.rb +0 -13
- data/app/controllers/railwatch/issues_controller.rb +0 -258
- data/app/controllers/railwatch/jobs_controller.rb +0 -63
- data/app/controllers/railwatch/llm_calls_controller.rb +0 -124
- data/app/controllers/railwatch/logs_controller.rb +0 -40
- data/app/controllers/railwatch/mails_controller.rb +0 -19
- data/app/controllers/railwatch/notifications_controller.rb +0 -11
- data/app/controllers/railwatch/outgoing_requests_controller.rb +0 -19
- data/app/controllers/railwatch/overview_controller.rb +0 -38
- data/app/controllers/railwatch/people_controller.rb +0 -25
- data/app/controllers/railwatch/processes_controller.rb +0 -33
- data/app/controllers/railwatch/profiles_controller.rb +0 -65
- data/app/controllers/railwatch/queries_controller.rb +0 -59
- data/app/controllers/railwatch/releases_controller.rb +0 -75
- data/app/controllers/railwatch/requests_controller.rb +0 -37
- data/app/controllers/railwatch/saved_views_controller.rb +0 -53
- data/app/controllers/railwatch/scheduled_tasks_controller.rb +0 -45
- data/app/controllers/railwatch/spans_controller.rb +0 -47
- data/app/controllers/railwatch/storage_ops_controller.rb +0 -15
- data/app/controllers/railwatch/tenants_controller.rb +0 -44
- data/app/controllers/railwatch/thresholds_controller.rb +0 -47
- data/app/controllers/railwatch/traces_controller.rb +0 -72
- data/app/controllers/railwatch/transactions_controller.rb +0 -21
- data/app/controllers/railwatch/view_renders_controller.rb +0 -28
- data/app/controllers/railwatch/visits_controller.rb +0 -53
- data/app/frontend/components/app-content.tsx +0 -26
- data/app/frontend/components/app-logo-icon.tsx +0 -23
- data/app/frontend/components/app-logo.tsx +0 -14
- data/app/frontend/components/app-shell.tsx +0 -38
- data/app/frontend/components/app-sidebar-header.tsx +0 -54
- data/app/frontend/components/app-sidebar.tsx +0 -94
- data/app/frontend/components/app-wordmark.tsx +0 -29
- data/app/frontend/components/breadcrumbs.tsx +0 -46
- data/app/frontend/components/icon.tsx +0 -16
- data/app/frontend/components/input-error.tsx +0 -18
- data/app/frontend/components/nav-footer.tsx +0 -46
- data/app/frontend/components/nav-main.tsx +0 -41
- data/app/frontend/components/nav-user.tsx +0 -50
- data/app/frontend/components/railwatch/chart-hover.tsx +0 -34
- data/app/frontend/components/railwatch/chart-panel.tsx +0 -170
- data/app/frontend/components/railwatch/code.tsx +0 -28
- data/app/frontend/components/railwatch/command-palette.tsx +0 -132
- data/app/frontend/components/railwatch/copy-block.tsx +0 -52
- data/app/frontend/components/railwatch/copy-id.tsx +0 -49
- data/app/frontend/components/railwatch/cursor-load-more.tsx +0 -39
- data/app/frontend/components/railwatch/data-table.tsx +0 -195
- data/app/frontend/components/railwatch/digit-roll.tsx +0 -312
- data/app/frontend/components/railwatch/empty-state.tsx +0 -159
- data/app/frontend/components/railwatch/env-nav.tsx +0 -130
- data/app/frontend/components/railwatch/env-switcher.tsx +0 -145
- data/app/frontend/components/railwatch/filter-bar.tsx +0 -153
- data/app/frontend/components/railwatch/flamegraph.tsx +0 -324
- data/app/frontend/components/railwatch/frames.tsx +0 -295
- data/app/frontend/components/railwatch/json-viewer.tsx +0 -159
- data/app/frontend/components/railwatch/live-dot.tsx +0 -78
- data/app/frontend/components/railwatch/live-toggle.tsx +0 -76
- data/app/frontend/components/railwatch/metric-chart.tsx +0 -112
- data/app/frontend/components/railwatch/mobile-page-switcher.tsx +0 -89
- data/app/frontend/components/railwatch/onboarding.tsx +0 -91
- data/app/frontend/components/railwatch/origin-identity.tsx +0 -84
- data/app/frontend/components/railwatch/page-header.tsx +0 -42
- data/app/frontend/components/railwatch/percentile-picker.tsx +0 -18
- data/app/frontend/components/railwatch/relative-time.tsx +0 -18
- data/app/frontend/components/railwatch/saved-views.tsx +0 -232
- data/app/frontend/components/railwatch/segmented.tsx +0 -64
- data/app/frontend/components/railwatch/series-chart.tsx +0 -400
- data/app/frontend/components/railwatch/shortcuts-dialog.tsx +0 -89
- data/app/frontend/components/railwatch/signal-toast.tsx +0 -121
- data/app/frontend/components/railwatch/sort-header.tsx +0 -37
- data/app/frontend/components/railwatch/source-link.tsx +0 -57
- data/app/frontend/components/railwatch/sparkline-cell.tsx +0 -14
- data/app/frontend/components/railwatch/sql-block.tsx +0 -116
- data/app/frontend/components/railwatch/stat.tsx +0 -185
- data/app/frontend/components/railwatch/status-badge.tsx +0 -79
- data/app/frontend/components/railwatch/step-picker.tsx +0 -57
- data/app/frontend/components/railwatch/timeline.tsx +0 -405
- data/app/frontend/components/railwatch/utilisation-bar.tsx +0 -44
- data/app/frontend/components/railwatch/window-picker.tsx +0 -147
- data/app/frontend/components/ui/avatar.tsx +0 -51
- data/app/frontend/components/ui/badge.tsx +0 -46
- data/app/frontend/components/ui/breadcrumb.tsx +0 -109
- data/app/frontend/components/ui/button.tsx +0 -60
- data/app/frontend/components/ui/card.tsx +0 -92
- data/app/frontend/components/ui/chart.tsx +0 -374
- data/app/frontend/components/ui/checkbox.tsx +0 -32
- data/app/frontend/components/ui/collapsible.tsx +0 -31
- data/app/frontend/components/ui/command.tsx +0 -182
- data/app/frontend/components/ui/dialog.tsx +0 -158
- data/app/frontend/components/ui/dropdown-menu.tsx +0 -255
- data/app/frontend/components/ui/hover-card.tsx +0 -42
- data/app/frontend/components/ui/input.tsx +0 -21
- data/app/frontend/components/ui/label.tsx +0 -24
- data/app/frontend/components/ui/popover.tsx +0 -87
- data/app/frontend/components/ui/select.tsx +0 -185
- data/app/frontend/components/ui/separator.tsx +0 -28
- data/app/frontend/components/ui/sheet.tsx +0 -137
- data/app/frontend/components/ui/sidebar.tsx +0 -726
- data/app/frontend/components/ui/skeleton.tsx +0 -13
- data/app/frontend/components/ui/sonner.tsx +0 -41
- data/app/frontend/components/ui/table.tsx +0 -114
- data/app/frontend/components/ui/tabs.tsx +0 -91
- data/app/frontend/components/ui/textarea.tsx +0 -18
- data/app/frontend/components/ui/tooltip.tsx +0 -61
- data/app/frontend/components/user-info.tsx +0 -32
- data/app/frontend/components/user-menu-content.tsx +0 -94
- data/app/frontend/entrypoints/application.css +0 -244
- data/app/frontend/entrypoints/inertia.tsx +0 -92
- data/app/frontend/fonts/CommitMono-Bold.woff2 +0 -0
- data/app/frontend/fonts/CommitMono-Regular.woff2 +0 -0
- data/app/frontend/fonts/Roboto-Black.woff2 +0 -0
- data/app/frontend/fonts/Roboto-Bold.woff2 +0 -0
- data/app/frontend/fonts/Roboto-Medium.woff2 +0 -0
- data/app/frontend/fonts/Roboto-Regular.woff2 +0 -0
- data/app/frontend/hooks/use-appearance.tsx +0 -67
- data/app/frontend/hooks/use-clipboard.ts +0 -32
- data/app/frontend/hooks/use-flash.tsx +0 -23
- data/app/frontend/hooks/use-hotkeys.ts +0 -63
- data/app/frontend/hooks/use-initials.tsx +0 -15
- data/app/frontend/hooks/use-live.ts +0 -205
- data/app/frontend/hooks/use-mobile-navigation.ts +0 -8
- data/app/frontend/hooks/use-mobile.ts +0 -21
- data/app/frontend/hooks/use-percentile.ts +0 -24
- data/app/frontend/hooks/use-reduced-motion.ts +0 -25
- data/app/frontend/hooks/use-row-nav.ts +0 -106
- data/app/frontend/hooks/use-step.ts +0 -27
- data/app/frontend/hooks/use-ticker.ts +0 -12
- data/app/frontend/hooks/use-window.ts +0 -58
- data/app/frontend/layouts/app/app-sidebar-layout.tsx +0 -107
- data/app/frontend/layouts/app-layout.tsx +0 -21
- data/app/frontend/layouts/env-layout.tsx +0 -53
- data/app/frontend/layouts/persistent-layout.tsx +0 -18
- data/app/frontend/lib/cable.ts +0 -10
- data/app/frontend/lib/env-pages.ts +0 -236
- data/app/frontend/lib/execution-path.ts +0 -55
- data/app/frontend/lib/explain.ts +0 -50
- data/app/frontend/lib/filter.ts +0 -25
- data/app/frontend/lib/flamegraph.ts +0 -155
- data/app/frontend/lib/format.ts +0 -71
- data/app/frontend/lib/keyboard.ts +0 -18
- data/app/frontend/lib/mount.ts +0 -23
- data/app/frontend/lib/source-link.ts +0 -217
- data/app/frontend/lib/utils.ts +0 -6
- data/app/frontend/pages/alerts/index.tsx +0 -171
- data/app/frontend/pages/broadcasts/index.tsx +0 -171
- data/app/frontend/pages/cache_events/index.tsx +0 -127
- data/app/frontend/pages/commands/index.tsx +0 -143
- data/app/frontend/pages/deploys/index.tsx +0 -94
- data/app/frontend/pages/deploys/show.tsx +0 -309
- data/app/frontend/pages/deprecations/index.tsx +0 -176
- data/app/frontend/pages/exceptions/index.tsx +0 -271
- data/app/frontend/pages/executions/show.tsx +0 -821
- data/app/frontend/pages/issues/index.tsx +0 -399
- data/app/frontend/pages/issues/show.tsx +0 -1367
- data/app/frontend/pages/jobs/index.tsx +0 -381
- data/app/frontend/pages/jobs/klass.tsx +0 -215
- data/app/frontend/pages/llm_calls/index.tsx +0 -664
- data/app/frontend/pages/logs/index.tsx +0 -303
- data/app/frontend/pages/mails/index.tsx +0 -218
- data/app/frontend/pages/notifications/index.tsx +0 -161
- data/app/frontend/pages/outgoing_requests/index.tsx +0 -309
- data/app/frontend/pages/overview/show.tsx +0 -333
- data/app/frontend/pages/people/index.tsx +0 -102
- data/app/frontend/pages/people/show.tsx +0 -149
- data/app/frontend/pages/processes/index.tsx +0 -335
- data/app/frontend/pages/profiles/index.tsx +0 -110
- data/app/frontend/pages/profiles/show.tsx +0 -105
- data/app/frontend/pages/queries/index.tsx +0 -492
- data/app/frontend/pages/queries/show.tsx +0 -276
- data/app/frontend/pages/releases/index.tsx +0 -190
- data/app/frontend/pages/releases/release-health.tsx +0 -68
- data/app/frontend/pages/releases/release-path.ts +0 -25
- data/app/frontend/pages/releases/show.tsx +0 -262
- data/app/frontend/pages/requests/index.tsx +0 -235
- data/app/frontend/pages/requests/route.tsx +0 -159
- data/app/frontend/pages/scheduled_tasks/index.tsx +0 -220
- data/app/frontend/pages/spans/index.tsx +0 -229
- data/app/frontend/pages/spans/show.tsx +0 -220
- data/app/frontend/pages/storage_ops/index.tsx +0 -150
- data/app/frontend/pages/tenants/index.tsx +0 -236
- data/app/frontend/pages/tenants/show.tsx +0 -477
- data/app/frontend/pages/tenants/tenant-path.ts +0 -26
- data/app/frontend/pages/thresholds/index.tsx +0 -414
- data/app/frontend/pages/traces/show.tsx +0 -208
- data/app/frontend/pages/transactions/index.tsx +0 -220
- data/app/frontend/pages/view_renders/index.tsx +0 -241
- data/app/frontend/pages/visits/index.tsx +0 -321
- data/app/frontend/public/icon.png +0 -0
- data/app/frontend/public/icon.svg +0 -5
- data/app/frontend/routes/index.d.ts +0 -2136
- data/app/frontend/routes/index.js +0 -2112
- data/app/frontend/types/globals.d.ts +0 -9
- data/app/frontend/types/index.ts +0 -288
- data/app/frontend/types/vite-env.d.ts +0 -9
- data/app/helpers/railwatch/assets_helper.rb +0 -52
- data/app/jobs/railwatch/anomaly_scan_job.rb +0 -11
- data/app/jobs/railwatch/application_job.rb +0 -7
- data/app/jobs/railwatch/auto_resolve_issues_job.rb +0 -19
- data/app/jobs/railwatch/check_scheduled_tasks_job.rb +0 -113
- data/app/jobs/railwatch/detect_anomalies_job.rb +0 -171
- data/app/jobs/railwatch/detect_performance_issues_job.rb +0 -95
- data/app/jobs/railwatch/group_exceptions_job.rb +0 -91
- data/app/jobs/railwatch/optimize_telemetry_job.rb +0 -23
- data/app/jobs/railwatch/performance_scan_job.rb +0 -11
- data/app/jobs/railwatch/prune_telemetry_job.rb +0 -129
- data/app/jobs/railwatch/release_health_rollup_job.rb +0 -64
- data/app/jobs/railwatch/rollup_catchup_job.rb +0 -21
- data/app/jobs/railwatch/rollup_job.rb +0 -132
- data/app/jobs/railwatch/scheduled_task_scan_job.rb +0 -11
- data/app/models/concerns/railwatch/detection_snapshotting.rb +0 -20
- data/app/models/railwatch/alert.rb +0 -229
- data/app/models/railwatch/alert_rule.rb +0 -121
- data/app/models/railwatch/anomaly_rule.rb +0 -51
- data/app/models/railwatch/application.rb +0 -44
- data/app/models/railwatch/application_record.rb +0 -33
- data/app/models/railwatch/comment.rb +0 -36
- data/app/models/railwatch/deploy.rb +0 -67
- data/app/models/railwatch/environment.rb +0 -68
- data/app/models/railwatch/execution_presenter.rb +0 -185
- data/app/models/railwatch/filter_query.rb +0 -184
- data/app/models/railwatch/followup_receipt.rb +0 -27
- data/app/models/railwatch/ingest/batch.rb +0 -355
- data/app/models/railwatch/ingest/mapper.rb +0 -585
- data/app/models/railwatch/ingest/payload.rb +0 -96
- data/app/models/railwatch/ingest/rollup_absorber.rb +0 -170
- data/app/models/railwatch/ingest/writer.rb +0 -137
- data/app/models/railwatch/issue.rb +0 -277
- data/app/models/railwatch/issue_activity.rb +0 -23
- data/app/models/railwatch/issue_detection_presenter.rb +0 -309
- data/app/models/railwatch/issue_detection_snapshot.rb +0 -77
- data/app/models/railwatch/maintenance_task.rb +0 -53
- data/app/models/railwatch/saved_view.rb +0 -63
- data/app/models/railwatch/telemetry/aggregations.rb +0 -251
- data/app/models/railwatch/telemetry/attachment.rb +0 -31
- data/app/models/railwatch/telemetry/bounded_gzip.rb +0 -101
- data/app/models/railwatch/telemetry/broadcast.rb +0 -13
- data/app/models/railwatch/telemetry/cache_event.rb +0 -16
- data/app/models/railwatch/telemetry/child.rb +0 -53
- data/app/models/railwatch/telemetry/cursor_page.rb +0 -99
- data/app/models/railwatch/telemetry/deprecation.rb +0 -13
- data/app/models/railwatch/telemetry/enqueued_job.rb +0 -13
- data/app/models/railwatch/telemetry/exception.rb +0 -28
- data/app/models/railwatch/telemetry/execution.rb +0 -152
- data/app/models/railwatch/telemetry/export_delivery.rb +0 -32
- data/app/models/railwatch/telemetry/export_destination.rb +0 -66
- data/app/models/railwatch/telemetry/health_sample.rb +0 -72
- data/app/models/railwatch/telemetry/ingest_batch.rb +0 -31
- data/app/models/railwatch/telemetry/llm_call.rb +0 -37
- data/app/models/railwatch/telemetry/log.rb +0 -91
- data/app/models/railwatch/telemetry/mail.rb +0 -13
- data/app/models/railwatch/telemetry/n_plus_one.rb +0 -92
- data/app/models/railwatch/telemetry/notification.rb +0 -13
- data/app/models/railwatch/telemetry/outgoing_request.rb +0 -13
- data/app/models/railwatch/telemetry/person.rb +0 -50
- data/app/models/railwatch/telemetry/process.rb +0 -10
- data/app/models/railwatch/telemetry/profile.rb +0 -37
- data/app/models/railwatch/telemetry/query.rb +0 -57
- data/app/models/railwatch/telemetry/query_shape.rb +0 -45
- data/app/models/railwatch/telemetry/release_health.rb +0 -69
- data/app/models/railwatch/telemetry/rollup.rb +0 -157
- data/app/models/railwatch/telemetry/session.rb +0 -24
- data/app/models/railwatch/telemetry/span.rb +0 -19
- data/app/models/railwatch/telemetry/storage_op.rb +0 -13
- data/app/models/railwatch/telemetry/tenant.rb +0 -240
- data/app/models/railwatch/telemetry/transaction.rb +0 -13
- data/app/models/railwatch/telemetry/view_render.rb +0 -13
- data/app/models/railwatch/telemetry/visit.rb +0 -24
- data/app/models/railwatch/telemetry_record.rb +0 -107
- data/app/models/railwatch/threshold.rb +0 -66
- data/app/models/railwatch/user.rb +0 -47
- data/app/models/railwatch/viewer.rb +0 -13
- data/app/models/railwatch/window.rb +0 -66
- data/app/views/layouts/railwatch/dashboard.html.erb +0 -25
- data/db/railwatch_migrate/20260916000000_create_railwatch_tables.rb +0 -151
- data/db/railwatch_migrate/20260917000000_create_railwatch_maintenance_tasks.rb +0 -18
- data/db/railwatch_migrate/20260917120000_create_railwatch_followup_receipts.rb +0 -20
- data/db/railwatch_migrate/20260918120000_widen_host_user_ids.rb +0 -71
- data/db/railwatch_telemetry_migrate/20260903000000_enable_incremental_vacuum.rb +0 -62
- data/db/railwatch_telemetry_migrate/20260903000001_create_telemetry.rb +0 -481
- data/db/railwatch_telemetry_migrate/20260903000002_rename_tenant_to_app_tenant.rb +0 -14
- data/db/railwatch_telemetry_migrate/20260903000003_add_statement_count_to_transactions.rb +0 -9
- data/db/railwatch_telemetry_migrate/20260903000004_add_role_and_channel.rb +0 -10
- data/db/railwatch_telemetry_migrate/20260903000005_add_locals_to_exceptions.rb +0 -9
- data/db/railwatch_telemetry_migrate/20260903000006_add_spans_health_vitals_and_fts.rb +0 -82
- data/db/railwatch_telemetry_migrate/20260903000007_rename_span_attributes_to_payload.rb +0 -10
- data/db/railwatch_telemetry_migrate/20260903000008_add_profiles_and_attachments.rb +0 -60
- data/db/railwatch_telemetry_migrate/20260903000009_add_truncated_to_attachments.rb +0 -9
- data/db/railwatch_telemetry_migrate/20260903000010_create_sessions_and_release_health.rb +0 -51
- data/db/railwatch_telemetry_migrate/20260903000011_add_fingerprint_to_exceptions.rb +0 -11
- data/db/railwatch_telemetry_migrate/20260904000012_add_failed_to_broadcasts.rb +0 -10
- data/db/railwatch_telemetry_migrate/20260904010000_add_filter_cursor_indexes.rb +0 -37
- data/db/railwatch_telemetry_migrate/20260904020000_add_n_plus_ones_execution_id_index.rb +0 -11
- data/db/railwatch_telemetry_migrate/20260904120000_create_query_shapes.rb +0 -15
- data/db/railwatch_telemetry_migrate/20260906120000_add_backpressure_factor_to_ingest_batches.rb +0 -9
- data/db/railwatch_telemetry_migrate/20260907000000_rename_lantern_version_on_processes.rb +0 -10
- data/db/railwatch_telemetry_migrate/20260913000000_rename_nightrail_version_on_processes.rb +0 -9
- data/db/railwatch_telemetry_migrate/20260914000000_drop_orphan_durable_ingest_tables.rb +0 -18
- data/db/railwatch_telemetry_migrate/20260914010000_drop_orphan_durable_ingest_columns.rb +0 -25
- data/db/railwatch_telemetry_migrate/20260915000000_create_llm_calls.rb +0 -55
- data/db/railwatch_telemetry_migrate/20260915120000_add_detail_to_llm_calls.rb +0 -21
- data/db/railwatch_telemetry_migrate/20260915200000_add_explained_index_to_queries.rb +0 -16
- data/db/railwatch_telemetry_migrate/20260915210000_add_slowest_index_to_queries.rb +0 -18
- data/db/railwatch_telemetry_migrate/20260917010000_add_batch_ledger_to_ingest_batches.rb +0 -16
- data/db/railwatch_telemetry_migrate/20260919000100_create_export_queue.rb +0 -146
- data/db/railwatch_telemetry_migrate/20260922000000_add_covering_indexes_for_dashboard_aggregates.rb +0 -34
- data/db/railwatch_telemetry_migrate/20260923000000_add_people_index.rb +0 -15
- data/db/railwatch_telemetry_migrate/20260925000000_add_tenant_summary_index.rb +0 -17
- data/db/railwatch_telemetry_migrate/20261008000000_add_in_transaction_to_outgoing_requests.rb +0 -10
- data/docs/embedded.md +0 -503
- data/lib/puma/plugin/railwatch.rb +0 -215
- data/lib/railwatch/dashboard_assets.rb +0 -45
- data/lib/railwatch/embedded.rb +0 -50
- data/lib/railwatch/export/client.rb +0 -124
- data/lib/railwatch/export/lease.rb +0 -56
- data/lib/railwatch/export/outbox.rb +0 -361
- data/lib/railwatch/export/policy.rb +0 -79
- data/lib/railwatch/export/sender.rb +0 -130
- data/lib/railwatch/ingest_request_body_limit.rb +0 -10
- data/lib/railwatch/maintenance.rb +0 -194
- data/lib/railwatch/patches/migration_busy_timeout.rb +0 -73
- data/lib/railwatch/transport/local.rb +0 -78
- data/lib/railwatch/transport/socket.rb +0 -183
- data/lib/railwatch/writer.rb +0 -370
- data/public/railwatch/assets/CommitMono-Bold-D6h61ieg.woff2 +0 -0
- data/public/railwatch/assets/CommitMono-Regular-zr8w7Obm.woff2 +0 -0
- data/public/railwatch/assets/Roboto-Black-auA4GeOK.woff2 +0 -0
- data/public/railwatch/assets/Roboto-Bold-CJLnO8j1.woff2 +0 -0
- data/public/railwatch/assets/Roboto-Medium-Cm2bwKpj.woff2 +0 -0
- data/public/railwatch/assets/Roboto-Regular-Chaq1-PV.woff2 +0 -0
- data/public/railwatch/assets/app-layout-by7G3sa1.js +0 -41
- data/public/railwatch/assets/application-Cc5v_Vk9.css +0 -1
- data/public/railwatch/assets/arrow-up-DCZ7emux.js +0 -1
- data/public/railwatch/assets/braces-CykT5_5u.js +0 -1
- data/public/railwatch/assets/card-C-PPSA0g.js +0 -1
- data/public/railwatch/assets/chart-Cov79YC5.js +0 -39
- data/public/railwatch/assets/chart-hover-DdK4E-2h.js +0 -1
- data/public/railwatch/assets/chart-panel-BPaYRXJB.js +0 -1
- data/public/railwatch/assets/code-BYjC4YZ_.js +0 -1
- data/public/railwatch/assets/copy-id-LPfoj9cC.js +0 -1
- data/public/railwatch/assets/cursor-load-more-DSdhgpGl.js +0 -1
- data/public/railwatch/assets/data-table-CQ_YRWQs.js +0 -1
- data/public/railwatch/assets/env-layout-CdMWbUkm.js +0 -1
- data/public/railwatch/assets/execution-path-7MYt-Qbn.js +0 -1
- data/public/railwatch/assets/filter-bar-CrzpQ_vD.js +0 -1
- data/public/railwatch/assets/flamegraph-BIFEdTAg.js +0 -2
- data/public/railwatch/assets/format-B9SDkrWj.js +0 -1
- data/public/railwatch/assets/frames-C5t-x4f0.js +0 -1
- data/public/railwatch/assets/index--NQ7us-L.js +0 -1
- data/public/railwatch/assets/index-2kgYe_99.js +0 -1
- data/public/railwatch/assets/index-4YEPHxtO.js +0 -1
- data/public/railwatch/assets/index-AOCC1GDJ.js +0 -1
- data/public/railwatch/assets/index-BEo-u0eO.js +0 -1
- data/public/railwatch/assets/index-BJ1V3w2N.js +0 -1
- data/public/railwatch/assets/index-BPoHsBKb.js +0 -1
- data/public/railwatch/assets/index-BZzyGUM3.js +0 -1
- data/public/railwatch/assets/index-BgVq7yKL.js +0 -1
- data/public/railwatch/assets/index-BqFGEZvW.js +0 -1
- data/public/railwatch/assets/index-ByuHJ1CH.js +0 -1
- data/public/railwatch/assets/index-C2j50AL2.js +0 -1
- data/public/railwatch/assets/index-CLEdTkvW.js +0 -1
- data/public/railwatch/assets/index-CWgq8qBu.js +0 -1
- data/public/railwatch/assets/index-CXQ7_oVj.js +0 -2
- data/public/railwatch/assets/index-CmyYrjS2.js +0 -1
- data/public/railwatch/assets/index-Cn9_HjDo.js +0 -1
- data/public/railwatch/assets/index-CsMAm9UK.js +0 -1
- data/public/railwatch/assets/index-D0Kk_oGY.js +0 -1
- data/public/railwatch/assets/index-DC9ZptJh.js +0 -1
- data/public/railwatch/assets/index-DNzg7jmV.js +0 -1
- data/public/railwatch/assets/index-DQ8uJO5f.js +0 -1
- data/public/railwatch/assets/index-Deq14BxB.js +0 -1
- data/public/railwatch/assets/index-IaV3Blzp.js +0 -1
- data/public/railwatch/assets/index-TYNWcJQs.js +0 -1
- data/public/railwatch/assets/index-WonH2fcZ.js +0 -1
- data/public/railwatch/assets/index-WxWUaH_d.js +0 -1
- data/public/railwatch/assets/index-mUNrl4ky.js +0 -1
- data/public/railwatch/assets/inertia-DfNRARuA.js +0 -97
- data/public/railwatch/assets/json-viewer-DMsF5glp.js +0 -1
- data/public/railwatch/assets/klass-CmHYk5rz.js +0 -1
- data/public/railwatch/assets/origin-identity-1R3bqa3R.js +0 -1
- data/public/railwatch/assets/percentile-picker-73z5PAps.js +0 -1
- data/public/railwatch/assets/relative-time-Dsc_cCdX.js +0 -1
- data/public/railwatch/assets/release-health-BV5OaOWd.js +0 -1
- data/public/railwatch/assets/route-CWh58C7K.js +0 -1
- data/public/railwatch/assets/segmented-DB4zh-Am.js +0 -1
- data/public/railwatch/assets/select-DBKjFlOX.js +0 -1
- data/public/railwatch/assets/series-chart-BaiDG795.js +0 -1
- data/public/railwatch/assets/show-B4ICCFGh.js +0 -1
- data/public/railwatch/assets/show-B5lOU9Gv.js +0 -1
- data/public/railwatch/assets/show-BYPB74t4.js +0 -2
- data/public/railwatch/assets/show-C7A0m2M8.js +0 -1
- data/public/railwatch/assets/show-DT5X1zqE.js +0 -1
- data/public/railwatch/assets/show-D_NBdXsn.js +0 -2
- data/public/railwatch/assets/show-DgPCnRg8.js +0 -1
- data/public/railwatch/assets/show-Yl69HF0x.js +0 -1
- data/public/railwatch/assets/show-_QxuUQCm.js +0 -3
- data/public/railwatch/assets/show-g__jnN36.js +0 -1
- data/public/railwatch/assets/show-l4ztfjl9.js +0 -1
- data/public/railwatch/assets/sort-header-BcG8ulEH.js +0 -1
- data/public/railwatch/assets/source-link-B2183i2-.js +0 -1
- data/public/railwatch/assets/sparkline-cell-B47ipscB.js +0 -1
- data/public/railwatch/assets/stat-DT2hhsqS.js +0 -1
- data/public/railwatch/assets/status-badge-CmbRKlY7.js +0 -1
- data/public/railwatch/assets/tenant-path-C4rNGauE.js +0 -1
- data/public/railwatch/assets/use-clipboard-oTNeP4ax.js +0 -1
- data/public/railwatch/assets/use-live-CLZZj245.js +0 -1
- data/public/railwatch/icon.png +0 -0
- data/public/railwatch/icon.svg +0 -5
- data/public/railwatch/manifest.json +0 -1245
- data/public/railwatch/rails-vite.json +0 -1
- /data/{app/frontend/lib → lib/generators/railwatch/install/templates}/railwatch.ts +0 -0
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 3620348235aae6e5733728931b85a9c0edd0ac31367a4fd143eceee1de28cbc0
|
|
4
|
+
data.tar.gz: 273a578b3059f4390854d7452df971d8223c9e4f6c8c6a9e7e8d9f46a27ef1f3
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 82640c29a57b4c99d890b40ef75179d635b53308879516ba4973aaed0cfa1179696e0ee14e6660be2eb59c935611eb395e9f508e583c2604fbe8a7e57da0f8ad
|
|
7
|
+
data.tar.gz: 53ff388054d12658c7d0cb99c3d0c3dd01be8579ac2227efbb07d65f008a766851761655904b081c8f344aa5db6f3ad9d2cb1e25a349bf30b943e85cb74489bc
|
data/AGENTS.md
CHANGED
|
@@ -4,9 +4,11 @@ About *using* the `railwatch` gem from a Rails application; copy
|
|
|
4
4
|
this into that application's repository. Index of everything else:
|
|
5
5
|
[`llms.txt`](llms.txt).
|
|
6
6
|
|
|
7
|
-
Railwatch instruments a Rails app end to end and
|
|
8
|
-
|
|
9
|
-
|
|
7
|
+
Railwatch instruments a Rails app end to end and sends linked telemetry over
|
|
8
|
+
HTTPS to a Railwatch server: Railwatch Cloud (`https://railwatch.rebulk.com`,
|
|
9
|
+
the default), a self-hosted [railwatch-rs](https://github.com/Rebulk/railwatch-rs),
|
|
10
|
+
or the one the [`railwatch-server`](https://github.com/Rebulk/railwatch-server)
|
|
11
|
+
gem runs next to Puma. Every request, job attempt, scheduled task run, and command is
|
|
10
12
|
an **execution**; every query, cache read, log line, outgoing HTTP call, LLM
|
|
11
13
|
call, view render, exception, and span is a child of one, linked by
|
|
12
14
|
`execution_id`/`trace_id`. It never writes to the app's primary database.
|
|
@@ -15,40 +17,41 @@ call, view render, exception, and span is a child of one, linked by
|
|
|
15
17
|
|
|
16
18
|
```sh
|
|
17
19
|
bundle add railwatch
|
|
18
|
-
bin/rails generate railwatch:install
|
|
19
|
-
bin/rails generate railwatch:install --
|
|
20
|
+
bin/rails generate railwatch:install --prompt-token --kamal-secrets # Railwatch Cloud
|
|
21
|
+
bin/rails generate railwatch:install --url=https://telemetry.example.com # self-hosted railwatch-rs
|
|
20
22
|
```
|
|
21
23
|
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
`RAILS_ENV=production bin/rails railwatch:authentication:configure` sets a
|
|
28
|
-
password. An exported `RAILWATCH_TOKEN` alone does not change the mode.
|
|
29
|
-
`--cloud`, or any of `--prompt-token`, `--token-stdin`, `--url`,
|
|
30
|
-
`--kamal-secrets`, sends telemetry to Railwatch Cloud instead.
|
|
31
|
-
|
|
32
|
-
Both modes write `config/initializers/railwatch.rb`, mount `Railwatch::Engine`
|
|
33
|
-
at `/railwatch`, add the Kamal `post-deploy` hook and the Inertia browser client
|
|
34
|
-
where the app has them, and require `railwatch/rspec` (or `railwatch/minitest`)
|
|
35
|
-
in the test helper; the cloud install then runs `railwatch:doctor`. A
|
|
24
|
+
The generator writes `config/initializers/railwatch.rb`, mounts
|
|
25
|
+
`Railwatch::Engine` at `/railwatch` (it serves only the browser beacon), adds
|
|
26
|
+
the Kamal `post-deploy` hook and the Inertia browser client where the app has
|
|
27
|
+
them, requires `railwatch/rspec` (or `railwatch/minitest`) in the test helper,
|
|
28
|
+
and runs `railwatch:doctor` (`--no-doctor` skips it). A
|
|
36
29
|
prompted/stdin/environment token goes into `.env` only when Git confirms that
|
|
37
|
-
file is ignored; token values are never printed.
|
|
38
|
-
that initializer; every option also has a
|
|
39
|
-
|
|
40
|
-
|
|
30
|
+
file is ignored; token values are never printed. Without a token the gem is
|
|
31
|
+
inert. Configuration lives only in that initializer; every option also has a
|
|
32
|
+
`RAILWATCH_*` environment variable.
|
|
33
|
+
|
|
34
|
+
Embedded (the dashboard inside the app, no token to manage): add
|
|
35
|
+
`gem "railwatch-server"` to the Gemfile and `plugin :railwatch_server` to
|
|
36
|
+
`config/puma.rb`. It provisions `storage/railwatch/<env>` on first boot and
|
|
37
|
+
points this agent at it. Its dashboard at `/railwatch` is gated by this gem's
|
|
38
|
+
`http_basic_auth_*` settings (open in development, 401 elsewhere until
|
|
39
|
+
`RAILS_ENV=production bin/rails railwatch:authentication:configure` sets a
|
|
40
|
+
password) or, with Basic off, by `c.base_controller_class`.
|
|
41
|
+
|
|
42
|
+
Railwatch 0.x's in-gem embedded mode (`c.transport = :local`, `plugin :railwatch`,
|
|
43
|
+
the `railwatch`/`railwatch_telemetry` databases) is gone in 1.0; remove all three
|
|
44
|
+
and add railwatch-server. Its old SQLite files are not migrated.
|
|
41
45
|
|
|
42
46
|
## Rake tasks
|
|
43
47
|
|
|
44
48
|
| Task | Does |
|
|
45
49
|
|---|---|
|
|
46
|
-
| `bin/rails railwatch:doctor` | ✓/✗ per check
|
|
47
|
-
| `bin/rails railwatch:authentication:configure` | Sets the
|
|
48
|
-
| `bin/rails railwatch:
|
|
49
|
-
| `bin/rails railwatch:
|
|
50
|
-
| `bin/rails railwatch:
|
|
51
|
-
| `bin/rails railwatch:deploy[ref,name,url]` | Records a deploy marker (in the embedded database, or on the cloud). Use as a release step when not deploying with Kamal. |
|
|
50
|
+
| `bin/rails railwatch:doctor` | ✓/✗ per check: token, token storage, ingest URL, reachability, middleware, engine mount, deploy, sample rates, ignored types, Kamal hook, browser client and whether an entrypoint calls it, profiler backend, test matchers. Exits non-zero on a missing or tracked token, or an unreachable host. **Run this first when telemetry is missing.** |
|
|
51
|
+
| `bin/rails railwatch:authentication:configure` | Sets the HTTP Basic credentials that gate railwatch-server's dashboard, for the current `RAILS_ENV`. |
|
|
52
|
+
| `bin/rails railwatch:token` | Where to create an ingest token for this app on the server `ingest_url` points at. |
|
|
53
|
+
| `bin/rails railwatch:mcp` | Paste-ready MCP client configuration for that server. |
|
|
54
|
+
| `bin/rails railwatch:deploy[ref,name,url]` | Records a deploy marker on the server. Use as a release step when not deploying with Kamal. |
|
|
52
55
|
| `bin/rails 'railwatch:sourcemaps[public,true]'` | Uploads Vite source maps for the configured deploy, then deletes acknowledged files. Run after building and before publishing assets. Omit `true` to retain files. See [Source maps](docs/source-maps.md). |
|
|
53
56
|
|
|
54
57
|
## Facade
|
|
@@ -89,9 +92,9 @@ Per action, in a controller class body: `railwatch_sample 0.01, only: :index`,
|
|
|
89
92
|
## Specs
|
|
90
93
|
|
|
91
94
|
`require "railwatch/rspec"` in `spec/rails_helper.rb` (or `"railwatch/minitest"` in
|
|
92
|
-
`test/test_helper.rb`). Railwatch must be enabled in the test env
|
|
93
|
-
|
|
94
|
-
|
|
95
|
+
`test/test_helper.rb`). Railwatch must be enabled in the test env, which
|
|
96
|
+
needs any non-blank `RAILWATCH_TOKEN` there (railwatch-server is off in test
|
|
97
|
+
and does not set one). Records
|
|
95
98
|
go to an in-memory transport, never over the wire. All matchers are block
|
|
96
99
|
matchers.
|
|
97
100
|
|
|
@@ -117,7 +120,8 @@ melt in production.
|
|
|
117
120
|
|
|
118
121
|
## MCP
|
|
119
122
|
|
|
120
|
-
Railwatch Cloud
|
|
123
|
+
Railwatch Cloud and railwatch-rs are MCP servers at `<ingest host>/mcp`
|
|
124
|
+
(with railwatch-server: the app's host plus `/railwatch/mcp`).
|
|
121
125
|
Generate a personal token at Settings → Profile → "API & MCP token", then:
|
|
122
126
|
|
|
123
127
|
```sh
|
data/CHANGELOG.md
CHANGED
|
@@ -6,6 +6,69 @@
|
|
|
6
6
|
filled in by the release commit, which is also the only commit that
|
|
7
7
|
touches lib/railwatch/version.rb and Gemfile.lock. See CONTRIBUTING.md. -->
|
|
8
8
|
|
|
9
|
+
## 1.1.0 (2026-10-22)
|
|
10
|
+
|
|
11
|
+
- A receiver that refuses the connection (nothing listening: a Railwatch
|
|
12
|
+
server restarting, or a deploy handing over to the next container) no
|
|
13
|
+
longer counts as backpressure. The retry ladder it starts used to double
|
|
14
|
+
the sampling divisor every flush tick, so the app's first requests after
|
|
15
|
+
the server came back were sampled out: a fresh app recorded 23-29 of 30
|
|
16
|
+
requests sent right after its embedded server was killed and restarted,
|
|
17
|
+
in every one of 10 runs. A timeout, a 5xx and a full buffer are still
|
|
18
|
+
pressure.
|
|
19
|
+
- `Configuration#local?` is gone. It was kept in 1.0.0 only for
|
|
20
|
+
railwatch-server 0.1.0; railwatch-server 0.1.1 no longer calls it.
|
|
21
|
+
|
|
22
|
+
## 1.0.0 (2026-10-22)
|
|
23
|
+
|
|
24
|
+
- **Breaking: `railwatch` is the agent only.** It instruments the app and
|
|
25
|
+
sends to an ingest URL: Railwatch Cloud (the default,
|
|
26
|
+
`https://railwatch.rebulk.com`) or a self-hosted
|
|
27
|
+
[railwatch-rs](https://github.com/Rebulk/railwatch-rs) server
|
|
28
|
+
(`RAILWATCH_INGEST_URL`, `RAILWATCH_TOKEN`). Embedded mode is gone from
|
|
29
|
+
this gem: `transport :local` / `RAILWATCH_TRANSPORT`, the two SQLite
|
|
30
|
+
databases (`railwatch`, `railwatch_telemetry`) and their migrations, the
|
|
31
|
+
Puma writer (`plugin :railwatch`), the maintenance clock, export to the
|
|
32
|
+
cloud, the dashboard pages, its live channel and its compiled bundle.
|
|
33
|
+
The dashboard is part of the server now, and the gem has no runtime
|
|
34
|
+
dependency on `inertia_rails` or `tdigest`.
|
|
35
|
+
- The dashboard inside the app is the separate
|
|
36
|
+
[railwatch-server](https://github.com/Rebulk/railwatch-server) gem. It
|
|
37
|
+
runs the railwatch-rs server next to Puma and points this agent at it.
|
|
38
|
+
- Removed settings: `transport`, `issue_prefix`, `repository_url`,
|
|
39
|
+
`retention_days`, `dashboard_user`, `dashboard_open`, `writer_socket`,
|
|
40
|
+
`migration_busy_timeout`, and every `export_*`, with their
|
|
41
|
+
`RAILWATCH_*` variables. Removed rake tasks: `railwatch:vacuum`,
|
|
42
|
+
`railwatch:vacuum:status`, `railwatch:export:status`, `:rebind` and
|
|
43
|
+
`:discard`. Removed: `Railwatch.migrations_path`,
|
|
44
|
+
`Railwatch.url_helpers`, `Railwatch.frontend_path`.
|
|
45
|
+
- `http_basic_auth_enabled`, `http_basic_auth_user`,
|
|
46
|
+
`http_basic_auth_password`, `base_controller_class` and
|
|
47
|
+
`bin/rails railwatch:authentication:configure` stay. They are the gate
|
|
48
|
+
railwatch-server puts in front of its dashboard, and do nothing without
|
|
49
|
+
it.
|
|
50
|
+
- `bin/rails generate railwatch:install` sets up the agent only: token,
|
|
51
|
+
ingest URL (`--url` for a self-hosted server), the beacon mount, the
|
|
52
|
+
Kamal hook, the browser client and the test helpers. It no longer
|
|
53
|
+
writes `config/database.yml` or `config/puma.rb`, and `--cloud` is gone
|
|
54
|
+
because there is no other mode.
|
|
55
|
+
- The browser client moved to
|
|
56
|
+
`lib/generators/railwatch/install/templates/railwatch.ts`
|
|
57
|
+
(`Railwatch.browser_client_path`). Apps that already copied it keep
|
|
58
|
+
their copy at `app/frontend/lib/railwatch.ts`.
|
|
59
|
+
- Upgrading an embedded 0.x install: delete `c.transport = :local` (or
|
|
60
|
+
`RAILWATCH_TRANSPORT=local`), delete `plugin :railwatch` from
|
|
61
|
+
`config/puma.rb` (Puma refuses to boot with a plugin it cannot find),
|
|
62
|
+
and delete the `railwatch` and `railwatch_telemetry` entries from
|
|
63
|
+
`config/database.yml`. Then add `gem "railwatch-server"` and
|
|
64
|
+
`plugin :railwatch_server`. The old data in
|
|
65
|
+
`storage/<env>_railwatch.sqlite3` and
|
|
66
|
+
`storage/<env>_railwatch_telemetry.sqlite3` is not migrated: railwatch-rs
|
|
67
|
+
has no import for these files (`railwatch import-rails` reads a
|
|
68
|
+
Railwatch Cloud install, not this gem's embedded databases), so the new
|
|
69
|
+
dashboard starts empty. Keep the old files only if you want them; they
|
|
70
|
+
can be deleted.
|
|
71
|
+
|
|
9
72
|
## 0.9.4 (2026-10-22)
|
|
10
73
|
|
|
11
74
|
- Sampling recovers as soon as ingest does. A receiver refusing with a
|
data/README.md
CHANGED
|
@@ -6,37 +6,26 @@ outgoing HTTP, storage, views, and logs, and links them into one trace
|
|
|
6
6
|
per execution, for about half a millisecond per request plus tens of
|
|
7
7
|
microseconds per query, with zero writes to your database.
|
|
8
8
|
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
Node, no Redis and no job worker. Railwatch Cloud is optional: it
|
|
13
|
-
delivers alerts to Slack, email, webhooks or Linear (including when the
|
|
14
|
-
app is down), serves MCP to your AI assistant, and puts many apps and
|
|
15
|
-
servers in one place.
|
|
9
|
+
The gem is the agent. It sends what it records over HTTPS to a
|
|
10
|
+
Railwatch server, which stores it, groups exceptions into issues, sends
|
|
11
|
+
alerts, and serves the dashboard and an MCP server:
|
|
16
12
|
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
Restart and open `/railwatch`. It is open in development; before you
|
|
25
|
-
deploy, give it a password with
|
|
26
|
-
`RAILS_ENV=production bin/rails railwatch:authentication:configure`
|
|
27
|
-
(it answers 401 in production until you do). On a PostgreSQL or MySQL
|
|
28
|
-
app without the `sqlite3` gem, the generator adds it to the Gemfile;
|
|
29
|
-
run `bundle install` and `bin/rails db:prepare` to finish.
|
|
13
|
+
- **Railwatch Cloud** at <https://railwatch.rebulk.com>, the default.
|
|
14
|
+
- **Self-hosted [railwatch-rs](https://github.com/Rebulk/railwatch-rs)**,
|
|
15
|
+
one static binary for many apps ([Self-hosting](docs/self-hosting.md)).
|
|
16
|
+
- **Embedded**: the [`railwatch-server`](https://github.com/Rebulk/railwatch-server)
|
|
17
|
+
gem runs that server next to Puma for one app and serves the dashboard
|
|
18
|
+
at `/railwatch`, with nothing else to run.
|
|
30
19
|
|
|
31
|
-
|
|
32
|
-
option:
|
|
20
|
+
## Install
|
|
33
21
|
|
|
34
22
|
```sh
|
|
35
|
-
bundle add railwatch
|
|
36
|
-
bin/rails generate railwatch:install --prompt-token
|
|
23
|
+
bundle add railwatch # 1. add the public gem
|
|
24
|
+
bin/rails generate railwatch:install --prompt-token # 2. hidden token input plus app wiring
|
|
37
25
|
bin/rails railwatch:doctor # check every piece is wired up after restart
|
|
38
26
|
```
|
|
39
27
|
|
|
28
|
+
For a self-hosted server, add `--url=https://telemetry.example.com`.
|
|
40
29
|
The generator's flags, getting a token, and deploying with Kamal,
|
|
41
30
|
Docker, Heroku, or Render are covered in
|
|
42
31
|
[Getting started](docs/getting-started.md). For an unreleased revision,
|
|
@@ -46,6 +35,36 @@ use the Git source instead:
|
|
|
46
35
|
gem "railwatch", github: "Rebulk/railwatch"
|
|
47
36
|
```
|
|
48
37
|
|
|
38
|
+
### Embedded
|
|
39
|
+
|
|
40
|
+
To keep everything inside the app, add `railwatch-server` next to this
|
|
41
|
+
gem:
|
|
42
|
+
|
|
43
|
+
```ruby
|
|
44
|
+
# Gemfile
|
|
45
|
+
gem "railwatch"
|
|
46
|
+
gem "railwatch-server"
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
```ruby
|
|
50
|
+
# config/puma.rb
|
|
51
|
+
plugin :railwatch_server
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
It provisions its data under `storage/railwatch/<env>` on first boot and
|
|
55
|
+
points this gem at it, so there is no token to manage. The dashboard at
|
|
56
|
+
`/railwatch` is open in development and answers 401 elsewhere until you
|
|
57
|
+
give it a password with
|
|
58
|
+
`RAILS_ENV=production bin/rails railwatch:authentication:configure`, or
|
|
59
|
+
put it behind your own admin authentication
|
|
60
|
+
([Configuration](docs/configuration.md#dashboard-gate-railwatch-server)).
|
|
61
|
+
Everything else is in the
|
|
62
|
+
[railwatch-server README](https://github.com/Rebulk/railwatch-server#readme).
|
|
63
|
+
|
|
64
|
+
Railwatch 0.x kept embedded telemetry in two SQLite databases written by
|
|
65
|
+
`plugin :railwatch`. 1.0 removes that mode; see
|
|
66
|
+
[Coming from 0.x embedded mode](docs/getting-started.md#coming-from-0x-embedded-mode).
|
|
67
|
+
|
|
49
68
|
## What you get
|
|
50
69
|
|
|
51
70
|
- Requests, jobs, scheduled tasks, commands, queries, exceptions, and
|
|
@@ -63,8 +82,8 @@ gem "railwatch", github: "Rebulk/railwatch"
|
|
|
63
82
|
and browser errors ([Getting started](docs/getting-started.md)).
|
|
64
83
|
- RSpec and Minitest matchers that turn a query budget into a CI gate
|
|
65
84
|
([Testing](docs/testing.md)).
|
|
66
|
-
-
|
|
67
|
-
Zed can read your production data
|
|
85
|
+
- An MCP server on the Railwatch server, so Claude Code, Cursor, VS Code,
|
|
86
|
+
or Zed can read your production data
|
|
68
87
|
([AI assistants and MCP](docs/ai-and-mcp.md)).
|
|
69
88
|
|
|
70
89
|
Configuration lives in `config/initializers/railwatch.rb`; most options
|
|
@@ -85,36 +104,12 @@ expect { get "/widgets" }.to have_railwatch_queries(at_most: 6)
|
|
|
85
104
|
expect { get "/widgets" }.not_to have_railwatch_n_plus_one
|
|
86
105
|
```
|
|
87
106
|
|
|
88
|
-
## Embedded mode
|
|
89
|
-
|
|
90
|
-
Telemetry goes to two SQLite files the app owns -- `railwatch` for
|
|
91
|
-
issues, comments and saved views, `railwatch_telemetry` for what the app
|
|
92
|
-
reports -- and the dashboard is served at `/railwatch` from a bundle
|
|
93
|
-
shipped inside the gem. Nothing leaves the machine unless you turn on
|
|
94
|
-
export to Railwatch Cloud, and there is nothing else to run.
|
|
95
|
-
|
|
96
|
-
Puma forks a single writer process (`plugin :railwatch`, which the
|
|
97
|
-
installer adds) that owns both files. The web workers hand it batches
|
|
98
|
-
over a Unix socket instead of writing SQLite on their own threads, and it
|
|
99
|
-
runs the maintenance clock too, so exception grouping, rollups, retention
|
|
100
|
-
and threshold scans happen without a queue.
|
|
101
|
-
|
|
102
|
-
That dashboard reads every query, log line and exception the app
|
|
103
|
-
produced, so it is gated the way Mission Control Jobs is: HTTP Basic is
|
|
104
|
-
on, and with no credentials every request is 401 until you set them
|
|
105
|
-
with `bin/rails railwatch:authentication:configure`. Development is the
|
|
106
|
-
exception: with no credentials set there, it is open. Apps that would
|
|
107
|
-
rather use their own authentication turn Basic off and gate the pages
|
|
108
|
-
with `base_controller_class` or a routes constraint around the mount; a
|
|
109
|
-
`dashboard_user` resolver then names the operator and authorizes live
|
|
110
|
-
updates, but does not gate pages. [Embedded mode](docs/embedded.md)
|
|
111
|
-
covers all of it, including upgrades and what it costs to store.
|
|
112
|
-
|
|
113
107
|
## Documentation
|
|
114
108
|
|
|
115
|
-
- [Getting started](docs/getting-started.md) — the
|
|
116
|
-
|
|
117
|
-
deploying with Kamal, Docker, Heroku, Render, or none
|
|
109
|
+
- [Getting started](docs/getting-started.md) — the install and its token,
|
|
110
|
+
embedded with railwatch-server, moving from 0.x embedded mode, the three
|
|
111
|
+
optional lines, and deploying with Kamal, Docker, Heroku, Render, or none
|
|
112
|
+
of them.
|
|
118
113
|
- [Configuration](docs/configuration.md) — every option and `RAILWATCH_*`
|
|
119
114
|
variable, field by field.
|
|
120
115
|
- [Record types](docs/records.md) — every record Railwatch ships and every
|
|
@@ -122,17 +117,13 @@ covers all of it, including upgrades and what it costs to store.
|
|
|
122
117
|
- [Testing](docs/testing.md) — the RSpec and Minitest matchers, and a CI
|
|
123
118
|
performance gate.
|
|
124
119
|
- [AI assistants and MCP](docs/ai-and-mcp.md) — connecting Claude Code,
|
|
125
|
-
Cursor, VS Code, or Zed to your production data
|
|
126
|
-
Cloud.
|
|
120
|
+
Cursor, VS Code, or Zed to your production data.
|
|
127
121
|
- [Replacing Sentry](docs/replacing-sentry.md) — a step-by-step migration,
|
|
128
122
|
option by option and call site by call site.
|
|
129
123
|
- [Coming from Laravel Nightwatch](docs/replacing-nightwatch.md) — the
|
|
130
124
|
record-type mapping and the sampling model, for Laravel people.
|
|
131
|
-
- [Embedded mode](docs/embedded.md) — the default: the whole dashboard
|
|
132
|
-
inside your app, telemetry in your own SQLite files, and optional
|
|
133
|
-
export to Railwatch Cloud.
|
|
134
125
|
- [Self-hosting](docs/self-hosting.md) — pointing the gem at your own
|
|
135
|
-
|
|
126
|
+
railwatch-rs server.
|
|
136
127
|
- [Troubleshooting](docs/troubleshooting.md) — every failure mode, paired
|
|
137
128
|
with the `railwatch:doctor` line it shows up as.
|
|
138
129
|
- [FAQ](docs/faq.md) — overhead numbers, retention, PII posture, SQLite.
|
data/config/routes.rb
CHANGED
|
@@ -2,63 +2,4 @@
|
|
|
2
2
|
|
|
3
3
|
Railwatch::Engine.routes.draw do
|
|
4
4
|
post "beacon", to: "beacon#create"
|
|
5
|
-
|
|
6
|
-
# The embedded dashboard. Same URL shape as the hosted platform so the
|
|
7
|
-
# prebuilt bundle's route helpers resolve unchanged once js-routes knows
|
|
8
|
-
# the mount point; a singleton install always answers for app 1, env 1.
|
|
9
|
-
root to: redirect { |_p, req| "#{req.script_name}/apps/1/envs/1" }
|
|
10
|
-
get "dashboard", to: redirect { |_p, req| "#{req.script_name}/apps/1/envs/1" }
|
|
11
|
-
get "docs", to: redirect("https://railwatch.rebulk.com/docs")
|
|
12
|
-
|
|
13
|
-
scope "apps/:application_id", as: :application do
|
|
14
|
-
get "/", to: redirect { |p, req| "#{req.script_name}/apps/#{p[:application_id]}/envs/1" }
|
|
15
|
-
scope "envs/:environment_id", as: :environment do
|
|
16
|
-
get "/", to: "overview#show", as: :overview
|
|
17
|
-
resources :requests, only: [ :index, :show ] do
|
|
18
|
-
get "routes/:group_hash", to: "requests#route", on: :collection, as: :route
|
|
19
|
-
end
|
|
20
|
-
resources :jobs, only: [ :index, :show ] do
|
|
21
|
-
get "classes/:group_hash", to: "jobs#klass", on: :collection, as: :klass
|
|
22
|
-
end
|
|
23
|
-
resources :scheduled_tasks, only: [ :index, :show ]
|
|
24
|
-
resources :commands, only: [ :index, :show ]
|
|
25
|
-
resources :executions, only: [ :show ]
|
|
26
|
-
resources :queries, only: [ :index, :show ]
|
|
27
|
-
resources :spans, only: [ :index, :show ]
|
|
28
|
-
resources :profiles, only: [ :index, :show ]
|
|
29
|
-
resources :attachments, only: [ :show ]
|
|
30
|
-
get "traces/:trace_id", to: "traces#show", as: :trace
|
|
31
|
-
resources :view_renders, path: "views", only: [ :index ]
|
|
32
|
-
resources :transactions, only: [ :index ]
|
|
33
|
-
resources :deprecations, only: [ :index ]
|
|
34
|
-
resources :exceptions, only: [ :index ]
|
|
35
|
-
resources :cache_events, path: "cache", only: [ :index ]
|
|
36
|
-
resources :mails, path: "mail", only: [ :index ]
|
|
37
|
-
resources :notifications, only: [ :index ]
|
|
38
|
-
resources :broadcasts, only: [ :index ]
|
|
39
|
-
resources :outgoing_requests, only: [ :index ]
|
|
40
|
-
resources :llm_calls, path: "llm", only: [ :index ]
|
|
41
|
-
resources :storage_ops, path: "storage", only: [ :index ]
|
|
42
|
-
resources :logs, only: [ :index ]
|
|
43
|
-
resources :people, path: "users", only: [ :index, :show ]
|
|
44
|
-
resources :deploys, only: [ :index, :show ]
|
|
45
|
-
resources :releases, only: [ :index, :show ]
|
|
46
|
-
resources :visits, only: [ :index ]
|
|
47
|
-
resources :processes, only: [ :index ]
|
|
48
|
-
resources :tenants, only: [ :index, :show ]
|
|
49
|
-
resources :saved_views, only: [ :create, :update, :destroy ]
|
|
50
|
-
resources :thresholds, only: [ :index, :create, :update, :destroy ]
|
|
51
|
-
resources :anomaly_rules, only: [ :create, :update, :destroy ]
|
|
52
|
-
resources :alerts, only: [ :index ]
|
|
53
|
-
end
|
|
54
|
-
end
|
|
55
|
-
|
|
56
|
-
resources :issues, only: [ :index, :show, :update ] do
|
|
57
|
-
resources :comments, only: [ :create ]
|
|
58
|
-
post :bulk, on: :collection
|
|
59
|
-
get :merge_candidates, on: :member
|
|
60
|
-
end
|
|
61
|
-
resources :alerts, only: [ :index ] do
|
|
62
|
-
post :retry, on: :member
|
|
63
|
-
end
|
|
64
5
|
end
|
data/docs/ai-and-mcp.md
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
# AI assistants and MCP
|
|
2
2
|
|
|
3
|
-
Railwatch Cloud
|
|
3
|
+
Railwatch Cloud, and any railwatch-rs server, is an
|
|
4
|
+
[MCP](https://modelcontextprotocol.io) server. Point
|
|
4
5
|
Claude Code, Claude Desktop, Cursor, VS Code, or Zed at it and the assistant
|
|
5
6
|
sitting in your editor can read the same production data your dashboards
|
|
6
7
|
show: issues and their stack traces, slow routes, the queries and N+1s
|
|
@@ -9,13 +10,13 @@ crash-free rates per release. It can also write — resolve an issue, set a
|
|
|
9
10
|
priority, leave a comment — and every write is signed with your user and the
|
|
10
11
|
agent's name in the issue's activity feed.
|
|
11
12
|
|
|
12
|
-
MCP is a Railwatch Cloud feature. The embedded dashboard at `/railwatch`
|
|
13
|
-
does not serve it; an embedded install gets it by
|
|
14
|
-
[exporting to the cloud](embedded.md#three-ways-to-run-it).
|
|
15
|
-
|
|
16
13
|
The endpoint is `<your ingest host>/mcp`. For the hosted platform that's
|
|
17
14
|
`https://railwatch.rebulk.com/mcp`; if you self-host, it is your own host (see
|
|
18
|
-
[`self-hosting.md`](self-hosting.md)).
|
|
15
|
+
[`self-hosting.md`](self-hosting.md)). With the `railwatch-server` gem the
|
|
16
|
+
server runs under the app's dashboard path, so the endpoint is the app's own
|
|
17
|
+
host plus `/railwatch/mcp`; see the
|
|
18
|
+
[railwatch-server README](https://github.com/Rebulk/railwatch-server#readme).
|
|
19
|
+
For Railwatch Cloud and a self-hosted server the gem knows which one you're on:
|
|
19
20
|
|
|
20
21
|
```sh
|
|
21
22
|
bin/rails railwatch:mcp
|
|
@@ -225,9 +226,9 @@ Copy either into your own app's repo to give its agent the same context.
|
|
|
225
226
|
|
|
226
227
|
## See also
|
|
227
228
|
|
|
228
|
-
- [`getting-started.md`](getting-started.md) — install, the
|
|
229
|
+
- [`getting-started.md`](getting-started.md) — install, the token,
|
|
229
230
|
first request.
|
|
230
231
|
- [`self-hosting.md`](self-hosting.md) — pointing the gem, and this endpoint,
|
|
231
|
-
at your own
|
|
232
|
+
at your own server.
|
|
232
233
|
- [`troubleshooting.md`](troubleshooting.md) — when something isn't
|
|
233
234
|
reporting.
|
data/docs/configuration.md
CHANGED
|
@@ -11,9 +11,9 @@ values set in the initializer always win over the env var.
|
|
|
11
11
|
|
|
12
12
|
| Attribute | Env var | Default | Meaning |
|
|
13
13
|
|---|---|---|---|
|
|
14
|
-
| `enabled` | `RAILWATCH_ENABLED` | `true` | Master switch.
|
|
15
|
-
| `token` | `RAILWATCH_TOKEN` | nil | Bearer token for `/ingest`. Required with
|
|
16
|
-
| `ingest_url` | `RAILWATCH_INGEST_URL` | `https://railwatch.rebulk.com` |
|
|
14
|
+
| `enabled` | `RAILWATCH_ENABLED` | `true` | Master switch. `Railwatch.enabled?` is also `false` whenever `token` is blank, so setting only `RAILWATCH_TOKEN` is enough to turn an install on. |
|
|
15
|
+
| `token` | `RAILWATCH_TOKEN` | nil | Bearer token for `/ingest`. Required; with railwatch-server installed it is set for you. |
|
|
16
|
+
| `ingest_url` | `RAILWATCH_INGEST_URL` | `https://railwatch.rebulk.com` | Server base URL. Point at a self-hosted railwatch-rs to override. |
|
|
17
17
|
| `allow_http` | `RAILWATCH_ALLOW_HTTP` | `false` | Permit a non-loopback plain HTTP ingest URL. HTTPS is required by default; `localhost`, `127.0.0.1`, and `::1` remain available for local self-hosted development. |
|
|
18
18
|
| `deploy` | `RAILWATCH_DEPLOY` | auto-detected (order below), then nil | Version tag stamped on every record and used by `railwatch:deploy`. Full 40-character SHAs are shortened to 12 characters. |
|
|
19
19
|
| `detect_deploy` | `RAILWATCH_DETECT_DEPLOY` | `true` | Detect deploys beyond `RAILWATCH_DEPLOY` and `KAMAL_VERSION`. Set false when the app deliberately reports no inferred deploy. |
|
|
@@ -25,7 +25,7 @@ values set in the initializer always win over the env var.
|
|
|
25
25
|
| `beacon_rate_limit` | `RAILWATCH_BEACON_RATE_LIMIT` | `120` | Beacon POSTs accepted per client IP per minute before `POST /railwatch/beacon` answers 429. The beacon is unauthenticated and keeps every browser error it is sent, so this is what stops a script from spending the app's event quota. Counted in the app's cache store; `0` turns it off. |
|
|
26
26
|
|
|
27
27
|
`Railwatch.enabled?` delegates to `config.enabled?`, which is `@enabled &&
|
|
28
|
-
|
|
28
|
+
token.present?`. There is no separate "is configured" check
|
|
29
29
|
elsewhere.
|
|
30
30
|
|
|
31
31
|
Deploy detection stops at the first value found: `RAILWATCH_DEPLOY`,
|
|
@@ -585,7 +585,7 @@ Rake tasks and Solid Queue jobs are never interactive.
|
|
|
585
585
|
|
|
586
586
|
| Attribute | Env var | Default | Meaning |
|
|
587
587
|
|---|---|---|---|
|
|
588
|
-
| `capture_exception_source` | `RAILWATCH_CAPTURE_EXCEPTION_SOURCE_CODE` | `true` | Record source snippet lines surrounding each in-application exception frame (sent to
|
|
588
|
+
| `capture_exception_source` | `RAILWATCH_CAPTURE_EXCEPTION_SOURCE_CODE` | `true` | Record source snippet lines surrounding each in-application exception frame (sent to whichever server the app reports to). This is on by default for crash context; disable it when source disclosure is outside the application's telemetry policy. |
|
|
589
589
|
| `capture_exception_locals` | `RAILWATCH_CAPTURE_EXCEPTION_LOCALS` | `false` | Snapshot the raising frame's local variables (up to 25, values truncated to 200 chars, run through the same filter as request params) onto each exception, like Sentry's locals panel. Installs a `TracePoint(:raise)`; opt in per environment. |
|
|
590
590
|
| `capture_request_payload` | `RAILWATCH_CAPTURE_REQUEST_PAYLOAD` | `false` | Capture (redacted) request params — only for a request that raised, never otherwise. |
|
|
591
591
|
| `capture_job_arguments` | `RAILWATCH_CAPTURE_JOB_ARGUMENTS` | `false` | Add the job's real arguments (`job.serialize["arguments"]`) to each `job_attempt`/`scheduled_task` record, capped at 8 KiB of JSON. Hash arguments run through the same filter as request params. Off by default because job arguments routinely carry PII; `arguments_preview` (argument *shapes* only) is always on regardless. |
|
|
@@ -900,72 +900,50 @@ in `lib/railwatch.rb`, unless noted:
|
|
|
900
900
|
`instrument_outgoing`, `flush`, `debug { }`. `pause`/`resume` are the
|
|
901
901
|
ignore block's building blocks, and are nestable.
|
|
902
902
|
|
|
903
|
-
##
|
|
903
|
+
## Dashboard gate (railwatch-server)
|
|
904
|
+
|
|
905
|
+
These settings do nothing on their own. They gate the dashboard that the
|
|
906
|
+
[`railwatch-server`](https://github.com/Rebulk/railwatch-server) gem
|
|
907
|
+
serves at `/railwatch` inside the app, so one setting covers it whichever
|
|
908
|
+
way it is installed.
|
|
904
909
|
|
|
905
910
|
```ruby
|
|
906
|
-
c.transport = :local # RAILWATCH_TRANSPORT; runtime default "http", but the installer writes :local
|
|
907
|
-
c.issue_prefix = "SHOP" # RAILWATCH_ISSUE_PREFIX; default from the app name
|
|
908
|
-
c.repository_url = "..." # RAILWATCH_REPOSITORY_URL
|
|
909
|
-
c.retention_days = 7 # RAILWATCH_RETENTION_DAYS
|
|
910
911
|
c.http_basic_auth_enabled = true # RAILWATCH_HTTP_BASIC_AUTH_ENABLED; on, and closed outside development until credentials exist
|
|
911
912
|
c.http_basic_auth_user = "ops" # RAILWATCH_HTTP_BASIC_AUTH_USER, or credentials railwatch.http_basic_auth_user
|
|
912
913
|
c.http_basic_auth_password = "..." # RAILWATCH_HTTP_BASIC_AUTH_PASSWORD, or credentials railwatch.http_basic_auth_password
|
|
913
914
|
c.base_controller_class = "AdminController" # RAILWATCH_BASE_CONTROLLER_CLASS; default ActionController::Base
|
|
914
|
-
c.dashboard_open = false # RAILWATCH_DASHBOARD_OPEN; default false, true makes it public on purpose
|
|
915
|
-
c.dashboard_user = ->(request) { { id:, name:, email: } or nil }
|
|
916
|
-
c.writer_socket = "tmp/sockets/railwatch-writer.sock" # RAILWATCH_WRITER_SOCKET
|
|
917
915
|
```
|
|
918
916
|
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
|
|
923
|
-
|
|
924
|
-
railwatch:authentication:configure` has written credentials; a host with
|
|
925
|
-
its own admin auth turns Basic off and sets `base_controller_class` or a
|
|
926
|
-
routes constraint. Full walkthrough: [Embedded mode](embedded.md).
|
|
927
|
-
|
|
928
|
-
### Export to Railwatch Cloud
|
|
929
|
-
|
|
930
|
-
An embedded install can also mirror every record to Railwatch Cloud.
|
|
931
|
-
Off unless `export_enabled` is set; a configured token alone sends
|
|
932
|
-
nothing. Only meaningful with `transport = :local`.
|
|
933
|
-
|
|
934
|
-
| Attribute | Env var | Default | Meaning |
|
|
935
|
-
|---|---|---|---|
|
|
936
|
-
| `export_enabled` | `RAILWATCH_EXPORT_ENABLED` | `false` | Mirror every record to the cloud as well as storing it locally. |
|
|
937
|
-
| `export_token` | `RAILWATCH_EXPORT_TOKEN` | `token` | Cloud environment token to send with. |
|
|
938
|
-
| `export_url` | `RAILWATCH_EXPORT_URL` | `{ingest_url}/ingest` | Where to send. |
|
|
939
|
-
| `export_max_bytes` | `RAILWATCH_EXPORT_MAX_BYTES` | `268435456` (256 MiB) | Queue ceiling in bytes. At capacity new work is refused and counted, not swapped for old. |
|
|
940
|
-
| `export_max_deliveries` | `RAILWATCH_EXPORT_MAX_DELIVERIES` | `100000` | Queue ceiling in deliveries. |
|
|
941
|
-
| `export_max_age` | `RAILWATCH_EXPORT_MAX_AGE_SECONDS` | `86400` | How long a queued delivery is kept. At most seven days, past which the receiver no longer recognises it. |
|
|
917
|
+
HTTP Basic is on by default and, outside development, answers 401 until
|
|
918
|
+
credentials exist: `bin/rails railwatch:authentication:configure` writes
|
|
919
|
+
them to the current environment's Rails credentials, or set the env vars.
|
|
920
|
+
In development with no credentials configured, it is open. An initializer
|
|
921
|
+
or env var that sets them wins over credentials.
|
|
942
922
|
|
|
943
|
-
|
|
944
|
-
|
|
945
|
-
|
|
923
|
+
An app with its own admin authentication turns Basic off and names a
|
|
924
|
+
base controller. railwatch-server's proxy controller inherits from
|
|
925
|
+
`base_controller_class`, so the app's own `before_action`s (require an
|
|
926
|
+
admin, redirect to sign-in) run in front of every dashboard request.
|
|
946
927
|
|
|
947
928
|
## Rake tasks
|
|
948
929
|
|
|
949
930
|
Ship with the gem via Rails::Engine's default `lib/tasks` convention, in
|
|
950
931
|
`lib/tasks/railwatch_tasks.rake`:
|
|
951
932
|
|
|
952
|
-
- **`railwatch:status`**
|
|
953
|
-
|
|
954
|
-
|
|
933
|
+
- **`railwatch:status`** pings `{ingest_url}/ingest/ping` with the
|
|
934
|
+
configured token, and aborts if `RAILWATCH_TOKEN` is unset or the ping
|
|
935
|
+
fails.
|
|
955
936
|
- **`railwatch:doctor`** prints a ✓/✗ checklist of the whole install.
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
stored, the ingest URL and its transport security, and
|
|
960
|
-
`GET /ingest/ping`. Then, either way: `Railwatch::Middleware::Request`
|
|
937
|
+
It checks the token, where the token is stored, the ingest URL and its
|
|
938
|
+
transport security, and `GET /ingest/ping`. Then
|
|
939
|
+
`Railwatch::Middleware::Request`
|
|
961
940
|
in the middleware stack, the mounted engine's beacon route,
|
|
962
941
|
`config.deploy` and its source, sample rates, ignored record types, the
|
|
963
942
|
Kamal `post-deploy` hook, the browser client and whether an entrypoint
|
|
964
943
|
calls it, the profiler backend, and the test matchers. It exits
|
|
965
944
|
non-zero only on the lines marked fatal in
|
|
966
945
|
[Troubleshooting](troubleshooting.md).
|
|
967
|
-
- **`railwatch:deploy[ref,name,url]`**
|
|
968
|
-
to the app's `railwatch` database. Cloud: POSTs `{deploy, ref, name,
|
|
946
|
+
- **`railwatch:deploy[ref,name,url]`** POSTs `{deploy, ref, name,
|
|
969
947
|
url, server, timestamp, performer, destination, service, commits}` to
|
|
970
948
|
`{ingest_url}/ingest/deploys`. `deploy` comes from `config.deploy`. It
|
|
971
949
|
aborts if that's unset. `ref` defaults to `git rev-parse HEAD` when not
|
|
@@ -974,29 +952,20 @@ Ship with the gem via Rails::Engine's default `lib/tasks` convention, in
|
|
|
974
952
|
`{sha, author, message, at}` objects, newest first, from `git log`. It
|
|
975
953
|
is empty inside an app container, which has no `.git`. That is why the
|
|
976
954
|
hook below posts from the deployer instead.
|
|
977
|
-
- **`railwatch:authentication:configure`** writes the
|
|
978
|
-
dashboard's HTTP Basic
|
|
979
|
-
credentials.
|
|
980
|
-
- **`railwatch:
|
|
981
|
-
|
|
982
|
-
|
|
983
|
-
abandon everything queued.
|
|
984
|
-
- **`railwatch:vacuum:status`** and **`railwatch:vacuum`** report and
|
|
985
|
-
reclaim the telemetry database's disk
|
|
986
|
-
([Embedded mode](embedded.md#giving-the-disk-back)).
|
|
987
|
-
- **`railwatch:token`** and **`railwatch:mcp`** print where to create a
|
|
988
|
-
cloud ingest token and paste-ready MCP client configuration.
|
|
955
|
+
- **`railwatch:authentication:configure`** writes the
|
|
956
|
+
[dashboard gate](#dashboard-gate-railwatch-server)'s HTTP Basic
|
|
957
|
+
credentials to the current environment's Rails credentials.
|
|
958
|
+
- **`railwatch:token`** and **`railwatch:mcp`** print where to create an
|
|
959
|
+
ingest token and paste-ready MCP client configuration for the server
|
|
960
|
+
`ingest_url` points at.
|
|
989
961
|
- **`railwatch:sourcemaps[directory,delete]`** uploads browser source
|
|
990
962
|
maps ([Source maps](source-maps.md)).
|
|
991
963
|
|
|
992
964
|
## Kamal integration
|
|
993
965
|
|
|
994
966
|
`bin/rails generate railwatch:install` writes `.kamal/hooks/post-deploy`,
|
|
995
|
-
but only if `config/deploy.yml` already exists.
|
|
996
|
-
`
|
|
997
|
-
`bin/rails railwatch:deploy[$KAMAL_VERSION]` in the primary container,
|
|
998
|
-
which records the marker in the embedded database, and stops. Otherwise
|
|
999
|
-
it no-ops when `RAILWATCH_TOKEN` isn't set. It never fails a deploy.
|
|
967
|
+
but only if `config/deploy.yml` already exists. It no-ops when
|
|
968
|
+
`RAILWATCH_TOKEN` isn't set. It never fails a deploy.
|
|
1000
969
|
Every network call ends in `|| true`.
|
|
1001
970
|
|
|
1002
971
|
The hook runs on the **deployer machine**, not in a container, which is
|