সংক্ষিপ্ত সংস্করণ
আপনার সরাসরি ডেটা মাইগ্রেশনে পরিচালনা কমান্ড ব্যবহার করা উচিত নয়loaddata
।
from django.db import migrations
from django.core.management import call_command
def load_fixture(apps, schema_editor):
call_command('loaddata', 'your_data.json', app_label='yourapp')
class Migration(migrations.Migration):
dependencies = [
]
operations = [
migrations.RunPython(load_fixture),
]
দীর্ঘ সংস্করণ
loaddata
সদ্ব্যবহার django.core.serializers.python.Deserializer
যা মাইগ্রেশন মধ্যে ঐতিহাসিক তথ্য deserialize সবচেয়ে আপ-টু-ডেট মডেল ব্যবহার করে। এটি ভুল আচরণ।
উদাহরণস্বরূপ, মনে করা হয় যে কোনও ডেটা মাইগ্রেশন রয়েছে যা loaddata
কোনও ফিক্সচার থেকে ডেটা লোড করার জন্য ম্যানেজমেন্ট কমান্ড ব্যবহার করে এবং এটি ইতিমধ্যে আপনার বিকাশের পরিবেশে প্রয়োগ করা হয়েছে।
পরে, আপনি সংশ্লিষ্ট মডেলটিতে একটি নতুন প্রয়োজনীয় ক্ষেত্র যুক্ত করার সিদ্ধান্ত নিয়েছেন, তাই আপনি এটি করেন এবং আপনার আপডেট হওয়া মডেলের বিপরীতে একটি নতুন মাইগ্রেশন করেন (এবং সম্ভবত ./manage.py makemigrations
আপনাকে অনুরোধ জানানো হলে নতুন ক্ষেত্রে একটি এক-অফ মূল্য প্রদান করবেন )।
আপনি পরবর্তী স্থানান্তর চালান, এবং সবকিছু ঠিক আছে।
অবশেষে, আপনি আপনার জাজানো অ্যাপ্লিকেশনটি বিকাশ সম্পন্ন করেছেন এবং আপনি এটি প্রোডাকশন সার্ভারে স্থাপন করেন। উত্পাদনের পরিবেশের উপর স্ক্র্যাচ থেকে পুরো মাইগ্রেশন চালানোর এখন সময়।
তবে ডেটা মাইগ্রেশন ব্যর্থ হয় । এর কারণ হ'ল loaddata
কমান্ড থেকে ডিসরিয়ালাইজড মডেল , যা বর্তমান কোডটি উপস্থাপন করে, আপনার যুক্ত হওয়া নতুন প্রয়োজনীয় ক্ষেত্রের খালি ডেটা দিয়ে সংরক্ষণ করা যাবে না । মূল ফিক্সিং এর জন্য প্রয়োজনীয় ডেটার অভাব রয়েছে!
আপনি যদি নতুন ক্ষেত্রের জন্য প্রয়োজনীয় ডেটা সহ ফিক্সচারটি আপডেট করেন তবে ডেটা মাইগ্রেশনটি এখনও ব্যর্থ হয় । যখন ডেটা মাইগ্রেশন চলমান থাকে, পরবর্তী মাইগ্রেশন যা ডাটাবেসে সংশ্লিষ্ট কলাম যুক্ত করে তা এখনও প্রয়োগ হয় না। আপনি কোনও কলামে ডেটা সংরক্ষণ করতে পারবেন না যা বিদ্যমান নেই!
উপসংহার: একটি ডেটা মাইগ্রেশনে,loaddata
কমান্ডটি মডেল এবং ডাটাবেসের মধ্যে সম্ভাব্য অসামঞ্জস্যতার পরিচয় দেয়। আপনার অবশ্যইএটি কোনও ডেটা মাইগ্রেশনে সরাসরি ব্যবহার করাউচিত নয় ।
সমাধান
loaddata
কমান্ডটি django.core.serializers.python._get_model
কোনও ফিক্সিং থেকে সংশ্লিষ্ট মডেলটি পেতে ফাংশনের উপর নির্ভর করে , যা কোনও মডেলের সর্বাধিক আপ-টু-ডেট সংস্করণ প্রদান করবে। আমাদের এটি বানর-প্যাচ করা দরকার যাতে এটি historicalতিহাসিক মডেলটি পায়।
(নিম্নলিখিত কোড জ্যাঙ্গো 1.8.x এর জন্য কাজ করে)
from django.db import migrations
from django.core.serializers import base, python
from django.core.management import call_command
def load_fixture(apps, schema_editor):
old_get_model = python._get_model
def _get_model(model_identifier):
try:
return apps.get_model(model_identifier)
except (LookupError, TypeError):
raise base.DeserializationError("Invalid model identifier: '%s'" % model_identifier)
python._get_model = _get_model
try:
call_command('loaddata', 'your_data.json', app_label='yourapp')
finally:
python._get_model = old_get_model
class Migration(migrations.Migration):
dependencies = [
]
operations = [
migrations.RunPython(load_fixture),
]