Skip to content

feat: improve multiple reservation conflict presentation - #164

Merged
KinjiKawaguchi merged 2 commits into
mainfrom
feat/126-conflict-presentation
Sep 21, 2026
Merged

KinjiKawaguchi merged 2 commits into
mainfrom
feat/126-conflict-presentation

Conversation

@KinjiKawaguchi

Copy link
Copy Markdown
Member

Why

When multiple reservations conflict with a new booking request, the
Slack error message repeats the heading block for each conflict. This
makes the message verbose and difficult to scan. Additionally, the
reader cannot tell at a glance how many conflicts there are without
scrolling through all of them.

What

  • Add a second template conflict_item to TemplateConfig for use when
    there are multiple conflicts. It renders each conflict without the
    leading heading (e.g. ⚠️ 予約が重複しています).
  • In conflict_message.rs, detect whether there are 1 or multiple
    conflicts:
    • Single conflict: Use the existing conflict template (unchanged,
      preserves all customizations)
    • Multiple conflicts: Show a conflict count line first
      (e.g. "3件の予約と重複しています。"), then list each conflict using
      the conflict_item template

This reduces visual repetition and makes conflict messages more scannable.

Example

Before:

❌ 予約の作成に失敗しました

⚠️ 予約が重複しています
👤 <@U01ALICE>
📅 2026-07-28 19:00 - 21:00
💻 GPU:0
   GPU:1

⚠️ 予約が重複しています      ← repeated heading
👤 <@U02BOB>
📅 2026-07-28 20:00 - 23:00
💻 GPU:2

After:

❌ 予約の作成に失敗しました

2件の予約と重複しています。

👤 <@U01ALICE>
📅 2026-07-28 19:00 - 21:00
💻 GPU:0
   GPU:1

👤 <@U02BOB>
📅 2026-07-28 20:00 - 23:00
💻 GPU:2

Closes #126

🤖 Generated with Claude Code

When multiple reservations conflict with a new booking request, replace
repeated heading blocks with a conflict count and simplified per-conflict
items, reducing visual noise and making the message easier to scan.

Add second template `conflict_item` for multiple-conflict rendering,
used only when there are 2+ conflicts. Single-conflict messages use the
existing `conflict` template unchanged, preserving customizations.

The conflict count line (e.g. "3件の予約と重複しています。") appears
once before the list, rather than repeating the heading per conflict.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Copilot AI lite review requested due to automatic review settings September 21, 2026 09:41
@KinjiKawaguchi KinjiKawaguchi added this to the v2.0.0 milestone Sep 21, 2026

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.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

…ogic

Add documentation for the new conflict_item template in ADMIN_GUIDE.md and
ADMIN_GUIDE_ja.md, explaining that it is used only for multiple conflicts
and that the conflict count line is appended by the builder, not part of
the template.

Extract common notification configuration resolution logic from build_one
and build_item into a separate render_customization_for_conflict function
to eliminate duplication and prevent Shotgun Surgery issues. Both functions
now use this helper to retrieve customization settings and timezone before
constructing the TemplateRenderer.

Also update config/resources.toml.example to include conflict_item as an
optional customization example.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Copilot AI review requested due to automatic review settings September 21, 2026 09:45

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.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

@KinjiKawaguchi
KinjiKawaguchi merged commit bbfb86b into main Sep 21, 2026
10 checks passed
KinjiKawaguchi pushed a commit that referenced this pull request Sep 21, 2026
🤖 I have created a release *beep* *boop*
---


##
[2.0.0](v1.8.0...v2.0.0)
(2026-09-21)


### ⚠ BREAKING CHANGES

* google_calendar_mappings.json is no longer read and the
GOOGLE_CALENDAR_MAPPINGS_FILE environment variable is gone (both are
ignored if left in place; reservation ids copied from pre-v1.5.1 event
descriptions stop resolving). In the library API,
GoogleCalendarUsageRepository::new no longer takes the mappings path.
* existing resources.toml files stop loading until calendar_id entries
are moved into the [storage] section (see the migration guide). In the
library API, load_config returns a (ResourceConfig, StorageConfig) pair,
ServerConfig and RoomConfig lose their calendar_id field, and
GoogleCalendarUsageRepository::new takes the StorageConfig.
* TemplateConfig gains a conflict_item field, so struct-literal
construction outside this crate needs updating.
* DetectIdleReservationsUseCase loses its IdentityLinkRepository type
parameter and constructor argument; judge_reservation_activity drops its
owner_identities parameter; GpuUsageReport gains a required unattributed
field; NotificationError gains a RecipientUnknown variant; public error
enums are non_exhaustive, so external matches need a wildcard arm.

### Features

* improve how multiple reservation conflicts are presented
([#164](#164))
([bbfb86b](bbfb86b))
* judge idle reservations by the reserved device, not process identity
([#161](#161))
([6141e74](6141e74))


### Code Refactoring

* drop the id-mapping file for calendar events
([#166](#166))
([88570ee](88570ee))
* separate the storage mapping from resource definitions
([#165](#165))
([cbc3fdc](cbc3fdc))

---
This PR was generated with [Release
Please](https://github.com/googleapis/release-please). See
[documentation](https://github.com/googleapis/release-please#release-please).

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
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.

Improve how multiple conflicts are presented

2 participants