How to Resolve Python "AttributeError: module 'datetime' has no attribute ..." (strptime, strftime, today, fromtimestamp, now)
When working with dates and times in Python, the datetime module is indispensable. However, its structure can sometimes lead to AttributeError exceptions, such as AttributeError: module 'datetime' has no attribute 'strptime', 'strftime', 'now', 'today', or 'fromtimestamp'. These errors typically arise from confusion between the datetime module itself and the datetime class contained within it, or from attempting to call instance methods inappropriately.
This guide clarifies the structure of the datetime module and provides clear solutions to fix these common attribute errors.
Understanding the datetime Module vs. datetime Class
This is the most crucial point:
datetime(lowercase): Refers to the module you import (import datetime). It acts as a container.datetime.datetime(Module.Class): Refers to the primary class inside thedatetimemodule. This class represents a specific point in time (date and time).datetime.date(Module.Class): Refers to another class inside thedatetimemodule, representing only a date (year, month, day).
Many useful functions for creating or manipulating date/time objects are class methods or static methods belonging to the datetime.datetime or datetime.date classes, not methods of the top-level datetime module itself. Methods for formatting existing date/time objects (like strftime) are instance methods.
Error Type 1: Calling Class/Static Methods on the Module
This covers errors like AttributeError: module 'datetime' has no attribute 'strptime', 'now', 'today', 'fromtimestamp'.
Examples
import datetime # Importing the MODULE
try:
# ⛔️ AttributeError: module 'datetime' has no attribute 'strptime'
dt_obj = datetime.strptime("21/11/25 09:30", "%d/%m/%y %H:%M")
except AttributeError as e:
print(f"strptime Error: {e}")
try:
# ⛔️ AttributeError: module 'datetime' has no attribute 'now'
now_time = datetime.now()
except AttributeError as e:
print(f"now Error: {e}")
try:
# ⛔️ AttributeError: module 'datetime' has no attribute 'today'
# Note: .today() exists on BOTH datetime.date and datetime.datetime classes
today_date = datetime.today()
except AttributeError as e:
print(f"today Error: {e}")
try:
# ⛔️ AttributeError: module 'datetime' has no attribute 'fromtimestamp'
ts_obj = datetime.fromtimestamp(1678886400)
except AttributeError as e:
print(f"fromtimestamp Error: {e}")
Cause: Method Belongs to the Class, Not the Module
The methods strptime, now, today, and fromtimestamp are defined within the datetime.datetime class (and today is also in datetime.date). You cannot call them directly on the datetime module object obtained via import datetime.
Solution 1: Use Full datetime.datetime or datetime.date Path
Access the methods through the class they belong to, using the full path module.class.method().
import datetime # Import the module
# ✅ Access via module.class
dt_obj = datetime.datetime.strptime("21/11/25 09:30", "%d/%m/%y %H:%M")
now_time = datetime.datetime.now()
today_datetime = datetime.datetime.today() # today() from datetime class
today_date = datetime.date.today() # today() from date class
ts_obj = datetime.datetime.fromtimestamp(1678886400)
print(f"strptime: {dt_obj}") # strptime: 2025-11-21 09:30:00
print(f"now: {now_time}") # now: 2025-04-17 09:36:27.839274
print(f"today (datetime): {today_datetime}") # today (datetime): 2025-04-17 09:36:27.839279
print(f"today (date): {today_date}") # today (date): 2025-04-17
print(f"fromtimestamp: {ts_obj}") # fromtimestamp: 2023-03-15 13:20:00
Solution 2: Import the Class Directly (Recommended)
This is often clearer and avoids the repetitive datetime.datetime. Import the specific class(es) you need from the module.
# ✅ Import the specific class(es)
from datetime import datetime, date, time # Import classes needed
dt_obj = datetime.strptime("21/11/25 09:30", "%d/%m/%y %H:%M")
now_time = datetime.now()
today_datetime = datetime.today()
today_date = date.today()
ts_obj = datetime.fromtimestamp(1678886400)
print(f"strptime: {dt_obj}") # strptime: 2025-11-21 09:30:00
print(f"now: {now_time}") # now: 2025-04-17 09:37:27.994833
print(f"today (datetime): {today_datetime}") # today (datetime): 2025-04-17 09:37:27.994838
print(f"today (date): {today_date}") # today (date): 2025-04-17
print(f"fromtimestamp: {ts_obj}") # fromtimestamp: 2023-03-15 13:20:00
Now you can call the class/static methods directly on the imported class name (datetime or date).
Solution 3: Use Aliases (as dt)
If you prefer shorter names, especially when importing the class directly, use an alias.
# ✅ Import the class with an alias
from datetime import datetime as dt, date
dt_obj = dt.strptime("21/11/22 09:30", "%d/%m/%y %H:%M")
now_time = dt.now()
today_dt = dt.today()
today_d = date.today()
ts_obj = dt.fromtimestamp(1678886400)
print(f"strptime: {dt_obj}") # strptime: 2022-11-21 09:30:00
print(f"now: {now_time}") # now: 2025-04-17 09:39:18.822739
print(f"today (datetime): {today_dt}") # today (datetime): 2025-04-17 09:39:18.822748
print(f"today (date): {today_d}") # today (date): 2025-04-17
print(f"fromtimestamp: {ts_obj}") # fromtimestamp: 2023-03-15 13:20:00
Error Type 2: Calling Instance Methods on the Module or Class
This covers errors like AttributeError: module 'datetime' has no attribute 'strftime'.
Example: strftime
import datetime
# Or: from datetime import datetime
try:
# ⛔️ AttributeError: module 'datetime' has no attribute 'strftime'
# Trying to call strftime on the module
formatted = datetime.strftime("%Y-%m-%d")
except AttributeError as e:
print(f"Error calling on module: {e}")
try:
# ⛔️ TypeError: descriptor 'strftime' for 'datetime.date' objects doesn't apply to a 'datetime.datetime' object
# (or similar TypeError if called on the class directly)
# Although the error message might differ slightly, the cause is the same:
# strftime needs an INSTANCE.
formatted_class = datetime.datetime.strftime("%Y-%m-%d")
except TypeError as e:
print(f"Error calling on class: {e}")
Cause: Method Belongs to an Instance, Not the Module/Class
Methods like strftime() are instance methods. They operate on a specific datetime object (an instance of the datetime.datetime class) that holds a particular date and time value. You cannot call them on the module or the class itself.
Solution: Create an Instance First, Then Call the Method
First, create a datetime object (using datetime.datetime.now(), datetime.datetime.today(), datetime.datetime.strptime(...), datetime.datetime(...) constructor, etc.). Then, call the instance method on that object.
from datetime import datetime # Import the class
# ✅ Create datetime instances first
now_instance = datetime.now()
specific_dt_instance = datetime(2023, 10, 27, 14, 0)
# ✅ Call strftime() on the instances
formatted_now = now_instance.strftime("%Y-%m-%d %H:%M:%S")
formatted_specific = specific_dt_instance.strftime("%A, %B %d, %Y")
print(f"Now instance: {now_instance}") # Now instance: 2025-04-17 09:40:11.431121
print(f"Formatted now: {formatted_now}") # Formatted now: 2025-04-17 09:40:11
print(f"Specific instance: {specific_dt_instance}") # Specific instance: 2023-10-27 14:00:00
print(f"Formatted specific: {formatted_specific}") # Formatted specific: Friday, October 27, 2023
Common Issue: Filename Shadowing (datetime.py)
Cause: Local File Interferes with Standard Module
If you name your own script datetime.py, Python's import system will likely find and import your file instead of the standard library datetime module when you write import datetime. Your file won't have the expected classes or methods, leading to AttributeError.
Solution: Rename Your Local datetime.py File
Avoid using standard library module names for your own files. Rename your datetime.py to something else (e.g., date_utils.py, main_app.py).
Debugging: Identifying the Conflict (__file__, dir())
- Check
__file__:import datetime; print(datetime.__file__). If it points to your project directory instead of the Python library path, you have a naming conflict. - Check
dir():import datetime; print(dir(datetime)). If the output lacksdatetime,date,time,timedelta, etc., you've imported your local file.
Related Error: Circular Import (partially initialized module)
If you use import datetime inside a file named datetime.py, you might get an error like AttributeError: partially initialized module 'datetime' has no attribute '...' (most likely due to a circular import).
Solution: Rename your datetime.py file.
Debugging with dir()
Using dir() helps clarify what's available:
dir(datetime)(afterimport datetime): Shows contents of the module (includesdatetimeclass,dateclass,timedelta, etc.).dir(datetime.datetime)(afterimport datetime) ordir(datetime)(afterfrom datetime import datetime): Shows contents of the class (includes class/static methods likenow,strptime).dir(my_dt_object)(wheremy_dt_object = datetime.datetime.now()): Shows contents of an instance (includes instance methods likestrftime,weekday, and attributes likeyear,month).
Conclusion
AttributeErrors related to the datetime module usually stem from:
- Confusing the module
datetimewith the classdatetime.datetime: Class/static methods (now,strptime, etc.) must be called via the class (e.g.,datetime.datetime.now()ordt.now()afterfrom datetime import datetime as dt). - Calling instance methods (
strftime) on the module or class: These methods must be called on an actualdatetimeobject instance. - Filename shadowing: Naming your script
datetime.pyprevents the correct module from being imported. Rename your file.
By understanding the module's structure and using the correct import and access patterns, you can reliably use Python's date and time functionalities. Importing the specific classes (from datetime import datetime, date) is often the clearest approach.