Commit Graph
1684 Commits
Author SHA1 Message Date
gorkem-bwl 210e03cea0 fix(client): refine table header divider and typography
- replace heavier per-cell header borders with one lighter row divider
- shrink header text to 11px with looser tracking for a more refined feel
- tighten failed-jobs labels: "Fail count" -> "Count", "Last failed at" -> "Last failed"
2026-04-26 00:13:27 -04:00
gorkem-bwl 995fc59299 feat(client): add pagination to team, notifications and status page tables 2026-04-26 00:13:23 -04:00
gorkem-bwl cbd8236cb4 chore(i18n): seed jobQueueExplainer and failedJobsExplainer for non-English locales 2026-04-26 00:13:19 -04:00
gorkem-bwl 095086cdfd chore(i18n): seed translations for new UI surfaces
Across en + 15 locales:
- pages.<X>.fallback.title / .description for every page that has an
  EmptyState (uptime, infrastructure, pageSpeed, notifications,
  maintenance, statusPages, incidents, logs, logs.queueFallback,
  checks, account.team).
- pages.<X>.header.title / .description for every page that uses the
  new PageHeader (same list, plus settings).
- pages.logs.diagnostics.sections.runtimeStats / .memoryCpu titles
  and descriptions for the diagnostics section explainers.
- components.pageHeader.links.support / docs / changelog tooltip
  labels.

en.json also gains pages.logs.jobQueueExplainer and
.failedJobsExplainer (English only — non-English locales fall back
to English until a translator sweep).
2026-04-25 23:28:51 -04:00
gorkem-bwl 59846a041f fix(client): dark-mode text-field polish
- MuiOutlinedInput hover override: was inheriting MUI's default
  white outline in dark mode (too bright). Now uses an alpha-23%
  white in dark and text.primary in light.
- TextInput: -webkit-autofill now repaints the input bg with
  background.paper (instead of Chrome's harsh blue/yellow autofill
  highlight), text in text.primary, with the standard 5000s-transition
  trick to suppress the brief flash. Works in both modes.
2026-04-25 23:28:32 -04:00
gorkem-bwl 7d91d9e28b fix(client): job queue table layout + theme-aware running-row tint
TableJobs:
- Cut from 11 to 7 columns, dropping active / runCount / failCount /
  lastFinishedAt (covered by Failed jobs table or by lastRun + lastRunTook).
- All cells get whiteSpace:nowrap + textOverflow:ellipsis + maxWidth so
  long timestamps and IDs no longer wrap and inflate row height; full
  value visible via title tooltip.
- Running-row tint: was theme.palette.success.light (too saturated in
  light, drowns white text in dark). Now #ECF7F2 in light, an 18%-alpha
  green in dark — readable in both modes.

TabQueue:
- One-line explainer above the Job queue heading, with the words
  "Highlighted rows" wrapped in the same green tint so the meaning
  is immediately associated.
- One-line explainer above Failed jobs heading too.
2026-04-25 23:27:50 -04:00
gorkem-bwl 752f59b09b feat(client): diagnostics page polish
- Stats and StatGauges use CSS grid (5 + 4 columns) so cards in each
  row are equal width; widths overridden against the legacy 25%-flex
  GradientBox so they fill their grid cell.
- DetailGauge gains a maxWidth prop (default 225) so consumers in
  wide grids can opt out of the cap.
- Section explainers above each row: "Runtime stats" + description,
  "Memory & CPU" + description (i18n driven, propagated to all 16
  locales via pages.logs.diagnostics.sections).
- Both grids render immediately with placeholder "—" values, so the
  initial paint shows the layout and values fill in as data loads
  (eliminates the layout shake when switching to the tab).
2026-04-25 23:27:35 -04:00
gorkem-bwl 262c4eee93 feat(client): PageHeader on every page; remove sidebar bottom menu
- New PageHeader component (variant D — grouped icon-pill toolbar):
  big title + muted description on the left, Support / Docs /
  Changelog as a 3-icon segmented pill on the right with tooltips.
  External links open in a new tab.
- BasePage / BasePageWithStates / MonitorBasePageWithStates accept
  a headerKey prop; when set, render PageHeader pulling
  pages.<headerKey>.header.title and .description from i18n.
  When unset, falls back to the existing breadcrumb (no behavior
  change for not-yet-migrated pages).
- All top-level pages (uptime, infrastructure, pageSpeed,
  notifications, maintenance, statusPages, incidents, logs, checks,
  account, settings) now pass their headerKey.
- Sidebar: removed the bottom menu (Support / Discussions / Docs /
  Changelog) since those links now live in the page header.
2026-04-25 23:27:22 -04:00
gorkem-bwl 031a6fdf3c feat(client): unified EmptyState across all pages and table empties
- New EmptyState + EmptyStateIllustration components: stacked-cards SVG
  with grid background, theme-aware light/dark palette.
- Variants: default (centered with title + description), compact
  (horizontal, in-section), fullscreen (vertically centers in viewport).
- Wired into Checks, Incidents, Logs (Logs+Queue tabs), Notifications,
  Maintenance, Status pages, and Team tab — each with i18n title +
  description and a fullscreen layout when truly empty.
- Table.EmptyView now wraps the EmptyState in a divider-bordered card
  so short messages no longer look orphaned.
- Incidents Option-A short-circuit: when summary.total === 0, replace
  the whole page chrome with EmptyState; otherwise keep filters + cards.
- Fallback.tsx (BaseFallback / EmptyFallback / EmptyMonitorFallback /
  ErrorFallback) refactored to delegate to EmptyState.
2026-04-25 23:26:34 -04:00
gorkem-bwl ff208710d7 feat(client): unified EmptyState component for empty/error placeholders
Replaces the cards-with-halo SkeletonCard fallback (which produced a
washed-out, hard-to-read placeholder) with a single canonical empty
state used everywhere in the app.

What's new:

- EmptyStateIllustration.tsx — custom inline SVG: two stacked monitor
  cards (front blue, back gray, both with hairline strokes and a soft
  fade toward the bottom), set against a faint grid of solid + dashed
  background lines. Uses only lightened palette tokens (#7DA8E8 blue,
  #B6C2CF gray, #CBD5E1 grid).
- EmptyState.tsx — the layout: illustration + title + description +
  optional CTA + optional secondary link + optional inline alert slot.
  Supports a compact horizontal variant for in-panel use.

Migrations:

- Fallback.tsx: BaseFallback / EmptyFallback / EmptyMonitorFallback /
  ErrorFallback now delegate to EmptyState. Public APIs unchanged so
  every existing consumer (BasePageWithStates, MonitorBasePageWithStates,
  Pages/Uptime, Pages/Notifications, Pages/Infrastructure, etc.) keeps
  working without edits.
- BasePage.tsx: PageSpeedKeyPriorityFallback rebuilt on top of EmptyState
  with the warning slot. Fixes the previous reports of "white cloudy
  area" + half-faded text — message and link now render in consistent
  dark text with green Settings link.

No prop changes for any page-level consumer. The illustration is a
single SVG with no external assets.
2026-04-25 21:19:52 -04:00
Gorkem Cetin 29f1041cc3 Merge pull request #3578 from ZeinebMegaadi/fix/docs-link
fix:replaced the broken link with the working one everywhere
2026-04-25 19:40:31 -04:00
ZeinebMegaadi a613bfb45a fix:replaced the broken link with the working one everywhere 2026-04-25 15:33:42 +01:00
Aicha Lassoued 625f9b588e Fix typo in heapAllocation string 2026-04-24 22:45:45 +01:00
Aicha Lassoued 6fa73dce49 fixed typo 2026-04-24 22:24:00 +01:00
gorkem-bwl 50fb4f47fd fix(client): hide Open site action when URL is not browser-openable
The Open site action in monitor row menus called `window.open(monitor.url)`
unconditionally, which produced unresolvable navigation for monitors
targeting internal services:
- Hardware monitors always point at a Capture agent (e.g.
  http://capture:59232/api/v1/metrics) that the user's browser can't
  reach.
- Port, ping, docker, game, grpc, and websocket monitors store hostnames
  or non-HTTP endpoints, which browsers can't load anyway.

This change hides the action where it can't possibly work:
- Removed entirely from the Infrastructure (hardware) monitors table.
- In the Uptime monitors table, only shown for http and pagespeed
  monitor types whose URL starts with http:// or https://.

A more comprehensive fix that adds a separate user-facing siteUrl
field on the Monitor schema is left for a follow-up.

Closes #3434
2026-04-23 23:38:07 -04:00
gorkem-bwl 944ee74a1d feat(status-page): four selectable themes for the public status page
Adds four fully-designed visual themes for the public status page
(refined | modern | bold | editorial) with a light/dark mode selector,
admin preview in a mock browser frame, and a shared theme provider
that keeps the component tree unified while letting each theme own
its visual identity.

## Selectable themes
- Refined — clean, flat cards, soft shadows, colored status dot.
- Modern — flat surfaces with a pulsing status dot and staggered
  fade-in cards.
- Bold — conic-gradient logo, 34px hero title with a check disc,
  subtle dual-radial glow on dark mode, accent-green hover border.
- Editorial — serif headings, narrow newspaper column, 'Service
  Report' eyebrow + title, flat rectangular badges and dateline.

## Architecture
- Single `StatusPageThemeProvider` hosts CSS custom-property tokens
  per theme and resolves light/dark based on admin-forced mode,
  falling back to `prefers-color-scheme` with a matchMedia listener.
- Each theme owns only its `*StatusPage.tsx` + scoped CSS file.
  The heatmap, histogram, and infrastructure renderers are shared
  across all four themes (parameterized by a `classPrefix`) to avoid
  the 12-file duplication the initial draft had.
- Renderer lookup table in `Status/index.tsx` replaces a 4-way
  ternary chain; unknown themes fall through to the legacy renderer.
- `resolveOverallStatus`, `statusBadgeKey`, `monoFirstChar`, and
  `monitorBadgeTone` are extracted to `themes/shared/overallStatus.tsx`.

## Admin UX
- `ThemePicker` uses the project's `RadioWithDescription` and
  `Select` components — one radio card per theme plus an Auto/
  Light-only/Dark-only mode dropdown.
- `BrowserFrame` wraps the preview in the admin panel with a mock
  chrome (traffic lights + URL bar) that adopts the status page's
  theme tokens. Edge-to-edge fill with no gray bleed.
- Public route renders the theme directly on the viewport with the
  document body painted to the theme background, reverted on unmount.

## Performance & polish
- Histogram's derived stats (padded array, max, avg, peak) are
  memoized on `checks`; `max` is reused for `peak` instead of
  computing twice.
- Editorial's dateline is wrapped in `useMemo` so the 10s poll
  doesn't rerender "April 23, 2026" as a changing string.
- Provider's `setSystemMode` reconciliation uses the updater form
  to avoid an extra render when the value is unchanged.
- `monoFirstChar` no longer uses a non-null assertion.

## Form plumbing
- `useStatusPageForm` defaults include `theme` + `themeMode`.
- `Validation/statusPage.ts` accepts both as optional zod enums.
- `Pages/StatusPage/Create/index.tsx` appends both to FormData on
  create and update.

## CLAUDE.md
- Dev port note: local client runs on 10001 (5173 is used by a
  different local project); server `CLIENT_HOST` is set to match.
2026-04-23 22:51:40 -04:00
Alex Holliday 5f12459bfd explicit import 2026-04-20 11:48:48 -07:00
Alex Holliday 27e866ba08 use lazy get 2026-04-20 11:47:43 -07:00
Alex Holliday f7a2b2af54 Merge branch 'develop' into fix/hide-register-tip-on-login 2026-04-20 11:28:25 -07:00
Alexander Holliday 984a611d19 Merge pull request #3534 from egeoztass/feat/twilio-sms-notification
feat: add Twilio SMS notification channel
2026-04-20 10:54:12 -07:00
gorkem-bwl 39011e2e33 style: apply prettier formatting 2026-04-20 13:53:50 -04:00
gorkem-bwl 4998fe4c94 fix: hide register tip on login and redirect to setup when no super admin (#3556)
## Changes
- Removed the "Register here" link from the login page — it misled users into thinking public registration was open.
- Added redirect from /login to /register when no super admin exists (initial setup).
- Added an info alert on the register page clarifying the page is only for initial setup; additional users are invited from team settings. Hidden for the invite-token flow.
- Extracted shared useSuperAdminRedirect hook to dedupe identical fetch/redirect logic across Login and Register.

## Benefits
- Clearer UX: login page no longer suggests self-registration is available post-setup.
- Correct routing on fresh installs: users land on the registration page instead of a login page they can't use.
2026-04-20 13:50:36 -04:00
egeoztassandClaude Opus 4.6 d5d6797f91 fix: use dedicated Twilio fields and add service switch case tests
- Added `accountSid` and `twilioPhoneNumber` fields to Notification
  type, MongoDB model, and frontend type instead of reusing
  `address` and `homeserverUrl`
- Updated provider, validation, form hook, and form UI to use new fields
- Added Pushover and Twilio to notificationsService routing tests
  (both handleNotifications and sendTestNotification)
- All 59 tests passing

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-17 23:11:11 +03:00
Alexander Holliday fa6aef1e86 Merge pull request #3518 from ZeinebMegaadi/fix/showing-down-for-down-monitors
Fix: added "down" display on down monitors instead of "Active for:..."
2026-04-17 10:17:34 -07:00
ZeinebMegaadi 26077151ef fix: added maintenance state 2026-04-16 20:54:09 +01:00
egeoztassandClaude Opus 4.6 9210259511 feat: add Twilio SMS notification channel
Adds Twilio SMS as a new notification channel, allowing users to
receive SMS alerts via the Twilio API.

Backend: provider using HTTP Basic Auth, type registration, validation,
service wiring. Uses existing fields: address (Account SID),
accessToken (Auth Token), homeserverUrl (From number), phone (To number).
Frontend: form UI with 4 fields, validation, i18n keys.
Tests: 18 provider tests + updated service test constructor.

Closes #3095

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-16 21:46:40 +03:00
Alexander Holliday e9a0914fad Merge pull request #3530 from egeoztass/feat/pushover-notification
feat: add Pushover notification channel
2026-04-16 11:21:43 -07:00
SkyKingPX 5920b92869 Run npm format 2026-04-16 19:55:17 +02:00
ZeinebMegaadi 58532d1ff6 fix(monitors): handle initializing and breached states in stat box 2026-04-16 18:09:05 +01:00
SkyKingPX 0d163e7100 Change Breached to exceeded thresholds 2026-04-16 18:56:06 +02:00
egeoztassandClaude Opus 4.6 cc1b6df8f2 style: run prettier on notification create page
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-16 16:55:30 +03:00
egeoztassandClaude Opus 4.6 97353bc7d2 feat: add Pushover notification channel
Adds Pushover as a new notification channel, allowing users to receive
push notifications on their devices via the Pushover API.

Backend: provider, type registration, validation, service wiring
Frontend: form UI with app token and user key fields, validation, i18n
Tests: full unit test suite (15 tests, 100% coverage on provider)

Closes #3445

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-16 16:25:24 +03:00
SkyKing_PX 675ec40836 Merge branch 'bluewave-labs:develop' into feat/improved-status-bar-messages 2026-04-16 13:40:10 +02:00
SkyKingPX 7b164e4df5 Make requested changes 2026-04-16 13:37:54 +02:00
Alex Holliday be3b7c2e86 add demo role to list of roles 2026-04-15 13:54:05 -07:00
Alex Holliday 564b356115 tighten streak time coniditional 2026-04-15 11:06:30 -07:00
ZeinebMegaadi b482e871a3 updated fix for same issue 2026-04-15 16:12:10 +01:00
ZeinebMegaadi f6222014b7 Fix: correct Active for display on down monitors 2026-04-15 14:51:12 +01:00
SkyKingPX a8339c0169 Improve status bar messages on public status pages 2026-04-14 19:32:05 +02:00
Alex Holliday 22498756cd add remaining zh-tw strings 2026-04-07 09:46:07 -07:00
gorkem-bwl eb4a92c84f fix: restructure and translate all i18n locale files
All 15 non-English locale files had a structural mismatch with en.json:
- en.json used nested keys (common.buttons.cancel)
- Other locales used flat keys (cancel, DeleteAccountButton)
- Result: 0.3% effective translation coverage at runtime

## Changes

Migration script (client/scripts/migrate-locales.ts):
- Restructures all locale files to match en.json's nested key structure
- Recovers existing translations via safe key-matching strategies
- Backs up originals to locales/backup/

Translation of all 15 languages:
- ar (94.6%), cs (91.6%), de (89.4%), es (92.6%), fi (94.2%)
- fr (86.7%), ja (93.3%), pt-BR (91.0%), ru (93.0%), th (93.4%)
- tr (91.9%), uk (94.3%), vi (92.5%), zh-CN (94.0%), zh-TW (94.2%)

Keys intentionally left in English are technical terms (HTTP, CPU,
Docker, gRPC, etc.), placeholder examples, and brand names.

en.json was NOT modified.
2026-04-03 23:35:14 -04:00
LeC-D 04dfff4ebd fix(notifications): remove redundant defaultValue prop and fix incident URL in telegram provider
- Remove redundant 'defaultValue' prop on Telegram chat ID Controller in create/index.tsx;
  the form already initialises via 'defaultValues: defaults' at the useForm level, making
  the per-Controller prop unnecessary and inconsistent with the reviewer's expectation.
- Fix 'View Incident' URL in telegram.ts: was pointing to the infrastructure details page
  (/infrastructure/:id) instead of the incidents page (/incidents/:id).
2026-03-27 14:19:27 -04:00
LeC-D 13a7ae82e3 fix(notifications): remove type casts with exhaustive type narrowing in useNotificationForm
Replace the loose NotificationDefaults intermediate type and 'as NotificationFormData'
cast with an exhaustive buildDefaults() helper that narrows each branch of the
discriminated union explicitly. TypeScript now infers the return type correctly from
the discriminated union without any casts, satisfying strong typing for all channels
(email, slack, discord, webhook, pager_duty, teams, matrix, telegram).
2026-03-26 14:07:50 -04:00
Leandre Chamberland-Dozois 4c94a7c21e fix: resolve TypeScript build errors in notification form types 2026-03-25 19:13:37 -04:00
LeC-D 40968c370b refactor(notifications): hoist default values, remove else block in useNotificationForm
Per @ajhollid review: define defaults up-front with a NotificationDefaults type
and eliminate the trailing else branch entirely. The if/else-if blocks only
override when the type is matrix or telegram.
2026-03-25 18:06:26 -04:00
LeC-DandClaude Opus 4.6 a864bc0c05 fix: run format and fix build errors
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-25 16:52:48 -04:00
LeC-D fe242b1977 fix: replace nested ternaries and remove type casts per review
- useNotificationForm: replace nested ternary with if/else if/else block
- TelegramProvider: type error as unknown and access properties safely
  via instanceof checks instead of casting to HTTPError
2026-03-25 14:03:49 -04:00
LeC-D d1f1d31ea2 fix(i18n): revert en.json to upstream format, keep only telegram keys
The previous commit reformatted the entire en.json (spaces → kept as-is
but accumulated unrelated upstream changes), creating a 1.3k line diff.

Restore the file to match upstream/develop exactly and add only the
Telegram-specific i18n keys required by this PR.
2026-03-24 17:22:34 -04:00
Léo eacbb227c3 feat(notifications): add Telegram notification channel (#2753)
Add Telegram as a new notification type, allowing users to receive
monitor alerts via a Telegram bot.

Configuration requires:
- Bot token (obtained from @BotFather)
- Chat ID (user, group, or channel)

Changes:
- TelegramProvider: sends HTML-formatted messages via Telegram Bot API
- NotificationsService: route telegram type to TelegramProvider
- Notification model/types: add 'telegram' to NotificationChannel enum
- Server validation: telegram schema (accessToken + address/chat_id)
- Client Types/Validation: telegram schema with accessToken + address
- useNotificationForm: handle telegram defaults
- Notifications create page: render Telegram config UI
- en.json: add telegram i18n keys
2026-03-24 10:15:46 -04:00
mannilakash 78566c0226 fix: modifying refreshInterval=10s for statusPage api 2026-03-19 11:34:26 -04:00