A privacy-first Home Assistant custom integration for recording menstrual bleeding days, estimating cycle phases, and exposing the results as sensors.
This project is for personal tracking and pattern recognition. It is not a medical device, diagnostic tool, contraceptive method, or fertility-planning method. Read
DISCLAIMER.mdbefore use.
- One configurable profile and one
Menstrual Cycledevice per person. - A master sensor on that device retains the complete cycle model as attributes.
- A focused set of useful values is exposed as entities for automations and visualisations.
- Persistent local history in Home Assistant's
.storagedirectory. - Current phase sensor state:
period,follicular,ovulation,luteal, orneutralwhen there is not enough history to determine a cycle. - Predicted next start, average cycle length, fertile-window dates, and days until the prediction.
- Services for adding, removing, importing, exporting, and clearing history.
- Inclusive cycle start/end date selection from the companion gauge card.
- A separate companion card repository:
menstrual-cycle-companion-cards.
- Open HACS → Integrations.
- Search for Menstrual Cycle Companion.
- Install it and restart Home Assistant.
- Open Settings → Devices & services → Add integration.
- Search for Menstrual Cycle Companion and create one profile per person.
- Install the optional cards from the cards repository, then add its JavaScript resources as described there.
For an unpublished repository, add each GitHub repository through HACS → Custom repositories using category Integration for this repository and Dashboard for the cards repository.
Copy custom_components/menstrual_cycle_companion into /config/custom_components/, restart Home Assistant, and add the integration through the UI. Do not configure it through YAML.
Create a profile with a stable profile name such as anna and a friendly name such as Anna. Home Assistant creates one device using that friendly name. The device contains a master sensor plus focused entities for Current Phase, prediction values, fertile-window dates, and start/end dates for menstruation, follicular, ovulation, and luteal phases; final entity IDs are controlled by Home Assistant's entity registry. The master sensor is the recommended entity for service calls and retains the complete attribute payload for existing cards.
Add confirmed bleeding days from a card or with a service:
action: menstrual_cycle_companion.add_cycle_start
data:
entity_id: sensor.anna
date: "2026-08-01"Import history in one operation:
action: menstrual_cycle_companion.set_cycle_history
data:
entity_id: sensor.anna
dates:
- "2026-05-03"
- "2026-05-04"
- "2026-06-01"
- "2026-06-02"
- "2026-07-01"Set a complete cycle range in one operation (both dates are included):
action: menstrual_cycle_companion.set_cycle_range
data:
entity_id: sensor.anna
start_date: "2026-08-01"
end_date: "2026-08-05"The Current Phase sensor state is one of period, follicular, ovulation, luteal, or neutral. The master sensor state remains the same for backwards compatibility. Every attribute below remains available on the master sensor:
historygrouped_startsbleeding_blocksnext_predicted_startpredicted_cycle_starts— a long-range set of predicted cycle startsavg_cycle_lengthcycle_length_samplescycle_length_variability_daysprediction_confidenceandprediction_methodfertile_window_startandfertile_window_enddays_until_next_startperiod_duration_daysperiod_duration_default_daysperiod_duration_learned_avg_daysmenstruation_startandmenstruation_endfollicular_phase_startandfollicular_phase_endovulation_dateovulation_startandovulation_end(the same date because ovulation is modelled as a one-day phase)luteal_phase_startandluteal_phase_endcurrent_phase
Date attributes are date sensors. The focused child entities expose the values most useful for automations and visualisations. Collection attributes remain on the master sensor and retain their complete values; Home Assistant entity states cannot be lists or dictionaries.
When upgrading from an earlier release, the integration removes child sensor entities that are no longer part of this focused set from Home Assistant's entity registry. Their historical state data is not deleted.
Predictions are personalized from the person's confirmed start history. The
model uses up to the eight most recent valid cycle intervals, gives newer
cycles more weight, and filters isolated recording outliers. Period duration is
learned from recent bleeding blocks once at least two blocks are available.
The predicted_cycle_starts attribute projects the current predicted cycle
length forward for a long-range forecast and is recalculated when history changes.
With no interval history, the model uses a clearly marked 28-day fallback;
this is replaced automatically as more entries are recorded. The prediction
metadata attributes expose the sample count, typical variation, method, and
confidence. All phase dates remain estimates, not medical guidance.
All services accept entity_id, profile, or entry_id when more than one profile exists. Using entity_id is recommended.
menstrual_cycle_companion.add_cycle_startmenstrual_cycle_companion.remove_cycle_startmenstrual_cycle_companion.set_cycle_rangemenstrual_cycle_companion.set_cycle_historymenstrual_cycle_companion.set_period_durationmenstrual_cycle_companion.refresh_cycle_modelmenstrual_cycle_companion.export_historymenstrual_cycle_companion.erase_all_history
Deletion requires both an explicit sensor entity_id and erase_all: true:
action: menstrual_cycle_companion.erase_all_history
data:
entity_id: sensor.anna
erase_all: trueExport a local backup:
action: menstrual_cycle_companion.export_history
data:
entity_id: sensor.anna
format: csv
filename: anna_cycle_backupExports are written to <config>/menstrual_cycle_companion_exports/.
The integration recalculates the cycle model when history or period-duration data changes, on startup, and automatically every two hours. The gauge card also provides a Refresh button for an on-demand recalculation. No separate Home Assistant automation is required.
Cards are intentionally distributed separately so the integration remains a standard HACS integration and the frontend package can be updated independently. Install menstrual-cycle-companion-cards for:
custom:menstrual-cycle-gauge-cardcustom:menstrual-cycle-heatmap-card
The cards require this integration and a configured sensor.
The gauge's outer ring uses these calculated boundaries to show the proposed menstruation, follicular, ovulation, and luteal phases. They are estimates based on the predicted next start and should not be treated as medical guidance.
The gauge card's calendar editor uses range selection by default: click the
first bleeding day, then click the last bleeding day. The selected interval is
shown immediately, and the completed range is written as confirmed bleeding
days. Set calendar_selection_mode: toggle in the card configuration to retain
single-day add/remove behavior.
Cycle history is sensitive health information. Keep Home Assistant access restricted, protect backups, and only create or share profiles with informed consent. See DISCLAIMER.md for the full health, privacy, and liability notice.
The repository includes HACS and Hassfest workflows. Python tests and Home Assistant test fixtures should be added before publishing a stable release. Validate JSON and YAML files and run JavaScript syntax checks in CI.
To publish a HACS-detectable release, update version.json (major, minor, or
patch) and push the change to main. The publishing workflow synchronizes the
integration manifest, creates a matching v<major>.<minor>.<patch> GitHub release,
and HACS can then detect that version.
Before publishing to HACS, set a non-empty description and valid topics in the GitHub repository's About settings (at minimum home-assistant and hacs). The CI workflow currently skips only those two API-managed checks because repository settings cannot be stored in this repository.
MIT. See LICENSE.