শেষ মাইগ্রেশনটি কীভাবে ফিরিয়ে আনবেন?


446

আমি একটি মাইগ্রেশন করেছি যাতে একটি নতুন টেবিল যুক্ত হয়েছে এবং নতুন স্থানান্তর তৈরি না করে এটিকে ফিরিয়ে নিয়ে মাইগ্রেশন মুছতে চাই।

আমি এটা কিভাবে করব? শেষ মাইগ্রেশনটি ফিরিয়ে আনার জন্য কোন আদেশ আছে এবং তারপরে আমি কেবল স্থানান্তর ফাইলটি মুছতে পারি?

উত্তর:


794

আপনি পূর্ববর্তী স্থানান্তরিত স্থানান্তর করে ফিরে যেতে পারেন।

উদাহরণস্বরূপ, যদি আপনার শেষ দুটি স্থানান্তর হয়:

  • 0010_previous_migration
  • 0011_migration_to_revert

তাহলে আপনি কি করবেন:

./manage.py migrate my_app 0010_previous_migration 

তারপরে আপনি মাইগ্রেশন মুছতে পারেন 0011_migration_to_revert

আপনি যদি জ্যাঙ্গো 1.8+ ব্যবহার করছেন তবে আপনি সমস্ত স্থানান্তরের নাম প্রদর্শন করতে পারেন

./manage.py showmigrations my_app

কোনও অ্যাপ্লিকেশনের জন্য সমস্ত মাইগ্রেশন বিপরীত করতে, আপনি চালাতে পারেন:

./manage.py migrate my_app zero

7
আমি এই সমস্যার জন্য বহু উত্তর দেখেছি যা পুরানো এবং কেবল আর কাজ করে না। +1 কারণ এটি জাঙ্গো 1.8 এর সাথে কাজ করে।
অ্যালানএসই

2
যদি অ্যাপটিতে কেবল একটি মাইগ্রেশন ফাইল / প্রাথমিক মাইগ্রেশন থাকে। এবং আমার সেই প্রাথমিক স্থানান্তরণটি পূর্বাবস্থায়িত করতে হবে?
আদিয়াত মোবারক

37
migrateকমান্ড আপনাকে ব্যবহার করেন ./manage.py migrate my_app zeroঅ্যাপের জন্য সব মাইগ্রেশন unapply করতে।
আলাসডায়ার

4
কোনও কারণে, ./manage.py মাইগ্রেট my_app 0010_প্রিয়_ম্যাগগ্রেশন আমার পক্ষে কাজ করে না। সুতরাং আমি ./manage.py মাইগ্রেট my_app 0010 ব্যবহার করার চেষ্টা করেছি এবং এটি কার্যকর হয়েছে। জ্যাঙ্গো ১.৮ পুরো মাইগ্রেশনের নাম না নেওয়ার কোনও কারণ?
বরুণ ভার্মা

4
আপনি যতক্ষণ না আপনার আসল মাইগ্রেশন নামটি ব্যবহার করছেন এবং না '0010_previous_migration', আমি জানি না আপনি কেন এই আচরণটি দেখবেন।
আলাসদায়ের

36

আলাসদায়েরের উত্তরটি মৌলিক বিষয়গুলি অন্তর্ভুক্ত করে

  • আপনি যে মাইগ্রেশন চান তা সনাক্ত করুন ./manage.py showmigrations
  • migrate অ্যাপের নাম এবং মাইগ্রেশন নাম ব্যবহার করে

তবে এটি উল্লেখ করা উচিত যে সমস্ত মাইগ্রেশন বিপরীত হতে পারে না । জ্যাঙ্গোর বিপরীত করার কোনও নিয়ম না থাকলে এটি ঘটে। আপনি স্বয়ংক্রিয়ভাবে মাইগ্রেশন করেছেন এমন বেশিরভাগ পরিবর্তনের জন্য ./manage.py makemigrations, বিপরীতটি সম্ভব হবে। যাইহোক, কাস্টম স্ক্রিপ্টগুলির জন্য এখানে উদাহরণ হিসাবে বর্ণিত হিসাবে ফরোয়ার্ড এবং বিপরীত দুটি লেখা থাকতে হবে:

https://docs.djangoproject.com/en/1.9/ref/migration-operations/

কীভাবে কোনও অন-আপ বিপরীতে করবেন

যদি আপনার কোনও RunPythonঅপারেশন ছিল , তবে সম্ভবত আপনি কোনও যুক্তিসঙ্গতভাবে কঠোর বিপরীতমুখী স্ক্রিপ্ট না লিখে মাইগ্রেশনটি ব্যাকআপ করতে চান। ডক্স (উপরের লিঙ্ক) থেকে উদাহরণটিতে নিম্নোক্ত দ্রুত হ্যাকটি এটির অনুমতি দেয়, ডাটাবেসটিকে একই অবস্থায় রেখে যে মাইগ্রেশন প্রয়োগের পরে, এটি বিপরীত হওয়ার পরেও হয়েছিল।

# -*- coding: utf-8 -*-
from __future__ import unicode_literals

from django.db import migrations, models

def forwards_func(apps, schema_editor):
    # We get the model from the versioned app registry;
    # if we directly import it, it'll be the wrong version
    Country = apps.get_model("myapp", "Country")
    db_alias = schema_editor.connection.alias
    Country.objects.using(db_alias).bulk_create([
        Country(name="USA", code="us"),
        Country(name="France", code="fr"),
    ])

class Migration(migrations.Migration):

    dependencies = []

    operations = [
        migrations.RunPython(forwards_func, lambda apps, schema_editor: None),
    ]

এটি জাঙ্গো 1..৮, ১.৯ এর জন্য কাজ করে


আপডেট: উপরের স্নিপেটের lambda apps, schema_editor: Noneসাথে প্রতিস্থাপন করা এটির লেখার আরও ভাল উপায় migrations.RunPython.noop। এগুলি উভয়ই কার্যত একই জিনিস। (মন্তব্যে ক্রেডিট)


5
জ্যাঙ্গো ১.৮ এর পর থেকে, আপনাকে RunPython.noopএকটি ইনলাইন ল্যাম্বডা বা সমমানের পরিবর্তে ব্যবহার করা উচিত : ডকস.ডজ্যাঙ্গোপ্রজেক্ট /en/1.8/ref/migration-operations/…
চাঁদমাইজার

@ স্পুনমিজার উদাহরণটির বাক্য গঠনে আমার মনে হয় যে এটির মতো দেখাচ্ছে migrations.RunPython(forwards_func, migrations.RunPython.noop)। এটি কার্যকরীভাবে পরীক্ষা করা দরকার। এটি এর উত্তর বা সম্পাদনা হিসাবে এটি যুক্ত করা উচিত।
অ্যালানএসই

13

এখানে আমার সমাধানটি দেওয়া হয়েছে, যেহেতু আপনি যখন ব্যবহার করবেন তখন উপরের সমাধানটি ব্যবহার-কেসটি সত্যিই কভার করে না RunPython

আপনি ওআরএম এর মাধ্যমে টেবিলটি অ্যাক্সেস করতে পারবেন

from django.db.migrations.recorder import MigrationRecorder

>>> MigrationRecorder.Migration.objects.all()
>>> MigrationRecorder.Migration.objects.latest('id')
Out[5]: <Migration: Migration 0050_auto_20170603_1814 for model>
>>> MigrationRecorder.Migration.objects.latest('id').delete()
Out[4]: (1, {u'migrations.Migration': 1})

সুতরাং আপনি টেবিলগুলি জিজ্ঞাসা করতে পারেন এবং আপনার জন্য প্রাসঙ্গিক এন্ট্রি মুছতে পারেন। এইভাবে আপনি বিশদটি সংশোধন করতে পারেন। সঙ্গে RynPythonমাইগ্রেশন আপনার কাছে ডেটা আছে যা যোগ করা হয়েছিল / পরিবর্তন / মুছে যত্ন নেওয়া দরকার। উপরের উদাহরণটি কেবল প্রদর্শন করে, কীভাবে আপনি জ্যাং ওআরএম এর মাধ্যমে টেবিলটি অ্যাক্সেস করেন।


ফরেনকিজের সাথে একাধিক স্থানান্তর সহ নতুন মডেল তৈরি করার সময়, সমস্ত কিছু ভুল বলে উপলব্ধি করা এবং নতুন মডেলগুলি সহ কখনও কখনও একই মডেলের নাম বা একই সম্পর্কের নামগুলি সহ: ২-৩টি স্থানান্তরকে পুনরায় চালু করা ... এই সমাধানটি স্পষ্টতই বিজয়ী is আমার ত্রুটির বার্তা ছিল যেমন django.db.utils.ProgrammingError: relation "<relation name>" already existsআমি একটি migrate --fakeভুল করেছি, তাই আমি ফিরে যাওয়ার চেষ্টা করেছি, তখন আমি psycopg2.ProgrammingError: relation "<other <relation name>" does not existধন্যবাদ পেয়েছি
onekiloparsec

10

আপনি যা করতে পারেন তা হ'ল ম্যানুয়ালি তৈরি টেবিলটি মুছুন delete

সেই সাথে আপনাকে সেই নির্দিষ্ট স্থানান্তর ফাইলটি মুছতে হবে। এছাড়াও, আপনাকে জ্যাঙ্গো-মাইগ্রেশন সারণিতে সেই নির্দিষ্ট প্রবেশটি মুছতে হবে (সম্ভবত আপনার ক্ষেত্রে এটি সর্বশেষ) যা সেই নির্দিষ্ট স্থানান্তরের সাথে সম্পর্কিত।


এক্ষেত্রে সতর্ক থাকুন - আপনার পর্যাপ্ত হতে ডিবি যাচাই করতে বাধ্য।
সাওওমির লেনার্ট

4
আমি খুব সাবধানে যোগ করা হবে। পোস্টগ্র্রেসে আপনি প্রচুর জিনিস ভাঙতে পারেন, উদাহরণস্বরূপ সীমাবদ্ধতা।
joedborg

9

বিবর্তনের পরে পর্যন্ত মাইগ্রেশন ফাইলটি মুছবেন না। আমি এই ভুলটি করেছিলাম এবং মাইগ্রেশন ফাইল ছাড়াই ডাটাবেসগুলি কী কী অপসারণ করতে পারে তা জানত না।

python manage.py showmigrations
python manage.py migrate {app name from show migrations} {00##_migration file.py}

মাইগ্রেশন ফাইল মুছুন। পছন্দসই মাইগ্রেশনটি আপনার মডেলগুলিতে আসার পরে ...

python manage.py makemigrations
python manage.py migrate

8

আমি এটি 1.9.1 এ করেছি (তৈরি হওয়া সর্বশেষ বা সর্বশেষতম স্থানান্তর মুছতে):

  1. rm <appname>/migrations/<migration #>*

    উদাহরণ: rm myapp/migrations/0011*

  2. ডাটাবেসে লগ ইন এবং এই এসকিউএল চালিত (এই উদাহরণে পোস্টগ্রিজ)

    delete from django_migrations where name like '0011%';

আমি তখন নতুন মাইগ্রেশন তৈরি করতে সক্ষম হয়েছি যা সবেমাত্র মুছে ফেলা মাইগ্রেশন নম্বর দিয়ে শুরু হয়েছিল (এই ক্ষেত্রে, 11)


1
+1 যদিও এটি কাজ করবে, আপনাকে শেষ উপায় হিসাবে এইভাবে সংরক্ষণ করতে হবে। এছাড়াও আপনার কলাম / টেবিলগুলি সম্পাদনা / ড্রপ করতে হবে যার মধ্যে সমস্যাযুক্ত স্থানান্তর অবদান রয়েছে।
নেহেম

ভাল পয়েন্ট - আমি মাইগ্রেশন তৈরি করার সময় এটি ব্যবহার করেছি তবে "./manage.py মাইগ্রেট"
চালাইনি

3

এই উত্তর অনুরূপ ক্ষেত্রেগুলির ক্ষেত্রে যদি আলাসদায়ের শীর্ষ উত্তরটি সহায়তা না করে । (উদাহরণস্বরূপ যদি অযাচিত মাইগ্রেশন প্রতিটি নতুন মাইগ্রেশন দিয়ে শীঘ্রই আবার তৈরি করা হয় বা এটি যদি বড় মাইগ্রেশনে থাকে তবে যেটি ফেরানো যায় না বা টেবিলটি ম্যানুয়ালি সরানো হয়েছে))

... মাইগ্রেশন মুছবেন, নতুন মাইগ্রেশন তৈরি না করে?

টিএল; ডিআর : আপনি কয়েকটি শেষ রিভার্টেড (বিভ্রান্ত) মাইগ্রেশন মুছতে পারেন এবং মডেলগুলি ঠিক করার পরে একটি নতুন তৈরি করতে পারেন । মাইগ্রেট কমান্ড দ্বারা কোনও সারণী তৈরি না করতে এটি কনফিগার করতে আপনি অন্যান্য পদ্ধতিগুলিও ব্যবহার করতে পারেনশেষ মাইগ্রেশনটি তৈরি করতে হবে যাতে এটি বর্তমান মডেলগুলির সাথে মেলে


যে মডেলটির উপস্থিতি থাকতে হবে এমন কোনও মডেলটির জন্য কেউ কোনও টেবিল তৈরি করতে চান না এমন ক্ষেত্রে :

ক) কোনও মেশিনে কোনও শর্তাবলীর কোনও শর্ত নেই এবং কোনও শর্ত নেই such

  • কখন: এটি অন্যান্য মডেলের মডেল উত্তরাধিকারের জন্য তৈরি একটি বেস মডেল।
  • সমাধান: সেট করুনclass Meta: abstract = True

খ) সারণীটি খুব কম, অন্য কোনও কিছু দ্বারা বা ম্যানুয়ালি একটি বিশেষ উপায়ে তৈরি করা হয়েছে।

  • সমাধান: ব্যবহার class Meta: managed = False
    মাইগ্রেশন তৈরি হয়, তবে কখনও পরীক্ষিত হয় না। মাইগ্রেশন ফাইলটি গুরুত্বপূর্ণ, অন্যথায় প্রজননযোগ্য প্রাথমিক অবস্থা থেকে শুরু করে ডাটাবেস পরীক্ষা চালানো যায় না।

গ) টেবিলটি কেবলমাত্র কিছু মেশিনে ব্যবহৃত হয় (যেমন উন্নয়নের ক্ষেত্রে)।

  • সমাধান: মডেলটিকে একটি নতুন অ্যাপ্লিকেশনে সরান যা কেবলমাত্র বিশেষ শর্তে INSTALLED_APPS এ যুক্ত হয় বা শর্তসাপেক্ষ ব্যবহার করে class Meta: managed = some_switch

২) প্রকল্পটি একাধিক ডাটাবেস ব্যবহার করেsettings.DATABASES

  • সমাধান: সারণীটি কোথায় তৈরি করা উচিত এবং কোথায় নয় তা পৃথক করার জন্য পদ্ধতি সহ একটি ডাটাবেস রাউটার লিখুন allow_migrate

জেঙ্গো ১.৯+ (এবং শুধুমাত্র বি, সি, ডি জ্যাঙ্গো ১.৮ এর ক্ষেত্রে) সহ সমস্ত ক্ষেত্রে এ), বি), সি), ডি) মাইগ্রেশন তৈরি করা হয়েছে, তবে কেবলমাত্র উপযুক্ত ক্ষেত্রে ডাটাবেসে প্রয়োগ করা হয়েছে বা কখনও না হলে তাই প্রয়োজন। জ্যাঙ্গো ১.৮ থেকে পরীক্ষা চালানোর জন্য মাইগ্রেশনগুলি প্রয়োজনীয় ছিল। পরিচালিত / অপরিশোধিত মডেলগুলির মধ্যে ফরেনকি তৈরি করা বা মডেলটিকে পরিচালিত = সত্য পরে তৈরি করতে, জাজানো ১.৯++ তে জালযুক্ত মডেলগুলির জন্য এমনকি পুরো প্রাসঙ্গিক বর্তমান অবস্থা মাইগ্রেশন দ্বারা রেকর্ড করা হয়েছে। (এই প্রশ্নটি জ্যাঙ্গো ১.৮ এর সময় লেখা হয়েছে। এখানে সমস্ত কিছু 1.8 থেকে বর্তমান 2.2 এর মধ্যে সংস্করণের জন্য বৈধ হওয়া উচিত)

যদি শেষ মাইগ্রেশনটি (যদি) সহজেই ফেরানো যায় না তবে সাবধানতার সাথে (ডাটাবেস ব্যাকআপের পরে) একটি জাল রিভার্ট করা সম্ভব ./manage.py migrate --fake my_app 0010_previous_migration , টেবিলটি ম্যানুয়ালি মুছে ফেলা সম্ভব।

প্রয়োজনে স্থির মডেল থেকে একটি নির্দিষ্ট স্থানান্তর তৈরি করুন এবং ডাটাবেস কাঠামো পরিবর্তন না করেই এটি প্রয়োগ করুন ./manage.py migrate --fake my_app 0011_fixed_migration


3

মাইগ্রেশনটি ফিরিয়ে আনার সময় যদি আপনি সমস্যার মুখোমুখি হন এবং কোনওভাবে এটিকে গোলমাল করেছেন তবে আপনি fakeস্থানান্তর করতে পারেন ।

./manage.py migrate <name> --ignore-ghost-migrations --merge --fake

জন্য জ্যাঙ্গো সংস্করণ <1.7 এই এন্ট্রি তৈরি করবে south_migrationhistoryটেবিল, আপনি যে এন্ট্রি মোছার প্রয়োজন হবে।

এখন আপনি সহজেই মাইগ্রেশন ফিরিয়ে দিতে সক্ষম হবেন।

PS: আমি অনেক সময় আটকে ছিলাম এবং ভুয়া মাইগ্রেশন করছিলাম এবং তারপরে ফিরে যাওয়া আমাকে সাহায্য করেছিল।


1
এই উত্তরটি জাজানো <1.7 এর জন্য।
hynekcer
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.