jackwener/OpenCLI · error · CommandExecutionError

expected array of DM channels, got ${typeof rows} (contract

Error message

expected array of DM channels, got ${typeof rows} (contract drift?)

What it means

The dm-list command expects the in-page evaluate snippet to return an array of DM channel objects via the dispatchEvaluateResult envelope. This CommandExecutionError signals 'contract drift': the browser-side snippet returned something other than an array, meaning the injected code or the upstream API response shape changed.

Source

Thrown at clis/slock/dm-list.js:32

  strategy: Strategy.COOKIE,
  browser: true,
  siteSession: 'persistent',
  args: [
    { name: 'server', help: 'Override active server (slug or id)' },
  ],
  columns: ['channelId', 'peerName', 'peerId', 'createdAt'],
  func: async (page, kwargs) => {
    await page.goto(SLOCK_HOME_URL);
    const snippet = buildFetchSnippet({
      method: 'GET',
      path: '/channels/dm',
      serverScoped: true,
      serverIdOverride: kwargs.server,
    });
    const result = await page.evaluate(`(async () => { ${snippet} })()`);
    const rows = dispatchEvaluateResult(result);
    if (!Array.isArray(rows)) {
      throw new CommandExecutionError(`expected array of DM channels, got ${typeof rows} (contract drift?)`);
    }
    return rows.map((c) => ({
      channelId: c.id ?? '',
      peerName: c.peerDisplayName ?? c.peerName ?? c.name ?? '',
      peerId: c.peerId ?? '',
      createdAt: c.createdAt ?? '',
    }));
  },
});

View on GitHub (pinned to 49907e53dc)

Solutions

  1. Update the slock CLI to the latest version so snippet and dispatcher agree on the envelope contract
  2. Log the raw evaluate result (dispatchEvaluateResult input) to inspect the actual shape returned
  3. If the API response shape changed, adjust the snippet to map/normalize the response to an array before returning

Example fix

// before
const rows = dispatchEvaluateResult(result);
// after
const raw = dispatchEvaluateResult(result);
const rows = Array.isArray(raw) ? raw : Array.isArray(raw?.data) ? raw.data : (() => { throw new CommandExecutionError('unexpected rows shape'); })();
Defensive patterns

Strategy: type-guard

Validate before calling

const rows = result && result.kind === 'ok' ? result.rows : null;
if (!Array.isArray(rows)) throw new Error('dm-list: rows is not an array — check CLI/snippet version');

Type guard

const isRowsArray = (r) => r != null && typeof r === 'object' && r.kind === 'ok' && Array.isArray(r.rows);

Try / catch

try { const rows = dispatchEvaluateResult(result); } catch (e) { if (/contract drift/.test(e.message)) { console.error('CLI/snippet version mismatch — upgrade the slock CLI'); } throw e; }

Prevention

When it happens

Trigger: The page.evaluate snippet returns an envelope whose rows field is not an array (e.g. API returned an object with an error payload that was misclassified as ok), or the snippet was refactored to return {data: [...]} instead of a bare array.

Common situations: Upstream Slack-like API changed its DM list response shape; a partial page load or CSP issue caused the snippet to return undefined; version mismatch between the CLI script and the injected snippet.

Understand the failure class

Background: Schema validation failed / invalid input schema: payload rejected because its shape doesn't match the expected schema — this error's family across 28 libraries.

Related errors


AI-assisted analysis of jackwener/OpenCLI@49907e53dc (2026-08-29). Data as JSON: /api/errors/20f314bbfdedfd26. Report an issue: GitHub.