Sleep cycle bedtime calculator
For a 07:00 alarm and five full cycles, lights out at 23:15, leaving 15 minutes to drift off; shorter options follow at 00:45, 02:15, 03:45 and 05:15. Type the wake-up time in 24-hour format. Free in your browser.
- Free
- Runs in your browser
- No sign-up
- Your data stays on your device
Run — free
Worked example
- Wake time
- 07:00
- Cycles
- 5
- Fall asleep minutes
- 15
- Cycle minutes
- 90
Waking up mid-cycle often feels worse than a shorter night that ends at a cycle boundary. This sleep cycle bedtime calculator takes the wake-up clock you actually need, subtracts the minutes you typically need to fall asleep, then walks backward in fixed ninety-minute blocks so every suggestion lands you at the end of a complete cycle rather than halfway through deep or REM sleep. You get a short list of clock times, each tagged with how many cycles and how many minutes of sleep that choice buys you, so you can pick a realistic bedtime for school, shift work, or an early flight without guessing.
How ninety-minute cycles turn a wake time into bedtimes
Adult sleep is often described as a sequence of roughly ninety-minute cycles that move through light sleep, deep sleep, and REM. Ending sleep near the end of a cycle tends to feel less jarring than an alarm that cuts into the middle of a stage, which is why many bedtime charts list several options spaced ninety minutes apart rather than a single fixed duration. Internally that clock is converted to minutes since midnight.
Times that cross midnight wrap with modular arithmetic on a one-thousand-four-hundred-forty-minute day, so a six-cycle plan for a 06:00 alarm can correctly suggest a bedtime the previous evening such as 20:45 when latency is fifteen minutes. The list is ordered from the longest sleep first to the shortest last, which matches how people usually scan options: aim for more rest when the calendar allows, then step down when the evening runs late.
FAQ
Why count back in 90-minute steps?
Adult sleep is often described as a sequence of roughly 90-minute cycles through light sleep, deep sleep and REM. Waking near the end of a cycle tends to feel less jarring than an alarm that cuts into the middle of a stage.
Is the time it takes to fall asleep counted as sleep?
No. Those minutes are time spent still awake after lights out, so every bedtime moves earlier by that amount. The sleep shown for each option covers whole cycles only, such as 450 minutes for five cycles.
Can I type my alarm as 7:00 AM?
No. Use the 24-hour format with hours and minutes, such as 07:00 or 06:30. Times written with AM or PM and bare numbers are not accepted, so convert a 12-hour time first.
What if the suggested bedtime falls on the previous evening?
That is expected for long nights: times wrap past midnight. With a 06:00 alarm, six cycles and 15 minutes to fall asleep, the first suggestion is 20:45 the evening before.
Related tools
For developers — API access
Everything on this page is available programmatically. This section is for teams who want to wire it into their own systems; everyone else can just use the tool above.
API endpoint
Prefer to automate it? One authenticated POST creates the task; the result comes back by webhook or a signed link. The same capability also runs here on the web, by email and from Telegram — and soon from our app too.
Call it from your stack
curl -X POST https://api.kit.forhosting.com/health/sleep-cycles-bedtime \
-H "Authorization: Bearer $KIT_KEY" \
-H "Content-Type: application/json" \
-d '{"wake_time":"07:00"}'const res = await fetch("https://api.kit.forhosting.com/health/sleep-cycles-bedtime", {
method: "POST",
headers: {
"Authorization": `Bearer ${process.env.KIT_KEY}`,
"Content-Type": "application/json"
},
body: JSON.stringify({
"wake_time": "07:00"
})
});
const { task_id } = await res.json();import os, requests
res = requests.post(
"https://api.kit.forhosting.com/health/sleep-cycles-bedtime",
headers={"Authorization": f"Bearer {os.environ['KIT_KEY']}"},
json={
"wake_time": "07:00"
},
)
task_id = res.json()["task_id"]<?php
$res = file_get_contents("https://api.kit.forhosting.com/health/sleep-cycles-bedtime", false, stream_context_create([
"http" => [
"method" => "POST",
"header" => "Authorization: Bearer " . getenv("KIT_KEY") . "\r\nContent-Type: application/json",
"content" => '{"wake_time":"07:00"}',
],
]));
$task = json_decode($res, true);body := bytes.NewBufferString(`{"wake_time":"07:00"}`)
req, _ := http.NewRequest("POST", "https://api.kit.forhosting.com/health/sleep-cycles-bedtime", body)
req.Header.Set("Authorization", "Bearer "+os.Getenv("KIT_KEY"))
req.Header.Set("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)Example request
{
"wake_time": "07:00"
}Example response
{
"task_id": "tsk_a1b2c3d4e5f6a1b2c3d4e5f6",
"type": "health.sleep_cycles_bedtime",
"status": "queued",
"_links": {
"result": "/tasks/tsk_…/result"
}
}The API is asynchronous: the call returns a task_id immediately and the result arrives by webhook. Polling is capped at 1 req/s per task.
Pricing
Published price — no tokens, no invented credits. A failed task is never charged.
Errors
| HTTP | Code | Meaning |
|---|---|---|
401 | unauthorized | Missing or invalid API key. |
402 | insufficient_balance | Your balance doesn't cover the task price. |
404 | unknown_type | That task type doesn't exist. |
429 | rate_limited | Too many requests. Use the webhook instead of polling. |
Technical notes
Invalid wake times and out-of-range cycle counts fail clearly with invalid_input instead of inventing a schedule.
How ninety-minute cycles turn a wake time into bedtimes
This calculator models that idea with a fixed cycle length of ninety minutes, returned in the response as cycle_minutes so clients never have to hard-code the constant. You supply wake_time as a twenty-four-hour HH:MM string such as 07:00 or 06:30. For each cycle count n from the requested maximum down to one, the bedtime is wake_time minus fall_asleep_minutes minus n times ninety. Each entry includes cycles, sleep_minutes (exactly n times ninety, not counting latency), and the zero-padded bedtime string. Latency is not added into sleep_minutes because it models time spent still awake after lights out; the bedtime is earlier so that true sleep can still fill whole cycles before the alarm.
Inputs, defaults, validation, and the response shape
The optional cycles parameter is an integer from one to twelve and defaults to six, covering about nine hours of pure sleep plus your fall-asleep buffer—enough range for most adult schedules without suggesting extreme twelve-hour nights unless you ask. The only required field is wake_time. It must be a string matching a strict twenty-four-hour pattern from 00:00 through 23:59; twelve-hour strings with AM or PM, bare numbers, and non-string values are rejected with invalid_input that names the field. The optional fall_asleep_minutes parameter is an integer from zero to one hundred twenty and defaults to fifteen, a common rule-of-thumb latency used in popular sleep-cycle charts. Values outside those ranges, non-integers, or a missing wake_time fail before any arithmetic runs, and those failures are not billed. On success the body echoes the normalized wake_time, the cycles and fall_asleep_minutes that were applied, cycle_minutes fixed at ninety, and the bedtimes array described above. Example: wake_time 07:00, cycles 5, fall_asleep_minutes 15 yields bedtimes 23:15 for five cycles (four hundred fifty minutes of sleep), then 00:45, 02:15, 03:45, and 05:15 for four through one cycles respectively. Pair the response with your own calendar UI if you want local timezone labels; this endpoint only reasons about wall-clock HH:MM values you provide.
Where a sleep cycle bedtime API earns its keep
School and shift-planning tools can precompute suggestions for fixed start times so users pick a sustainable lights-out clock rather than scrolling endlessly. Content sites that rank for sleep cycle bedtime calculator benefit from a free browser path that matches the paid automation path byte-for-byte on the same pure module, so demos and production jobs never disagree. Treat the ninety-minute cycle length as a practical planning heuristic, not a medical diagnosis; individual cycle lengths vary, and people with sleep disorders should follow clinical advice. Wellness apps and coaching bots need a tiny, offline-safe primitive that turns an alarm time into a short menu of bedtimes without shipping a sleep-science model or calling a cloud inference endpoint. API automation at $0.002 per successful call lets batch planners generate tables for many wake times—for example every fifteen minutes across a morning window—while invalid input never consumes balance.
Integration use cases
Plan tonight around a fixed alarm
Enter tomorrow’s wake_time to see which bedtimes complete whole 90-minute cycles, then pick the latest option that still fits your evening.
Shift work and early flights
Recompute bedtimes whenever the call-out or departure time changes, adjusting fall_asleep_minutes if you know you take longer to drop off.
Wellness apps and chatbots
Call the API from a bot or mobile backend to offer cycle-aligned bedtime menus without storing health data or running an ML model.
Technical questions
How does the sleep cycle bedtime calculator work?
It subtracts fall_asleep_minutes and n×90 minutes from your wake_time for each cycle count from cycles down to 1, wrapping midnight, and returns those bedtimes with sleep_minutes per option.
What time format should I use for wake_time?
A 24-hour HH:MM string from 00:00 to 23:59 (for example 07:00 or 06:30). Invalid formats raise invalid_input and are not billed.
How long is one sleep cycle here?
A fixed 90 minutes, reported as cycle_minutes. sleep_minutes on each suggestion is exactly the cycle count times 90.
What do cycles and fall_asleep_minutes default to?
cycles defaults to 6 (range 1–12). fall_asleep_minutes defaults to 15 (range 0–120). Both must be integers when provided.
What does the API cost?
The browser tool is free. Successful API calls use prepaid KIT balance at $0.002 per call; invalid input is not billed.