Terminal-Native · macOS Calendar · Keyboard-First

Time blocking,
right in the terminal.

Blocker pulls your macOS calendar into a beautiful terminal UI. Create work blocks, dismiss noise, resize and move tasks — plan your entire day without leaving the keyboard.

blocker — Monday, February 17
     [ Monday, February 17 ]   10:15 AM

  ALL DAY  Presidents' Day

  08:00  · · · · · · · · · · · · · · · · ·
  08:15  · · · · · · · · · · · · · · · · ·
  08:30  · · · · · · · · · · · · · · · · ·
  08:45  · · · · · · · · · · · · · · · · ·
  09:00   Write API proposal                      9:00 – 10:00am
  09:15  
  09:30  
  09:45  
10:00   Team standup                             10:00 – 10:30am
  10:15  
  10:30  · · · · · · · · · · · · · · · · ·
  10:45  · · · · · · · · · · · · · · · · ·
  11:00   ✓ Draft release notes                   11:00 – 11:30am
  11:15  

  j/k navigate · [ ] day · enter block · d dismiss · c complete · m move · q quit
📅

Calendar Integration

Pulls events from macOS Calendar via icalBuddy. See your real schedule — meetings, all-day events, and time blocks — right in the terminal.

Keyboard-First

Vim-style navigation, single-key actions, and modal editing. Create, move, resize, complete, and dismiss blocks without touching the mouse.

💾

Local Persistence

Work blocks and dismissed events are saved to ~/.blocker/ as simple JSON files, one per day. No database, no cloud, no accounts.

Zero Config

Install icalBuddy, build the binary, and run. No config files, no setup wizard. Blocker works out of the box with sensible defaults.

Plan your day with
15-minute precision.

Everything you need to turn a wall of calendar events into a focused plan of attack.

Core

Time Slot Grid

Your day is rendered as 15-minute slots from 8 AM to 6 PM. Calendar events and work blocks fill the grid, while empty slots show dot leaders for clean visual texture. Day bounds automatically expand to fit early or late events.

08:00  · · · · · · · · ·
08:15  · · · · · · · · ·
08:30   Deep work session
08:45  
09:00  
09:15  
09:30   Design review
09:45  
Plan

Work Blocks

Press enter on an empty slot to create a work block. Type a label and confirm. Blocks start at one slot and can be extended with J/K to resize.

Focus

Dismiss & Complete

Press d to dismiss noisy calendar events you don't need to see. Press c to mark work blocks as completed. Both states persist across sessions.

Arrange

Move Blocks

Press m to enter move mode. Use j/k to slide the block up or down. Collision detection prevents overlaps. Press enter to confirm or esc to cancel.

Navigate

Date Switching

Press [ and ] to move between days. State is automatically saved when you leave a day and loaded when you arrive. Press g to jump back to today.

Sync

Auto Refresh

Calendar events refresh every 5 minutes when viewing today. Your work blocks and dismissals are preserved across refreshes. Press r to refresh manually.

Context

Now Indicator

A yellow arrow in the gutter marks the current time slot. On launch, the cursor jumps directly to "now" so you always start where you are in the day.

Events

All-Day Events

All-day calendar events are displayed in a purple banner above the time grid. Holidays, PTO, and multi-day events stay visible without cluttering the timeline.

Safe

Collision Detection

Moving or resizing blocks into occupied slots is blocked automatically. No accidental overlaps, no broken layouts. The grid stays clean.

Two block types.
One unified timeline.

Calendar events and work blocks live side by side. Each has its own color and behavior.

Calendar Events

Fetched from macOS Calendar via icalBuddy. Displayed in cyan. Can be dismissed but not edited or moved — they reflect your real calendar.

10:00   Team standup          10:00 – 10:30am
10:15  
d dismiss / restore

Work Blocks

Created by you to plan focused work. Displayed in green. Fully editable — move, resize, complete, or delete them freely.

09:00   Write API proposal    9:00 – 10:00am
09:15  
09:30  
09:45  
c complete m move J/K resize x delete

Every action is
one keystroke away.

Vim-style bindings with modal editing. Normal, Creating, and Moving modes keep context clear.

Navigation

j / kMove cursor down / up
[ / ]Previous / next day
gJump to now (or today)

Blocks

enter / aCreate block on empty slot
cToggle completion
xDelete work block
mEnter move mode
J / KExtend / shrink block

Calendar

dDismiss / restore event
rRefresh calendar events

Modes

enterConfirm (creating / moving)
escCancel current mode
qQuit blocker

Up and running
in four steps.

1

Install icalBuddy

Blocker reads your calendar through icalBuddy, a macOS CLI tool. Install it with brew install ical-buddy and grant Calendar access in System Settings.

2

Build & Run

Clone the repo and build with make build. The compiled binary has zero runtime dependencies beyond icalBuddy. Run ./blocker to launch.

3

Plan Your Day

Navigate to empty slots and press enter to create work blocks. Dismiss calendar noise with d. Resize blocks with J/K until your day is mapped out.

4

Execute & Complete

As you work through the day, press c to mark blocks complete. Navigate between days with [ / ]. Everything saves automatically.

Simple architecture,
reliable by design.

01

Elm Architecture

Built on Bubbletea's Model-Update-View pattern. Every keypress produces a message, the model updates, and the view re-renders. State is predictable and easy to reason about.

02

Modal Editing

Three clean modes — Normal, Creating, and Moving — keep keybindings context-aware. Each mode has its own update function and help bar. No accidental actions.

03

File-Per-Day Storage

Each day's state is a single JSON file in ~/.blocker/. Work blocks, completion status, and dismissed events are all captured. No database, no migrations.

04

Calendar Bridge

Calendar events are fetched via icalBuddy shell commands, parsed into blocks, and merged with persisted work blocks. Auto-refresh keeps things current without polling aggressively.

Data Flow
📅
macOS
Calendar
icalBuddy
🛠
Parser
🖥
Bubbletea
TUI
💾
~/.blocker/
JSON
Calendar events refresh every 5 minutes. Work blocks persist to disk on every change.

Built with
proven tools.

🛠

Go

Fast compilation, single binary output, excellent concurrency.

Bubbletea

Elm-architecture TUI framework from Charmbracelet. Clean, testable, composable.

🎨

Lipgloss

Declarative terminal styling. Colors, borders, padding — CSS-like API for the terminal.

📅

icalBuddy

macOS CLI for reading Calendar.app events. Lightweight bridge to native calendar data.

📄

JSON Files

One file per day in ~/.blocker/. Human-readable, git-friendly, zero setup.

💻

macOS Native

Leverages macOS Calendar and privacy permissions. Designed for the Mac terminal workflow.

15 min
Slot Duration
3
Editing Modes
5 min
Auto Refresh
0
Config Files Needed

Ready to block
your day?

Blocker is open source and free. Build from source in seconds.

# Install icalBuddy (macOS Calendar bridge)
$ brew install ical-buddy

# Clone and build
$ git clone https://github.com/cochranjd/blocker.git
$ cd blocker && make build

# Run it
$ ./blocker