본문 바로가기
Programming/Django

🛠 Django Admin 설정 중 FieldError: username 오류 해결기 (TDD 기반 개발)

by Mandy's 2025. 8. 6.

✨ 목차

  1. 프로젝트 상황
  2. TDD 방식으로 Admin 페이지 테스트 작성
  3. 발생한 오류 분석
  4. 원인: 커스텀 User 모델과 Django 기본 Admin의 충돌
  5. 해결 방법: UserAdmin 커스터마이징
  6. 마무리하며

1. 프로젝트 상황

현재 Django 심화 강의를 들으며 TDD 방식으로 프로젝트를 구성하고 있습니다.
관리자(Admin) 페이지를 세팅하는 단계에서 다음과 같은 테스트 코드를 작성했습니다.

# core/tests/test_admin.py

class AdminSiteTests(TestCase):
    def setUp(self):
        self.client = Client()
        self.admin_user = get_user_model().objects.create_superuser(
            email='admin@example.com',
            password='testpass123',
        )
        self.client.force_login(self.admin_user)
        self.user = get_user_model().objects.create_user(
            email='user@example.com',
            password='testpass123',
            name='Test User'
        )

    def test_user_list(self):
        url = reverse('admin:core_user_changelist')
        res = self.client.get(url)
        self.assertContains(res, self.user.name)
        self.assertContains(res, self.user.email)

    def test_edit_user_page(self):
        url = reverse('admin:core_user_change', args=[self.user.id])
        res = self.client.get(url)
        self.assertEqual(res.status_code, 200)

    def test_create_user_page(self):
        url = reverse('admin:core_user_add')
        res = self.client.get(url)
        self.assertEqual(res.status_code, 200)

2. TDD 기반 개발 중 발생한 에러

테스트를 실행하자, 모든 테스트가 통과하지는 않았습니다.

python manage.py test

다음과 같은 에러가 발생했죠:

FieldError: Unknown field(s) (username) specified for User.

3. 오류 원인 분석

이 에러 메시지는 Django의 admin.py에 등록한 UserAdmin 클래스가 존재하지 않는 필드 username을 사용하고 있다는 것을 뜻합니다.

그런데 저는 AbstractBaseUser를 상속받은 커스텀 유저 모델을 사용 중이고,
이 모델은 email을 유일한 식별자로 사용하도록 설계했습니다. 즉, username 필드는 애초에 존재하지 않습니다.

하지만 Django의 기본 UserAdmin은 username, first_name, last_name 등을 자동으로 참조하게 되어 있어 충돌이 발생한 것입니다.


4. 원인 요약

  • ✅ 나는 email을 아이디로 사용하는 커스텀 User 모델을 만들었음
  • ❌ 그런데 기본 UserAdmin은 여전히 username을 포함한 필드를 참조함
  • ⚠ 따라서 admin:core_user_add 페이지 (유저 생성 페이지) 테스트에서 오류 발생

5. 해결 방법 – UserAdmin 커스터마이징

admin.py에서 UserAdmin 클래스를 오버라이딩해서 username을 완전히 제거해야 합니다.
또한, add_fieldsets도 반드시 명시해줘야 합니다. 안 그러면 user 생성 페이지에서 다시 기본 필드셋을 참조해 에러가 납니다.

# core/admin.py

from django.contrib import admin
from django.contrib.auth.admin import UserAdmin as BaseUserAdmin
from django.utils.translation import gettext_lazy as _
from core import models

class UserAdmin(BaseUserAdmin):
    """Define the admin pages for users."""
    ordering = ['id']
    list_display = ['email', 'name']
    fieldsets = (
        (None, {'fields': ('email', 'password')}),
        (_('Permissions'), {
            'fields': (
                'is_active',
                'is_staff',
                'is_superuser',
            )
        }),
        (_('Important dates'), {'fields': ('last_login',)}),
    )
    add_fieldsets = (
        (None, {
            'classes': ('wide',),
            'fields': ('email', 'password1', 'password2'),
        }),
    )
    readonly_fields = ['last_login']

admin.site.register(models.User, UserAdmin)

이렇게 설정한 후 다시 테스트를 실행하면... 🎉

OK

성공적으로 모든 테스트가 통과합니다.


6. 마무리하며

TDD 방식으로 개발할 때의 장점은 문제가 생겼을 때 빠르게 탐지할 수 있다는 점입니다.
이번 오류도 미리 작성한 테스트 덕분에 admin 페이지가 잘못 설정된 사실을 빠르게 알 수 있었습니다.

또한, 커스텀 유저 모델을 쓸 때는 Django 기본 Admin 설정을 반드시 직접 커스터마이징해야 한다는 점도 배웠습니다.

앞으로도 TDD 기반으로 차근차근 개발하면서, 이런 시행착오들을 기록해보려 합니다.
도움이 되셨다면 댓글이나 공감 부탁드립니다 🙌