koala73/worldmonitor · error · Error

[initRamp] waveLabelOffset=${offset} signals resumption afte

Error message

[initRamp] waveLabelOffset=${offset} signals resumption after manual waves; seedLastWaveBroadcastId + seedLastWaveSentAt are required so the first cron tick can apply the kill-gate against the prior wave. Pass them, or set waveLabelOffset=0 to start a fresh ramp.

What it means

Thrown by initRamp when waveLabelOffset > 0 (signaling the ramp resumes after one or more manually-sent waves) but the seed pair (seedLastWaveBroadcastId + seedLastWaveSentAt) is not provided. The first cron tick must apply the kill-gate against the prior wave, which requires the seed broadcast id and timestamp. Without them, the kill-gate would be silently skipped — a dangerous failure mode.

Source

Thrown at convex/broadcast/rampRunner.ts:180

    excludeNonEnglish: v.optional(v.boolean()),
  },
  handler: async (ctx, args) => {
    if (args.rampCurve.length === 0) {
      throw new Error("[initRamp] rampCurve must be non-empty");
    }
    if (args.rampCurve.some((n) => !Number.isInteger(n) || n <= 0)) {
      throw new Error("[initRamp] rampCurve entries must be positive integers");
    }
    const offset = args.waveLabelOffset ?? 0;
    const hasSeedBroadcast = !!args.seedLastWaveBroadcastId;
    const hasSeedSentAt = typeof args.seedLastWaveSentAt === "number";
    if (hasSeedBroadcast !== hasSeedSentAt) {
      throw new Error(
        "[initRamp] seedLastWaveBroadcastId and seedLastWaveSentAt must be provided together.",
      );
    }
    if (offset > 0 && !hasSeedBroadcast) {
      throw new Error(
        `[initRamp] waveLabelOffset=${offset} signals resumption after manual waves; seedLastWaveBroadcastId + seedLastWaveSentAt are required so the first cron tick can apply the kill-gate against the prior wave. Pass them, or set waveLabelOffset=0 to start a fresh ramp.`,
      );
    }
    const existing = await ctx.db
      .query("broadcastRampConfig")
      .withIndex("by_key", (q) => q.eq("key", RAMP_KEY))
      .first();
    if (existing) {
      throw new Error(
        `[initRamp] ramp already configured (active=${existing.active}, tier=${existing.currentTier}). Run abortRamp first if reconfiguring.`,
      );
    }
    await ctx.db.insert("broadcastRampConfig", {
      key: RAMP_KEY,
      active: true,
      rampCurve: args.rampCurve,
      currentTier: -1,
      waveLabelPrefix: args.waveLabelPrefix,

View on GitHub (pinned to ffec79ac33)

Solutions

  1. Provide seedLastWaveBroadcastId and seedLastWaveSentAt when waveLabelOffset > 0, so the first cron tick can evaluate the kill-gate against the prior wave.
  2. Alternatively, set waveLabelOffset=0 to start a fresh ramp with no prior waves (no seed needed).
  3. Follow the resume-ramp runbook: capture the last manual wave's broadcast id and sent timestamp before calling initRamp.

Example fix

// before
await initRamp(ctx, {
  rampCurve: [500, 1000], waveLabelPrefix: "w",
  waveLabelOffset: 7, // signals resumption, but no seed
});
// after — seed the prior wave
await initRamp(ctx, {
  rampCurve: [500, 1000], waveLabelPrefix: "w",
  waveLabelOffset: 7,
  seedLastWaveBroadcastId: "last-broadcast-id",
  seedLastWaveSentAt: Date.parse("2024-10-14T00:00:00Z"),
});
Defensive patterns

Strategy: validation

Validate before calling

const offset = args.waveLabelOffset ?? 0;
if (offset > 0 && (!args.seedLastWaveBroadcastId || typeof args.seedLastWaveSentAt !== "number")) {
  throw new Error("waveLabelOffset > 0 requires seedLastWaveBroadcastId + seedLastWaveSentAt");
}
await initRamp(ctx, args);

Prevention

When it happens

Trigger: Calling initRamp with waveLabelOffset set to a positive number (e.g. 7, meaning waves 0-6 were sent manually) but without seedLastWaveBroadcastId and seedLastWaveSentAt; resuming a ramp after manual waves and forgetting to seed the prior-wave state.

Common situations: Operator sent several waves manually before enabling the auto-ramp, then called initRamp with the offset but didn't pass the seed values; a resume-ramp runbook step was skipped.

Related errors


AI-assisted analysis of koala73/worldmonitor@ffec79ac33 (2026-08-12). Data as JSON: /api/errors/2d7dcaf9c3a2d600. Report an issue: GitHub.