Fact Box |
|
---|---|
Language | Python |
License | BSD |
GitHub | KristianOellegaard/django-hvad |
PyPI | django-hvad |
First Release | 2011 |
Status | Archived |
django-hvad (which means "what" in Danish) is a translation framework for Django models that makes internationalization painless. It allows you to translate your Django models into multiple languages using the normal Django ORM, without the complexity and performance overhead of other solutions.
Origins
django-hvad started as a fork of django-nani by Jonas Obrist. While django-nani provided the foundational concepts, I created hvad to take the project in a new direction with different design choices and features. The fork allowed the community to explore different approaches to solving Django translation challenges.
The Translation Problem
When building international Django applications, I quickly discovered that handling translations for database content was surprisingly difficult. The existing solutions at the time had significant drawbacks:
- Required complex queries and custom managers
- Added multiple database queries for translated content
- Broke standard Django ORM patterns
- Made it difficult to work with translated and non-translated models consistently
I wanted something that felt natural - where you could just use the Django ORM as usual, and it would automatically handle translations based on the current language.
The hvad Approach
django-hvad introduced a simple yet powerful pattern:
class Product(TranslatableModel):
# Non-translated fields
price = models.DecimalField()
sku = models.CharField()
translations = TranslatedFields(
# Translated fields
name=models.CharField(max_length=255),
description=models.TextField(),
)
Key Innovations
1. Transparent ORM Integration
Once configured, you work with translated models just like regular Django models:
# Automatically returns content in the current language
product = Product.objects.language('da').get(sku='ABC123')
print(product.name) # Returns Danish name
2. Performance Optimization
Unlike solutions that required separate queries for translations, hvad uses an INNER JOIN
to an indexed key. This meant:
- No additional queries for reads
- Minimal performance overhead
- Efficient database utilization
3. Natural Fallbacks
The library handled language fallbacks gracefully - if a translation didn't exist in the requested language, it could fall back to a default language automatically.
4. Complete QuerySet Support
You could filter, order, and aggregate using translated fields just like any other Django field:
Product.objects.language('en').filter(name__icontains='laptop').order_by('name')
Design Philosophy
Several principles guided hvad's development:
- Unobtrusive: Shouldn't require rethinking how you write Django applications
- Efficient: Performance should be comparable to non-translated models
- Reliable: Extensive test coverage (300+ test cases)
- Compatible: Work seamlessly with existing Django projects
Migration Path
One of hvad's strengths was easy migration from django-multilingual-ng, the previous popular solution. This made it practical for existing projects to adopt hvad without a complete rewrite.
Real-World Impact
django-hvad was adopted by numerous Django projects that needed multi-language support:
- E-commerce platforms serving multiple markets
- Content management systems
- SaaS applications with international customers
- Government and institutional websites
The project proved that you could build powerful abstractions while maintaining simplicity and performance.
Evolution and Legacy
After several years of active development and maintenance, I handed off the project to other maintainers. The project remained actively maintained through Django 1.11.
Eventually, the Django community converged around django-parler as the recommended translation solution, which built upon many of the concepts pioneered in hvad and nani while taking the implementation in new directions.
Technical Achievements
django-hvad demonstrated several important technical concepts:
Custom QuerySet Magic: Showed how to extend Django's ORM in powerful but intuitive ways
Translation Layer Design: Proved that translation frameworks don't need to be complex to be powerful
Test-Driven Development: Maintained reliability through comprehensive test coverage
API Design: Created an API that felt natural to Django developers
Lessons in Open Source
Building and maintaining django-hvad taught me important lessons about open source projects:
- Solve Real Problems: The best libraries emerge from actual needs, not theoretical exercises
- Standing on Shoulders: Forking django-nani gave us a foundation to build upon and explore different directions
- API Design Matters: A good API can make complex problems feel simple
- Community Building: Successful projects require more than code - they need documentation, examples, and responsive maintenance
- Know When to Let Go: Sometimes the best thing you can do for a project is hand it off to maintainers who can take it further
Why "hvad"?
The name "hvad" (Danish for "what") was chosen as a nod to my Danish heritage and as a playful reference to the question developers often ask: "what's the translation for this content?" The name stuck, and became part of the Django ecosystem's colorful naming tradition.
Lasting Impact
While django-hvad itself is no longer actively maintained, its influence lives on. The patterns and approaches it pioneered can be seen in modern Django translation frameworks. It proved that internationalization doesn't have to be painful and that good abstraction layers can make complex problems tractable.
For me, django-hvad represents an important lesson: the best tools are often invisible. They solve a hard problem so well that users barely notice they're there - they just get to focus on building their applications.
Credit
Thanks to Jonas Obrist for creating django-nani, which provided the foundation for hvad. The open source community thrives when we build upon each other's work.