actualbudget/actual · error · Error
Invalid cutoff date: expected a valid date (e.g. YYYY-MM-DD)
Error message
Invalid cutoff date: expected a valid date (e.g. YYYY-MM-DD).
What it means
The accounts `transactions` (or similar) command accepts --cutoff as a date. It parses with new Date() and rejects values that produce NaN time — i.e. anything not a parseable date like YYYY-MM-DD. The guard catches malformed dates such as '2024-13-45' or '31/02/2024'.
Source
Thrown at packages/cli/src/commands/accounts.ts:168
opts,
async () => {
await api.deleteAccount(id);
printOutput({ success: true, id }, opts.format);
},
{ mutates: true },
);
});
accounts
.command('balance <id>')
.description('Get account balance')
.option('--cutoff <date>', 'Cutoff date (YYYY-MM-DD)')
.action(async (id: string, cmdOpts) => {
let cutoff: Date | undefined;
if (cmdOpts.cutoff) {
const cutoffDate = new Date(cmdOpts.cutoff);
if (Number.isNaN(cutoffDate.getTime())) {
throw new Error(
'Invalid cutoff date: expected a valid date (e.g. YYYY-MM-DD).',
);
}
cutoff = cutoffDate;
}
const opts = program.opts();
await withConnection(
opts,
async () => {
const balance = await api.getAccountBalance(id, cutoff);
printOutput({ id, balance }, opts.format);
},
{ mutates: false },
);
});
}
View on GitHub (pinned to d4334cb6e6)
Solutions
- Pass an ISO date: --cutoff 2024-06-30.
- Generate the date programmatically: $(date -I) or $(date +%F) in shell.
- Validate the date in the calling script before invoking the CLI.
- If a full ISO timestamp is desired, it also parses — but prefer plain YYYY-MM-DD for consistency.
Example fix
// before actual accounts transactions acct_1 --cutoff 30/06/2024 // after actual accounts transactions acct_1 --cutoff "$(date -d '30 days ago' +%F)"
Defensive patterns
Strategy: validation
Validate before calling
function isValidIsoDate(s: string): boolean {
return /^\d{4}-\d{2}-\d{2}$/.test(s) && !Number.isNaN(new Date(s + 'T00:00:00Z').getTime());
}
if (!isValidIsoDate(cutoffArg)) throw new Error(`Bad --cutoff: ${cutoffArg}`); Type guard
function isIsoDateString(v: unknown): v is string {
return typeof v === 'string' && /^\d{4}-\d{2}-\d{2}$/.test(v) && !Number.isNaN(new Date(v + 'T00:00:00Z').getTime());
} Try / catch
try {
await runCli(['accounts', 'transactions', id, '--cutoff', cutoff]);
} catch (e) {
if (String(e.message).includes('Invalid cutoff date')) {
console.error('Use YYYY-MM-DD, e.g. --cutoff 2024-06-30');
process.exitCode = 2;
} else throw e;
} Prevention
- Always use ISO YYYY-MM-DD format for date flags.
- Generate dates with `date +%F` / `date -I` instead of hand-writing them.
- Reject locale formats (DD/MM/YYYY) in wrapper scripts.
- Beware shell separators: keep --cutoff and its value as separate tokens.
When it happens
Trigger: Running the command with `--cutoff foo`, `--cutoff 2024-13-01`, `--cutoff 01/31/2024` in locales where that string fails to parse, or `--cutoff` followed by another flag so it received the wrong token.
Common situations: Non-ISO date formats from regional habit (DD/MM/YYYY); dates built from shell variables with wrong format; forgetting the space so --cutoff=2024-1-5 partial garbage; timezone edge strings like '2024-02-30' (invalid day).
Related errors
- Invalid --name: must be a non-empty string.
- No update fields provided. Use --name or --offbudget.
- No update fields provided. Use --name or --hidden.
- No update fields provided. Use --name or --hidden.
- No fields to update. Use --name to specify a new name.
AI-assisted analysis of actualbudget/actual@d4334cb6e6 (2026-08-29).
Data as JSON: /api/errors/6a83d757c5bcce4c.
Report an issue: GitHub.