Django South - la tabella esiste già


188

Sto cercando di iniziare con South. Avevo un database esistente e ho aggiunto South ( syncdb, schemamigration --initial).

Quindi, ho aggiornato models.pyper aggiungere un campo ed eseguito ./manage.py schemamigration myapp --auto. Sembrava trovare il campo e ha detto che avrei potuto applicarlo con ./manage.py migrate myapp. Ma farlo ha dato l'errore:

django.db.utils.DatabaseError: table "myapp_tablename" already exists

tablenameè la prima tabella elencata in models.py.

Sto correndo Django 1.2, a sud 0.7

Risposte:


311

poiché hai già creato le tabelle nel database, devi solo eseguire la migrazione iniziale come falsa

./manage.py migrate myapp --fake

assicurarsi che lo schema dei modelli sia uguale allo schema delle tabelle nel database.


1
Capito grazie. In realtà è migrare e non schemamigrazione, ma la tua risposta mi ha portato nella giusta direzione.
Steve,

1
il mio errore ha appena copiato il comando da OP, comando corretto ./manage.py migrate myapp --fake
Ashok

Questa soluzione non ha risolto il problema nel mio caso. Non ho modificato il database e ho bloccato alcune visualizzazioni perché il campo non era stato creato sul tavolo. Ho dovuto commentare la nuova proprietà, migrare di nuovo con falso per ristabilire tutto, e la seconda volta che ho provato ha funzionato che ancora non capisco ... :)
Mc-

1
@Ashok forse dovresti anche specificare che dobbiamo rifare un schemamigrationprima migratenel caso in cui abbiamo già apportato modifiche prima dell'ultimo schemamigration.
Pierre de LESPINAY,

3
Questo non mi ha aiutato. Avevo già una tabella nel mio database e, dopo aver simulato la migrazione, non c'era modo di aggiungere altre tabelle contraffatte. Ho dovuto abbandonare tutti i tavoli e ricominciare da capo.
Shailen,

41

Anche se la tabella "myapp_tablename" esiste già un errore smette di sollevare dopo che ho fatto ./manage.py migrare myapp --fake, DatabaseError non mostra tale colonna: myapp_mymodel.added_field.

Ho esattamente lo stesso problema!

1.Controllare innanzitutto il numero di migrazione che sta causando questo. Supponiamo che sia: 0010.

2.È necessario:

./manage.py schemamigration myapp --add-field MyModel.added_field
./manage.py migrate myapp

se manca più di un campo, è necessario ripeterlo per ciascun campo.

3.Ora atterri con un sacco di nuove migrazioni, quindi rimuovi i loro file da myapp / migrations (0011 e oltre se hai bisogno di aggiungere più campi).

4. Esegui questo:

./manage.py migrate myapp 0010

Ora prova ./manage.py migrare myapp

Se non fallisce sei pronto. Doppio controllo se non manca un campo.

MODIFICARE:

Questo problema può verificarsi anche quando si dispone di un database di produzione per il quale si installa South e la prima migrazione iniziale creata in un altro ambiente duplica ciò che già si possiede nel proprio database. La soluzione è molto più semplice qui:

  1. Finta la prima migrazione:

    ./manage migrate myapp 0001 --fake

  2. Rotola con il resto delle migrazioni:

    ./manage migrate myapp


10

Quando ho riscontrato questo errore, aveva una causa diversa.

Nel mio caso South aveva in qualche modo lasciato nel mio DB una tabella vuota temporanea, che viene utilizzata in _remake_table () . Probabilmente avevo interrotto una migrazione in un modo che non avrei dovuto. In ogni caso, ogni successiva nuova migrazione, quando chiamato _remake_table (), è stato gettando l'errore sqlite3.pypysqlite2.dbapi2.OperationalError: table "_south_new_myapp_mymodel" already exists, poiché ha già esiste e non doveva essere lì.

La piccola novità mi sembrò strana, così sfogliai il mio DB, vidi il tavolo _south_new_myapp_mymodel, mi grattai la testa, guardai la fonte di South , decisi che era spazzatura, lasciò cadere il tavolo e tutto andò bene.


Questo è quello che ho visto, e se l'avessi trovato, mi avrebbe risparmiato mezz'ora di mal di cervello. Abbastanza spiacevole, ma si tratta di tabelle di migrazione temporanee e vengono lasciate in giro durante una migrazione non riuscita, probabilmente a scopo di ispezione. Il mio si è verificato a causa di un problema di integrità del database durante il tentativo di migrazione.
Danny Staple,

Questo deve essere più in alto! Se stai usando un db senza transazioni di schema, questo può succedere abbastanza facilmente
Yuji 'Tomita' Tomita

2

Se hai problemi con i tuoi modelli che non corrispondono al tuo database, come @pielgrzym, e vuoi migrare automaticamente il database in modo che corrisponda all'ultimo file models.py (e cancellare tutti i dati che non verranno ricreati dalle fixture durante migrate):

manage.py schemamigration myapp --initial
manage.py migrate myapp --fake
manage.py migrate myapp zero
manage.py migrate myapp

Questo eliminerà e ricrea solo le tabelle del database esistenti nella tua ultima models.py dei file, in modo da avere le tabelle della spazzatura nel database precedenti syncdbs o migrates. Per sbarazzarsi di quelli, precedere tutte queste migrazioni con:

manage.py sqlclear myapp | manage.py sqlshell

E se questo lascia ancora un po 'di CRUFT nel tuo database, dovrai fare un inspectdbe creare il models.pyfile da quello (per le tabelle e l'app che vuoi cancellare) prima di fare il sqlcleare poi ripristinare i tuoi modelli originali. creando la --initialmigrazione e migrando verso di essa. Tutto questo per evitare di perdere tempo con il particolare sapore di SQL di cui il tuo database ha bisogno.


1

Perform these steps in order may help you:

1) python manage.py schemamigration apps.appname --initial

Il passaggio precedente crea la cartella di migrazione come predefinita.

2) python manage.py migrare apps.appname --fake

genera una migrazione falsa.

3) python manage.py schemamigration apps.appname --auto

Quindi puoi aggiungere campi come desideri ed eseguire il comando sopra.

4) python manage.py migra apps.appname


1

Se disponi di un database e un'app esistenti, puoi utilizzare il comando di conversione sud

./manage.py convert_to_south myapp

Questo deve essere applicato prima di apportare modifiche a ciò che è già nel database.

Il comando convert_to_south funziona esclusivamente sul primo computer su cui lo si esegue. Dopo aver eseguito il commit delle migrazioni iniziali effettuate nel tuo VCS, dovrai eseguire ./manage.py migrate myapp 0001 --fakesu ogni macchina che ha una copia della base di codice (assicurati prima che siano aggiornati con i modelli e lo schema). rif: http://south.readthedocs.org/en/latest/convertinganapp.html


0

Come soluzione temporanea, è possibile commentare la creazione della tabella nello script di migrazione.

class Migration(migrations.Migration):

    dependencies = [
        (...)
    ]

    operations = [
        #migrations.CreateModel(
        #    name='TABLE',
        #    fields=[
        #            ....
        #            ....
        #    ],
        #),
        ....
        ....

O

Se la tabella esistente non contiene righe (vuote), quindi considerare di eliminare la tabella come di seguito. (Questa correzione è consigliata solo se la tabella non contiene righe) . Assicurarsi inoltre che questa operazione prima dell'operazione createModel.

class Migration(migrations.Migration):

    dependencies = [
        (...),
    ]

    operations = [
        migrations.RunSQL("DROP TABLE myapp_tablename;")
    ]

0

Un'altra soluzione (forse una soluzione temporanea).

$ python manage.py sqlmigrate APP_NAME MIGRATION_NAME

per esempio.,.

$ python manage.py sqlmigrate users 0029_auto_20170310_1117

Questo elencherà tutte le migrazioni nelle query sql non elaborate. È possibile selezionare le query che si desidera eseguire evitando la parte che crea la tabella esistente

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.