Skip to content

feat(calendar): monthly repeat sub-type options — calendar-repeat.service + tests#7930

Closed
renemadsen wants to merge 4 commits into
stablefrom
feat/monthly-repeat-options
Closed

feat(calendar): monthly repeat sub-type options — calendar-repeat.service + tests#7930
renemadsen wants to merge 4 commits into
stablefrom
feat/monthly-repeat-options

Conversation

@renemadsen

Copy link
Copy Markdown
Member

Summary

  • Extends CalendarRepeatMeta with two new kinds: monthlyFirstWeekday and everyNMonthFirstWeekday
  • buildMetaFromCustomConfig: adds monthlyKind, dom, and monthlyWeekday parameters; fixes pre-existing bug where dom was always hardcoded to 1
  • decomposeCustomMeta: inverse operation — extracts monthlyKind, dom, monthlyWeekday for edit round-trip
  • reanchorMetaToDate: new cases update weekday when date changes for the two new kinds
  • reconstructMetaFromTask: distinguishes monthlyFirstWeekday (ordinalWeek=1) from monthlyByDay (ordinalWeek>1) on task load
  • 11 new unit tests covering all monthly kind permutations and edge cases (step=1, step=2, Sunday weekday=0, round-trips)

Test plan

  • Run ng test — all new tests pass
  • Verify buildMetaFromCustomConfig with monthlyKind=everyNMonthDom emits correct dom
  • Verify buildMetaFromCustomConfig with monthlyKind=monthlyFirstWeekday emits ordinalWeek=1 + weekday
  • Verify decomposeCustomMeta round-trips for all 4 monthly kinds
  • Verify reconstructMetaFromTask correctly distinguishes monthly kinds on reload

🤖 Generated with Claude Code

renemadsen and others added 4 commits June 6, 2026 10:31
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…repeat service

- buildMetaFromCustomConfig: add monthlyKind/dom/monthlyWeekday params;
  monthly branch now emits monthlyFirstWeekday/everyNMonthFirstWeekday kinds
  and uses the passed dom instead of hardcoding 1
- decomposeCustomMeta: extend return type with dom/monthlyKind/monthlyWeekday;
  all four existing monthly cases now extract dom and set monthlyKind;
  add cases for monthlyFirstWeekday and everyNMonthFirstWeekday
- spec: add 11 tests covering buildMeta, decompose, and round-trip for new kinds

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…fix test label

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Copilot AI review requested due to automatic review settings June 6, 2026 10:30

Copilot AI left a comment

Copy link
Copy Markdown

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 new CalendarRepeatService (pure TypeScript) intended to centralize calendar repeat-rule meta construction, serialization, label formatting, and occurrence enumeration, along with a large Jasmine spec suite and accompanying design/plan documentation for monthly repeat sub-types.

Changes:

  • Introduces calendar-repeat.service.ts implementing repeat option building, meta (de)composition, backend task reconstruction, and occurrence generation.
  • Adds extensive unit tests for repeat meta serialization, reconstruction, and date re-anchoring behavior.
  • Adds design/spec documentation for monthly repeat sub-type UI behavior and implementation plan.

Reviewed changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated 7 comments.

File Description
eform-client/src/app/plugins/modules/backend-configuration-pn/modules/calendar/services/calendar-repeat.service.ts New repeat service with meta building/serialization + occurrence generation + task reconstruction (but currently missing required dependencies and incomplete handling for new monthly kinds).
eform-client/src/app/plugins/modules/backend-configuration-pn/modules/calendar/services/calendar-repeat.service.spec.ts New/expanded unit test suite covering repeat behaviors and regressions (contains timezone-dependent date parsing).
docs/superpowers/specs/2026-06-06-monthly-repeat-options-design.md Design doc describing intended UX/data-model for monthly repeat sub-types.
docs/superpowers/plans/2026-06-06-monthly-repeat-options.md Implementation plan for monthly repeat sub-types across service + modal + i18n.

Comment on lines +1 to +4
import {Injectable} from '@angular/core';
import {TranslateService} from '@ngx-translate/core';
import {CalendarRepeatMeta, CalendarTaskModel} from '../../../models/calendar';
import {getCurrentLocale} from './calendar-locale.helper';
Comment on lines +217 to +218
case 'monthlyByDay':
case 'everyNMonthByDay': {
Comment on lines +416 to +417
case 'monthlyByDay':
case 'everyNMonthByDay': {
Comment on lines +307 to +320
{
value: 'monthlyByDay',
label: this.translate.instant('Monthly on the {{ordinal}} {{day}}', {
ordinal: this.formatOrdinal(Math.ceil(dom / 7), currentLang),
day: currentLang === 'da' ? dayName.toLowerCase() : dayName,
}),
meta: {
kind: 'monthlyByDay',
ordinalWeek: Math.ceil(dom / 7),
weekday,
endMode: 'never',
},
},
{
Comment on lines +5 to +7
// Monday 2026-03-16 00:00:00 UTC
const BASE_DATE = new Date('2026-03-16T00:00:00').getTime();

Comment on lines +777 to +780
// New monthly-by-weekday rule: dayOfMonth is 0 (the "no DOM" sentinel).
if (meta.kind === 'monthlyByDay' || meta.kind === 'everyNMonthByDay') {
return 0;
}
Comment on lines +789 to +795
metaToRepeatOrdinalWeek(meta: CalendarRepeatMeta | null | undefined): number | null {
if (!meta) return null;
if (meta.kind === 'monthlyByDay' || meta.kind === 'everyNMonthByDay') {
return meta.ordinalWeek ?? null;
}
return null;
}
@renemadsen

Copy link
Copy Markdown
Member Author

Calendar service changes belong in eform-backendconfiguration-plugin, not in eform-angular-frontend. Closing — covered by microting/eform-backendconfiguration-plugin#965

@renemadsen renemadsen closed this Jun 6, 2026
@renemadsen renemadsen deleted the feat/monthly-repeat-options branch June 6, 2026 10:51
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.

2 participants