cally #
Note
This tool is a work in progress.
"What times work for you?"
Create simple copy-paste schedules from casual shorthand that you can easily remember. Great if you're repeatedly emailing your availability but can't use any automatic tools (and extra great if you're tired of making typos in dates or timezones).
% cally "mon 9am-12pm; wed-fri 10a-12p; sat all-day; wed 2:13-5:30p; tue 9:30-11pm"
Mon May 11: 9am–12pm ET
Wed May 13: 10am–12pm ET
Thu May 14: 10am–12pm ET
Fri May 15: 10am–12pm ET
Sat May 16: all day
Wed May 20: 2:13–5:30pm ET
Tue May 26: 9:30–11pm ET
This is motivated by my own calendar experience, which (unfortunately) exists across different personal and professional calendars that I can neither automatically synchronize query via API access. So, I end up reading them manually, switching between applications multiple times, and hand-writing my availability -- often making silly typos or timezone errors in the process.
Goals #
- Easy to write input DSL, matching a (particular) mental model
- Easy to sanity-check output
- Easy to copy-paste to email or messages
- Easy for recipients to read with explicit dates and times
Alternate timezones can be calculated for you:
% cally --tzs=ET,PT,CET "mon 9a-12p; tue 8-9; wed 8-16"
Mon May 11: 9am–12pm ET (6–9am PT, 3–6pm CET)
Tue May 12: 8–9am ET (5–6am PT, 2–3pm CET)
Wed May 13: 8am–4pm ET (5am–1pm PT, 2–10pm CET)
Input can be either 12-hour format with some kind of meridiem notation (e.g. "4pm"/"4p") or 24-hour format:
% cally "mon 9a-12p; tue 8-9; wed 8-10, 12-16"
Mon May 11: 9am–12pm ET
Tue May 12: 8–9am ET
Wed May 13: 8am–4pm ET
Dates auto-advance to the "next possible" day:
% cally "mon 9a-12p; mon 4-5p"
Mon May 11: 9am–12pm ET
Mon May 18: 4–5pm ET
Install #
You'll need a Rust toolchain. Install via rustup if you don't have one.
git clone https://tangled.org/paeth.xyz/cally cally
cd cally
cargo install --path .
That builds in release mode and installs the dollysay binary into ~/.cargo/bin/, which rustup already puts on your $PATH.
What cally does NOT do (yet?) #
- validate that time slots are separate
- combine time slots
- output to 24-hour format
- Accept all timezone shorthands (e.g. "ET")
DSL Grammar #
In BNF:
input := day_expr ((';' | '\n') day_expr)*
day_expr := day_spec slot (',' slot)*
day_spec := dow ('-' dow)?
slot := 'all-day' | time '-' time
time := H[:MM] (am|pm|a|p)?
dow := mon|tue|wed|thu|fri|sat|sun
Acknowledgements #
Made entirely possible thanks to the Chumsky parser library and Chrono for handling dates and timezones.
TODO #
- better ariadne parsing errors
- handle all timezone shorthands (e.g. "CET") /IANA (e.g. "Europe_Paris") codes as input
- option to output 12 or 24 hr formats
- option to specify "start" date
- auto-join consecutive time slots? e.g. "mon 1-2p, 2-4p" becomes "Monday 1-4pm"
- accept other common strings, e.g. "m", "tues", "th"