একাধিক পাস সহ কোর ডেটা মাইগ্রেশনের উদাহরণ বা ব্যাখ্যা?


85

আমার আইফোন অ্যাপ্লিকেশনটিকে এর মূল ডেটা স্টোরটি স্থানান্তর করতে হবে এবং কিছু ডেটাবেস বেশ বড়। অ্যাপলের ডকুমেন্টেশন মেমরির ব্যবহার হ্রাস করতে ডেটা মাইগ্রেট করতে "একাধিক পাস" ব্যবহার করার পরামর্শ দেয়। তবে ডকুমেন্টেশন খুব সীমাবদ্ধ এবং কীভাবে আসলে এটি করা যায় তা খুব ভালভাবে ব্যাখ্যা করে না। কেউ আমাকে একটি ভাল উদাহরণের দিকে নির্দেশ করতে পারে, বা কীভাবে এটি এড়াতে পারে তার প্রক্রিয়াটি বিশদভাবে ব্যাখ্যা করতে পারে?


আপনি কি আসলে স্মৃতি সমস্যা চালিয়েছেন? আপনার মাইগ্রেশন লাইটওয়েট নাকি এনএসমিগ্রেশন ম্যানেজারটি ব্যবহার করতে চান?
নিক ওয়েইভার

হ্যাঁ, জিডিবি কনসোলটি দেখিয়েছিল যে এখানে মেমরির সতর্কতা ছিল এবং এরপরে সীমাবদ্ধ মেমরির কারণে অ্যাপ্লিকেশানটি ক্র্যাশ হয়ে গেছে। আমি হালকা ওজনের স্থানান্তর এবং এনএসমিগ্রেশন ম্যানেজার উভয়ই চেষ্টা করেছি, তবে এখনই আমি এনএসমিগ্রেশন ম্যানেজার ব্যবহার করার চেষ্টা করছি trying
জেসন

ঠিক আছে, আপনি কি আরও কিছু বিশদে যেতে পারেন যা পরিবর্তিত হয়েছে?
নিক ওয়েইভার

অবশেষে, আমি খুঁজে পেয়েছি, আমার উত্তরটি পড়ুন।
নিক ওয়েইভার

হ্যালো জেসন, আপনি কি প্রশ্নটির মতো ঠিক করতে পারবেন?
ইউচেন ঝং

উত্তর:


175

অ্যাপল তাদের ডকুমেন্টেশনে কী ইঙ্গিত দেয় তা আমি খুঁজে বের করেছি । এটি প্রকৃতপক্ষে খুব সহজ তবে সুস্পষ্ট হওয়ার আগে অনেক দীর্ঘ পথ যেতে হবে। আমি একটি উদাহরণ দিয়ে ব্যাখ্যাটি বর্ণনা করব। প্রাথমিক পরিস্থিতি হ'ল:

ডেটা মডেল সংস্করণ 1

এখানে চিত্র বর্ণনা লিখুন এখানে চিত্র বর্ণনা লিখুন

আপনি "মূল ডেটা স্টোরেজ সহ নেভিগেশন ভিত্তিক অ্যাপ্লিকেশন" টেম্পলেট দিয়ে একটি প্রকল্প তৈরি করার সময় এটি আপনার পাওয়া মডেল। আমি এটি সংকলন করেছি এবং কিছু ভিন্ন মান সহ সমস্ত 2k এন্ট্রি তৈরি করতে লুপের জন্য কিছু সহায়তায় কঠোর হিট করেছি। সেখানে আমরা এনএসডিট মান সহ 2.000 ইভেন্টে যাই।

এখন আমরা ডেটা মডেলের একটি দ্বিতীয় সংস্করণ যুক্ত করব, যা দেখতে এটির মতো দেখাচ্ছে:

এখানে চিত্র বর্ণনা লিখুন

ডেটা মডেল সংস্করণ 2

পার্থক্যটি হ'ল: ইভেন্ট সত্তা চলে গেছে, এবং আমরা দুটি নতুন পেয়েছি। একটি যা টাইমস্ট্যাম্প হিসাবে সংরক্ষণ করে doubleএবং দ্বিতীয়টি যা একটি তারিখ হিসাবে সংরক্ষণ করে NSString

লক্ষ্যটি হ'ল সমস্ত সংস্করণ 1 ইভেন্ট দুটি নতুন সত্তায় স্থানান্তর করা এবং মাইগ্রেশনের সাথে মানগুলি রূপান্তর করা। এটি পৃথক সত্তায় পৃথক ধরণের হিসাবে প্রতিটি মানের দ্বিগুণ হয়।

স্থানান্তর করতে, আমরা হাতে মাইগ্রেশন চয়ন করি এবং আমরা ম্যাপিং মডেলগুলি দিয়ে এটি করি। এটিও আপনার প্রশ্নের উত্তরের প্রথম অংশ। আমরা মাইগ্রেশনটি দুটি পদক্ষেপে করব, কারণ 2 কে এন্ট্রি স্থানান্তর করতে দীর্ঘ সময় নিচ্ছে এবং আমরা মেমরির পদক্ষেপ কম রাখতে চাই।

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

আমাদের দুটি ম্যাপিং মডেল ফিরে।

আমরা এটির মতো প্রথম ম্যাপিং মডেল তৈরি করি:

1. নতুন ফাইল -> রিসোর্স -> ম্যাপিং মডেল এখানে চিত্র বর্ণনা লিখুন

২. একটি নাম চয়ন করুন, আমি স্টিপওনকে বেছে নিয়েছি

৩. উত্স এবং গন্তব্য ডেটা মডেল সেট করুন

এখানে চিত্র বর্ণনা লিখুন

ম্যাপিং মডেল পদক্ষেপ এক

এখানে চিত্র বর্ণনা লিখুন

এখানে চিত্র বর্ণনা লিখুন

এখানে চিত্র বর্ণনা লিখুন

মাল্টি পাস মাইগ্রেশনের জন্য কাস্টম সত্তা মাইগ্রেশন নীতিগুলির প্রয়োজন নেই, তবে আমরা উদাহরণের জন্য আরও কিছু বিশদ পেতে এটি করব। সুতরাং আমরা সত্তায় একটি কাস্টম নীতি যুক্ত করি। এটি সর্বদা একটি সাবক্লাস হয়NSEntityMigrationPolicy

এখানে চিত্র বর্ণনা লিখুন

এই নীতি শ্রেণিটি আমাদের মাইগ্রেশনটি ঘটানোর জন্য কিছু পদ্ধতি প্রয়োগ করে। তবে এটি এক্ষেত্রে সহজ তাই আমাদের কেবল একটি পদ্ধতি প্রয়োগ করতে হবে:createDestinationInstancesForSourceInstance:entityMapping:manager:error:

বাস্তবায়নটি দেখতে এইরকম হবে:

স্টেপঅনেইটিটিমিগ্রেশনপলিসি.এম

#import "StepOneEntityMigrationPolicy.h"


@implementation StepOneEntityMigrationPolicy

- (BOOL)createDestinationInstancesForSourceInstance:(NSManagedObject *)sInstance 
                                      entityMapping:(NSEntityMapping *)mapping 
                                            manager:(NSMigrationManager *)manager 
                                              error:(NSError **)error
{
    // Create a new object for the model context
    NSManagedObject *newObject = 
        [NSEntityDescription insertNewObjectForEntityForName:[mapping destinationEntityName] 
                                      inManagedObjectContext:[manager destinationContext]];

    // do our transfer of nsdate to nsstring
    NSDate *date = [sInstance valueForKey:@"timeStamp"];
    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
    [dateFormatter setTimeStyle:NSDateFormatterMediumStyle];
    [dateFormatter setDateStyle:NSDateFormatterMediumStyle];    

    // set the value for our new object
    [newObject setValue:[dateFormatter stringFromDate:date] forKey:@"printedDate"];
    [dateFormatter release];

    // do the coupling of old and new
    [manager associateSourceInstance:sInstance withDestinationInstance:newObject forEntityMapping:mapping];

    return YES;
}

চূড়ান্ত পদক্ষেপ: মাইগ্রেশন নিজেই

আমি দ্বিতীয় ম্যাপিংয়ের মডেল স্থাপনের জন্য অংশটি এড়িয়ে যাব যা প্রায় অভিন্ন, NSDate কে ডাবল রূপান্তর করতে ব্যবহৃত একটি সময়IntervalSince1970 ব্যবহৃত হয়েছিল।

অবশেষে আমাদের মাইগ্রেশন ট্রিগার করতে হবে। আমি আপাতত বয়লারপ্লেট কোডটি এড়িয়ে যাব। আপনার যদি এটির প্রয়োজন হয় তবে আমি এখানে পোস্ট করব। এটি মাইগ্রেশন প্রক্রিয়াটি অনুকূলিতকরণে পাওয়া যাবে এটি প্রথম দুটি কোড উদাহরণগুলির একমাত্র মার্জ। তৃতীয় ও শেষ অংশ নিম্নরূপ সংশোধন করা হবে: বর্গ পদ্ধতি ব্যবহার করে পরিবর্তে NSMappingModelবর্গ mappingModelFromBundles:forSourceModel:destinationModel:আমরা ব্যবহার করবেinitWithContentsOfURL: কারণ বর্গ পদ্ধতি শুধুমাত্র এক, হয়তো প্রথম পাওয়া ম্যাপিং বান্ডিল মডেল ফিরে আসবে।

এখন আমরা দুটি ম্যাপিং মডেল পেয়েছি যা লুপের প্রতিটি পাসে ব্যবহৃত হতে পারে এবং মাইগ্রেশন পদ্ধতিটি মাইগ্রেশন ম্যানেজারকে প্রেরণ করতে পারে। এটাই.

NSArray *mappingModelNames = [NSArray arrayWithObjects:@"StepOne", @"StepTwo", nil];
NSDictionary *sourceStoreOptions = nil;

NSURL *destinationStoreURL = [[self applicationDocumentsDirectory] URLByAppendingPathComponent:@"CoreDataMigrationNew.sqlite"];

NSString *destinationStoreType = NSSQLiteStoreType;

NSDictionary *destinationStoreOptions = nil;

for (NSString *mappingModelName in mappingModelNames) {
    NSURL *fileURL = [[NSBundle mainBundle] URLForResource:mappingModelName withExtension:@"cdm"];

    NSMappingModel *mappingModel = [[NSMappingModel alloc] initWithContentsOfURL:fileURL];

    BOOL ok = [migrationManager migrateStoreFromURL:sourceStoreURL
                                               type:sourceStoreType
                                            options:sourceStoreOptions
                                   withMappingModel:mappingModel
                                   toDestinationURL:destinationStoreURL
                                    destinationType:destinationStoreType
                                 destinationOptions:destinationStoreOptions
                                              error:&error2];
    [mappingModel release];
} 

মন্তব্য

  • একটি মানচিত্রের মডেলটি cdmবান্ডলে শেষ হয় ।

  • গন্তব্য স্টোর সরবরাহ করতে হবে এবং উত্স স্টোর হওয়া উচিত নয়। আপনি সফল স্থানান্তরিত হওয়ার পরে পুরানোটিকে মুছুন এবং নতুনটির নাম পরিবর্তন করতে পারবেন।

  • আমি ম্যাপিং মডেলগুলি তৈরির পরে ডেটা মডেলটিতে কিছু পরিবর্তন করেছি, এর ফলে কিছু সামঞ্জস্যতা ত্রুটি হয়েছে, যা আমি কেবল ম্যাপিং মডেলগুলি পুনরায় তৈরি করার মাধ্যমে সমাধান করতে পারি।


59
রক্তাক্ত নরক যে জটিল। অ্যাপল কী ভাবছিল?
আরথ

7
আমি জানি না, তবে যখনই আমি মূল ডেটাগুলি একটি ভাল ধারণা বলে মনে করি আমি একটি সহজ এবং আরও রক্ষণাবেক্ষণযোগ্য সমাধানের জন্য চেষ্টা করি try
নিক ওয়েইভার

4
ধন্যবাদ! এটি একটি চমত্কার উত্তর। এটি জটিল বলে মনে হচ্ছে, তবে আপনি একবারে পদক্ষেপগুলি শিখলে এটি খুব খারাপ নয়। সবচেয়ে বড় সমস্যা হ'ল ডকুমেন্টেশনটি আপনার কাছে এটির মতো বানান করে না।
বেন্টফোর্ড

4
মাইগ্রেশন প্রক্রিয়াটি কাস্টমাইজ করার জন্য আপডেট হওয়া লিঙ্কটি এখানে। এই পোস্টটি লেখা হওয়ার পরে এটি সরানো হয়েছে। বিকাশকারী
অ্যাপ্লিকেশন

@ নিকউইভার আপনি কীভাবে গন্তব্যস্থল নির্ধারণ করছেন? আপনি কি এটি তৈরি করছেন বা মাইগ্রেশন প্রক্রিয়া চলাকালীন এটি মূল ডেটা সিস্টেম দ্বারা তৈরি হয়ে গেছে ????
দেব জিআর

3

এই প্রশ্নগুলি সম্পর্কিত:

মেমরির সমস্যাগুলি আইফোনে বড় আকারের কোরডেটা ডেটাস্টোরগুলিতে স্থানান্তরিত করে

আইওএস সহ খণ্ডগুলিতে একাধিক পাস কোর ডেটা মাইগ্রেশন

প্রথম লিঙ্কটি উদ্ধৃত করতে:

এটি "একাধিক পাস" বিভাগে অফিসিয়াল ডকুমেন্টেশনে আলোচনা করা হয়েছে, তবে মনে হচ্ছে তাদের প্রস্তাবিত পদ্ধতির সত্তার প্রকার অনুসারে আপনার স্থানান্তরকে বিভক্ত করা, অর্থাত্ একাধিক ম্যাপিং মডেল তৈরি করা, যার প্রত্যেকটি সত্তার প্রকারের একটি উপসেট স্থানান্তরিত করে সম্পূর্ণ ডেটা মডেল।


4
লিঙ্কগুলির জন্য ধন্যবাদ। সমস্যাটি হ'ল কোনও একত্রে এটি কীভাবে একাধিক পাসে সেট আপ করা যায় তা বিশদে বিশদভাবে ব্যাখ্যা করে না । আমি কীভাবে একাধিক ম্যাপিং মডেল সেট আপ করব যাতে এটি কার্যকরভাবে কাজ করে?
জেসন

-5

ধরুন আপনার ডাটাবেস স্কিমাতে স্ট্যান্ডার্ড ধরণের উদাহরণ ব্যবহারের জন্য ব্যক্তি, শিক্ষার্থী, কোর্স, শ্রেণি এবং নিবন্ধকরণ রয়েছে যেখানে শিক্ষার্থী সাবক্লাসের ব্যক্তি, শ্রেণি প্রয়োগের কোর্স এবং নিবন্ধকরণ ক্লাস এবং শিক্ষার্থীর সাথে যোগ দেয়। আপনি যদি এই সমস্ত সারণী সংজ্ঞায় পরিবর্তন করে থাকেন তবে আপনাকে বেস ক্লাসগুলি শুরু করতে হবে এবং আপনার পথে কাজ করতে হবে। সুতরাং, আপনি নিবন্ধকরণগুলিতে রূপান্তরকরণ দিয়ে শুরু করতে পারবেন না, কারণ প্রতিটি নিবন্ধন রেকর্ড সেখানে ক্লাস এবং শিক্ষার্থীদের থাকার উপর নির্ভর করে। সুতরাং, আপনি কেবল ব্যক্তি টেবিলটি স্থানান্তরিত করে, বিদ্যমান সারিগুলি নতুন টেবিলের অনুলিপি করে এবং সেখানে যে কোনও নতুন ক্ষেত্র পূরণ করতে (যদি সম্ভব হয়) এবং মুছে ফেলা কলামগুলি ত্যাগ করে শুরু করবেন। অটোরিলিজ পুলে প্রতিটি মাইগ্রেশন করুন, যাতে এটি শেষ হয়ে গেলে, আপনার স্মৃতি আবার শুরু হয়।

ব্যক্তির টেবিলটি শেষ হয়ে গেলে আপনি ছাত্র টেবিলটি ওভারে রূপান্তর করতে পারেন। তারপরে কোর্সে এবং তারপরে ক্লাসে এবং শেষ পর্যন্ত রেজিস্ট্রেশন টেবিলের দিকে যেতে হবে।

অন্য বিবেচনাটি হ'ল রেকর্ডের সংখ্যা, যদি ব্যক্তির এক হাজার সারি থাকে, আপনাকে প্রতি 100 বা ততোধিক একটি রিলিজের সমতুল্য এনএস-ম্যানেজডঅবজেক্ট কার্যকর করতে হবে, যা পরিচালিত অবজেক্ট প্রসঙ্গটি বলতে হবে [এমওসি রিফ্রেশঅবজেক্ট: ওব মার্জ চেঞ্জস: না]; এছাড়াও আপনার বাসি ডেটা টাইমার উপায় কম সেট করুন, যাতে মেমরি প্রায়শই ফ্লাশ হয়।


সুতরাং আপনি কি মূলত একটি নতুন মূল ডেটা স্কিমা রাখার পরামর্শ দিচ্ছেন যা পুরাতন স্কিমাটির অংশ নয় এবং হাতে নতুনভাবে স্কিমায় ডেটা অনুলিপি করছেন?
জেসন

-1 আপনার ডাটাবেস ম্যানুয়ালি ম্যাপিং প্রয়োজন হয় না। হালকা ওজনের স্থানান্তর ব্যবহার করে বা স্পষ্ট ম্যাপিংমডেলগুলি সহ আপনি মোতায়েন করা ডেটাবেসগুলি স্থানান্তর করতে পারেন।
বেন্টফোর্ড 14'12
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.