Openstatus sdk www.openstatus.dev
at maintenance-api 1145 lines 32 kB view raw view rendered
1# OpenStatus Node.js SDK (Beta) 2 3[![JSR](https://jsr.io/badges/@openstatus/sdk-node)](https://jsr.io/@openstatus/sdk-node) 4[![npm](https://img.shields.io/npm/v/@openstatus/sdk-node)](https://www.npmjs.com/package/@openstatus/sdk-node) 5[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT) 6 7Official Node.js SDK for [OpenStatus](https://openstatus.dev) - The open-source 8status page with uptime monitoring. 9 10## Features 11 12### Status Page 13 14- **Status Pages** - Create and manage public status pages with custom domains 15- **Page Components** - Add monitor-based or static components with grouping 16- **Subscribers** - Manage email subscriptions for status updates 17- **Status Reports** - Manage incident reports with update timelines 18- **Maintenance Windows** - Schedule and manage planned maintenance periods 19 20### Monitoring 21 22- **HTTP Monitoring** - Monitor websites and APIs with customizable assertions 23- **TCP Monitoring** - Check database connections and other TCP services 24- **DNS Monitoring** - Verify DNS records and resolution 25 26- **Global Regions** - Monitor from 28 locations worldwide 27- **Type-safe** - Full TypeScript support with generated types from protobuf 28 29## Installation 30 31### JSR 32 33```bash 34npx jsr add @openstatus/sdk-node 35``` 36 37### npm 38 39```bash 40npm install @openstatus/sdk-node 41``` 42 43### Deno 44 45```typescript 46import { openstatus } from "jsr:@openstatus/sdk-node"; 47``` 48 49## Quick Start 50 51```typescript 52import { 53 HTTPMethod, 54 NumberComparator, 55 openstatus, 56 Periodicity, 57 Region, 58} from "@openstatus/sdk-node"; 59 60const headers = { 61 "x-openstatus-key": `${process.env.OPENSTATUS_API_KEY}`, 62}; 63 64// Create a monitor 65const { monitor } = await openstatus.monitor.v1.MonitorService 66 .createHTTPMonitor( 67 { 68 monitor: { 69 name: "My API", 70 url: "https://api.example.com/health", 71 periodicity: Periodicity.PERIODICITY_1M, 72 method: HTTPMethod.HTTP_METHOD_GET, 73 regions: [Region.FLY_AMS, Region.FLY_IAD, Region.FLY_SYD], 74 active: true, 75 statusCodeAssertions: [ 76 { comparator: NumberComparator.EQUAL, target: BigInt(200) }, 77 ], 78 }, 79 }, 80 { headers }, 81 ); 82 83console.log(`Monitor created: ${monitor?.id}`); 84 85// List all monitors 86const { httpMonitors, tcpMonitors, dnsMonitors, totalSize } = await openstatus 87 .monitor.v1.MonitorService.listMonitors({}, { headers }); 88 89console.log(`Found ${totalSize} monitors`); 90``` 91 92## Authentication 93 94All API requests require an API key. Get yours from the 95[OpenStatus dashboard](https://www.openstatus.dev/app). 96 97```typescript 98const headers = { 99 "x-openstatus-key": `${process.env.OPENSTATUS_API_KEY}`, 100}; 101 102// Pass headers to any service method 103await openstatus.monitor.v1.MonitorService.listMonitors({}, { headers }); 104``` 105 106## Environment Variables 107 108| Variable | Description | Default | 109| -------------------- | ----------------------- | -------------------------------- | 110| `OPENSTATUS_API_KEY` | Your OpenStatus API key | - | 111| `OPENSTATUS_API_URL` | Custom API endpoint | `https://api.openstatus.dev/rpc` | 112 113## API Reference 114 115### Monitor Service 116 117#### `createHTTPMonitor(request, options)` 118 119Create an HTTP/HTTPS monitor. 120 121```typescript 122import { HTTPMethod, Periodicity, Region } from "@openstatus/sdk-node"; 123 124const { monitor } = await openstatus.monitor.v1.MonitorService 125 .createHTTPMonitor( 126 { 127 monitor: { 128 name: "My Website", 129 url: "https://example.com", 130 periodicity: Periodicity.PERIODICITY_1M, 131 method: HTTPMethod.HTTP_METHOD_GET, 132 regions: [Region.FLY_AMS, Region.FLY_IAD, Region.FLY_SYD], 133 active: true, 134 }, 135 }, 136 { headers }, 137 ); 138``` 139 140#### `updateHTTPMonitor(request, options)` 141 142Update an existing HTTP monitor. 143 144```typescript 145const { monitor } = await openstatus.monitor.v1.MonitorService 146 .updateHTTPMonitor( 147 { 148 id: "mon_123", 149 monitor: { 150 name: "Updated Name", 151 active: false, 152 }, 153 }, 154 { headers }, 155 ); 156``` 157 158#### `createTCPMonitor(request, options)` 159 160Create a TCP connection monitor. 161 162```typescript 163const { monitor } = await openstatus.monitor.v1.MonitorService.createTCPMonitor( 164 { 165 monitor: { 166 name: "Database", 167 uri: "db.example.com:5432", 168 periodicity: Periodicity.PERIODICITY_5M, 169 regions: [Region.FLY_AMS, Region.FLY_IAD], 170 active: true, 171 }, 172 }, 173 { headers }, 174); 175``` 176 177#### `updateTCPMonitor(request, options)` 178 179Update an existing TCP monitor. 180 181```typescript 182const { monitor } = await openstatus.monitor.v1.MonitorService.updateTCPMonitor( 183 { 184 id: "mon_123", 185 monitor: { 186 name: "Updated Database Monitor", 187 }, 188 }, 189 { headers }, 190); 191``` 192 193#### `createDNSMonitor(request, options)` 194 195Create a DNS resolution monitor. 196 197```typescript 198import { RecordComparator } from "@openstatus/sdk-node"; 199 200const { monitor } = await openstatus.monitor.v1.MonitorService.createDNSMonitor( 201 { 202 monitor: { 203 name: "DNS Check", 204 uri: "example.com", 205 periodicity: Periodicity.PERIODICITY_10M, 206 regions: [Region.FLY_AMS], 207 active: true, 208 recordAssertions: [ 209 { 210 record: "A", 211 comparator: RecordComparator.EQUAL, 212 target: "93.184.216.34", 213 }, 214 ], 215 }, 216 }, 217 { headers }, 218); 219``` 220 221#### `updateDNSMonitor(request, options)` 222 223Update an existing DNS monitor. 224 225```typescript 226const { monitor } = await openstatus.monitor.v1.MonitorService.updateDNSMonitor( 227 { 228 id: "mon_123", 229 monitor: { 230 name: "Updated DNS Check", 231 }, 232 }, 233 { headers }, 234); 235``` 236 237#### `listMonitors(request, options)` 238 239List all monitors with pagination. Returns monitors grouped by type. 240 241```typescript 242const { httpMonitors, tcpMonitors, dnsMonitors, nextPageToken, totalSize } = 243 await openstatus.monitor.v1.MonitorService.listMonitors( 244 { pageSize: 10, pageToken: "" }, 245 { headers }, 246 ); 247``` 248 249#### `triggerMonitor(request, options)` 250 251Trigger an immediate check. 252 253```typescript 254const { success } = await openstatus.monitor.v1.MonitorService.triggerMonitor( 255 { id: "mon_123" }, 256 { headers }, 257); 258``` 259 260#### `deleteMonitor(request, options)` 261 262Delete a monitor. 263 264```typescript 265const { success } = await openstatus.monitor.v1.MonitorService.deleteMonitor( 266 { id: "mon_123" }, 267 { headers }, 268); 269``` 270 271#### `getMonitorStatus(request, options)` 272 273Get the current status of a monitor across all configured regions. 274 275```typescript 276import { MonitorStatus, Region } from "@openstatus/sdk-node"; 277 278const { id, regions } = await openstatus.monitor.v1.MonitorService 279 .getMonitorStatus( 280 { id: "mon_123" }, 281 { headers }, 282 ); 283 284// regions is an array of { region, status } 285// region: Region enum value (e.g., Region.FLY_AMS) 286// status: MonitorStatus.ACTIVE, MonitorStatus.DEGRADED, or MonitorStatus.ERROR 287for (const { region, status } of regions) { 288 console.log(`${Region[region]}: ${MonitorStatus[status]}`); 289} 290``` 291 292#### `getMonitorSummary(request, options)` 293 294Get aggregated metrics and latency percentiles for a monitor. 295 296```typescript 297import { TimeRange } from "@openstatus/sdk-node"; 298 299const summary = await openstatus.monitor.v1.MonitorService.getMonitorSummary( 300 { 301 id: "mon_123", 302 timeRange: TimeRange.TIME_RANGE_7D, // TIME_RANGE_1D, TIME_RANGE_7D, or TIME_RANGE_14D 303 regions: [], // optional: filter by specific regions 304 }, 305 { headers }, 306); 307 308console.log(`Last ping: ${summary.lastPingAt}`); 309console.log(`Success: ${summary.totalSuccessful}`); 310console.log(`Degraded: ${summary.totalDegraded}`); 311console.log(`Failed: ${summary.totalFailed}`); 312console.log(`P50 latency: ${summary.p50}ms`); 313console.log(`P75 latency: ${summary.p75}ms`); 314console.log(`P90 latency: ${summary.p90}ms`); 315console.log(`P95 latency: ${summary.p95}ms`); 316console.log(`P99 latency: ${summary.p99}ms`); 317``` 318 319### Health Service 320 321Check API health status (no authentication required). 322 323```typescript 324import { ServingStatus } from "@openstatus/sdk-node"; 325 326const { status } = await openstatus.health.v1.HealthService.check({}); 327console.log(ServingStatus[status]); // "SERVING" 328``` 329 330### Status Report Service 331 332Manage incident and maintenance reports with update timelines. 333 334#### `createStatusReport(request, options)` 335 336Create a new status report. 337 338```typescript 339import { StatusReportStatus } from "@openstatus/sdk-node"; 340 341const { statusReport } = await openstatus.statusReport.v1.StatusReportService 342 .createStatusReport( 343 { 344 title: "API Degradation", 345 status: StatusReportStatus.INVESTIGATING, 346 message: "We are investigating reports of increased latency.", 347 date: "2024-01-15T10:30:00", 348 pageId: "page_123", 349 pageComponentIds: ["comp_456"], 350 notify: true, 351 }, 352 { headers }, 353 ); 354 355console.log(`Status report created: ${statusReport?.id}`); 356``` 357 358#### `getStatusReport(request, options)` 359 360Get a status report by ID (includes full update timeline). 361 362```typescript 363const { statusReport } = await openstatus.statusReport.v1.StatusReportService 364 .getStatusReport( 365 { id: "sr_123" }, 366 { headers }, 367 ); 368 369console.log(`Title: ${statusReport?.title}`); 370console.log(`Status: ${StatusReportStatus[statusReport?.status ?? 0]}`); 371 372// Access update timeline 373for (const update of statusReport?.updates ?? []) { 374 console.log(`${update.date}: ${update.message}`); 375} 376``` 377 378#### `listStatusReports(request, options)` 379 380List all status reports with pagination and optional filtering. 381 382```typescript 383import { StatusReportStatus } from "@openstatus/sdk-node"; 384 385const { statusReports, totalSize } = await openstatus.statusReport.v1 386 .StatusReportService.listStatusReports( 387 { 388 limit: 10, 389 offset: 0, 390 statuses: [ 391 StatusReportStatus.INVESTIGATING, 392 StatusReportStatus.IDENTIFIED, 393 ], 394 }, 395 { headers }, 396 ); 397 398console.log(`Found ${totalSize} status reports`); 399``` 400 401#### `updateStatusReport(request, options)` 402 403Update status report metadata (title, page components). 404 405```typescript 406const { statusReport } = await openstatus.statusReport.v1.StatusReportService 407 .updateStatusReport( 408 { 409 id: "sr_123", 410 title: "Updated Title", 411 pageComponentIds: ["comp_456", "comp_789"], 412 }, 413 { headers }, 414 ); 415``` 416 417#### `deleteStatusReport(request, options)` 418 419Delete a status report and all its updates. 420 421```typescript 422const { success } = await openstatus.statusReport.v1.StatusReportService 423 .deleteStatusReport( 424 { id: "sr_123" }, 425 { headers }, 426 ); 427``` 428 429#### `addStatusReportUpdate(request, options)` 430 431Add a new update to an existing status report timeline. 432 433```typescript 434import { StatusReportStatus } from "@openstatus/sdk-node"; 435 436const { statusReport } = await openstatus.statusReport.v1.StatusReportService 437 .addStatusReportUpdate( 438 { 439 statusReportId: "sr_123", 440 status: StatusReportStatus.IDENTIFIED, 441 message: 442 "The issue has been identified as a database connection problem.", 443 date: "2024-01-15T11:00:00", // optional, defaults to current time 444 notify: true, 445 }, 446 { headers }, 447 ); 448``` 449 450### Status Report Status 451 452| Enum Value | Description | 453| --------------- | -------------------------------- | 454| `UNSPECIFIED` | Default/unspecified status | 455| `INVESTIGATING` | Actively investigating the issue | 456| `IDENTIFIED` | Root cause has been identified | 457| `MONITORING` | Fix deployed, monitoring | 458| `RESOLVED` | Issue fully resolved | 459 460### Status Page Service 461 462Manage status pages, components, and subscribers. 463 464#### `createStatusPage(request, options)` 465 466Create a new status page. 467 468```typescript 469const { statusPage } = await openstatus.statusPage.v1.StatusPageService 470 .createStatusPage( 471 { 472 title: "My Service Status", 473 slug: "my-service", 474 description: "Status page for My Service", 475 homepageUrl: "https://example.com", 476 contactUrl: "https://example.com/contact", 477 }, 478 { headers }, 479 ); 480 481console.log(`Status page created: ${statusPage?.id}`); 482``` 483 484#### `getStatusPage(request, options)` 485 486Get a status page by ID. 487 488```typescript 489const { statusPage } = await openstatus.statusPage.v1.StatusPageService 490 .getStatusPage( 491 { id: "page_123" }, 492 { headers }, 493 ); 494``` 495 496#### `listStatusPages(request, options)` 497 498List all status pages with pagination. 499 500```typescript 501const { statusPages, totalSize } = await openstatus.statusPage.v1 502 .StatusPageService.listStatusPages( 503 { limit: 10, offset: 0 }, 504 { headers }, 505 ); 506 507console.log(`Found ${totalSize} status pages`); 508``` 509 510#### `updateStatusPage(request, options)` 511 512Update a status page. 513 514```typescript 515const { statusPage } = await openstatus.statusPage.v1.StatusPageService 516 .updateStatusPage( 517 { 518 id: "page_123", 519 title: "Updated Title", 520 description: "Updated description", 521 }, 522 { headers }, 523 ); 524``` 525 526#### `deleteStatusPage(request, options)` 527 528Delete a status page. 529 530```typescript 531const { success } = await openstatus.statusPage.v1.StatusPageService 532 .deleteStatusPage( 533 { id: "page_123" }, 534 { headers }, 535 ); 536``` 537 538#### `addMonitorComponent(request, options)` 539 540Add a monitor-based component to a status page. 541 542```typescript 543const { component } = await openstatus.statusPage.v1.StatusPageService 544 .addMonitorComponent( 545 { 546 pageId: "page_123", 547 monitorId: "mon_456", 548 name: "API Server", 549 description: "Main API endpoint", 550 order: 1, 551 }, 552 { headers }, 553 ); 554``` 555 556#### `addStaticComponent(request, options)` 557 558Add a static component (not linked to a monitor). 559 560```typescript 561const { component } = await openstatus.statusPage.v1.StatusPageService 562 .addStaticComponent( 563 { 564 pageId: "page_123", 565 name: "Third-party Service", 566 description: "External dependency", 567 order: 2, 568 }, 569 { headers }, 570 ); 571``` 572 573#### `updateComponent(request, options)` 574 575Update a component. 576 577```typescript 578const { component } = await openstatus.statusPage.v1.StatusPageService 579 .updateComponent( 580 { 581 id: "comp_123", 582 name: "Updated Component Name", 583 order: 3, 584 }, 585 { headers }, 586 ); 587``` 588 589#### `removeComponent(request, options)` 590 591Remove a component from a status page. 592 593```typescript 594const { success } = await openstatus.statusPage.v1.StatusPageService 595 .removeComponent( 596 { id: "comp_123" }, 597 { headers }, 598 ); 599``` 600 601#### `createComponentGroup(request, options)` 602 603Create a component group. 604 605```typescript 606const { group } = await openstatus.statusPage.v1.StatusPageService 607 .createComponentGroup( 608 { 609 pageId: "page_123", 610 name: "Core Services", 611 }, 612 { headers }, 613 ); 614``` 615 616#### `updateComponentGroup(request, options)` 617 618Update a component group. 619 620```typescript 621const { group } = await openstatus.statusPage.v1.StatusPageService 622 .updateComponentGroup( 623 { 624 id: "group_123", 625 name: "Updated Group Name", 626 }, 627 { headers }, 628 ); 629``` 630 631#### `deleteComponentGroup(request, options)` 632 633Delete a component group. 634 635```typescript 636const { success } = await openstatus.statusPage.v1.StatusPageService 637 .deleteComponentGroup( 638 { id: "group_123" }, 639 { headers }, 640 ); 641``` 642 643#### `subscribeToPage(request, options)` 644 645Subscribe an email to status page updates. 646 647```typescript 648const { subscriber } = await openstatus.statusPage.v1.StatusPageService 649 .subscribeToPage( 650 { 651 pageId: "page_123", 652 email: "user@example.com", 653 }, 654 { headers }, 655 ); 656``` 657 658#### `unsubscribeFromPage(request, options)` 659 660Unsubscribe from a status page. 661 662```typescript 663// By email 664const { success } = await openstatus.statusPage.v1.StatusPageService 665 .unsubscribeFromPage( 666 { 667 pageId: "page_123", 668 identifier: { case: "email", value: "user@example.com" }, 669 }, 670 { headers }, 671 ); 672 673// Or by subscriber ID 674const { success: success2 } = await openstatus.statusPage.v1.StatusPageService 675 .unsubscribeFromPage( 676 { 677 pageId: "page_123", 678 identifier: { case: "id", value: "sub_456" }, 679 }, 680 { headers }, 681 ); 682``` 683 684#### `listSubscribers(request, options)` 685 686List all subscribers for a status page. 687 688```typescript 689const { subscribers, totalSize } = await openstatus.statusPage.v1 690 .StatusPageService.listSubscribers( 691 { 692 pageId: "page_123", 693 limit: 50, 694 offset: 0, 695 includeUnsubscribed: false, 696 }, 697 { headers }, 698 ); 699``` 700 701#### `getStatusPageContent(request, options)` 702 703Get full status page content including components, groups, and active reports. 704 705```typescript 706const content = await openstatus.statusPage.v1.StatusPageService 707 .getStatusPageContent( 708 { identifier: { case: "slug", value: "my-service" } }, 709 { headers }, 710 ); 711 712console.log(`Page: ${content.statusPage?.title}`); 713console.log(`Components: ${content.components.length}`); 714console.log(`Active reports: ${content.statusReports.length}`); 715``` 716 717#### `getOverallStatus(request, options)` 718 719Get the aggregated status of a status page. 720 721```typescript 722import { OverallStatus } from "@openstatus/sdk-node"; 723 724const { overallStatus, componentStatuses } = await openstatus.statusPage.v1 725 .StatusPageService.getOverallStatus( 726 { identifier: { case: "id", value: "page_123" } }, 727 { headers }, 728 ); 729 730console.log(`Overall: ${OverallStatus[overallStatus]}`); 731for (const { componentId, status } of componentStatuses) { 732 console.log(` ${componentId}: ${OverallStatus[status]}`); 733} 734``` 735 736### Maintenance Service 737 738Manage scheduled maintenance windows. 739 740#### `createMaintenance(request, options)` 741 742Create a new maintenance window. 743 744```typescript 745const { maintenance } = await openstatus.maintenance.v1.MaintenanceService 746 .createMaintenance( 747 { 748 title: "Database Upgrade", 749 message: "We will be upgrading our database infrastructure.", 750 from: "2024-01-20T02:00:00Z", 751 to: "2024-01-20T04:00:00Z", 752 pageId: "page_123", 753 pageComponentIds: ["comp_456"], 754 notify: true, 755 }, 756 { headers }, 757 ); 758 759console.log(`Maintenance created: ${maintenance?.id}`); 760``` 761 762#### `getMaintenance(request, options)` 763 764Get a maintenance window by ID. 765 766```typescript 767const { maintenance } = await openstatus.maintenance.v1.MaintenanceService 768 .getMaintenance( 769 { id: "maint_123" }, 770 { headers }, 771 ); 772 773console.log(`Title: ${maintenance?.title}`); 774console.log(`From: ${maintenance?.from}`); 775console.log(`To: ${maintenance?.to}`); 776``` 777 778#### `listMaintenances(request, options)` 779 780List all maintenance windows with pagination and optional filtering. 781 782```typescript 783const { maintenances, totalSize } = await openstatus.maintenance.v1 784 .MaintenanceService.listMaintenances( 785 { 786 limit: 10, 787 offset: 0, 788 pageId: "page_123", // optional filter 789 }, 790 { headers }, 791 ); 792 793console.log(`Found ${totalSize} maintenance windows`); 794``` 795 796#### `updateMaintenance(request, options)` 797 798Update a maintenance window. 799 800```typescript 801const { maintenance } = await openstatus.maintenance.v1.MaintenanceService 802 .updateMaintenance( 803 { 804 id: "maint_123", 805 title: "Extended Database Upgrade", 806 to: "2024-01-20T06:00:00Z", 807 }, 808 { headers }, 809 ); 810``` 811 812#### `deleteMaintenance(request, options)` 813 814Delete a maintenance window. 815 816```typescript 817const { success } = await openstatus.maintenance.v1.MaintenanceService 818 .deleteMaintenance( 819 { id: "maint_123" }, 820 { headers }, 821 ); 822``` 823 824### Status Page Options 825 826| Option | Type | Required | Description | 827| ------------- | ------ | -------- | ---------------------------------------- | 828| `title` | string | Yes | Title of the status page (max 256 chars) | 829| `slug` | string | Yes | URL-friendly slug (lowercase, hyphens) | 830| `description` | string | No | Description (max 2048 chars) | 831| `homepageUrl` | string | No | Link to your homepage | 832| `contactUrl` | string | No | Link to your contact page | 833 834### Page Access Type 835 836| Enum Value | Description | 837| -------------------- | ----------------------- | 838| `UNSPECIFIED` | Default/unspecified | 839| `PUBLIC` | Publicly accessible | 840| `PASSWORD_PROTECTED` | Requires password | 841| `AUTHENTICATED` | Requires authentication | 842 843### Page Theme 844 845| Enum Value | Description | 846| ------------- | ------------------- | 847| `UNSPECIFIED` | Default/unspecified | 848| `SYSTEM` | Follow system theme | 849| `LIGHT` | Light theme | 850| `DARK` | Dark theme | 851 852### Overall Status 853 854| Enum Value | Description | 855| ---------------- | --------------------------- | 856| `UNSPECIFIED` | Default/unspecified | 857| `OPERATIONAL` | All systems operational | 858| `DEGRADED` | Performance is degraded | 859| `PARTIAL_OUTAGE` | Some systems are down | 860| `MAJOR_OUTAGE` | Major systems are down | 861| `MAINTENANCE` | Scheduled maintenance | 862| `UNKNOWN` | Status cannot be determined | 863 864### Page Component Type 865 866| Enum Value | Description | 867| ------------- | ------------------------- | 868| `UNSPECIFIED` | Default/unspecified | 869| `MONITOR` | Linked to a monitor | 870| `STATIC` | Static component (manual) | 871 872## Monitor Options 873 874### HTTP Monitor 875 876| Option | Type | Required | Description | 877| ---------------------- | ------------------- | -------- | --------------------------------------------------- | 878| `name` | string | Yes | Monitor name (max 256 chars) | 879| `url` | string | Yes | URL to monitor (max 2048 chars) | 880| `periodicity` | Periodicity | Yes | Check interval (see [Periodicity](#periodicity)) | 881| `method` | HTTPMethod | No | HTTP method (see [HTTP Methods](#http-methods)) | 882| `body` | string | No | Request body | 883| `headers` | Headers[] | No | Custom headers (`{ key: string, value: string }[]`) | 884| `timeout` | bigint | No | Timeout in ms (default: 45000, max: 120000) | 885| `retry` | bigint | No | Retry attempts (default: 3, max: 10) | 886| `followRedirects` | boolean | No | Follow redirects (default: true) | 887| `regions` | Region[] | No | [Regions](#regions) for checks | 888| `active` | boolean | No | Enable monitoring (default: false) | 889| `public` | boolean | No | Public visibility (default: false) | 890| `degradedAt` | bigint | No | Latency threshold (ms) for degraded status | 891| `description` | string | No | Monitor description (max 1024 chars) | 892| `statusCodeAssertions` | array | No | [Status code assertions](#status-code-assertions) | 893| `bodyAssertions` | array | No | [Body assertions](#body-assertions) | 894| `headerAssertions` | array | No | [Header assertions](#header-assertions) | 895| `openTelemetry` | OpenTelemetryConfig | No | OpenTelemetry export configuration | 896 897### TCP Monitor 898 899| Option | Type | Required | Description | 900| --------------- | ------------------- | -------- | ------------------------------------------------ | 901| `name` | string | Yes | Monitor name (max 256 chars) | 902| `uri` | string | Yes | `host:port` to monitor (max 2048 chars) | 903| `periodicity` | Periodicity | Yes | Check interval (see [Periodicity](#periodicity)) | 904| `timeout` | bigint | No | Timeout in ms (default: 45000, max: 120000) | 905| `retry` | bigint | No | Retry attempts (default: 3, max: 10) | 906| `regions` | Region[] | No | [Regions](#regions) for checks | 907| `active` | boolean | No | Enable monitoring (default: false) | 908| `public` | boolean | No | Public visibility (default: false) | 909| `degradedAt` | bigint | No | Latency threshold (ms) for degraded status | 910| `description` | string | No | Monitor description (max 1024 chars) | 911| `openTelemetry` | OpenTelemetryConfig | No | OpenTelemetry export configuration | 912 913### DNS Monitor 914 915| Option | Type | Required | Description | 916| ------------------ | ------------------- | -------- | ------------------------------------------------ | 917| `name` | string | Yes | Monitor name (max 256 chars) | 918| `uri` | string | Yes | Domain to resolve (max 2048 chars) | 919| `periodicity` | Periodicity | Yes | Check interval (see [Periodicity](#periodicity)) | 920| `timeout` | bigint | No | Timeout in ms (default: 45000, max: 120000) | 921| `retry` | bigint | No | Retry attempts (default: 3, max: 10) | 922| `regions` | Region[] | No | [Regions](#regions) for checks | 923| `active` | boolean | No | Enable monitoring (default: false) | 924| `public` | boolean | No | Public visibility (default: false) | 925| `degradedAt` | bigint | No | Latency threshold (ms) for degraded status | 926| `description` | string | No | Monitor description (max 1024 chars) | 927| `recordAssertions` | array | No | [DNS record assertions](#dns-record-assertions) | 928| `openTelemetry` | OpenTelemetryConfig | No | OpenTelemetry export configuration | 929 930### Periodicity 931 932| Enum Value | Description | 933| ----------------- | ----------- | 934| `PERIODICITY_30S` | Every 30s | 935| `PERIODICITY_1M` | Every 1m | 936| `PERIODICITY_5M` | Every 5m | 937| `PERIODICITY_10M` | Every 10m | 938| `PERIODICITY_30M` | Every 30m | 939| `PERIODICITY_1H` | Every 1h | 940 941### HTTP Methods 942 943| Enum Value | Description | 944| --------------------- | ----------- | 945| `HTTP_METHOD_GET` | GET | 946| `HTTP_METHOD_POST` | POST | 947| `HTTP_METHOD_HEAD` | HEAD | 948| `HTTP_METHOD_PUT` | PUT | 949| `HTTP_METHOD_PATCH` | PATCH | 950| `HTTP_METHOD_DELETE` | DELETE | 951| `HTTP_METHOD_TRACE` | TRACE | 952| `HTTP_METHOD_CONNECT` | CONNECT | 953| `HTTP_METHOD_OPTIONS` | OPTIONS | 954 955## Assertions 956 957All assertion comparators are exported as enums from the SDK. 958 959### Status Code Assertions 960 961Validate HTTP response status codes using `NumberComparator`. 962 963```typescript 964import { NumberComparator } from "@openstatus/sdk-node"; 965 966{ 967 statusCodeAssertions: [ 968 { comparator: NumberComparator.EQUAL, target: BigInt(200) }, 969 { comparator: NumberComparator.LESS_THAN, target: BigInt(400) }, 970 ]; 971} 972``` 973 974**NumberComparator values:** 975 976| Enum Value | Description | 977| ----------------------- | --------------------- | 978| `EQUAL` | Equal to target | 979| `NOT_EQUAL` | Not equal to target | 980| `GREATER_THAN` | Greater than target | 981| `GREATER_THAN_OR_EQUAL` | Greater than or equal | 982| `LESS_THAN` | Less than target | 983| `LESS_THAN_OR_EQUAL` | Less than or equal | 984 985### Body Assertions 986 987Validate response body content using `StringComparator`. 988 989```typescript 990import { StringComparator } from "@openstatus/sdk-node"; 991 992{ 993 bodyAssertions: [ 994 { comparator: StringComparator.CONTAINS, target: '"status":"ok"' }, 995 { comparator: StringComparator.NOT_EMPTY, target: "" }, 996 ]; 997} 998``` 999 1000**StringComparator values:** 1001 1002| Enum Value | Description | 1003| ----------------------- | --------------------------- | 1004| `CONTAINS` | Contains target string | 1005| `NOT_CONTAINS` | Does not contain target | 1006| `EQUAL` | Equal to target | 1007| `NOT_EQUAL` | Not equal to target | 1008| `EMPTY` | Body is empty | 1009| `NOT_EMPTY` | Body is not empty | 1010| `GREATER_THAN` | Lexicographically greater | 1011| `GREATER_THAN_OR_EQUAL` | Lexicographically >= target | 1012| `LESS_THAN` | Lexicographically less | 1013| `LESS_THAN_OR_EQUAL` | Lexicographically <= target | 1014 1015### Header Assertions 1016 1017Validate response headers using `StringComparator`. 1018 1019```typescript 1020import { StringComparator } from "@openstatus/sdk-node"; 1021 1022{ 1023 headerAssertions: [ 1024 { 1025 key: "content-type", 1026 comparator: StringComparator.CONTAINS, 1027 target: "application/json", 1028 }, 1029 ]; 1030} 1031``` 1032 1033### DNS Record Assertions 1034 1035Validate DNS records using `RecordComparator`. 1036 1037```typescript 1038import { RecordComparator } from "@openstatus/sdk-node"; 1039 1040{ 1041 recordAssertions: [ 1042 { 1043 record: "A", 1044 comparator: RecordComparator.EQUAL, 1045 target: "93.184.216.34", 1046 }, 1047 { record: "CNAME", comparator: RecordComparator.CONTAINS, target: "cdn" }, 1048 ]; 1049} 1050``` 1051 1052**RecordComparator values:** 1053 1054| Enum Value | Description | 1055| -------------- | ----------------------- | 1056| `EQUAL` | Equal to target | 1057| `NOT_EQUAL` | Not equal to target | 1058| `CONTAINS` | Contains target string | 1059| `NOT_CONTAINS` | Does not contain target | 1060 1061**Supported record types:** `A`, `AAAA`, `CNAME`, `MX`, `TXT` 1062 1063## Regions 1064 1065Monitor from 28 global locations across multiple providers. Use the `Region` 1066enum: 1067 1068```typescript 1069import { Region } from "@openstatus/sdk-node"; 1070 1071// Example: Use specific regions 1072regions: [Region.FLY_AMS, Region.FLY_IAD, Region.KOYEB_FRA]; 1073``` 1074 1075### Fly.io Regions 1076 1077| Enum Value | Location | 1078| ---------- | --------------- | 1079| `FLY_AMS` | Amsterdam | 1080| `FLY_ARN` | Stockholm | 1081| `FLY_BOM` | Mumbai | 1082| `FLY_CDG` | Paris | 1083| `FLY_DFW` | Dallas | 1084| `FLY_EWR` | Newark | 1085| `FLY_FRA` | Frankfurt | 1086| `FLY_GRU` | São Paulo | 1087| `FLY_IAD` | Washington D.C. | 1088| `FLY_JNB` | Johannesburg | 1089| `FLY_LAX` | Los Angeles | 1090| `FLY_LHR` | London | 1091| `FLY_NRT` | Tokyo | 1092| `FLY_ORD` | Chicago | 1093| `FLY_SJC` | San Jose | 1094| `FLY_SIN` | Singapore | 1095| `FLY_SYD` | Sydney | 1096| `FLY_YYZ` | Toronto | 1097 1098### Koyeb Regions 1099 1100| Enum Value | Location | 1101| ----------- | ------------- | 1102| `KOYEB_FRA` | Frankfurt | 1103| `KOYEB_PAR` | Paris | 1104| `KOYEB_SFO` | San Francisco | 1105| `KOYEB_SIN` | Singapore | 1106| `KOYEB_TYO` | Tokyo | 1107| `KOYEB_WAS` | Washington | 1108 1109### Railway Regions 1110 1111| Enum Value | Location | 1112| ------------------------- | -------------- | 1113| `RAILWAY_US_WEST2` | US West | 1114| `RAILWAY_US_EAST4` | US East | 1115| `RAILWAY_EUROPE_WEST4` | Europe West | 1116| `RAILWAY_ASIA_SOUTHEAST1` | Asia Southeast | 1117 1118## Error Handling 1119 1120The SDK uses Connect RPC. Errors include a `code` and `message`: 1121 1122```typescript 1123import { ConnectError } from "@connectrpc/connect"; 1124 1125try { 1126 await openstatus.monitor.v1.MonitorService.deleteMonitor( 1127 { id: "invalid" }, 1128 { headers }, 1129 ); 1130} catch (error) { 1131 if (error instanceof ConnectError) { 1132 console.error(`Error ${error.code}: ${error.message}`); 1133 } 1134} 1135``` 1136 1137## Related 1138 1139- [OpenStatus](https://openstatus.dev) - Open-source monitoring platform 1140- [Documentation](https://docs.openstatus.dev) - Full API documentation 1141- [Status Page](https://status.openstatus.dev) - OpenStatus service status 1142 1143## License 1144 1145MIT