migrations.RunPython可以运行任意python代码吗?

时间:2015-07-02 19:14:06

标签: python django django-migrations

我希望在迁移结束时包含许多原始SQL文件(函数,触发器......)的处理。

我想写我的own Special operation,但我已经被告知要使用django.db.migrations.RunPython()命令,并在被调用的函数中放入一些django.db.migrations.RunSQL()命令。

由于RunPython()采用可调用的2个实例(一个App和一个SchemaEditor),我非常怀疑(我稍微查看了一下)我可以用纯python代码调用一个函数,看起来它只能执行ORM操作。我应该在RunPython中使用execute_from_command_line()吗?或者这种注定要失败的方式?或做得不好?

from __future__ import unicode_literals
from django.db import migrations

def load_sql(apps, schema_editor):

    from os.path import normpath, dirname, isfile, join
    from os import listdir

    sql_folder_path = '/backoffice/sql/'

    def load_raw_sql(folder_inside):
        folder_path = join(sql_folder_path, folder_inside)
        sql_files = [join(folder_path, f) for f in listdir(folder_path) if isfile(join(folder_path, f))]
        for sql_file in sql_files:
            with open(sql_file, 'r') as g:
                migrations.RunSQL(g.read())

    folders = ['functions', 'index', 'triggers']

    for folder in folders:
        load_raw_sql(folder)


class Migration(migrations.Migration):
    dependencies = [
        ('app1', '0001_squashed_0018_auto_20150616_0708'),
    ]

    operations = [
        migrations.RunPython(load_sql),
    ]

我们正在使用PostGreSQL。 提前感谢您的回答。

2 个答案:

答案 0 :(得分:3)

我认为很明显,一个名为RunPython的操作可以运行python代码,但简短的回答是肯定的,你可以在RunPython操作中做任何你想做的事情。

要考虑的主要问题是,您编写的代码需要在将来继续工作(或者直到您压缩迁移),因为每次运行migratemakemigrations时,所有以前的迁移都需要用于导出数据库的当前状态。

答案 1 :(得分:1)

django.db.migration.RunPython可以接受任何python代码。 这里的问题是我试图在RunPython()调用中使用RunSQL(),这似乎不适用于我的情况,因为我没有提供应用程序和架构编辑器。 感谢光标,我设法运行我的一批SQL文件,并在我的callable中写道:

from django.db import migrations
cursor = connections['default'].cursor()
sql = "FOO;"
cursor.execute(sql)