DEV Community

Papon Ahasan
Papon Ahasan

Posted on • Edited on

Data Backup & Caching strategy Android

Data Backup

<application
    android:allowBackup="false"
    android:fullBackupContent="false"
    android:usesCleartextTraffic="false"
    tools:targetApi="m">
</application>
Enter fullscreen mode Exit fullscreen mode

android:allowBackup="true" এর মানে: অ্যাপ ডেটা ব্যাকআপের অনুমতি দিবে

  • আপনার অ্যাপের ডেটা (SharedPreferences, ফাইল, ডাটাবেস ইত্যাদি) স্বয়ংক্রিয়ভাবে ইউজারের Google অ্যাকাউন্টে ব্যাকআপ হবে। এর ফলে, যদি ইউজার ফোন বদলে বা ফ্যাক্টরি রিসেট করে, তারা তাদের অ্যাপ ডেটা পুনরায় রিস্টোর করতে পারবে।

  • আপনার অ্যাপ নিজে Google লগইন বা অন্য কোনো authentication সিস্টেম ব্যবহার করবে না। ব্যাকআপ-রিস্টোর ফিচারটির জন্য Android OS নিজেই কাজ করে, আপনাকে আলাদা কোড লিখতে হয় না। অর্থাৎ, ইউজার ফোনে যেকোনো Google Account লগইন করলেই, Android System সেই অ্যাকাউন্টের সাথে আপনার অ্যাপের ব্যাকআপ ডেটা সিঙ্ক করবে।

  • এতে ইউজারের জন্য সুবিধা: ইউজারের ডেটা হারানোর ঝুঁকি কমে। ডাটা সেফটি এবং continuity বজায় থাকে। ইউজার এক্সপেরিয়েন্স ভালো হয়।

  • যদি আপনার অ্যাপের ডেটায় সেন্সিটিভ তথ্য থাকে (পাসওয়ার্ড, টোকেন, ব্যাংক বা স্বাস্থ্য তথ্য), তাহলে ব্যাকআপ দেওয়া সিকিউরিটি ঝুঁকি হতে পারে। এমন ক্ষেত্রে ব্যাকআপ অফ রাখা ভালো।

২. android:fullBackupContent="true" (বা ফাইল না দিলে ডিফল্ট true ধরা হয়) এর মানে: ডিফল্ট বা নির্দিষ্ট কনফিগারেশন অনুযায়ী ব্যাকআপ

  • এটি নির্ধারণ করে আপনার অ্যাপের কোন কোন ডেটা ব্যাকআপ হবে।

  • যদি true থাকে বা কোনো ফাইল না দেওয়া হয়, তাহলে অ্যাপের সব প্রাইভেট ফাইলগুলো ব্যাকআপ হবে।

  • আপনি চাইলে একটি XML ফাইল দিয়ে নির্দিষ্ট ফাইল বা ফোল্ডার ব্যাকআপ থেকে বাদ দিতে পারেন। যদি আপনি ব্যাকআপ নিয়ন্ত্রণ করতে না চান, তাহল android:fullBackupContent="true" অথবা ফাইল না দিলেও চলে। তখন ডিফল্ট ভাবে সবকিছু ব্যাকআপ হয়।

কিন্তু সিকিউর বা বড় অ্যাপের ক্ষেত্রে প্রয়োজন অনুযায়ী ফাইল/ফোল্ডার বাদ দেয়া ভালো।

// res/xml/backup_rules.xml
<?xml version="1.0" encoding="utf-8"?>
<full-backup-content>
    <!-- ব্যাকআপ থেকে 'cache' ফোল্ডার বাদ দিন -->
    <exclude domain="file" path="cache/" />

    <!-- ব্যাকআপ থেকে 'temp_files' ফোল্ডার বাদ দিন -->
    <exclude domain="file" path="temp_files/" />

    <!-- ব্যাকআপ থেকে 'databases/my_db.db' বাদ দিন -->
    <exclude domain="database" path="my_db.db" />

    <!-- ব্যাকআপ থেকে SharedPreferences বাদ দিতে পারেন (optional) -->
    <!-- <exclude domain="sharedpref" path="my_prefs.xml" /> -->

    <!-- ব্যাকআপে অন্য সব কিছু অন্তর্ভুক্ত হবে -->
</full-backup-content>

// AndroidManifest.xml
<application
    android:allowBackup="true"
    android:fullBackupContent="@xml/backup_rules"
    ... >
    ...
</application>
Enter fullscreen mode Exit fullscreen mode
  • domain বলতে বোঝায় ডেটার ধরন, যেমনঃ

    • "file" = অ্যাপের ফাইল ডিরেক্টরি (internal storage)
    • "database" = SQLite ডাটাবেস ফাইল
    • "sharedpref" = SharedPreferences ফাইল
    • path হলো সেই ফাইল বা ফোল্ডারের নাম বা লোকেশন (relative path) ফলে কি হয়? আপনি যা এক্সক্লুড (exclude) করবেন, সেই ডেটা ব্যাকআপ হবে না। বাকিটা স্বাভাবিকভাবেই ব্যাকআপে যাবে।

Caching strategy

1️⃣ LruCache – Stores data in memory and removes the least recently used items when full.
Example: Keep recently loaded images or data so they show instantly next time.

2️⃣ LinkedHashMap (accessOrder = true) – Your own simple version of LruCache.
Example: Keep last opened chats or last played songs in order.

3️⃣ HashMap + timestamp – Add a “time saved” with each item so it expires after X minutes.
Example: Store weather data for 5 minutes to avoid new network calls.

4️⃣ Network response caching

object RetrofitInstance {

    private const val CACHE_SIZE_BYTES = 10 * 1024 * 1024L // 10 MB
    private const val BASE_URL = HEALTH_TIPS_BASE_URL

    @Volatile
    private var postApi: PostApi? = null

    fun getApi(context: Context): PostApi {
        return postApi ?: synchronized(this) {
            postApi ?: buildRetrofit(context).also { postApi = it }
        }
    }

    private fun buildRetrofit(context: Context): PostApi {
        val cacheDir = File(context.cacheDir, "http_cache")
        val cache = Cache(cacheDir, CACHE_SIZE_BYTES)

        val cacheInterceptor = Interceptor { chain ->
            var request = chain.request()

            if (!NetworkCheckUtils.isConnect(context)) {
                // Offline: allow cache up to 7 days old
                request = request.newBuilder()
                    .header("Cache-Control", "public, only-if-cached, max-stale=604800")
                    .build()
            }

            val response = chain.proceed(request)

            // Online: keep cache for 1 min
            val maxAge = 60 // seconds
            response.newBuilder()
                .header("Cache-Control", "public, max-age=$maxAge")
                .build()
        }

        val loggingInterceptor = HttpLoggingInterceptor().apply {
            level = HttpLoggingInterceptor.Level.BODY
        }

        val okHttpClient = OkHttpClient.Builder()
            .cache(cache)
            .addInterceptor(cacheInterceptor)          // Offline cache
            .addNetworkInterceptor(cacheInterceptor)   // Online cache
            .addInterceptor(loggingInterceptor)
            .connectTimeout(30, TimeUnit.SECONDS)
            .readTimeout(30, TimeUnit.SECONDS)
            .writeTimeout(30, TimeUnit.SECONDS)
            .build()

        return Retrofit.Builder()
            .baseUrl(BASE_URL)
            .addConverterFactory(GsonConverterFactory.create())
            .client(okHttpClient)
            .build()
            .create(PostApi::class.java)
    }
}

- Cache সিস্টেম একই থাকবে  অনলাইনে  মিনিট, অফলাইনে  দিন পর্যন্ত ডেটা রাখা হবে।
Enter fullscreen mode Exit fullscreen mode

⦿ পারফরম্যান্স বাড়ে

  • Offline cache → অ্যাপ সার্ভারে হিট না দিয়ে দ্রুত ডেটা দেখায়।
  • Online cache → একই ডেটা বারবার ফেচ না করে ক্যাশ থেকে লোড করে (ব্যান্ডউইথ বাঁচে)।
  • মেমরি ও CPU খরচ কম হবে।
  • App এর নেটওয়ার্ক পারফরম্যান্স বাড়বে

⦿ ইউজার এক্সপেরিয়েন্স ভালো হয়

  • ইন্টারনেট স্লো হলেও বা মাঝে মাঝে কানেকশন ড্রপ হলেও ডেটা সঙ্গে সঙ্গে দেখা যাবে।
  • Offline অবস্থায় ফাঁকা স্ক্রিন বা এরর মেসেজ না দিয়ে শেষবারের ডেটা দেখানো যাবে।

caching-in-android-strategies

caching-process-in-android

Top comments (0)