jackwener/OpenCLI · error · CommandExecutionError

Nothing changed. Open the profile in the browser and retry.

Error message

Nothing changed. Open the profile in the browser and retry.

What it means

CommandExecutionError (code COMMAND_EXEC) from `twitter unfollow` when the in-page script completed with ok:false and no pending write (unconfirmed=false): the unfollow definitively did not occur. The message is the page script's failure text and the hint 'Nothing changed. Open the profile in the browser and retry.' confirms state is untouched and retrying is safe.

Source

Thrown at clis/twitter/unfollow.js:73

            confirmBtn.click();
            await new Promise(r => setTimeout(r, 1000));

            // Verify
            const verify = document.querySelector('[data-testid$="-follow"]');
            if (verify) {
                return { ok: true, message: 'Successfully unfollowed @${username}.' };
            } else {
                return { ok: false, unconfirmed: true, message: 'Unfollow action initiated but UI did not update.' };
            }
        } catch (e) {
            return { ok: false, unconfirmed: writeStarted, message: e.toString() };
        }
    })()`);
        if (result.unconfirmed) {
            throw new TimeoutError('twitter unfollow confirmation', 1, `${result.message} Check the profile before retrying; the unfollow may already have succeeded.`);
        }
        if (!result.ok) {
            throw new CommandExecutionError(result.message, 'Nothing changed. Open the profile in the browser and retry.');
        }
        await page.wait(2);
        return [{
                status: 'success',
                message: result.message
            }];
    }
});

View on GitHub (pinned to 49907e53dc)

Solutions

  1. Read the underlying result.message in the error output to see which in-page step failed
  2. Open https://x.com/<username> in the browser to confirm the profile loads, you are logged in, and you actually follow the account, then retry
  3. If selectors consistently fail, suspect an X markup change — update or report the library
Defensive patterns

Strategy: try-catch

Validate before calling

// preflight: profile loads and the Following toggle exists
await page.goto(`https://x.com/${username}`);
await page.waitForSelector('[data-testid="primaryColumn"]', { timeout: 10000 });
// if the Following button is absent, you are not following this account

Type guard

function isCommandExecError(e) { return e && e.code === 'COMMAND_EXEC'; }

Try / catch

try {
  await cli.run(['twitter', 'unfollow', user]);
} catch (e) {
  if (e.code === 'COMMAND_EXEC' && /Nothing changed/.test(e.hint || '')) {
    // clean failure — safe to retry after fixing the cause
    console.error(`Unfollow failed cleanly: ${e.message}`);
  } else throw e;
}

Prevention

When it happens

Trigger: The evaluate()'d unfollow script threw before any click (writeStarted=false) — e.g. follow-state button not found on the profile — returning {ok:false, unconfirmed:false}, so CommandExecutionError wraps the script's message.

Common situations: You were not actually following the user so the 'Following' toggle is absent; X profile markup change breaking selectors; page rendered a login wall or error state; protected/suspended profile rendering a different layout.

Related errors


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