Skip to content

Add configurable month interval to monthly repeat_every modes#39

Merged
gensyn merged 7 commits intomainfrom
copilot/add-month-interval-options
Apr 22, 2026
Merged

Add configurable month interval to monthly repeat_every modes#39
gensyn merged 7 commits intomainfrom
copilot/add-month-interval-options

Conversation

Copy link
Copy Markdown
Contributor

Copilot AI commented Apr 19, 2026

  • Previous session: panel changes (months interval, hide mark-done, name filter)
  • task-tracker-card.js: add _monthIntervalSuffix helper — appends , every N months for month-based schedule types when interval > 1
  • task-tracker-card.js: hide "Mark as done" button when repeat_mode === "repeat_every" and state is done (no-op)

Copilot AI linked an issue Apr 19, 2026 that may be closed by this pull request
- Add CONF_REPEAT_MONTHS_INTERVAL constant to const.py
- Update coordinator to accept and use repeat_months_interval in all three
  monthly repeat_every modes (day_of_month, weekday_of_month, days_before_end_of_month)
- Convert _calc_most_recent_day_of_month and _calc_most_recent_days_before_end_of_month
  from static methods to instance methods to support anchor-based cycle walking
- Add months_interval parameter to all relevant next/most-recent calculation methods
- Update config_flow.py: add field to schemas and validate months_interval >= 1
- Update options_flow.py: add field to schemas and validate months_interval >= 1
- Bump config version 1.6 -> 1.7 with migration adding repeat_months_interval
- Update strings.json and translations/en.json with new field labels/descriptions
- Update tests: fix static-method calls, add tests for interval calculations,
  migration 1.6->1.7, validation, and end-to-end quarterly/annual scenarios
  (287 tests pass, 81% code coverage)

Agent-Logs-Url: https://github.com/gensyn/task_tracker/sessions/cfb4d6c9-460e-4b1b-b2cb-cd17f30ffc4d

Co-authored-by: gensyn <36128035+gensyn@users.noreply.github.com>
Copilot AI changed the title [WIP] Add month interval options for task scheduling Add configurable month interval to monthly repeat_every modes Apr 19, 2026
Copilot AI requested a review from gensyn April 19, 2026 06:26
…lations; update README

Agent-Logs-Url: https://github.com/gensyn/task_tracker/sessions/58de6290-816c-4639-aae4-b0efe9e8896a

Co-authored-by: gensyn <36128035+gensyn@users.noreply.github.com>
…erval > 1; add regression tests

Agent-Logs-Url: https://github.com/gensyn/task_tracker/sessions/c8420ddd-c73c-4bab-8f3b-6a9819901cd8

Co-authored-by: gensyn <36128035+gensyn@users.noreply.github.com>
@gensyn gensyn marked this pull request as ready for review April 22, 2026 10:43
Copilot AI review requested due to automatic review settings April 22, 2026 10:43
@gensyn gensyn merged commit ba703b1 into main Apr 22, 2026
6 checks passed
@gensyn gensyn deleted the copilot/add-month-interval-options branch April 22, 2026 10:43
Copy link
Copy Markdown

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adds a configurable month interval for month-based repeat_every schedule types (e.g., quarterly/annually) across the backend (options + due-date calculations), migrations, and frontend display, plus small panel/card UX improvements.

Changes:

  • Introduces repeat_months_interval (>= 1) for month-based repeat_every modes, including config/options flow validation, coordinator calculations, and migration to config minor version 1.7.
  • Updates UI (card + panel) to display “every N months” suffix for month-based schedules and hides “Mark as done” when it’s a no-op for repeat_every tasks already in done.
  • Expands translations + documentation and adds unit tests covering interval behavior and validation.

Reviewed changes

Copilot reviewed 17 out of 18 changed files in this pull request and generated 5 comments.

Show a summary per file
File Description
const.py Adds CONF_REPEAT_MONTHS_INTERVAL constant.
coordinator.py Implements month-interval logic for next/most-recent calculations in month-based schedules.
config_flow.py Adds repeat_months_interval to relevant schemas and validates it; bumps MINOR_VERSION to 7.
options_flow.py Adds schemas/validation and persists repeat_months_interval via validate_options.
__init__.py Passes repeat_months_interval into the coordinator; migrates 1.6→1.7 to backfill the new option.
sensor.py Exposes repeat_months_interval as an extra attribute for month-based repeat_every types.
frontend/task-tracker-card.js Appends “every N months” suffix and hides “Mark as done” when it’s a no-op.
frontend/task-tracker-panel.js Adds name filtering, month interval suffix in schedule text, and hides “Mark as done” when it’s a no-op.
translations/en.json Adds labels/descriptions + error key for repeat_months_interval, plus name-filter placeholder.
translations/fr.json Adds labels/descriptions + error key for repeat_months_interval, plus name-filter placeholder.
translations/de.json Adds labels/descriptions + error key for repeat_months_interval, plus name-filter placeholder.
strings.json Adds base English strings for repeat_months_interval and name-filter placeholder.
README.md Documents month-interval semantics for monthly schedule types and related UI behavior.
tests/unit_tests/test_sensor.py Updates existing tests and adds extensive coverage for month interval behavior + regressions.
tests/unit_tests/test_config_flow.py Adds coverage for repeat_months_interval in config flow + validation.
tests/unit_tests/test_options_flow.py Adds coverage for repeat_months_interval persistence/validation in options flow.
tests/unit_tests/test_init.py Adds migration tests for 1.6→1.7 and updates future-minor-version guard.
assets/8_panel.png Updates panel screenshot asset.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +42 to +43
const sp = n === 1 ? "singular" : "plural";
return `,\u00a0${this._t("every")}\u00a0${n}\u00a0${this._t(`month_${sp}`)}`;
Copy link

Copilot AI Apr 22, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

_monthIntervalSuffix returns early for n <= 1, so n === 1 can never reach the sp assignment. This makes the singular branch dead code and potentially confusing. Simplify by removing the unreachable conditional (or adjust the early-return if you intended to handle n === 1 here).

Suggested change
const sp = n === 1 ? "singular" : "plural";
return `,\u00a0${this._t("every")}\u00a0${n}\u00a0${this._t(`month_${sp}`)}`;
return `,\u00a0${this._t("every")}\u00a0${n}\u00a0${this._t("month_plural")}`;

Copilot uses AI. Check for mistakes.
Comment thread translations/fr.json
@@ -6,7 +6,7 @@
"error": {
"unknown": "Erreur inattendue",
"invalid_month_day": "Le jour du mois doit être compris entre 1 et 31",
Copy link

Copilot AI Apr 22, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In the config.error section, the invalid_days_before_end translation key was removed. The config flow still uses invalid_days_before_end for the days-before-end-of-month step, so this will show as an untranslated key in the UI. Add invalid_days_before_end back alongside invalid_months_interval.

Suggested change
"invalid_month_day": "Le jour du mois doit être compris entre 1 et 31",
"invalid_month_day": "Le jour du mois doit être compris entre 1 et 31",
"invalid_days_before_end": "Le nombre de jours avant la fin du mois doit être supérieur ou égal à 0",

Copilot uses AI. Check for mistakes.
Comment thread translations/de.json
@@ -6,7 +6,7 @@
"error": {
"unknown": "Unerwarteter Fehler",
"invalid_month_day": "Der Tag im Monat muss zwischen 1 und 31 liegen",
Copy link

Copilot AI Apr 22, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In the config.error section, the invalid_days_before_end translation key was removed. The config flow still uses invalid_days_before_end for the days-before-end-of-month step, so this will show as an untranslated key in the UI. Add invalid_days_before_end back alongside invalid_months_interval.

Suggested change
"invalid_month_day": "Der Tag im Monat muss zwischen 1 und 31 liegen",
"invalid_month_day": "Der Tag im Monat muss zwischen 1 und 31 liegen",
"invalid_days_before_end": "Die Anzahl der Tage vor Monatsende muss mindestens 0 betragen",

Copilot uses AI. Check for mistakes.
Comment thread README.md
</tr>
</table>

> **Note:** For tasks of mode "repeat every" in state "done", the button "Mark is done" is not shown, as clicking it would not change the state of the task.
Copy link

Copilot AI Apr 22, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The note says the button "Mark is done"; elsewhere in the UI it’s "Mark as done". Update this wording for consistency and grammar.

Suggested change
> **Note:** For tasks of mode "repeat every" in state "done", the button "Mark is done" is not shown, as clicking it would not change the state of the task.
> **Note:** For tasks of mode "repeat every" in state "done", the button "Mark as done" is not shown, as clicking it would not change the state of the task.

Copilot uses AI. Check for mistakes.
Comment on lines +151 to +152
const sp = n === 1 ? "singular" : "plural";
return `,\u00a0${this._t("every")}\u00a0${n}\u00a0${this._t(`month_${sp}`)}`;
Copy link

Copilot AI Apr 22, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

_monthIntervalSuffix returns early for n <= 1, so n === 1 can never reach the sp assignment. This makes the singular branch dead code and potentially confusing. Simplify by removing the unreachable conditional (or adjust the early-return if you intended to handle n === 1 here).

Suggested change
const sp = n === 1 ? "singular" : "plural";
return `,\u00a0${this._t("every")}\u00a0${n}\u00a0${this._t(`month_${sp}`)}`;
return `,\u00a0${this._t("every")}\u00a0${n}\u00a0${this._t("month_plural")}`;

Copilot uses AI. Check for mistakes.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Interval Options

3 participants