Argument
Meditation timer app for daily sit: the one timing structure that lives outside an app
Every other guide on this topic walks you through five timer apps. This one walks through a timing primitive that does not run inside any app at all: a recurring Google Calendar event with a shared Meet link, set to the longer of two practitioners' chosen durations, generated by 533 lines of TypeScript in a public repo.
The thesis
A meditation timer app is one timing primitive for a daily sit. It is the most common one. You install something, you set a duration, you tap start, you tap stop, and a sound or a notification marks the boundaries. There is nothing wrong with this shape. It works. The lists of recommended timer apps that currently appear when you search this topic, Insight Timer, Medito, Oak, Plum Village, Tide, Zen Moment, Meditation Assistant on F-Droid, all do this shape well, and several of them are free.
There is a second timing primitive that almost never shows up in those lists. It is older than any of the apps. It runs outside phone software. It is what the matching engine on this site does, specifically and only: a recurring Google Calendar event with another practitioner attached, that fires at the same UTC minute every day, with a Meet link that lives at one URL forever.
This page is about that second primitive. What it is, how it works, where the code lives, why someone might prefer it to an app, and where it falls short. It is not a recommendation. The tradition reserves recommendations about how to practice for authorized assistant teachers and a 10-day course at dhamma.org. What follows is descriptive only.
Two shapes for the same problem
Toggle between the two shapes. The job each one is trying to do is identical: keep a person sitting at roughly the same time of day, for roughly the same duration, most days of the week. The means they use to get there are different.
A native binary on the phone. A configurable countdown. A bell sound at the start, optional interval bells, a closing chime. Daily reminder notification. A streak counter that resets if you miss a day. Push notifications. Often a paid tier for guided content.
- Reminder is a phone notification you can dismiss
- Duration is set by the practitioner alone
- Cadence is a calendar pattern stored in the app
- Skipping a day is a private fact between you and the app
Where the daily cadence is actually written
In a timer app, the cadence lives in the app's local storage: 'remind every day at 7:00 AM, weekdays only, no weekends.' If you uninstall the app, the cadence is gone. If the phone reboots and the app's background permission was revoked, the cadence is gone. The cadence is a property of the app's process.
In the appointment shape, the cadence lives in the calendar event. One specific line of code writes it. The file is src/lib/google-meet.ts in the public repo. The function is createMeetEvent. The line is line 75. Once the event is created, the cadence is stored on Google's calendar servers, replicated to every device both participants are signed into, and survives an app reinstall, a phone reboot, an OS upgrade, and most other things. The cadence is a property of the calendar event, not the local app.
The shape that comes out the other end is a Calendar event titled something like Vipassana Practice Buddy with Matt and Jane, recurring daily at the matched UTC minute, with a Meet link auto-generated by Calendar's conferenceData.createRequest field and a conferenceDataVersion=1 query parameter on the API call. Both attendees see the same event, both reminders are whatever Google Calendar normally fires for accepted events, and the Meet URL never rotates.
Why the duration is set to Math.max of the two choices
Two people on the waitlist almost never pick the same duration. One picks twenty minutes because that is what their schedule currently allows. The other picks an hour because that is the tradition's recommendation and they want to honor it. The matching code reads both values and chooses the longer one for the calendar event length.
This is a small editorial decision and it is visible in the source. The function is parseDurationMinutes, defined at the bottom of the route file. It returns Math.max(parse(a), parse(b)). The other reasonable choice would have been Math.min, which would optimize for both people staying for the entire sit. Picking the longer duration optimizes for the more committed end of the pair: the longer-sit person gets the room for as long as they need it, and the shorter-sit person can leave when their own duration is up.
A timer app does not face this question, because a timer app has one user and one duration. The appointment shape introduces the two-body problem and the system has to answer it. The answer this codebase chose is the longer of two. A different fork could reasonably pick differently.
What the timing structure cannot do
An honest argument has to mark the limits of the thing it argues for. The appointment-shape timing primitive does not replace a timer app for several practitioners.
Limits worth naming
- It needs another human. A solo practitioner with no waitlist match available has no appointment, and a timer app is the right tool.
- It needs Google Calendar and Google Meet. Practitioners on iCloud-only or self-hosted calendar setups will find the integration worse.
- It cannot enforce duration mid-sit. There is no bell sound at the matched duration boundary. If you want a bell, you bring your own.
- It does not record sit history, sensation notes, or progress charts. None of those exist on the site.
- It cannot teach the technique. For technique, an authorized assistant teacher and a 10-day course at dhamma.org are the only path the tradition supports.
- It defaults to daily. There is no every-other-day or weekdays-only mode. RRULE:FREQ=DAILY is hard-coded.
Timer app vs. recurring appointment
The two timing primitives, side by side. Neither is universally better. The right one depends on the practitioner.
| Feature | Meditation timer app | Recurring appointment (vipassana.cool) |
|---|---|---|
| What runs at the appointed time | A countdown clock and a bell sound, played by an app on the practitioner's phone or laptop | A Google Calendar event with a Meet link. The link goes live and another person joins it at the same minute |
| How the duration is chosen | A slider in the app's settings, set by the practitioner, often defaulting to twenty minutes | parseDurationMinutes in src/app/api/auto-match/route.ts, returns Math.max of the two participants' chosen durations from the waitlist form |
| How daily cadence is enforced | A scheduled local notification, which the user can dismiss without consequence | RRULE:FREQ=DAILY on the calendar event itself, plus the soft pressure of a recurring appointment another person has on their calendar |
| What you install | A native iOS or Android binary from the App Store or Play Store, often 30 to 80 megabytes | Nothing. Google Calendar and Google Meet are tools the practitioner already has, and the email arrives once |
| What happens if you skip a day | The streak resets. Some apps gamify this with a fire emoji or a recovery feature | The other person sees you did not show up. There is no streak; there is a human noticing. Different kind of feedback |
| Who decides the cadence is daily | The practitioner. The default in most apps is daily, but it is configurable | The matching code, which hard-codes RRULE:FREQ=DAILY in src/lib/google-meet.ts at line 75. Daily is the only cadence the system produces |
| What it teaches about practice | Sometimes a guided session library, sometimes course content, sometimes nothing besides the timer | Nothing. By design. For the technique, dhamma.org and an authorized assistant teacher |
The counterargument, taken seriously
The strongest case against the appointment shape is autonomy. A timer app is fully under the practitioner's control. They choose duration, time, sound, frequency. They can change anything in two taps. The appointment shape removes some of that control: the time is matched to a partner's availability within sixty UTC minutes, the duration is forced to the longer of two, the cadence is daily, and changing any of it either re-runs the matcher or quietly stops being honored.
For a practitioner whose goal is exact ritual control, a timer app is straightforwardly the better fit. For a practitioner whose goal is to keep showing up, and who has noticed that the variable that breaks first is the showing up (not the ritual quality), a recurring appointment with another person is a different category of structure. The site is built for that second type of practitioner. It will disappoint the first type, and that is fair.
A second counterargument is privacy. A timer app touches no third party with the fact of your sit. The appointment shape, by definition, has another human in it. Some practitioners specifically do not want that. Sitting alone is a complete practice; the tradition has always supported it. The site does not exist to dispute that.
Where this leaves the question
There is no single answer to 'what timer should I use for my daily sit.' There are at least two answers, and most articles on this topic only describe one of them. A timer app on a phone is a real timing primitive that works for many practitioners. A recurring calendar event with another practitioner is also a real timing primitive, and it works for others.
If a phone timer is what you want, the existing roundups have you covered. Insight Timer is the largest free library, Medito is the cleanest nonprofit option, Oak and Tide are the most widely recommended commercial picks, and Meditation Assistant on F-Droid is the most unopinionated. Use whichever fits.
If a recurring calendar event with another old student is what you want, that is what this site does, and the code is small enough that you can read it end to end in an afternoon. The waitlist is at vipassana.cool/practice-buddy if you have done a 10-day course already, and dhamma.org is the right next step if you have not.
Want to talk through the matching logic?
Fifteen minutes to walk through the source, the matching rules, and whether a paired recurring appointment is a fit for your daily practice.
Frequently asked questions
Does this site publish a meditation timer app?
No. There is no downloadable app, no countdown screen, no bell sound, no streak counter on this site. The product is a single email plus a recurring Google Calendar event with a Meet link, shared between two old students whose preferred sit times in UTC fall within sixty minutes of each other. The 'timing' is the calendar event itself, not a piece of software running on either person's phone. If you want a timer app, the existing roundups (Insight Timer, Medito, Oak, Plum Village, Tide, and similar) cover that category well.
What is the actual timing primitive on vipassana.cool?
A recurring Google Calendar event. The relevant code lives at src/lib/google-meet.ts in the public repo. Line 75 sets recurrence to RRULE:FREQ=DAILY and the start time is built from the matched UTC minute. The Calendar API auto-generates a Meet link via createRequest, which becomes the permanent room for that pair. There is no separate timer process. The reminder is whatever Google Calendar normally fires for an event you accepted: a desktop notification, a phone notification, an email at minus ten minutes. The cadence is daily by RRULE.
How long is the sit set to?
The duration is decided by code, not by an app slider. In src/app/api/auto-match/route.ts, the function parseDurationMinutes (lines 520 to 532) reads each person's session_duration string from the waitlist row, parses '15', '20', '30', '45', '2 hours', or defaults to 60, and then returns Math.max of the two values. If person A picks 30 and person B picks 60, the calendar event is set to 60. The longer-of-two rule is a small editorial decision: it errs on the side of the more committed sit. Either person can leave the call when their own duration is up; the appointment length is the upper bound, not a prescription.
Why use a calendar event instead of a timer app?
Because the structure that holds a daily sit together for most people is a social commitment, not a notification. A timer app fires a sound and goes silent if you ignore it. A calendar event with another human attached has a different gravity: someone is on the other end of the Meet link at that time, and that fact is what most people report makes the sit happen. The choice is descriptive, not prescriptive. Timer apps are useful for many practitioners. This site is for the subset who already tried that structure and noticed it stopped working alone.
Does the site teach the technique?
No, deliberately not. The Goenka tradition reserves technique transmission for an authorized assistant teacher inside a 10-day residential course, and this site holds that line. There is no guided audio, no instruction text, no per-day prescription. For any operational question about how to practice, what to do with a difficulty on the cushion, or whether your home practice is going correctly, please contact an authorized assistant teacher at a 10-day course or visit dhamma.org.
What if I prefer a timer app instead of a recurring calendar event?
Use one. This page is not arguing every practitioner should switch to a paired calendar event. Many old students sit alone for years and find a simple timer is plenty. The page exists because the topic 'meditation timer app for daily sit' produces ten near-identical articles online, all listing the same four or five apps, and none describe the alternative timing structure. This page describes that alternative. The two structures coexist.
Is the calendar event recurring forever, or just for a few days?
Forever, in the sense that RRULE:FREQ=DAILY in Google Calendar with no end date is unbounded. The Meet link in the event is also persistent; both people can hop into the same URL day after day without re-creating anything. If a pair stops sitting, the event still appears on their calendars until one of them deletes it. The system does not auto-cancel. This is intentional: the event is meant to behave like a standing meeting between two friends, not a contract.
Where can I see the code that creates the calendar event?
github.com/m13v/vipassana-cool. Two files, both small. src/lib/google-meet.ts, 114 lines, contains createMeetEvent, which posts to https://www.googleapis.com/calendar/v3/calendars/primary/events with conferenceDataVersion=1 so that Calendar auto-generates the Meet URL. src/app/api/auto-match/route.ts, 533 lines, calls createMeetEvent once per matched pair after running the eligibility and pairing logic. There is no other timing surface; everything else is database rows and email composition.
What about timezone changes, daylight saving time, or travel?
The matching code stores each person's preferred sit time in their local timezone string (e.g. America/Los_Angeles), and converts to UTC on every cron tick rather than caching. This is the function toUtcTime in src/lib/db.ts; it is called once per session slot at lines 113 and 121 of the route file. The recurring calendar event itself is scheduled with timeZone: 'UTC', so each side's calendar renders the daily appointment in their own local time and rolls with DST automatically. Travel is the user's call; pausing the calendar event when they are away is a one-click action in Google Calendar.
Is this only for old students who finished a 10-day course?
The matching system is tuned for old students because the technique is taught in residential format and people who have done a course tend to want a daily sit afterwards. The waitlist asks 'is_old_student' as a soft preference, and the matcher prefers pairing old-student to old-student where possible (see the bothOld scoring axis in route.ts). If you have not done a course yet, the right next step is dhamma.org, not a timer app and not this site.
For any operational question about how to practice, please contact an authorized assistant teacher at a 10-day course or visit dhamma.org. This site does not teach the technique and does not give practice instruction.
Comments (••)
Leave a comment to see what others are saying.Public and anonymous. No signup.