Add temporal utility as optional template variant#113
Conversation
f719e71 to
befec8a
Compare
a-musing-moose
left a comment
There was a problem hiding this comment.
Rather than use both the exclude option in copier.yml and adding the if use_temporal tags in each file - you can change the file name to include the if statement directly.
I am also concerned that these test specify the Melbourne Time zone, but settings.py have UTC.
Finally - Does this need to be an option? Should we just include it regardless? I think it is useful set of utilities any any project.
9fec36e to
1eeca9e
Compare
a-musing-moose
left a comment
There was a problem hiding this comment.
Nearly there - the only blocking change I need to see resolved is the param renaming in the extract_datetime_from_string function (or it's removal). Although the documentation re-framing would be nice to have now too.
|
|
||
|
|
||
| def extract_datetime_from_string( | ||
| file_name: str, delimiters: abc.Iterable[str] = (".", "_") |
There was a problem hiding this comment.
Issue: Rename the parameter file_name to something generic like value
The use of file_name feels like a hang over from this functions use in the Middy's project to extra datetime from transferred filenames.
In fact I might consider dropping this function entirely from the generic temporal implementation both because it is feels a little too Middy's file name specific and because it is the only part of temporal that requires the addition of dateutils. That said, if you think it still has sufficient re-usability - then just go for the parameter rename.
There was a problem hiding this comment.
Good catch! I renamed the param and left it for now since I believe this can be a helpful in some projects.
| |--------------|----------------| | ||
| | `datetime.datetime.now()` | `temporal.now()` | | ||
| | `datetime.datetime.today()` | `temporal.today()` | | ||
| | `datetime.datetime.utcnow()` | `temporal.now()` | |
There was a problem hiding this comment.
Suggestion: you can drop utcnow
utcnow is a deprecated function already, and our temporal.now() is not a direct equivalent unless the TZ is set to UTC.
| | `datetime.datetime.utcnow()` | `temporal.now()` | | ||
| | `datetime.date.today()` | `temporal.today()` | | ||
|
|
||
| ## Available Functions |
There was a problem hiding this comment.
Suggestion: Drop the exhaustive list of functions
This document will be out of date as soon as anything changes in the temporal module. So the module is a better source of truth... unless you use mkdocstring to generate this portion of the document.
There was a problem hiding this comment.
Suggestion: Reframe this as a "how-to" on working with dates and times
I think this document floats a little between pure reference and guidance. So a how-to is probably a better fit.
Move to how-tos/datetimes.md and talk more generally about working with dates, times and timezones.
You can introduce the temporal modules as a collection of functions to help you do the right thing.
You can also talk in a how to about good practices when testing code that uses or manipulates datetimes. Calling out that this is the number one cause of flaky tests and that any tests that rely on "now" or datetime/timezone manipulations should use time_machine to ensure a consistent time in which the test operates.
You could even talk about trying to call temporal.now() only at the top level interfaces (views, tasks) and passing them down to business logic. So that the business logic can be more easily isolated for testing purposes. .i.e. if a function takes now (or as_of) as a parameter is probably doesn't need to use time_machine as the supplied date never changes.
Makes the timezone-aware datetime utilities optional through a new use_temporal configuration flag. When disabled, the utils folders and related dependencies are excluded from generated projects. The temporal utility now includes only universally useful datetime helpers: `now()`, `today()`, `yesterday()`, `tomorrow()`, `midnight()`, `make_tz_aware()`, `DatetimeRange`, `extract_datetime_from_string()`, `get_weekdays()`, and `get_weekdays_between()`.
f214ff0 to
3219eb2
Compare
a-musing-moose
left a comment
There was a problem hiding this comment.
The code is fine now - just one little correction in the documentation and a couple of thoughts/notes that might be worth discussing.
| datetimes timezone-aware immediately: | ||
|
|
||
| ```python | ||
| from {{ project_module }}.utils.temporal import make_tz_aware |
There was a problem hiding this comment.
Issue: from {{ project_module }}.utils import temporal
I know this only an examples, but I would like to continue to re-enforce importing modules not properties.
| **Important:** Even if your users are all in one timezone (e.g., "Australia/Melbourne"), | ||
| use `"UTC"` as your `TIME_ZONE`. Django will store all data in UTC and convert to user | ||
| timezones when displaying. This avoids DST bugs and makes your data portable. |
There was a problem hiding this comment.
If USE_TZ is set to true than Django will store in UTC regardless of what TIME_ZONE is set to. I cannot remember if this is a Django or Postgres thing - but the outcome is the same.
But I don't think Django will automatically know the user's timezone and perform the conversion in render. I think you need to either set TIME_ZONE or use the timezone.activate() method to set the timezone for the current request.
If you only really care about the local tz, it might be easier to just set TIME_ZONE to that. We do that for Middy's I think.
There was a problem hiding this comment.
I've added a section to explain this.
3219eb2 to
5808992
Compare
5808992 to
2b454cc
Compare
This change makes the timezone-aware datetime utilities
optional through a new use_temporal configuration flag. When disabled, the utils folders and related dependencies are excluded from generated projects.The temporal utility now includes only universally useful datetime helpers:
now(),today(),yesterday(),tomorrow(),midnight(),make_tz_aware(),DatetimeRange,extract_datetime_from_string(),get_weekdays(), andget_weekdays_between().