开发者

Django south from MySQL to postgresql

I f开发者_高级运维irst started using MySQL in one of my apps and I am now thinking of moving from MySQL to PostgreSQL.

I have South installed for migrations. When I set up a new DB in postgres I successfully synced my apps and got to a complete halt in one of my last migrations.

> project:0056_auto__chg_field_project_project_length
Traceback (most recent call last):
  File "./manage.py", line 11, in <module>
    execute_manager(settings)
  File "/Users/ApPeL/.virtualenvs/fundedbyme.com/lib/python2.7/site-packages/django/core/management/__init__.py", line 438, in execute_manager
    utility.execute()
  File "/Users/ApPeL/.virtualenvs/fundedbyme.com/lib/python2.7/site-packages/django/core/management/__init__.py", line 379, in execute
    self.fetch_command(subcommand).run_from_argv(self.argv)
  File "/Users/ApPeL/.virtualenvs/fundedbyme.com/lib/python2.7/site-packages/django/core/management/base.py", line 191, in run_from_argv
    self.execute(*args, **options.__dict__)
  File "/Users/ApPeL/.virtualenvs/fundedbyme.com/lib/python2.7/site-packages/django/core/management/base.py", line 220, in execute
    output = self.handle(*args, **options)
  File "/Library/Python/2.7/site-packages/south/management/commands/migrate.py", line 105, in handle
    ignore_ghosts = ignore_ghosts,
  File "/Library/Python/2.7/site-packages/south/migration/__init__.py", line 191, in migrate_app
    success = migrator.migrate_many(target, workplan, database)
  File "/Library/Python/2.7/site-packages/south/migration/migrators.py", line 221, in migrate_many
    result = migrator.__class__.migrate_many(migrator, target, migrations, database)
  File "/Library/Python/2.7/site-packages/south/migration/migrators.py", line 292, in migrate_many
    result = self.migrate(migration, database)
  File "/Library/Python/2.7/site-packages/south/migration/migrators.py", line 125, in migrate
    result = self.run(migration)
  File "/Library/Python/2.7/site-packages/south/migration/migrators.py", line 99, in run
    return self.run_migration(migration)
  File "/Library/Python/2.7/site-packages/south/migration/migrators.py", line 81, in run_migration
    migration_function()
  File "/Library/Python/2.7/site-packages/south/migration/migrators.py", line 57, in <lambda>
    return (lambda: direction(orm))
  File "/Users/ApPeL/Sites/Django/fundedbyme/project/migrations/0056_auto__chg_field_project_project_length.py", line 12, in forwards
    db.alter_column('project_project', 'project_length', self.gf('django.db.models.fields.IntegerField')())
  File "/Library/Python/2.7/site-packages/south/db/generic.py", line 382, in alter_column
    flatten(values),
  File "/Library/Python/2.7/site-packages/south/db/generic.py", line 150, in execute
    cursor.execute(sql, params)
  File "/Users/ApPeL/.virtualenvs/fundedbyme.com/lib/python2.7/site-packages/django/db/backends/postgresql_psycopg2/base.py", line 44, in execute
    return self.cursor.execute(query, args)
django.db.utils.DatabaseError: column "project_length" cannot be cast to type integer

I am wondering if there is some workaround for this?


You current migration works that way:

  1. Alter column "project_length" to another type.

It is broken because you are making alter that is not supported by PostgreSQL.

You must fix your migration. You can change it to following migration (it will work, but probably can be done easier):

  1. Create another column project_length_tmp with type you want to project_length have and some default value.
  2. Make data migration from column project_length to project_lenght_tmp (see data migrations in south docs).
  3. Remove column project_length.
  4. Rename column project_length_tmp to project_length.

Kind complicated migration but it have two major strengths: 1. It will work on all databases. 2. It is compatible with your old migration, so you can just override old migration (change the file) and it will be fine.

Approach 2

Another approach to your problem would be just to remove all your migrations and start from scratch. If you have only single deployment of your project it will work fine for you.


You don't provide any details of the SQL being executed, but it seems unlikely that it's an ALTER TYPE failing - assuming the SQL is correct.

=> CREATE TABLE t (c_text text, c_date date, c_datearray date[]);
CREATE TABLE
=> INSERT INTO t VALUES ('abc','2011-01-02',ARRAY['2011-01-02'::date,'2011-02-03'::date]);
INSERT 0 1
=> ALTER TABLE t ALTER COLUMN c_text TYPE integer USING (length(c_text));
ALTER TABLE
=> ALTER TABLE t ALTER COLUMN c_date TYPE integer USING (c_date - '2001-01-01');
ALTER TABLE
=> ALTER TABLE t ALTER COLUMN c_datearray TYPE integer USING (array_upper(c_datearray, 1));
ALTER TABLE
=> SELECT * FROM t;
 c_text | c_date | c_datearray 
--------+--------+-------------
      3 |   3653 |           2
(1 row)

There's not much you can't do. I'm guessing it's incorrect SQL being generated from this Django module you are using.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜