soff-cron

v0.0.7~2KB Core

Lightweight, tree-shakeable cron expression parser and human-readable formatter. Convert between cron expressions and natural language - perfect for non-technical users!

Live Demo - Cron Formatter
Validation:✓ Valid

Human-readable:

at 09:00, weekdays

Natural Language → Cron

"every 5 minutes"

*/5 * * * *
en

"todos los días a las 2 am"

0 2 * * *
es

"weekdays at 9am"

0 9 * * 1-5
en

"cada lunes a las 10am"

0 10 * * 1
es

"every monday"

0 0 * * 1
en

"fines de semana a las 10am"

0 10 * * 0,6
es
Cron → Human Readable
0 9 * * 1-5

at 09:00, weekdays

en
*/15 * * * *

every 15 minutes, every day

en
0 0 * * *

a las 00:00, todos los días

es
0 9-17 * * 1-5

between 09:00 and 17:00, weekdays

en
@daily

todos los días

es
0 0 1 * *

at 00:00, on day 1

en

Installation

npm install soff-cron

Quick Start

import { humanizeCron } from 'soff-cron';

// Convert natural language to cron expressions
humanizeCron('every 5 minutes', { locale: 'en' });
// → { success: true, cronExpression: "*/5 * * * *" }

humanizeCron('todos los días a las 2 am', { locale: 'es' });
// → { success: true, cronExpression: "0 2 * * *" }

humanizeCron('every monday at 10am', { locale: 'en' });
// → { success: true, cronExpression: "0 10 * * 1" }

humanizeCron('días de semana a las 9am', { locale: 'es' });
// → { success: true, cronExpression: "0 9 * * 1-5" }

// Error handling with suggestions
humanizeCron('invalid text', { locale: 'en' });
// → {
//   success: false,
//   error: "Could not parse...",
//   suggestions: ["every 5 minutes", "every day at 9 am"]
// }

Features

🗣️ Natural Language

Convert human-readable text like "every 5 minutes" to cron expressions. Perfect for non-technical users!

🌍 Internationalization

Built-in support for English and Spanish with extensible i18n system.

✅ Full Validation

Validates standard 5-field and 6-field (with seconds) cron expressions.

📅 Named Values

Support for month names (JAN, FEB) and day names (MON, TUE).

🔖 Special Keywords

@yearly, @monthly, @weekly, @daily, @hourly, @midnight shortcuts.

💡 Smart Suggestions

Get helpful suggestions when natural language text cannot be parsed.

Cron Syntax Reference

Standard Format (5 fields)

* * * * *
│ │ │ │ │
│ │ │ │ └─ Day of week (0-7, SUN-SAT)
│ │ │ └─── Month (1-12, JAN-DEC)
│ │ └───── Day of month (1-31)
│ └─────── Hour (0-23)
└───────── Minute (0-59)

With Seconds (6 fields)

* * * * * *
│ │ │ │ │ │
│ │ │ │ │ └─ Day of week (0-7)
│ │ │ │ └─── Month (1-12)
│ │ │ └───── Day of month (1-31)
│ │ └─────── Hour (0-23)
│ └───────── Minute (0-59)
└─────────── Second (0-59)

Special Characters

*Any value (wildcard)
,List separator (e.g., 1,3,5)
-Range (e.g., 1-5)
/Step values (e.g., */15)
?No specific value (day fields only)

API Reference

humanizeCron() ✨ NEW
humanizeCron(text: string, options?: HumanizerOptions): HumanizerResult

interface HumanizerOptions {
  locale?: 'en' | 'es';           // Default: 'en'
}

interface HumanizerResult {
  success: boolean;
  cronExpression?: string;
  error?: string;
  suggestions?: string[];
}

// Supported patterns (English):
// - Time intervals: "every minute", "every 5 minutes", "every 2 hours"
// - Daily: "every day", "every day at 2am", "at 14:30"
// - Weekly: "every week", "every monday", "every monday at 10am"
// - Monthly: "every month", "on the 1st of every month"
// - Weekdays: "weekdays at 9am", "weekends at 10am"

// Patrones soportados (Español):
// - Intervalos: "cada minuto", "cada 5 minutos", "cada 2 horas"
// - Diario: "todos los días", "todos los días a las 2am", "a las 14:30"
// - Semanal: "cada semana", "todos los lunes", "cada lunes a las 10am"
// - Mensual: "cada mes", "el día 1 de cada mes"
// - Días laborales: "días de semana a las 9am", "fines de semana a las 10am"
formatCron()
formatCron(expression: string, options?: FormatterOptions): string

interface FormatterOptions {
  locale?: 'en' | 'es';           // Default: 'en'
  use24HourFormat?: boolean;       // Default: true
  includeSeconds?: boolean;        // Default: false
  verbose?: boolean;               // Default: false
}
validateCron()
validateCron(expression: string, allowSeconds?: boolean): ValidationResult

interface ValidationResult {
  isValid: boolean;
  error?: string;
  field?: 'second' | 'minute' | 'hour' | 'dayOfMonth' | 'month' | 'dayOfWeek';
}
parseCron()
parseCron(expression: string, allowSeconds?: boolean): ParsedCron

interface ParsedCron {
  isSpecial: boolean;
  specialKeyword?: string;
  second?: CronField;
  minute: CronField;
  hour: CronField;
  dayOfMonth: CronField;
  month: CronField;
  dayOfWeek: CronField;
}

interface CronField {
  raw: string;
  values: number[];
  isWildcard: boolean;
  isRange: boolean;
  isStep: boolean;
  isList: boolean;
}

Tree-shaking

Import only what you need for optimal bundle size:

// Import core functions (without i18n)
import { validateCron, parseCron } from 'soff-cron';

// Import specific i18n
import { es } from 'soff-cron/i18n/es';
import { en } from 'soff-cron/i18n/en';

// Import types
import type { ParsedCron, FormatterOptions } from 'soff-cron';