3.8 KiB
3.8 KiB
2026-02-19 Initialization
- Decision log initialized.
2026-02-19 Expose crawling.recheck_hours in Settings UI
Decision
Added UI control and persistence for recheck_hours in SettingsDialog to expose previously invisible setting.
Changes Made
-
settings_dialog.py:_init_crawl_tab() (lines 142-147)
- Added ComboBox for "상세 재수집 주기 (시간)" with options [1,2,3,6,12,24]
- Loads from
settings['crawling']['recheck_hours']with default 3 - Positioned after unchecked_interval control for logical UI flow
-
settings_dialog.py:save_all() (line 417)
- Added persistence:
settings['crawling']['recheck_hours'] = int(self.combo_recheck_hours.get()) - Placed with other crawling settings (after interval_minutes)
- Added persistence:
-
test_settings_dialog_update_policy.py
- Added
recheck_hours: 3to initial controller.settings - Added
combo_recheck_hours = _DummyField("6")test field - Added assertion:
self.assertEqual(crawling_settings["recheck_hours"], 6)
- Added
Why This Approach
- Default fallback (3 hours) ensures backward compatibility
- ComboBox values match expected scheduler time scales
- Test verifies persistence through save_all() flow
- No changes to controller/scheduler - they already use the key
- Consistent with existing pattern (interval_minutes control)
Verified
- Unit test passes:
test_save_all_persists_update_policy_fields - Value correctly loaded from settings
- Value correctly saved on save_all()
2026-02-19 Add 5-hour option to recheck-hours ComboBox
Decision
Added "5" to the recheck_hours ComboBox values to enable explicit user selection of 5-hour interval.
Change
- settings_dialog.py:line 143
- Updated values: ["1", "2", "3", "5", "6", "12", "24"] (inserted "5" between "3" and "6")
- Maintains numeric ordering
- No logic changes to save() or load flow
2026-02-19 Prevent duplicate unchecked notification dialogs
Decision
Implement singleton behavior for unchecked notification dialogs (title prefix ⚠️ 미확인 VOC).
Allow regular new notifications to open multiple dialogs as before.
Implementation
- notification_dialog.py (lines 4-6, 8-15, 20, 22-24, 59-62, 86, 88-101):
- Added class variable
_unchecked_dialog = Noneto track open unchecked dialog - In
__init__: Check if incoming title is unchecked notification (startswith⚠️ 미확인 VOC) - If unchecked AND one already open → lift() and focus_force() existing dialog, return early (no new instance)
- If unchecked AND none open → store reference in
_unchecked_dialog - Modified close button (line 61) to call
self._on_close()instead ofself.destroy() - Added
_on_close()method (lines 97-101): Cleans up_unchecked_dialogreference before destroying - Updated
_on_view()and_on_open_list()to call_on_close()instead of directdestroy()
- Added class variable
Behavior
- Unchecked dialogs (⚠️ 미확인 VOC): Maximum one open at a time; new attempts bring existing to front
- Regular notifications (신규 알림): Unchanged; multiple can open (checked in title prefix)
- Cleanup: Reference cleared when dialog closes via any path (button, protocol handler, or methods)
Why This Approach
- Minimal scope: Changes only notification_dialog.py, no controller/scheduler modifications
- Non-intrusive: Regular new notifications unaffected; only unchecked notifications deduplicated
- Safe cleanup:
_on_close()ensures_unchecked_dialogref cleared regardless of close method - Semantic check: title.startswith("⚠️ 미확인 VOC") is the exact prefix used by notifier
Verified
- Syntax: python -m py_compile passed
- No regressions: All button callbacks still work (updated to use _on_close)
- LSP: Only pre-existing MAIN_COLOR hasattr error (unrelated)