Last modified: Dec 06, 2025 By Alexander Williams
Fix TypeError: object not JSON serializable
You see this error often in Python. It happens when you try to convert data to JSON. The json.dumps() function cannot handle certain objects.
This guide explains the error. It shows you how to fix it. You will learn about JSON-compatible types. You will also learn to use custom serializers.
Understanding the JSON Serialization Error
JSON is a text format for data exchange. Python's json module converts Python objects to JSON strings. This process is called serialization.
The json.dumps() function does this conversion. It only works with specific data types. These are basic types like strings, numbers, lists, and dictionaries.
If your data contains an unsupported type, Python raises the error. The error message is "TypeError: Object of type X is not JSON serializable".
Common Causes of the Error
Many Python objects are not natively JSON serializable. You will encounter this with custom classes. You will also see it with datetime objects and sets.
Other common culprits include NumPy arrays and complex numbers. Even a simple range object can cause this issue. It is similar to other type errors like Fix Python TypeError: 'range' object item assignment.
The root cause is always the same. You are trying to serialize a data type that the json module does not understand by default.
JSON-Compatible Python Data Types
First, know what works. The JSON standard supports a limited set of types. Python maps these to its own built-in types.
Here is the complete list of compatible Python types:
- dict: Maps to a JSON object.
- list, tuple: Map to a JSON array.
- str: Maps to a JSON string.
- int, float: Map to a JSON number.
- True/False: Map to JSON true/false.
- None: Maps to JSON null.
Anything outside this list will cause the TypeError. This includes common objects like datetime.datetime.
Example: Reproducing the Error
Let's create a simple example. We will try to serialize a dictionary containing a datetime object.
import json
from datetime import datetime
# Create data with a datetime object
data = {
"event": "Meeting",
"time": datetime.now() # This is NOT JSON serializable!
}
# This line will raise the TypeError
json_string = json.dumps(data)
TypeError: Object of type datetime is not JSON serializable
The error is clear. The datetime object is the problem. The json.dumps() function does not know how to convert it.
Solution 1: Convert to a String Manually
The simplest fix is to convert the object before serialization. For a datetime, convert it to an ISO format string.
Strings are perfectly JSON serializable. This approach gives you full control over the format.
import json
from datetime import datetime
data = {
"event": "Meeting",
"time": datetime.now().isoformat() # Convert to string first
}
# Now it works!
json_string = json.dumps(data)
print(json_string)
{"event": "Meeting", "time": "2023-10-27T14:30:15.123456"}
This method works well for simple cases. You must manually convert every non-serializable field. For complex data, this can be tedious.
Solution 2: Use the default Parameter in json.dumps
Python's json.dumps() function has a default parameter. It is a function that handles unknown objects.
When the serializer finds an unknown type, it calls your default function. This function should return a JSON-serializable version of the object.
import json
from datetime import datetime
def custom_serializer(obj):
"""Handle non-serializable objects."""
if isinstance(obj, datetime):
return obj.isoformat()
# Add more type checks here if needed
raise TypeError(f"Type {type(obj)} not serializable")
data = {
"event": "Meeting",
"time": datetime.now(),
"participants": 5 # This is an int, so it's fine
}
# Pass our custom function to the 'default' parameter
json_string = json.dumps(data, default=custom_serializer)
print(json_string)
{"event": "Meeting", "time": "2023-10-27T14:30:15.123456", "participants": 5}
This is a powerful and clean solution. You define the conversion logic in one place. The serializer uses it for all objects in your data structure.
Solution 3: Create a Custom JSONEncoder Class
For more complex applications, create a custom encoder. Subclass json.JSONEncoder and override its default method.
This is the most object-oriented approach. It is ideal if you need to serialize many custom types.
import json
from datetime import datetime
class CustomEncoder(json.JSONEncoder):
def default(self, obj):
# Handle datetime objects
if isinstance(obj, datetime):
return obj.isoformat()
# Handle sets by converting to list
if isinstance(obj, set):
return list(obj)
# Let the base class handle the rest (it will raise TypeError)
return super().default(obj)
# Example data with multiple complex types
data = {
"timestamp": datetime.now(),
"unique_ids": {101, 102, 103}, # This is a set
"name": "Project Data"
}
# Use the custom encoder
json_string = json.dumps(data, cls=CustomEncoder)
print(json_string)
{"timestamp": "2023-10-27T14:30:15.123456", "unique_ids": [101, 102, 103], "name": "Project Data"}
The custom encoder cleanly handles both datetime and set objects. You can extend it to handle any custom class you create.
Handling Custom Class Objects
Your own classes are not JSON serializable. You must define how to convert them. Add a method to your class that returns a serializable dictionary.
A common pattern is to add a to_dict() or __dict__ method. Then, teach your encoder to use it.
import json
class User:
def __init__(self, name, age):
self.name = name
self.age = age
def to_dict(self):
# Return a simple, serializable dictionary
return {"name": self.name, "age": self.age}
class CustomClassEncoder(json.JSONEncoder):
def default(self, obj):
# Check if the object has a to_dict method
if hasattr(obj, 'to_dict'):
return obj.to_dict()
return super().default(obj)
user = User("Alice", 30)
data = {"user": user}
json_string = json.dumps(data, cls=CustomClassEncoder)
print(json_string)
{"user": {"name": "Alice", "age": 30}}
This pattern is very flexible. It lets each class define its own serialization logic. Your encoder just needs to call the right method.
Debugging Tips and Best Practices
First, identify the offending object. The error message names the type. Use print statements to inspect your data structure.
Consider using the pprint module for complex nested data. It helps you see the exact structure.
Remember, errors can be nested. A dictionary might look fine, but a value inside could be the problem. This is similar to issues with Fix TypeError: unhashable type 'dict' in Python, where the problem is inside a structure.
Always test your custom encoder or default function thoroughly. Make sure it handles all edge cases in your data.
Related TypeErrors in Python
Understanding this error helps with others. Python has many type-related errors. They often stem from mismatched expectations.
For instance, Fix TypeError: a bytes-like object is required, not 'str' deals with string/bytes confusion. The principle is similar: ensure data matches the function's requirements.
Mastering type handling is a key Python skill. It prevents many common bugs.
Conclusion
The "object is not JSON serializable" error is common. It is also easy to fix once you understand JSON's limits.
The key is to convert unsupported types to supported ones. You can do this manually, with a default function, or a custom encoder.
For simple cases, pre-convert your data. For complex applications, a custom JSONEncoder is best.
Always know your data types. Plan your serialization strategy early. This will save you debugging time later.
Now you can handle this error confidently. Your Python programs will reliably exchange JSON data with any system.