Skip to content

Conversation

kic68
Copy link
Contributor

@kic68 kic68 commented Aug 19, 2025

With this fix the sensors will also show trains after midnight - otherwise the list empties out after 23:00.

Proposed Changes

My private departure monitor was not showing trains after midnight on the next day. So the list became smaller and smaller after 23:00 and was always completely empty shortly before midnight. Right after midnight the "missing" trains were then shown.

Related Issues

[Bug]: Trains after midnight are not shown (#50)

Summary by CodeRabbit

  • Bug Fixes
    • Ensures time-only departures (HH:MM) that have already passed today are scheduled for the next day, preventing past departures from appearing.
    • Improves accuracy of upcoming departures around midnight and late-night scenarios.
    • Continues to safely skip invalid time formats, reducing potential disruptions on the info screen.

With this fix the sensors will also show trains after midnight - otherwise the list empties out after 23:00.
Copy link

coderabbitai bot commented Aug 19, 2025

Walkthrough

Enhanced departure time parsing in _async_update_data to roll over to the next day when an HH:MM value is earlier than the current time. Existing error handling for invalid formats remains. Minor non-functional formatting tweak (trailing newline in async_unload_entry).

Changes

Cohort / File(s) Summary
Time parsing rollover logic
custom_components/db_infoscreen/__init__.py
Adjusts HH:MM parsing to create a candidate with today’s date; if candidate < now, advances by one day. Retains ValueError logging and skip behavior. Minor formatting (newline) in async_unload_entry.

Sequence Diagram(s)

sequenceDiagram
  autonumber
  actor HA as Home Assistant
  participant Comp as db_infoscreen component
  participant Time as datetime.now()

  HA->>Comp: _async_update_data()
  Comp->>Time: now = datetime.now()
  loop For each entry
    Comp->>Comp: Parse HH:MM
    alt Invalid time format
      Comp->>Comp: Log error, skip entry
    else Valid time
      Comp->>Comp: candidate = today @ HH:MM
      alt candidate < now
        Comp->>Comp: candidate = candidate + 1 day
      end
      Comp->>Comp: departure_time = candidate
    end
  end
  Comp-->>HA: Updated data
Loading

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~10 minutes

Poem

I nibble on times in the garden of now,
If clocks run behind, I hop to tomorrow’s bough.
Errors? I twitch, then skip with care—
Parsley minutes, celery air.
One tidy newline, thump of delight—
Departures aligned, all timing just right. 🐇⌚️

Tip

🔌 Remote MCP (Model Context Protocol) integration is now available!

Pro plan users can now connect to remote MCP servers from the Integrations page. Connect with popular remote MCPs such as Notion and Linear to add more context to your reviews and chats.

✨ Finishing Touches
  • 📝 Generate Docstrings
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.

Support

Need help? Create a ticket on our support page for assistance with any issues or questions.

CodeRabbit Commands (Invoked using PR/Issue comments)

Type @coderabbitai help to get the list of available commands.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Status, Documentation and Community

  • Visit our Status Page to check the current availability of CodeRabbit.
  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1> [!CAUTION]

Some comments are outside the diff and can’t be posted inline due to platform limits.

🔭 Outside diff range comments (3)
custom_components/db_infoscreen/__init__.py (3)

244-251: Arrival parsing: add next-day rollover for HH:MM and support ISO with seconds (consistency with departure).

Right now, arrivals parsed from HH:MM are pinned to “today” without rolling over to the next day. After 23:xx, this can mislabel midnight+ arrivals and diverge from the fixed departure handling.

Apply this diff to mirror the departure parsing behavior and accept both ISO forms:

-                                if "T" in scheduled_arrival:
-                                    arrival_time = datetime.strptime(scheduled_arrival, "%Y-%m-%dT%H:%M")
-                                else:
-                                    now = datetime.now()
-                                    arrival_time = datetime.strptime(scheduled_arrival, "%H:%M").replace(
-                                        year=now.year, month=now.month, day=now.day
-                                    )
+                                try:
+                                    # Try ISO with seconds
+                                    arrival_time = datetime.strptime(scheduled_arrival, "%Y-%m-%dT%H:%M:%S")
+                                except ValueError:
+                                    try:
+                                        # Try ISO without seconds
+                                        arrival_time = datetime.strptime(scheduled_arrival, "%Y-%m-%dT%H:%M")
+                                    except ValueError:
+                                        # Fallback to HH:MM with next-day rollover
+                                        now = datetime.now()
+                                        arrival_candidate = datetime.strptime(scheduled_arrival, "%H:%M").replace(
+                                            year=now.year, month=now.month, day=now.day
+                                        )
+                                        if arrival_candidate < now:
+                                            arrival_candidate += timedelta(days=1)
+                                        arrival_time = arrival_candidate

Also applies to: 242-259


276-285: Bug: Delay is added to departure_time twice.

departure_time is incremented at Line 277 and again at Line 285, effectively double-counting the delay. This skews offset filtering and displayed times.

Remove the first addition (keep the later block that logs and handles fallback):

-                        if not self.drop_late_trains:
-                            departure_time += timedelta(minutes=delay_departure or 0)
-
                         # Apply any delay to the departure time, if applicable
                         if not self.drop_late_trains:
                             _LOGGER.debug("Departure time without added delay: %s", departure_time)
                             if delay_departure is None:
                                 delay_departure = 0  # Set delay to 0 as fallback if no valid delay has been found
                             departure_time += timedelta(minutes=delay_departure)
                             _LOGGER.debug("Departure time with added delay: %s", departure_time)

352-352: Possible type bug: default for drop_late_trains is a list, but used as a boolean.

drop_late_trains is handled as a boolean (e.g., if not self.drop_late_trains:), but here the default is []. This leads to surprising behavior (empty list is falsy).

Use a boolean default:

-    drop_late_trains = config_entry.data.get(CONF_DROP_LATE_TRAINS, [])
+    drop_late_trains = config_entry.data.get(CONF_DROP_LATE_TRAINS, False)
🧹 Nitpick comments (2)
custom_components/db_infoscreen/__init__.py (2)

263-275: Dead/unreachable branch and potential AttributeError on string .date()

delay_arrival is set to 0 when None (Lines 239–241). Therefore, elif delay_arrival is None: (Line 263) never executes. If it did, scheduled_arrival is a string here and calling .date() would raise.

  • Remove the unreachable elif delay_arrival is None: block entirely.
  • If you want to keep the “no delay” path explicit, parse scheduled_arrival to a datetime (using the same logic as above) before formatting.

I can provide a follow-up patch removing that branch if you prefer.


118-132: Optional: Use timezone-aware now() from Home Assistant and compute it once.

Multiple calls to datetime.now() produce naive datetimes and may cross minute boundaries mid-loop. Home Assistant provides dt_util.now() (timezone-aware). Compute now once at the start and reuse.

  • Add import:
from homeassistant.util import dt as dt_util
  • At the start of _async_update_data, capture now = dt_util.now(), and reuse it in:
    • setting self.last_update
    • departure and arrival parsing rollovers
    • date comparisons for formatting
    • offset calculation

If you want, I can prepare a targeted patch adjusting these call sites.

Also applies to: 195-205, 247-251, 220-224, 229-233, 255-258

📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

💡 Knowledge Base configuration:

  • MCP integration is disabled by default for public repositories
  • Jira integration is disabled by default for public repositories
  • Linear integration is disabled by default for public repositories

You can enable these sources in your CodeRabbit configuration.

📥 Commits

Reviewing files that changed from the base of the PR and between ada4b35 and a0430ca.

📒 Files selected for processing (1)
  • custom_components/db_infoscreen/__init__.py (2 hunks)
🔇 Additional comments (2)
custom_components/db_infoscreen/__init__.py (2)

195-205: LGTM on the midnight rollover approach.

The “if candidate < now then +1 day” logic is the right fix to show departures after midnight on the next day.


373-373: LGTM: trailing newline preservation in async_unload_entry.

No functional change; consistent formatting.

@FaserF FaserF merged commit d422220 into FaserF:main Aug 23, 2025
6 checks passed
@FaserF
Copy link
Owner

FaserF commented Aug 23, 2025

Thanks!

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