任意の言語から ping する

SteadyCron ハートビート URL を成功・失敗時に ping するコピー&ペースト用スニペット — Bash、Python、Node.js、PHP、Ruby、Go、PowerShell、Docker、systemd。

ハートビートチェックはジョブが動いたときにリクエストを送る URL です。以下のスニペットをコピーして <your-ping-token> を置き換えれば監視が始まります。成功時はベース URL に、失敗時は /fail に ping します。スタックした実行を検出したい場合は /start を最初に ping します。

ping URL は https://ping.steadycron.com/<your-ping-token> の形式です — ハートビートを作成した後、チェックのページで確認できます。

curl(ワンライナー)

curl -fsS -m 10 --retry 3 https://ping.steadycron.com/<your-ping-token>

-f は HTTP エラーで失敗、-s はサイレント、-m 10 で時間を制限、--retry 3 で一時的なネットワーク障害に対応。

Bash(start / success / fail)

#!/usr/bin/env bash
set -euo pipefail
TOKEN=<your-ping-token>
PING="https://ping.steadycron.com/$TOKEN"

curl -fsS -m 10 "$PING/start"            # ジョブ開始

if ./run-job.sh; then
  curl -fsS -m 10 "$PING"                # 成功
else
  curl -fsS -m 10 "$PING/fail"           # 明示的な失敗
fi

任意のコマンドをラップ

コマンドがゼロ以外で終了した場合に自動的に /fail を ping — ジョブ自体を編集不要:

TOKEN=<your-ping-token>
PING="https://ping.steadycron.com/$TOKEN"
./run-job.sh && curl -fsS "$PING" || curl -fsS "$PING/fail"

Python

import subprocess
import urllib.request

TOKEN = "<your-ping-token>"
PING = f"https://ping.steadycron.com/{TOKEN}"

def ping(suffix=""):
    try:
        urllib.request.urlopen(PING + suffix, timeout=10)
    except Exception:
        pass  # 監視でジョブを壊さないようにする

ping("/start")
try:
    subprocess.run(["./run-job.sh"], check=True)
    ping()           # 成功
except subprocess.CalledProcessError:
    ping("/fail")    # 失敗

Node.js

const TOKEN = "<your-ping-token>";
const PING = `https://ping.steadycron.com/${TOKEN}`;

const ping = (suffix = "") =>
  fetch(PING + suffix, { signal: AbortSignal.timeout(10_000) }).catch(() => {});

await ping("/start");
try {
  await runJob();
  await ping();          // 成功
} catch {
  await ping("/fail");   // 失敗
}

PHP

<?php
$token = "<your-ping-token>";
$ping  = "https://ping.steadycron.com/$token";

function ping(string $url): void {
    @file_get_contents($url, false, stream_context_create([
        "http" => ["timeout" => 10, "ignore_errors" => true],
    ]));
}

ping("$ping/start");
$exit = 0;
system("./run-job.sh", $exit);
ping($exit === 0 ? $ping : "$ping/fail");

Ruby

require "net/http"

token = "<your-ping-token>"
ping  = "https://ping.steadycron.com/#{token}"

def hit(url) = Net::HTTP.get_response(URI(url)) rescue nil

hit("#{ping}/start")
if system("./run-job.sh")
  hit(ping)          # 成功
else
  hit("#{ping}/fail")
end

Go

package main

import (
	"net/http"
	"os/exec"
	"time"
)

const ping = "https://ping.steadycron.com/<your-ping-token>"

func hit(suffix string) {
	c := &http.Client{Timeout: 10 * time.Second}
	if resp, err := c.Get(ping + suffix); err == nil {
		resp.Body.Close()
	}
}

func main() {
	hit("/start")
	if err := exec.Command("./run-job.sh").Run(); err == nil {
		hit("") // 成功
	} else {
		hit("/fail")
	}
}

PowerShell(Windows / スケジュールタスク)

$token = "<your-ping-token>"
$ping  = "https://ping.steadycron.com/$token"

function Ping($url) { try { Invoke-WebRequest -UseBasicParsing -TimeoutSec 10 $url | Out-Null } catch {} }

Ping "$ping/start"
& ".\run-job.ps1"
if ($LASTEXITCODE -eq 0) { Ping $ping } else { Ping "$ping/fail" }

Docker ヘルスチェック

HEALTHCHECK --interval=5m --timeout=10s \
  CMD curl -fsS https://ping.steadycron.com/<your-ping-token> || exit 1

systemd タイマー

タイマーが実行するサービスに ExecStartPost / ExecStopPost を追加します。

[Service]
Type=oneshot
ExecStart=/usr/local/bin/run-job.sh
ExecStartPost=/usr/bin/curl -fsS https://ping.steadycron.com/<your-ping-token>

次のステップ