Миграция обновлений набора запросов Django - PullRequest
1 голос
/ 15 октября 2019

Я пытаюсь оптимизировать миграцию, она занимает слишком много времени, около 15 минут каждый раз, когда вы пытаетесь ее запустить, потому что в этой таблице много данных. Это старая база данных с датами типа «14102019» (% d% m% Y) в виде строки и их необходимо преобразовать в DateField. Я создал DateField для обоих.

База данных - MySQL.

dtobito и dtnasc - это старые строки, которые необходимо преобразовать

data_obito и data_nasc это новые поля DateFields

Что работает (очень медленно):

def date_to_datefield(apps, schema_editor):
    Obitos = apps.get_model('core', 'Obitos')

    for obito in Obitos.objects.all():
        if obito.dtnasc and obito.dtnasc != '':
            obito.data_nasc = datetime.strptime(obito.dtnasc, '%d%m%Y')
        if obito.dtobito and obito.dtobito != '':
            obito.data_obito = datetime.strptime(obito.dtobito, '%d%m%Y')
        obito.save()

Что не работает:

Obitos.objects.update(
    data_nasc=datetime.strptime(F('dtnasc'), '%d%m%Y'),
    data_obito=datetime.strptime(F('dtobito'), '%d%m%Y')
)

Что может работать, но я нене знаю как:

Obitos.objects.raw("""
        UPDATE obitos new,
        (
            SELECT 
                STR_TO_DATE(dtnasc, '%d%m%Y') AS dtnasc,
                STR_TO_DATE(dtobito, '%d%m%Y') AS dtobito,
            FROM obitos
        ) old
        SET new.data_nasc = old.dtnasc
        SET new.data_obtio = old.dtobito
    """)

1 Ответ

0 голосов
/ 15 октября 2019

Попробуйте использовать bulk_update:

def date_to_datefield(apps, schema_editor):
    Obitos = apps.get_model('core', 'Obitos')

    objs = []

    def to_date_object(date_string):
        return datetime.strptime(date_string, '%d%m%Y')

    for obito in Obitos.objects.all():
        updated = False
        if obito.dtnasc:
            obito.data_nasc = to_date_object(obito.dtnasc)
            updated = True
        if obito.dtobito:
            obito.data_obito = to_date_object(obito.dtobito)
            updated = True
        if updated:
            objs.append(obito)

    if objs:
        Obitos.objects.bulk_update(objs, ['data_nasc', 'data_obito'])
...