DataStore: এটি কী, ডেটা স্টোরেজের মৌলিক বিষয় এবং SharedPreferences-এর প্রতিস্থাপন

লেখক: IT Sectr প্রকাশিত: 2026-03-12 পড়ার সময়: 9 মিনিট

DataStore হল Jetpack লাইব্রেরির একটি উপাদান যা Android অ্যাপ্লিকেশনে অল্প পরিমাণ ডেটা সংরক্ষণের জন্য ডিজাইন করা হয়েছে। SharedPreferences-এর বিপরীতে, এটি অ্যাসিঙ্ক্রোনাসভাবে কাজ করে এবং সমবর্তী অ্যাক্সেসের অধীনে ডেটার সামঞ্জস্য নিশ্চিত করে। Google, 2024-এর মতে, DataStore Kotlin Coroutines এবং Flow ব্যবহার করে, যা এটিকে প্রধান থ্রেডের জন্য নিরাপদ এবং রিঅ্যাকটিভ আর্কিটেকচারের জন্য উপযুক্ত করে তোলে।

মূল পয়েন্ট

  • DataStore — অ্যাসিঙ্ক্রোনাস API এবং Protocol Buffers-এর মাধ্যমে ডেটা টাইপ সহ SharedPreferences-এর প্রতিস্থাপন
  • Preferences DataStore — Flow এবং ট্রানজেকশনের মাধ্যমে পড়ার সাথে সহজ কী-ভ্যালু স্টোর
  • Proto DataStore — স্বয়ংক্রিয় স্কিমা মাইগ্রেশন সহ টাইপকৃত স্টোরেজ
  • SharedPreferences — সিঙ্ক্রোনাস API, বড় ভলিউমে UI-থ্রেড ব্লক করে
  • মাইগ্রেশন ডেটা ক্ষতি ছাড়াই SharedPreferencesMigration ইন্টারফেসের মাধ্যমে সম্পাদিত হয়

DataStore কী?

DataStore হল Android-এ স্থানীয় ডেটা স্টোরেজের জন্য Google-এর সমাধান, যা 2020 সালে SharedPreferences-এর বিকল্প হিসেবে উপস্থাপিত হয়েছিল। এটি দুটি মোড সমর্থন করে: Preferences DataStore (সরল কী-ভ্যালু জোড়া) এবং Proto DataStore (Protocol Buffers-এর উপর ভিত্তি করে টাইপকৃত স্কিমা)।

প্রধান সুবিধা হল সম্পূর্ণ অ্যাসিঙ্ক্রোনাসিটি: সমস্ত রিড অপারেশন Kotlin Coroutines থেকে Flow রিটার্ন করে এবং রাইটগুলি coroutine-প্রসঙ্গে সম্পাদিত হয়। এটি প্রধান থ্রেড ব্লকিং দূর করে, যা বড় পরিমাণ ডেটা নিয়ে কাজ করার সময় SharedPreferences-এর একটি সাধারণ সমস্যা ছিল।

DataStore অপারেশনের পরমাণুতা নিশ্চিত করে: সমবর্তী রাইটগুলি তার ট্রানজেকশনাল মডেলের কারণে ডেটা ক্ষতি করে না। যদি দুটি উপাদান একই সাথে একই মান পরিবর্তন করে, DataStore compare-and-swap প্রক্রিয়ার মাধ্যমে সঠিকভাবে দ্বন্দ্ব পরিচালনা করে।

Google I/O 2023-এর মতে, DataStore 40% নতুন Android প্রকল্পে ব্যবহৃত হয়, এবং Google সেই সমস্ত অ্যাপ্লিকেশনে SharedPreferences থেকে মাইগ্রেট করার সুপারিশ করে যেখানে সেটিংস স্টোরেজ স্থিতিশীলতা প্রয়োজন।

DataStore আর্কিটেকচার

DataStore-এর মূলে রয়েছে SingleProcessDataStore — একটি বাস্তবায়ন যা একটি প্রক্রিয়ার মধ্যে কাজ করে। এটি ফাইল-লকিং সহ ফাইল-ভিত্তিক স্টোরেজ ব্যবহার করে: ডেটা লেখার সময়, ফাইলটি লক হয়ে যায়, যা সমবর্তী অ্যাক্সেসের অধীনে দূষণ প্রতিরোধ করে।

DataStore স্বয়ংক্রিয়ভাবে ডিসিরিয়ালাইজেশন ত্রুটিগুলি পরিচালনা করে: ফাইলটি দূষিত হলে, এটি একটি ডিফল্ট মান ফেরত দেয় এবং ফাইলটি ওভাররাইট করে। এই আচরণ corruptionHandler-এর মাধ্যমে কনফিগারযোগ্য, যা DataStore তৈরি করার সময় সেট করা যেতে পারে।

SharedPreferences-এর সমস্যা যা DataStore সমাধান করে

SharedPreferences তিনটি মৌলিক সমস্যায় ভোগে: প্রধান থ্রেডে সিঙ্ক্রোনাস ডিস্ক রিডিং, সমবর্তী রাইটের জন্য পরমাণুতা গ্যারান্টির অভাব এবং রিঅ্যাকটিভভাবে পরিবর্তন ট্র্যাক করতে অক্ষমতা। DataStore তিনটিই সমাধান করে: পর্যবেক্ষণের জন্য Flow, পরমাণুতার জন্য ফাইল লকিং এবং থ্রেড নিরাপত্তার জন্য অ্যাসিঙ্ক্রোনাস API।

Android-এ DataStore কীভাবে কাজ করে?

DataStore ডিভাইসের অভ্যন্তরীণ স্টোরেজে ফাইলে ডেটা সংরক্ষণ করে। Preferences DataStore SharedPreferences-এর মতো ফাইল ফরম্যাট ব্যবহার করে তবে অখণ্ডতা পরীক্ষার জন্য অতিরিক্ত মেটাডেটা সহ। Proto DataStore বাইনারি Protocol Buffers ফরম্যাট ব্যবহার করে, যা ফাইলের আকার হ্রাস করে এবং সিরিয়ালাইজেশন ত্বরান্বিত করে।

ডেটা পড়ার সময়, DataStore সম্পূর্ণ ফাইলটি একবার মেমরিতে লোড করে, তারপর সাবস্ক্রাইবাররা Flow-এর মাধ্যমে বর্তমান অবস্থা পায়। পরিবর্তনগুলি সমস্ত সক্রিয় সাবস্ক্রাইবারকে স্বয়ংক্রিয়ভাবে সম্প্রচারিত হয় — SharedPreferences-এর মতো ম্যানুয়াল listener নিবন্ধনের প্রয়োজন নেই।

Preferences DataStore কীভাবে কাজ করে

Preferences DataStore একটি Map-এর উপর ভিত্তি করে একটি অন্তর্নির্মিত সিরিয়ালাইজেশন প্রক্রিয়া ব্যবহার করে। প্রতিটি এন্ট্রি একটি স্ট্রিং এবং একটি আদিম টাইপের (Int, Boolean, Float, Long, String, Set) জোড়া। ডেটা SharedPreferences-এর মতো XML ফাইলে সংরক্ষণ করা হয়, তবে ফাইল লকিংয়ের মাধ্যমে পরমাণু লেখার সাথে।

Preferences DataStore তৈরির উদাহরণ: Context-এ preferencesDataStore এক্সটেনশন ফাইল নামের সাথে একটি সিঙ্গেলটন তৈরি করে। বারবার কল করলে, একই ইনস্ট্যান্স ফেরত দেওয়া হয় — এটি ফাইল ডুপ্লিকেশন এবং বিভিন্ন স্টোরেজ ইনস্ট্যান্সের মধ্যে বিভ্রান্তি দূর করে।

Proto DataStore কীভাবে কাজ করে

Proto DataStore-এর জন্য .proto ফাইলের মাধ্যমে ডেটা স্কিমা সংজ্ঞায়িত করা এবং protobuf-প্লাগইনের সাথে কম্পাইল করা প্রয়োজন। জেনারেটেড Java ক্লাসটি সমস্ত ফিল্ডের জন্য একমাত্র এন্ট্রি পয়েন্ট হিসাবে ব্যবহৃত হয় — এটি SharedPreferences-এ সাধারণ কী টাইপো দূর করে।

Proto DataStore স্কিমা একবার সংজ্ঞায়িত করা হয় এবং পুরানো ডেটা না হারিয়ে নতুন ফিল্ড যোগ করার সমর্থন করে। যদি অ্যাপ্লিকেশনের নতুন সংস্করণ ডিফল্ট মান সহ একটি ফিল্ড যোগ করে, পুরানো ফাইলটি সঠিকভাবে ডিসিরিয়ালাইজ করা হবে — ব্যাকওয়ার্ড কম্প্যাটিবিলিটি প্রোটোকলে নির্মিত।

Preferences DataStore এবং Proto DataStore: তুলনা

Preferences DataStore এবং Proto DataStore-এর মধ্যে পছন্দ ডেটা জটিলতা এবং টাইপিং প্রয়োজনীয়তার উপর নির্ভর করে। উভয় বিকল্প অ্যাসিঙ্ক্রোনাস এবং ট্রানজেকশনাল, তবে টাইপ-সেফটি এবং সিরিয়ালাইজেশন কর্মক্ষমতায় ভিন্ন।

বৈশিষ্ট্যPreferences DataStoreProto DataStore
টাইপিংদুর্বল (কী-ভ্যালু)শক্তিশালী (জেনারেটেড ক্লাস)
সিরিয়ালাইজেশনXML (অন্তর্নির্মিত)Protocol Buffers (protobuf)
ফাইলের আকারবড় (পাঠযোগ্য XML)ছোট (বাইনারি)
জটিলতাকম (.proto ছাড়া)মাঝারি (.proto প্রয়োজন)
স্কিমা মাইগ্রেশনকোনো স্কিমা নেইস্বয়ংক্রিয় (proto)
সামঞ্জস্যতাSharedPreferences (মাইগ্রেশনের মাধ্যমে)শুধুমাত্র Proto DataStore

কখন Preferences DataStore নির্বাচন করবেন

Preferences DataStore সাধারণ সেটিংসের জন্য উপযুক্ত: ফিচার ফ্ল্যাগ, অথরাইজেশন টোকেন স্ট্রিং, অ্যাপ্লিকেশন লঞ্চ কাউন্ট। যদি ডেটা ছোট হয় (10–15 কী পর্যন্ত) এবং কঠোর স্কিমার প্রয়োজন না হয়, তাহলে Preferences DataStore protobuf-প্লাগইন সংযোগ ছাড়াই ন্যূনতম প্রবেশ সীমা প্রদান করে।

কখন Proto DataStore নির্বাচন করবেন

Proto DataStore ন্যায়সঙ্গত যখন ডেটা কাঠামো জটিল হয় বা অ্যাপ্লিকেশন সংস্করণগুলির মধ্যে পরিবর্তিত হতে পারে। উদাহরণস্বরূপ, ব্যবহারকারী প্রোফাইল সেটিংস বা 20+ ফিল্ড সহ A/B পরীক্ষা কনফিগারেশন। Protobuf শক্তিশালী টাইপিং এবং স্বয়ংক্রিয় মাইগ্রেশন প্রদান করে, কী অমিলের কারণে রানটাইম ত্রুটিগুলি দূর করে।

SharedPreferences থেকে DataStore-এ মাইগ্রেট কীভাবে করবেন

Google SharedPreferencesMigration ক্লাসের মাধ্যমে একটি অন্তর্নির্মিত মাইগ্রেশন প্রক্রিয়া প্রদান করে। অ্যাপ্লিকেশন আপডেটের পরে প্রথম লঞ্চে মাইগ্রেশন একবার সম্পাদিত হয়: DataStore SharedPreferences থেকে ডেটা পড়ে, এটি নিজস্ব ফরম্যাটে লেখে এবং মাইগ্রেশন সম্পূর্ণ হিসাবে চিহ্নিত করে।

মাইগ্রেশন কাস্টম ট্রান্সফরমেশন সমর্থন করে: যদি SharedPreferences-এর কীগুলি কাঙ্ক্ষিত DataStore কীগুলির সাথে মেলে না, তাহলে আপনি SharedPreferencesMigration-এর মাধ্যমে একটি ট্রান্সফরমেশন ফাংশন নির্দিষ্ট করতে পারেন। এটি মাইগ্রেশনের সময় কীগুলির নাম পরিবর্তন এবং ডেটা টাইপ পরিবর্তনের অনুমতি দেয়।

ধাপে ধাপে মাইগ্রেশন

প্রথম ধাপে, build.gradle-এ DataStore যোগ করুন এবং মাইগ্রেশন সহ একটি DataStore ইনস্ট্যান্স তৈরি করুন: SharedPreferencesMigration SharedPreferences ফাইলের নাম এবং স্থানান্তরের জন্য কীগুলির সেট গ্রহণ করে। দ্বিতীয় ধাপে, SharedPreferences-এর মাধ্যমে কাজ করা সমস্ত কোড সরান এবং DataStore কল দিয়ে প্রতিস্থাপন করুন। তৃতীয় ধাপে, মাইগ্রেশন পরীক্ষা করুন: প্রথম লঞ্চে, DataStore-এ ডেটা উপস্থিত হওয়া উচিত এবং পুরানো SharedPreferences ফাইলটি আর ব্যবহার করা উচিত নয়।

kotlin
val Context.dataStore by preferencesDataStore(
    name = "settings",
    produceMigrations = { context ->
        listOf(
            SharedPreferencesMigration(context, "old_prefs")
        )
    }
)

কোডে DataStore ব্যবহারের উদাহরণ

DataStore বিদ্যমান প্রকল্পে সহজেই একীভূত হয়। নীচে Preferences DataStore এবং Proto DataStore-এর জন্য ব্যবহারিক উদাহরণ দেওয়া হল — উভয়ই ডেটা পড়া, লেখা এবং রিঅ্যাকটিভ পর্যবেক্ষণ প্রদর্শন করে।

Preferences DataStore: সেটিংস পড়া এবং লেখা

এই উদাহরণে, Preferences DataStore তিনটি সেটিংস সংরক্ষণ করে: ডার্ক থিম, ব্যবহারকারীর নাম এবং লঞ্চ কাউন্ট। রিডিং .data এক্সটেনশনের মাধ্যমে করা হয়, যা Flow রিটার্ন করে। রাইটিং .edit সাসপেন্ড ফাংশনের মাধ্যমে করা হয়, যা পরিবর্তনের পরমাণুতা নিশ্চিত করে।

kotlin
val Context.settingsDataStore by preferencesDataStore(name = "settings")

val isDarkMode: Flow<Boolean> = settingsDataStore.data
    .map { preferences ->
        preferences[booleanPreferencesKey("dark_mode")] ?: false
    }

suspend fun toggleDarkMode() {
    settingsDataStore.edit { prefs ->
        val current = prefs[booleanPreferencesKey("dark_mode")] ?: false
        prefs[booleanPreferencesKey("dark_mode")] = !current
    }
}

Proto DataStore: স্কিমা এবং ব্যবহার

Proto DataStore-এর জন্য .proto ফাইল সংজ্ঞায়িত করা প্রয়োজন। কম্পাইলেশনের পরে, একটি UserSettings ক্লাস তৈরি হয় যা পড়া এবং লেখার জন্য ব্যবহৃত হয়। স্কিমার সংস্করণ মাইগ্রেশনগুলি একই .proto ফাইলে বর্ণিত হয় এবং স্বয়ংক্রিয়ভাবে প্রয়োগ হয়।

kotlin
// user_preferences.proto
syntax = "proto3";

message UserPreferences {
    string display_name = 1;
    int32 notification_count = 2;
    bool notifications_enabled = 3;
}

// DataStore থেকে পড়া
val userPreferencesFlow: Flow<UserPreferences> =
    protoDataStore.data

// নতুন মান লেখা
suspend fun updateDisplayName(name: String) {
    protoDataStore.updateData { prefs ->
        prefs.toBuilder()
            .setDisplayName(name)
            .build()
    }
}

পরিবর্তনের রিঅ্যাকটিভ পর্যবেক্ষণ

DataStore ViewModel-এর মাধ্যমে MVVM আর্কিটেকচারের সাথে একীভূত হয়। DataStore থেকে Flow .stateIn-এর মাধ্যমে সংগ্রহ করা হয় এবং UI-তে ব্যবহৃত হয়। প্রতিটি ডেটা পরিবর্তনের সাথে, UI স্বয়ংক্রিয়ভাবে আপডেট হয় — ম্যানুয়াল আপডেট বা LiveData-এর প্রয়োজন নেই।

kotlin
class SettingsViewModel(
    private val dataStore: DataStore<Preferences>
) : ViewModel() {

    val uiState: StateFlow<SettingsUiState> =
        dataStore.data
            .map { prefs ->
                SettingsUiState(
                    isDarkMode = prefs[booleanPreferencesKey("dark_mode")] ?: false,
                    counter = prefs[intPreferencesKey("launch_count")] ?: 0
                )
            }
            .stateIn(
                scope = viewModelScope,
                started = SharingStarted.WhileSubscribed(5000),
                initialValue = SettingsUiState()
            )
}

প্রায়শই জিজ্ঞাসিত প্রশ্ন

DataStore কীভাবে SharedPreferences-এর চেয়ে ভাল?

DataStore অ্যাসিঙ্ক্রোনাসভাবে কাজ করে (UI থ্রেড ব্লক করে না), ট্রানজেকশনের মাধ্যমে সমবর্তী অ্যাক্সেস সমর্থন করে এবং Flow-এর মাধ্যমে পরিবর্তনের রিঅ্যাকটিভ সাবস্ক্রিপশনের অনুমতি দেয়। SharedPreferences একটি সিঙ্ক্রোনাস API যার বড় ডেটা ভলিউমে ANR-এর ঝুঁকি এবং কোনো অন্তর্নির্মিত রিঅ্যাকটিভিটি সমর্থন নেই।

DataStore কি Java-এর সাথে ব্যবহার করা যেতে পারে?

DataStore Kotlin-এ লেখা এবং Kotlin Coroutines প্রয়োজন। Java থেকে এটি ব্যবহার করা সম্ভব তবে অসুবিধাজনক: আপনাকে CompletableFuture দিয়ে র্যাপার তৈরি করতে হবে বা ম্যানুয়ালি coroutines পরিচালনা করতে হবে। Java প্রকল্পের জন্য, Google SharedPreferences রাখার বা মডিউলে Kotlin যোগ করার সুপারিশ করে।

DataStore কি বড় পরিমাণ ডেটা সংরক্ষণের জন্য উপযুক্ত?

DataStore পড়ার সময় সম্পূর্ণ ফাইল মেমরিতে লোড করে, তাই এটি তালিকা বা বড় বস্তু সংরক্ষণের জন্য উপযুক্ত নয়। এই ধরনের পরিস্থিতির জন্য, Room বা SQLite ব্যবহার করুন। DataStore সেটিংস এবং ছোট কাঠামোবদ্ধ ডেটা — শত কিলোবাইট পর্যন্ত — এর জন্য অপ্টিমাইজ করা।

দূষিত DataStore ফাইলের ত্রুটি কীভাবে পরিচালনা করবেন?

DataStore তৈরি করার সময়, আপনি একটি corruptionHandler পাস করতে পারেন — একটি ফাংশন যা ফাইল দূষিত হলে কল করা হয়। ডিফল্টরূপে, DataStore একটি CorruptionException নিক্ষেপ করে। corruptionHandler-এ, আপনি খালি ডেটা ফেরত দিতে পারেন, এরপর DataStore ফাইলটি সঠিক অবস্থায় ওভাররাইট করবে।

Proto DataStore-এর জন্য কি .proto ফাইল আবশ্যক?

হ্যাঁ, Proto DataStore-এর জন্য .proto ফাইলে স্কিমা সংজ্ঞায়িত করা এবং protobuf-gradle-plugin সংযোগ করা প্রয়োজন। যদি প্রকল্প ছোট হয় এবং ডেটা সহজ হয়, তাহলে Preferences DataStore ব্যবহার করা সহজ — এটির অতিরিক্ত বিল্ড কনফিগারেশনের প্রয়োজন নেই।

সারাংশ

  • DataStore — Kotlin Coroutines এবং Flow-এর সাথে কাজ করা SharedPreferences-এর আধুনিক প্রতিস্থাপন
  • Preferences DataStore — স্কিমা ছাড়া সরল কী-ভ্যালু, সেটিংসের জন্য উপযুক্ত
  • Proto DataStore — protobuf স্কিমা এবং অটো-মাইগ্রেশন সহ টাইপকৃত স্টোরেজ
  • মাইগ্রেশন SharedPreferences থেকে DataStore-এ SharedPreferencesMigration-এর মাধ্যমে নির্মিত
  • থ্রেড নিরাপত্তা — সমস্ত অপারেশন অ্যাসিঙ্ক্রোনাস, UI ব্লকিং দূর করা হয়েছে
  • রিঅ্যাকটিভিটি — Flow প্রতিটি ডেটা পরিবর্তনে সাবস্ক্রাইবারদের জানায়
  • সুপারিশ — সমস্ত নতুন Android প্রকল্পে DataStore ব্যবহার করুন, সেটিংস নিয়ে কাজ করার সময় বিদ্যমান প্রকল্পগুলি মাইগ্রেট করুন

আমরা একটি মোবাইল অ্যাপ্লিকেশন টার্নকি তৈরি করব

IT Sectr 2017 সাল থেকে স্টার্টআপ এবং ব্যবসার জন্য iOS এবং Android অ্যাপ্লিকেশন তৈরি করে। আমরা আপনাকে পরামর্শ দেব এবং সেরা সমাধান প্রস্তাব করব।

প্রকল্প নিয়ে আলোচনা করুন

আরও পড়ুন