-
-
Couldn't load subscription status.
- Fork 33.3k
Description
Feature or enhancement
Proposal:
Add a format() method to datetime.timedelta objects to simplify formatting time durations for display, similar to how datetime objects have strftime().
Has this already been discussed elsewhere?
I have already searched and did not find an existing issue or discussion.
Links to previous discussion of this feature:
No response
The Problem
Currently, formatting a timedelta object for display requires manual arithmetic and is error-prone:
from datetime import timedelta
# Current approach - requires manual calculation
def format_timedelta(td):
days = td.days
hours, remainder = divmod(td.seconds, 3600)
minutes, seconds = divmod(remainder, 60)
if days:
return f"{days}d {hours}h {minutes}m {seconds}s"
elif hours:
return f"{hours}h {minutes}m {seconds}s"
else:
return f"{minutes}m {seconds}s"
duration = timedelta(days=2, hours=3, minutes=30, seconds=45)
print(format_timedelta(duration)) # "2d 3h 30m 45s"This pattern is repeated across many codebases, indicating a common need.
Proposed Solution
Add a format() method to timedelta that accepts a format string:
from datetime import timedelta
duration = timedelta(days=2, hours=3, minutes=30, seconds=45)
# Proposed new method
print(duration.format("%d days, %H:%M:%S")) # "2 days, 03:30:45"
print(duration.format("%H hours %M minutes")) # "51 hours 30 minutes"
print(duration.format("%d days")) # "2 days"
# For durations less than a day
short_duration = timedelta(hours=1, minutes=30)
print(short_duration.format("%H:%M:%S")) # "01:30:00"Proposed Format Codes
Basic format codes (similar to strftime where applicable):
%d- days%H- hours (00-23, remainder after days)%M- minutes (00-59, remainder after hours)%S- seconds (00-59, remainder after minutes)%f- microseconds (000000-999999)
Total duration codes (useful for elapsed time):
%th- total hours (float)%tm- total minutes (float)%ts- total seconds (float)
Real-World Use Cases
Server/Application Monitoring:
uptime = datetime.now() - server_start
status = f"Uptime: {uptime.format('%d days, %H:%M:%S')}"User-Friendly Task Duration:
elapsed = end_time - start_time
print(f"Backup completed in {elapsed.format('%H:%M:%S')}")Video/Media Duration:
video_length = timedelta(seconds=7265)
display = video_length.format("%H:%M:%S") # "02:01:05"Benefits
- Reduces boilerplate - No more divmod arithmetic in application code
- Improves readability - Intent is clear from the format string
- Consistency - Similar API to datetime.strftime()
- Fewer bugs - Centralized, tested implementation
Questions for Core Developers
- Should the format codes exactly match strftime where possible, or use a simpler subset?
- How should negative timedeltas be handled in formatting?
- Would a simpler API be preferred (e.g., just common formats like
to_hhmmss())?
I'm happy to implement this feature following the agreed-upon design, write tests, and update documentation. I have already set up the CPython development environment and am familiar with the datetime module structure.
Has this already been discussed elsewhere?
No response given
Links to previous discussion of this feature:
No response