﻿id	summary	reporter	owner	description	type	status	component	version	severity	resolution	keywords	cc	stage	has_patch	needs_docs	needs_tests	needs_better_patch	easy	ui_ux
31245	CharField doesn't accept bytestrings in default parameter in Django 2.2.	Tony S Yu	nobody	"= System details =

- Migrations generated in Django 1.11.28 + Python 2.7
- Migrations run on Django 2.2.10 + Python 3.6
- Database backend: `django.db.backends.mysql`

= Summary =
We recently upgraded an app from Django 1.11 to 2.2. When a developer on the team attempted to re-install the app from scratch some time later, they ran into the following exception:
{{{
django.db.utils.OperationalError: (1067, ""Invalid default value for '<charfield>'"")
}}}
where the `<charfield>` had **`choices` containing //bytestring// db values and //unicode// string labels** (i.e. `choices=[(<bytes>, <str>),...]`)

I reproduced this in isolation using a modified version of [https://docs.djangoproject.com/en/3.0/ref/models/fields/#choices the Students example from the docs]:  
{{{
#!python
class Student(models.Model):

    name = models.CharField(max_length=300)

    FRESHMAN = 'FR'
    SOPHOMORE = 'SO'
    JUNIOR = 'JR'
    SENIOR = 'SR'
    GRADUATE = 'GR'
    YEAR_IN_SCHOOL_CHOICES = [
        (FRESHMAN, u'Freshman'),
        (SOPHOMORE, u'Sophomore'),
        (JUNIOR, u'Junior'),
        (SENIOR, u'Senior'),
        (GRADUATE, u'Graduate'),
    ]
    year_in_school = models.CharField(
        max_length=2,
        choices=YEAR_IN_SCHOOL_CHOICES,
        default=FRESHMAN,
    )
}}}
The main modification is that the `choices` labels are explicitly unicode, but the db values are unprefixed strings (bytestrings in Python 2, unicode in Python 3). (Note that the actual code generated choices from an `Enum`, which when combined with Python 2 using unicode literals causes bytestring db values and unicode labels used above.)

In practice, I wasn't able to reproduce the error without splitting up the `year_in_school` migration from the model creation. (The `name` field was added to the model to create an initial migration.)

Running the `year_in_school` migration using Django 1.11.28 (on Python 2.7) generates the following migration:
{{{
#!python
# -*- coding: utf-8 -*-
# Generated by Django 1.11.28 on 2020-02-07 17:07
from __future__ import unicode_literals

from django.db import migrations, models


class Migration(migrations.Migration):

    dependencies = [
        ('djangodebug', '0001_initial'),
    ]

    operations = [
        migrations.AddField(
            model_name='student',
            name='year_in_school',
            field=models.CharField(choices=[(b'FR', 'Freshman'), (b'SO', 'Sophomore'), (b'JR', 'Junior'), (b'SR', 'Senior'), (b'GR', 'Graduate')], default=b'FR', max_length=2),
        ),
    ]
}}}
**Running that migration in Django 1.11 (on either Python 2 or 3) works fine. Running the migration in Django 2.2 throws the following error**:
{{{
django.db.utils.OperationalError: (1067, ""Invalid default value for 'year_in_school'"")
}}}

= Additional Notes =

== Workarounds ==
- Downgrade to Django 1.11 and run migrations, then revert to Django 2.2
- Manually modify migration files to use unicode strings (i.e. remove `b` prefix from strings)"	Bug	closed	Database layer (models, ORM)	2.2	Normal	invalid			Unreviewed	0	0	0	0	0	0
