npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@ottercoders/pulumi-oneuptime

v0.7.0

Published

A native [Pulumi](https://www.pulumi.com/) provider for managing [OneUptime](https://oneuptime.com/) monitoring resources.

Readme

Pulumi OneUptime Provider

A native Pulumi provider for managing OneUptime monitoring resources.

Installation

Go

go get github.com/ottercoders/pulumi-oneuptime/sdk/go/oneuptime

Node.js

npm install @ottercoders/pulumi-oneuptime

Python

pip install pulumi-oneuptime

Configuration

The provider requires an API key and optionally a base URL and default project ID.

| Property | Environment Variable | Required | Default | Description | |-------------|--------------------------|----------|--------------------------|--------------------------------------| | apiKey | ONEUPTIME_API_KEY | Yes | | API key for authentication | | baseUrl | ONEUPTIME_BASE_URL | No | https://oneuptime.com | Base URL of the OneUptime instance | | projectId | ONEUPTIME_PROJECT_ID | No | | Default project ID for all resources |

Using Pulumi Config

pulumi config set oneuptime:apiKey --secret <your-api-key>
pulumi config set oneuptime:projectId <your-project-id>

# For self-hosted instances
pulumi config set oneuptime:baseUrl https://your-instance.example.com

Using Environment Variables

export ONEUPTIME_API_KEY="your-api-key"
export ONEUPTIME_PROJECT_ID="your-project-id"

Resources

All resources (except Project) accept an optional projectId property. When omitted, the provider-level projectId config is used. Every resource exposes resourceId, slug, createdAt, and updatedAt as outputs.

| Resource | Description | |----------------------|------------------------------------------| | Team | Manages teams within a project | | Monitor | Manages monitors (API, website, etc.) | | StatusPage | Manages public/private status pages | | Incident | Manages incidents | | OnCallDutyPolicy | Manages on-call duty escalation policies | | Label | Manages labels for categorizing resources | | MonitorGroup | Manages logical groupings of monitors | | IncidentState | Manages incident workflow states (e.g. Created, Acknowledged, Resolved) | | IncidentSeverity | Manages incident severity levels (e.g. Critical, Major, Minor) | | AlertState | Manages alert workflow states | | AlertSeverity | Manages alert severity levels | | Project | Manages OneUptime projects | | StatusPageGroup | Groups monitors on a status page | | StatusPageResource | Links a monitor or monitor group to a status page | | OnCallDutyPolicyEscalationRule | Escalation timing/order within an on-call policy | | OnCallDutyPolicySchedule | Rotation schedule within an on-call policy | | OnCallDutyPolicyEscalationRuleSchedule | Assigns an on-call schedule as a paging target on an escalation rule | | OnCallDutyPolicyEscalationRuleUser | Assigns a specific user as a paging target on an escalation rule | | OnCallDutyPolicyEscalationRuleTeam | Assigns a whole team as a paging target on an escalation rule | | ProjectSSO | OIDC/SAML SSO configuration | | Domain | Verified email domain for SSO user matching | | ProjectSsoTeam | Auto-assigns SSO users to a team on first login | | ApiKey | API key lifecycle (the apiKey output is a secret) | | ApiKeyPermission | Fine-grained permissions on an API key | | TeamMember | Adds an existing user to a team | | TeamPermission | Assigns permissions to a team | | MonitorTeamOwner | Team owns a monitor | | MonitorUserOwner | User owns a monitor | | MonitorGroupResource | Adds a monitor to a monitor group | | Probe | Monitoring probe registration (the key output is a secret) | | StatusPageAnnouncement | Announcement banner on status pages | | StatusPageDomain | Binds a custom domain to a status page | | StatusPageHeaderLink | Link in the status page header | | StatusPageFooterLink | Link in the status page footer | | StatusPageSubscriber | Email/SMS/webhook subscriber | | StatusPageTeamOwner | Team owns a status page | | StatusPageUserOwner | User owns a status page | | IncidentTemplate | Standardized template for incident creation | | IncidentNoteTemplate | Reusable incident note template | | ScheduledMaintenanceEvent | Planned maintenance window | | ScheduledMaintenanceState | Workflow state for maintenance events | | ScheduledMaintenanceTemplate | Template for maintenance events | | Workflow | Automation workflow |

Bootstrap flow

The provider cannot create the very first OneUptime user or the master API key; both must be set up via the OneUptime UI:

  1. Install OneUptime and register an admin user via the UI
  2. Create a project in the UI
  3. Mint the master API key in Project Settings → API Keys
  4. Set oneuptime:apiKey in your Pulumi config (or export ONEUPTIME_API_KEY)
  5. Everything else — additional API keys, team membership, permissions, monitors, etc. — is declarative from here on

On-call: wiring paging targets

An OnCallDutyPolicyEscalationRule by itself doesn't page anyone — it's just a timing/order slot. Attach at least one of the three "target" resources to it:

import * as oneuptime from "@ottercoders/pulumi-oneuptime";

const policy = new oneuptime.OnCallDutyPolicy("primary", { name: "Primary paging" });

const firstRule = new oneuptime.OnCallDutyPolicyEscalationRule("first", {
    onCallDutyPolicyId: policy.resourceId,
    order: 1,
    escalateAfterInMinutes: 0,
});

// Choose one or more target resources — all three can coexist on the same rule.
new oneuptime.OnCallDutyPolicyEscalationRuleUser("oncall-user", {
    onCallDutyPolicyId: policy.resourceId,
    onCallDutyPolicyEscalationRuleId: firstRule.resourceId,
    userId: primaryOncallUserId,
});

new oneuptime.OnCallDutyPolicyEscalationRuleTeam("oncall-team", {
    onCallDutyPolicyId: policy.resourceId,
    onCallDutyPolicyEscalationRuleId: firstRule.resourceId,
    teamId: sreTeamId,
});

new oneuptime.OnCallDutyPolicyEscalationRuleSchedule("oncall-sched", {
    onCallDutyPolicyId: policy.resourceId,
    onCallDutyPolicyEscalationRuleId: firstRule.resourceId,
    onCallDutyPolicyScheduleId: rotationScheduleId,
});

On-call schedule layers with typed rotation

OnCallScheduleLayer.rotation and .restrictionTimes are typed — you don't need to hand-build the OneUptime envelope JSON:

new oneuptime.OnCallScheduleLayer("weekly-primary", {
    onCallDutyPolicyScheduleId: scheduleId,
    name: "Weekly primary",
    order: 1,
    startsAt: "2026-01-06T00:00:00Z",
    handOffTime: "2026-01-13T00:00:00Z",
    rotation: { intervalType: "Week", intervalCount: 1 },
    restrictionTimes: {
        restrictionType: "Weekly",
        weeklyRestrictionTimes: [{
            startDay: "Monday", endDay: "Friday",
            startTime: "09:00", endTime: "17:00",
        }],
    },
});

Workflows

Workflow.graph is a free-form JSON object — OneUptime intentionally doesn't expose a typed schema for it (see the comment in Common/Models/DatabaseModels/Workflow.ts: "Ideally, create this via UI and not via API"). The recommended flow is:

  1. Build and test the workflow in the OneUptime UI.
  2. Export its graph JSON (from the UI or by reading the record via the API).
  3. Paste that JSON into the graph field of a Pulumi Workflow resource.

This keeps the declarative boundary aligned with OneUptime's own guidance and avoids a schema that would drift on every upstream release.

Default resources — look up, don't create

OneUptime auto-creates a default set of rows in every project and does not allow them to be deleted. Trying to create a resource with one of these names returns HTTP 400 "already exists":

  • MonitorStatus: Operational, Degraded, Offline
  • IncidentState: Created, Acknowledged, Resolved
  • IncidentSeverity: Critical, Major, Minor (varies by OneUptime version)
  • AlertState / AlertSeverity: similar defaults

Reference these from your program using the corresponding data source instead of declaring a resource:

import * as oneuptime from "@ottercoders/pulumi-oneuptime";

const operational = oneuptime.getMonitorStatusOutput({ name: "Operational" });
const resolved    = oneuptime.getIncidentStateOutput({ name: "Resolved" });
const critical    = oneuptime.getIncidentSeverityOutput({ name: "Critical" });

new oneuptime.Monitor("web", {
    name: "Website",
    monitorType: "Website",
    currentMonitorStatusId: operational.resourceId,
});

Only declare MonitorStatus / IncidentState / IncidentSeverity resources for custom statuses/states your workflow adds on top of the defaults.

Resource Properties

Team

| Property | Type | Required | Description | |---------------|--------|----------|----------------------| | name | string | Yes | Team name | | description | string | No | Team description |

Monitor

| Property | Type | Required | Description | |----------------------------------|-----------------------|----------|---------------------------------------------------------------------------------------------------------------------------| | name | string | Yes | Monitor name | | monitorType | string | Yes | One of the 23 MonitorType values — e.g. "Website", "API", "Ping", "Port", "Incoming Request", "Server" | | currentMonitorStatusId | string | Yes | ID of the current monitor status (from a MonitorStatus resource or getMonitorStatus data source) | | description | string | No | Monitor description | | disableActiveMonitoring | bool | No | Disable active monitoring | | monitoringInterval | string | No | Check interval (e.g. "1m", "5m") | | monitorSteps | MonitorStep[] | No (Yes for non-Manual) | Probe steps with destinations, request config, and decision criteria. See Monitor steps below | | defaultMonitorStatusId | string | No | Fallback status when no criteria match | | labels | string[] | No | Label resource IDs to attach (ManyToMany) | | customFields | map | No | Free-form values keyed by MonitorCustomField name | | postUpdatesToWorkspaceChannels | WorkspaceChannelRef[] | No | Slack/Teams channels to notify on status changes |

Output-only: resourceId, slug, createdAt, updatedAt, incomingRequestSecretKey (secret), serverMonitorSecretKey (secret), incomingEmailSecretKey (secret), incomingMonitorRequest, incomingEmailMonitorRequest, serverMonitorResponse.

Monitor steps

Each MonitorStep configures one probe and its decision logic. Populate only the sub-monitor field (logMonitor, snmpMonitor, dnsMonitor, etc.) that matches the parent monitor's monitorType; omit the rest. A minimal Website step looks like:

import * as oneuptime from "@ottercoders/pulumi-oneuptime";

const offline = oneuptime.getMonitorStatusOutput({ name: "Offline" });
const operational = oneuptime.getMonitorStatusOutput({ name: "Operational" });

new oneuptime.Monitor("web", {
    name: "Marketing site",
    monitorType: "Website",
    currentMonitorStatusId: operational.resourceId,
    monitorSteps: [{
        id: "step-root",
        monitorDestination: "https://example.com",
        requestType: "GET",
        monitorCriteria: {
            criteriaInstances: [{
                id: "down-on-5xx",
                name: "Down if 5xx",
                description: "Server-side failure",
                filterCondition: "Any",
                filters: [{
                    checkOn: "Response Status Code",
                    filterType: "Greater Than",
                    value: "499",
                }],
                monitorStatusId: offline.resourceId,
                changeMonitorStatus: true,
            }],
        },
    }],
});

For an API monitor add requestHeaders/requestBody on the step. For SNMP/DNS/Kubernetes/Docker/Synthetic monitors populate the matching snmpMonitor / dnsMonitor / kubernetesMonitor / dockerMonitor / customCode fields and set filters[].checkOn to the appropriate value ("SNMP OID Value", "DNS Response Time (in ms)", "CPU Usage (in %)", etc.). filters[].checkOn and filters[].filterType use OneUptime's full display strings verbatim.

Server-generated secret keys

IncomingRequest, Server, and IncomingEmail monitor types expose auto-generated secret keys the server wires at create time. Read them from the outputs to construct webhook/agent URLs:

const server = new oneuptime.Monitor("db", {
    name: "Database host",
    monitorType: "Server",
    currentMonitorStatusId: operational.resourceId,
});

export const agentUrl = pulumi.interpolate`https://oneuptime.example.com/api/server-monitor/response/ingest/${server.serverMonitorSecretKey}`;

Pulumi encrypts these in state (AlwaysSecret) and redacts them from pulumi stack output unless --show-secrets is passed.

StatusPage

| Property | Type | Required | Description | |-------------------------------------|--------|----------|-----------------------------------| | name | string | Yes | Status page name | | description | string | No | Status page description | | pageTitle | string | No | HTML page title | | pageDescription | string | No | Page description text | | isPublicStatusPage | bool | No | Whether the page is public | | showIncidentHistoryInDays | int | No | Days of incident history to show | | showAnnouncementHistoryInDays | int | No | Days of announcement history | | showScheduledEventHistoryInDays | int | No | Days of scheduled event history |

Incident

| Property | Type | Required | Description | |---------------------------|--------|----------|---------------------------------| | title | string | Yes | Incident title | | currentIncidentStateId | string | Yes | ID of the current state | | incidentSeverityId | string | Yes | ID of the severity level | | description | string | No | Incident description | | declaredAt | string | No | When the incident was declared |

OnCallDutyPolicy

| Property | Type | Required | Description | |-----------------------------------------------|--------|----------|------------------------------------------| | name | string | Yes | Policy name | | description | string | No | Policy description | | repeatPolicyIfNoOneAcknowledges | bool | No | Repeat if no acknowledgement | | repeatPolicyIfNoOneAcknowledgesNoOfTimes | int | No | Number of times to repeat |

Label

| Property | Type | Required | Description | |---------------|--------|----------|--------------------------------------| | name | string | Yes | Label name | | color | string | Yes | Hex color code (e.g. #e74c3c) | | description | string | No | Label description |

MonitorGroup

| Property | Type | Required | Description | |---------------|--------|----------|---------------------------| | name | string | Yes | Group name | | description | string | No | Group description |

IncidentState

| Property | Type | Required | Description | |-----------------------|--------|----------|------------------------------------| | name | string | Yes | State name | | color | string | Yes | Hex color code | | description | string | No | State description | | isCreatedState | bool | No | Mark as the initial created state | | isAcknowledgedState | bool | No | Mark as the acknowledged state | | isResolvedState | bool | No | Mark as the resolved state | | order | int | No | Display order |

IncidentSeverity

| Property | Type | Required | Description | |---------------|--------|----------|--------------------------------| | name | string | Yes | Severity name | | color | string | Yes | Hex color code | | description | string | No | Severity description | | order | int | No | Display order (1 = most severe)|

AlertState

| Property | Type | Required | Description | |-----------------------|--------|----------|------------------------------------| | name | string | Yes | State name | | color | string | Yes | Hex color code | | description | string | No | State description | | isCreatedState | bool | No | Mark as the initial created state | | isAcknowledgedState | bool | No | Mark as the acknowledged state | | isResolvedState | bool | No | Mark as the resolved state | | order | int | No | Display order |

AlertSeverity

| Property | Type | Required | Description | |---------------|--------|----------|--------------------------------| | name | string | Yes | Severity name | | color | string | Yes | Hex color code | | description | string | No | Severity description | | order | int | No | Display order (1 = most severe)|

Project

| Property | Type | Required | Description | |---------------|--------|----------|------------------------| | name | string | Yes | Project name | | description | string | No | Project description |

Note: The Project resource does not accept a projectId property since it represents the project itself.

Example

YAML

name: oneuptime-example
runtime: yaml
resources:
  engineering-team:
    type: oneuptime:resources:Team
    properties:
      name: Engineering
      description: Engineering team managed by Pulumi

  api-monitor:
    type: oneuptime:resources:Monitor
    properties:
      name: API Health Check
      monitorType: API
      currentMonitorStatusId: ${monitorStatusId}

  status-page:
    type: oneuptime:resources:StatusPage
    properties:
      name: Public Status
      pageTitle: Service Status
      isPublicStatusPage: true
      showIncidentHistoryInDays: 14

  env-label:
    type: oneuptime:resources:Label
    properties:
      name: production
      color: "#e74c3c"
      description: Production environment

  api-monitors:
    type: oneuptime:resources:MonitorGroup
    properties:
      name: API Monitors
      description: All API health check monitors

  critical-severity:
    type: oneuptime:resources:IncidentSeverity
    properties:
      name: Critical
      color: "#e74c3c"
      description: Service is completely down
      order: 1

TypeScript

import * as oneuptime from "@ottercoders/pulumi-oneuptime";

const team = new oneuptime.resources.Team("engineering", {
    name: "Engineering",
    description: "Engineering team",
});

const label = new oneuptime.resources.Label("production", {
    name: "production",
    color: "#e74c3c",
    description: "Production environment",
});

const severity = new oneuptime.resources.IncidentSeverity("critical", {
    name: "Critical",
    color: "#e74c3c",
    description: "Service is completely down",
    order: 1,
});

Python

from pulumi_oneuptime import resources

team = resources.Team("engineering",
    name="Engineering",
    description="Engineering team",
)

label = resources.Label("production",
    name="production",
    color="#e74c3c",
    description="Production environment",
)

severity = resources.IncidentSeverity("critical",
    name="Critical",
    color="#e74c3c",
    description="Service is completely down",
    order=1,
)

Development

Prerequisites

Build

make provider    # Build the provider binary
make install     # Install to $GOPATH/bin
make schema      # Generate schema.json
make sdk         # Generate SDKs (Go, Node.js, Python, .NET)
make test        # Run unit tests
make lint        # Run linter
make clean       # Remove build artifacts

Testing

Unit tests use mocked HTTP servers and require no credentials:

make test

Acceptance tests run against a real OneUptime instance:

export ONEUPTIME_API_KEY="your-key"
export ONEUPTIME_PROJECT_ID="your-project-id"
make test-acceptance

Adding a New Resource

  1. Create a new file in provider/resources/ (e.g., workflow.go)
  2. Define Args, State, and resource structs with pulumi:"..." and json:"..." tags
  3. Implement Create, Read, Update, Delete methods following the pattern in existing resources
  4. Register the resource in provider/provider.go

License

Apache 2.0 - See LICENSE for details.