ইন্টারনেট না থাকলেও কাজ করে এমন মোবাইল চেকলিস্ট অ্যাপ কীভাবে ডিজাইন, বানানো এবং টেস্ট করবেন শিখুন: লোকাল স্টোরেজ, সিঙ্ক, কনফ্লিক্ট, সিকিউরিটি ও রিলিজ টিপস।

কোন ডাটাবেস বা সিঙ্ক কৌশল বেছে নেবেন তার আগে, ঠিক করে নিন কারা অফলাইন চেকলিস্টে ভরসা করবে—আর তাদের জন্য “অফলাইন” আসলে কী মানে। একটি বাড়ির অর্গানাইজারের অ্যাপের প্রত্যাশা ভিজিটিং ইনস্পেক্টরের (বেসমেন্ট, ফ্যাক্টরি, গ্রামীণ সাইট) প্রত্যাশার থেকে অনেক আলাদা।
প্রাথমিক ব্যবহারকারী এবং তাদের পরিবেশ নাম লেখার মাধ্যমে শুরু করুন:
প্রতিটি গ্রুপের জন্য ডিভাইস সীমাবদ্ধতা (শেয়ার করা ডিভাইস বনাম পার্সোনাল), সাধারণ সেশন দৈর্ঘ্য, এবং কতবার তারা অনলাইনে ফিরে আসে তা নোট করুন।
কানেকটিভিটি ছাড়া ব্যবহারকারীরা কোন মৌলিক কাজগুলো সম্পন্ন করতে পারবে তা লেখুন:
“নিস-টু-হ্যাভ” অ্যাকশনগুলোও তালিকাভুক্ত করুন যা বিলম্ব করা যাবে (যেমন গ্লোবাল ইতিহাস সার্চ, রিপোর্ট এক্সপোর্ট)।
কোনটি সম্পূর্ণভাবে অফলাইনে কাজ করবে (নতুন চেকলিস্ট রান তৈরি, অগ্রগতি তাত্ক্ষণিকভাবে সংরক্ষণ, ফটো সংযুক্ত করা) এবং কোনটি বিলম্ব করা যাবে (মিডিয়া আপলোড, দলের সাথে সিঙ্ক, অ্যাডমিন সম্পাদনা) তা স্পষ্ট করুন।
যদি আপনি কমপ্লায়েন্স নিয়মের আওতায় কাজ করেন, তাহলে দ্রুত থেকেই প্রয়োজনীয়তা নির্ধারণ করুন: ট্রাস্টেড টাইমস্ট্যাম্প, ব্যবহারকারী পরিচয়, অনবদ্য কার্যকলাপ লগ, এবং সাবমিশনের পরে সম্পাদনা সম্পর্কে নিয়ম। এগুলো আপনার ডেটা মডেল ও ভবিষ্যৎ সিঙ্ক ডিজাইনে প্রভাব ফেলবে।
একটি অফলাইন চেকলিস্ট অ্যাপ সফল হবে বা ব্যর্থ হবে এক প্রাথমিক সিদ্ধান্তের উপর: অফলাইন-প্রথম নাকি ফলব্যাক সহ অনলাইন-প্রথম।
অফলাইন-প্রথম মানে ফোনটাকেই প্রধান কাজের জায়গা হিসেবে ধরা। নেটওয়ার্ক একটি বান্দর নয়: সিঙ্কিং ব্যাকগ্রাউন্ড টাস্ক; অ্যাপ ব্যবহারের জন্য বাধ্যতামূলক নয়।
অনলাইন-প্রথম (ফলব্যাকসহ) মানে সার্ভার বেশিরভাগ সময়ে সত্যের উৎস, এবং অ্যাপ কেবল অফলাইনে “লাইমপ” করে (প্রায়শই রিড-ওনলি বা সীমিত সম্পাদনা)।
জব সাইট, ওয়্যারহাউস, ফ্লাইট, ও বেসমেন্টে ব্যবহৃত চেকলিস্টের জন্য, সাধারণত অফলাইন-প্রথম উপযুক্ত কারণ এটি কাজে জরুরী মুহূর্তে “দুঃখিত, পরে চেষ্টা করুন” ধরনের পরিস্থিতি এড়ায়।
রিড/রাইট নিয়ম সম্পর্কে স্পষ্ট থাকুন। একটি বাস্তবসম্মত অফলাইন-প্রথম বেসলাইন:
কিছু যদি অফলাইনে সীমাবদ্ধ করা হয় (উদাহরণ: নতুন টিম মেম্বার আমন্ত্রণ), UI-তে তা বলুন এবং কারণ দেখান।
অফলাইন-প্রথমও একটি প্রতিশ্রুতি দরকার: আপনার কাজ সংযোগ ফিরে এলে সিঙ্ক হবে। সিদ্ধান্ত নিন ও যোগাযোগ করুন:\n\n- ডেটা কতদিন লোকাল থাকবে আগে অ্যাপ ব্যবহারকারীর কাছে নোট করবে (উদাহরণ: “7 দিন ধরে সিঙ্ক হয়নি”)।\n- যদি ব্যবহারকারী লগআউট করে, রিইনস্টল করে, বা স্টোরেজ শেষ হয়ে যায় তখন কী হবে।\n- অ্যাপ কি মাঝে মাঝে অনলাইন চেক-ইন দরকার করবে কিনা (কমপ্লায়েন্স বা অ্যাকাউন্ট স্ট্যাটাস)।
সিঙ্গেল-ইউজার চেকলিস্ট সহজ: কনফ্লিক্ট বিরল এবং স্বয়ংক্রিয়ভাবে সমাধান করা যায়।
টিম ও শেয়ার্ড লিস্টে কঠোর নিয়ম প্রয়োজন: দুইজনই একই আইটেম অফলাইনে এডিট করতে পারে। আগে থেকেই সিদ্ধান্ত নিন আপনি ভবিষ্যতে রিয়েল-টাইম কল্যাবোরেশন সমর্থন করবেন কি না, এবং এখন থেকেই মাল্টি-ডিভাইস সিঙ্ক, অডিট ইতিহাস, এবং স্পষ্ট “last updated by” কিউ ডিজাইন করুন যাতে অবাক না হন।
একটি ভাল অফলাইন চেকলিস্ট অ্যাপ মূলত ডেটার সমস্যা। আপনার মডেল পরিষ্কার এবং পূর্বানুমেয় হলে, অফলাইন এডিট, রিট্রাই এবং সিঙ্ক অনেক সহজ হয়ে যায়।
কারো যে টেমপ্লেট পূরণ করে তা ও যে টেমপ্লেট লেখা হয়েছে তা আলাদা করে শুরু করুন।
এতে আপনি টেমপ্লেট আপডেট করার সময় ঐতিহাসিক সাবমিশন ভেঙে পড়া এড়াতে পারবেন।
প্রতিটি প্রশ্ন/টাস্ককে একটি আইটেম হিসেবে গ্রহণ করুন যার একটি স্থায়ী ID আছে। একটি রান+আইটেমে লিঙ্ক করা উত্তর-গুলো আলাদা করে স্টোর করুন।
প্রায়োগিক ফিল্ডগুলো অন্তর্ভুক্ত করুন:
id: স্থায়ী UUID (ক্লায়েন্ট-সাইডে তৈরি যাতে এটি অফলাইনে বিদ্যমান থাকে)\n- template_version: কোন টেমপ্লেট ভার্সন থেকে রান শুরু করা হয়েছে তা জানার জন্য\n- updated_at: প্রতিটি রেকর্ডের শেষ পরিবর্তনের টাইমস্ট্যাম্প\n- version (বা revision): প্রতিটি লোকাল পরিবর্তনে বাড়ানো একটি পূর্ণসংখ্যাএই “কে কী বদলালো, কখন” হিন্টগুলো আপনার পরে সিঙ্ক লজিকের ভিত্তি।
অফলাইন কাজ প্রায়শই বিরতিপূর্ণ। status (draft, in_progress, submitted), started_at, এবং last_opened_at মতো ফিল্ড যোগ করুন। উত্তরগুলোর জন্য nullable মান অনুমতি দিন এবং একটি হালকা “validation state” রাখুন যাতে ব্যবহারকারীরা বাধ্যতামূলক আইটেম না থাকলেও ড্রাফট সংরক্ষণ করতে পারে।
ফটো ও ফাইলগুলোকে মূল চেকলিস্ট টেবিলে ব্লব হিসেবে না রেখে রেফারেন্স করুন।
একটি attachments টেবিল তৈরি করুন যাতে থাকে:\n\n- লোকাল ফাইল পাথ / URI\n- রিমোট URL (আপলোডের পরে)\n- MIME টাইপ, সাইজ\n- answer_id (বা run_id) লিঙ্ক\n- আপলোড স্টেট (pending, uploading, uploaded, failed)
এতে চেকলিস্ট রিড দ্রুত থাকে এবং আপলোড রিট্রাই সহজ হয়।
অফলাইন চেকলিস্ট লাইভ বা মরবে লোকাল স্টোরের উপর। কিছু দ্রুত, সার্চযোগ্য, এবং আপগ্রেডযোগ্য দরকার—কারণ ইউজাররা আসলেই “আর এক ফিল্ড” চাইলেই আপনার স্কিমা বদলে যাবে।
কমন “লিস্ট স্ক্রিন” দিক থেকে ডিজাইন করুন। বেশি ব্যবহৃত ফিল্ডগুলো ইনডেক্স করুন:\n\n- status (open/completed/failed)\n- dates (scheduledAt, completedAt)\n- locationId / siteId\n- assigneeId
সাবধান: সবকিছু ইনডেক্স করা লেখাকে ধীর করে এবং স্টোরেজ বাড়ায়—কম সংখ্যক বুদ্ধিমান ইনডেক্সই ভালো।
প্রতিটি পরিবর্তনের সাথে:\n\n- একটি স্কিমা ভার্সন বাম্প\n- একটি মাইগ্রেশন স্ক্রিপ্ট (টেবল তৈরি/আল্টার, ইনডেক্স যোগ)\n- ঐচ্ছিক ব্যাকফিল (যেমন নতুন priority ফিল্ড টেমপ্লেট ডিফল্ট থেকে সেট করা)
ভর্তি ডেটা নিয়ে মাইগ্রেশন টেস্ট করুন—ফাঁকা DB নয়।
লোকাল DB ধীরে ধীরে বাড়ে। আগেভাগেই পরিকল্পনা করুন:\n\n- পেজিনেশন লিস্ট ভিউ-এর জন্য (limit/offset বা কার্সর বাই ডেট)\n- প্রুনিং রুলস (উদাহরণ: ৯০ দিন পরে সিঙ্ক হওয়া সম্পন্ন আইটেমের লোকাল কপি মুছে ফেলা)\n- আর্কাইভিং (ইতিহাস রাখুন কিন্তু “আর্কাইভ টেবিল” বা কম্প্রেসড রেকর্ডে সরান)
এতে মোবাইলটি অনেক মাস ব্যবহার পরেও দ্রুত থাকবে।
ভালো একটি অফলাইন চেকলিস্ট অ্যাপ “সিঙ্ক স্ক্রিন” করে না—এটি ব্যবহারকারীর অ্যাকশন সিঙ্ক করে। সবচেয়ে সহজ উপায় হলো একটি আউটবক্স (সিঙ্ক) কিউ: ব্যবহারকারী যে প্রতিটি পরিবর্তন করে তা প্রথমে লোকালভাবে রেকর্ড করা হয়, পরে সার্ভারে পাঠানো হয়।
যখন ব্যবহারকারী একটি আইটেম চেক করে, নোট যোগ করে, বা একটি চেকলিস্ট সম্পন্ন করে, সেই অ্যাকশনটি লোকাল টেবিলে outbox_events হিসেবে লিখুন যার মধ্যে থাকবে:\n\n- একটি ইউনিক event_id (UUID)\n- type (উদাহরণ: CHECK_ITEM, ADD_NOTE)\n- payload (বিস্তারিত)\n- created_at\n- status (pending, sending, sent, failed)
এটি অফলাইন কাজ ইন্সট্যান্ট এবং পূর্বানুমেয় করে: UI লোকাল DB থেকে আপডেট হয়, আর সিঙ্ক সিস্টেম ব্যাকগ্রাউন্ডে কাজ করে।
সিঙ্ক ক্রমাগত না চালান। পরিষ্কার ট্রিগার বেছে নিন যাতে ব্যবহারকারীরা টাইমলি আপডেট পায় কিন্তু ব্যাটারি নিঃশেষ না হয়:\n\n- অ্যাপ স্টার্ট / রিজিউম: পেন্ডিং ইভেন্ট দ্রুত ফ্লাশ করুন\n- কানেকটিভিটি পরিবর্তন: নেটওয়ার্ক ফিরে এলে পুনরায় চেষ্টা করুন\n- ম্যানুয়াল “Sync now”: ব্যবহারকারীদের জন্য সেফটি ভালভ\n- ব্যাকগ্রাউন্ড টাস্ক (যদি অনুমতি থাকে): সময়ে সময়ে ক্যাচ-আপ
নিয়মগুলো সরল ও দৃশ্যমান রাখুন। যদি অ্যাপ সিঙ্ক করতে না পারে, একটি ছোট স্ট্যাটাস ইন্ডিকেটর দেখান এবং কাজ ব্যবহারযোগ্য রাখুন।
প্রতিটি চেকবক্সের জন্য আলাদা HTTP কল পাঠানোর বদলে, একাধিক আউটবক্স ইভেন্ট ব্যাচ করে পাঠান (যেমন 20–100 ইভেন্ট)। ব্যাচিং রেডিও ওয়েকআপ কমায়, খারাপ নেটওয়ার্কে থ্রুপুট বাড়ায় এবং সিঙ্ক সময় ছোট রাখে।
বাস্তব নেটওয়ার্ক অনুরোধ হারিয়ে দেয়। আপনার সিঙ্ক ধরে নেবে প্রতিটি অনুরোধ দুবারও পাঠানো হতে পারে।
প্রতিটি ইভেন্টকে আইডেমপটেন্ট করুন event_id দিয়ে এবং সার্ভার প্রক্রিয়াজাত ID সংরক্ষণ করে (অথবা idempotency key ব্যবহার করুন)। একই ইভেন্ট আবার এলে সার্ভার সাফল্য ফেরত দিবে কিন্তু দ্বিগুণ প্রয়োগ করবে না। এতে ব্যাকঅফসহ আগ্রসিভ রিট্রাই করা যায়।
অফলাইন চেকলিস্ট চমৎকারভাবে সহজ মনে হলেও একই চেকলিস্টে দুই ডিভাইসে এডিট হলে সমস্যা দেখা দেয়। যদি আপনি কনফ্লিক্ট সম্পর্কে আগে থেকে পরিকল্পনা না করেন, তবে মিসিং আইটেম, ডুপ্লিকেট টাস্ক, বা ওভাররাইটেড নোট—এসব হবে।
সাধারণ প্যাটার্নগুলো:
অগ্রিম একটি স্ট্রাটেজি বেছে নিন এবং কোথায় প্রযোজ্য তা স্পষ্ট করুন:
অধিকাংশ অ্যাপ মিশ্র করে: ডিফল্টে per-field merge, কিছু ক্ষেত্রে LWW, এবং যেখানে দরকার সেখানে user-assisted resolution।
কনফ্লিক্ট পরে “বোধ” করার মতো নয়—আপনাকে ডেটায় সংকেত রাখতে হবে:\n\n- প্রতিটি চেকলিস্ট/আইটেমে সার্ভার রিভিশন (ইনক্রিমেন্টিং সংখ্যা) বা ETag।\n- ব্যবহারকারী এডিট শুরু করার সময় রেকর্ড করা লোকাল বেস রিভিশন।\n- ঐচ্ছিক: অপারেশন টাইমস্ট্যাম্প এবং ডিভাইস/ব্যবহারকারী ID অডিটযোগ্যতার জন্য।
সিঙ্কের সময়, যদি সার্ভার রিভিশন লোকাল বেস রিভিশন থেকে বদলে যায়, তবে কনফ্লিক্ট আছে।
যখন ব্যবহারকারীর ইনপুট দরকার, দ্রুত রাখুন:\n\n- “আপনার ভার্সন” বনাম “সার্ভার ভার্সন” দেখান যেখানে ভিন্ন ফিল্ডগুলো হাইলাইট করা আছে।\n- অফার করুন Keep mine / Keep theirs এবং টেক্সট ফিল্ডের জন্য ঐচ্ছিক Copy both।\n- ব্যবহারকারীদের ইনলাইন রেজলভ করার সুযোগ দিন; পুরো অ্যাপ ব্লক করবেন না।
আগেভাগেই পরিকল্পনা করলে আপনার সিঙ্ক লজিক, স্টোরেজ স্কিমা এবং UX সঙ্গত থাকে—আর লঞ্চের ঠিক আগে অপ্রত্যাশিত সমস্যা এড়ানো যায়।
অফলাইন সাপোর্ট তখনই “রিয়েল” মনে হয় যখন UI পরিষ্কার করে বলে কি হচ্ছে। ওয়্যারহাউস, হাসপাতাল, বা জব সাইটের ব্যবহারকারীরা জানতে চান তাদের কাজ নিরাপদ কি না।
কী স্ক্রিনগুলোর উপরে একটি ছোট, স্থায়ী স্টেট ইন্ডিকেটর দেখান:
অ্যাপ অফলাইন গেলে ব্লকিং পপ-আপ এড়ান—একটি হালকা ব্যানার যা ডিসমিস করা যায় যথেষ্ট। অনলাইন এলে একটি সংক্ষিপ্ত “Syncing…” স্টেট দেখান, পরে চুপচাপ তা মুছুন।
প্রতিটি সম্পাদনা অবিলম্বে সেভ হয়েছে বলে অনুভব করানো উচিত, এমনকি ডিকনেক্টেড হলেও। একটি ভালো প্যাটার্ন তিন-স্টেজ সেভ স্ট্যাটাস:
এই ফিডব্যাক ক্রিয়ার নিকটেই রাখুন: চেকলিস্ট শিরোনামের পাশে, আইটেম রো লেভেলে (সমালোচনামূলক ফিল্ডের জন্য), অথবা একটি ছোট ফুটার সারাংশে (“3 changes pending sync”)। যদি কিছু সিঙ্ক করতে ব্যর্থ হয়, স্পষ্ট রিট্রাই অ্যাকশন দেখান—ব্যবহারকারীকে খোঁজাখুঁজি করাতে দেবেন না।
অফলাইন কাজ ভুল বাড়ায়। গার্ডরেইল যোগ করুন:\n\n- ড্রাফট অর্ধেক সম্পন্ন চেকলিস্টের জন্য (টাইপ করার সময় অটো-সেভ)\n- Undo দ্রুত reverals এর জন্য (বিশেষত টগল ও ডিলিট)\n- Confirm destructive actions যখন একাধিক আইটেম বা পুরো চেকলিস্ট মুছে যায়
সর্বশেষ কয়েক মিনিটের জন্য “Restore recently deleted” ভিউ বিবেচনা করুন।
চেকলিস্ট প্রায়শই টুল বা গ্লাভ পরা অবস্থায় পূরণ করা হয়। গতি অগ্রাধিকার দিন:\n\n- বড় ট্যাপ টার্গেট টগল ও চেকবক্সের জন্য\n- স্মার্ট ডিফল্ট (পূর্বনির্ধারিত অ্যাসাইনী, লোকেশন, সাধারণ মান)\n- দ্রুত অ্যাকশন (আইটেম যোগ, সব চিহ্নিত করা, শেষ এন্ট্রি ডুপ্লিকেট করা)
হ্যাপি পথের জন্য ডিজাইন করুন: ব্যবহারকারীরা দ্রুত চেকলিস্ট পূরণ করতে পারবে, অ্যাপ পরে চুপচাপ অফলাইন বিবরণ সামলাবে।
অফলাইন চেকলিস্ট ভাঙে যদি ব্যবহারকারী প্রয়োজনীয় প্রাসঙ্গিকতা (টেমপ্লেট, সরঞ্জাম তালিকা, সাইট ইনফো, রিকোয়ার্ড ফটো, সেফটি রুল) অ্যাক্সেস করতে না পারে। এগুলোকে “রেফারেন্স ডেটা” হিসেবে বিবেচনা করে লোকালি ক্যাশ করুন।
কমপক্ষে সেই সেট ক্যাশ করুন যা কাজ সম্পন্ন করার জন্য দরকার:
একটি দীর্ঘমেয়াদী নিয়ম: যদি UI অনলাইনে খুললে স্পিনার দেখায়, তাহলে সেই নির্ভরশীলতা ক্যাশ করুন।
সবকিছু একই সততার প্রয়োজন নেই। প্রতিটি ডেটা টাইপের জন্য TTL নির্ধারণ করুন:\n\n- টেমপ্লেট: বড় TTL (দিবস/সপ্তাহ) তবে অ্যাপ স্টার্ট বা অনলাইন হলে রিফ্রেশ করুন\n- কমপ্লায়েন্স/সেফটি রুল: ছোট TTL (ঘণ্টা/দিন) এবং বেশি আগ্রাসী রিফ্রেশ\n- বড় মিডিয়া: অন-ডিমান্ড ফেচ করুন, কিন্তু “মাস্ট-হ্যাভ” আইটেমগুলো অফলাইনে পিন করুন
ইভেন্ট-ভিত্তিক রিফ্রেশ ট্রিগারও যোগ করুন: ব্যবহারকারী সাইট/প্রজেক্ট বদলে দিল, নতুন অ্যাসাইনমেন্ট পেল, অথবা একটি টেমপ্লেট খোলে যা সম্প্রতি চেক করা হয়নি।
যদি কেউ মধ্যবর্তী চেকলিস্টের সময় টেমপ্লেট আপডেট হয়ে যায়, ফর্ম নাটকীয়ভাবে চেঞ্জ করা থেকে বিরত থাকুন। একটি স্পষ্ট “template updated” ব্যানার দেখান এবং অপশন দিন:\n\n- Cached ভার্সন ধরে চালিয়ে যান (সবচেয়ে পূর্বানুমেয়)\n- আপডেট করে পরিবর্তনগুলো রিভিউ করুন (শর্ট ডিফ দেখান: যোগ/বিয়োগ করা ফিল্ড)
নতুন রিকোয়ার্ড ফিল্ড উপস্থিত হলে চেকলিস্টকে “submit করার আগে আপডেট প্রয়োজন” হিসেবে মার্ক করুন ব্লক না করে।
ভার্সনিং ও ডেল্ট ব্যবহার করুন: কেবল পরিবর্তিত টেমপ্লেট/লুকআপ রো সিঙ্ক করুন (updatedAt বা সার্ভার চেঞ্জ টোকেন দ্বারা)। প্রতিটি dataset-এর জন্য সিঙ্ক কার্সর সেভ করুন যাতে অ্যাপ দ্রুত রিস্যুম করতে পারে এবং ব্যান্ডউইথ কম লাগে—এইটা সেলুলার নেটওয়ার্কে বিশেষভাবে জরুরি।
অফলাইন চেকলিস্ট ব্যবহারের সুবিধা হল ডেটা ডিভাইসে থাকে—কিন্তু এর মানে আপনি ডিভাইস হারানো, শেয়ার হওয়া, বা কমপ্রোমাইজ হলে সুরক্ষাটা নিশ্চিত করবেন।
কী কী থেকে রক্ষা করবেন তা ঠিক করুন:\n\n- আনলক করা ডিভাইসের কাছে casual attacker\n- হারানো/চুরি ডিভাইস পরে এক্সেস করা\n- মালওয়্যার বা রুটেড/জেইলব্রোকেন ডিভাইস (এগুলোকে পুরোপুরি ডিফেন্ড করা কঠিন)
এটি ঠিক করে দেবে কতটা সিকিউরিটি দরকার ছাড়া অ্যাপ ধীর করবে না।
অ্যাক্সেস টোকেন কখনই প্লেইন লোকাল স্টোরেজে রাখবেন না। OS-দ্বারা প্রদত্ত নিরাপদ স্টোর ব্যবহার করুন:\n\n- iOS: Keychain\n- Android: Keystore (উদাহরণ: EncryptedSharedPreferences বা লাইব্রেরি র্যাপার)
লোকাল ডাটাবেসে দীর্ঘস্থায়ী সিক্রেট রাখবেন না। যদি DB এনক্রিপশনের জন্য কী লাগবে, সেই কী Keychain/Keystore-এ রাখুন।
যদি চেকলিস্টে পার্সোনাল ডেটা, ঠিকানা, ফটো, বা কমপ্লায়েন্স নোট থাকে তবে DB এনক্রিপশন ভালো ধারণা। ট্রেডঅফগুলো:\n\n- সামান্য পারফর্মেন্স ওভারহেড\n- কী ম্যানেজমেন্ট ও রিকভারি জটিলতা
যদি মূল ঝুঁকি হল “কেউ অ্যাপ ফাইল ব্রাউজ করে দেখে ফেলে”, তাহলে এনক্রিপশন মূল্যবান। যদি ডিভাইসগুলো ইতিমধ্যে OS-লেভেল ফুল-ডিস্ক এনক্রিপশন ব্যবহার করে এবং ডেটা কম সেনসিটিভ হয়, আপনি এটাকে বাদ দিতে পারেন।
পরিকল্পনা রাখুন সেশন এক্সপায়ার হলে কি হবে:\n\n- ইতিমধ্যে ডাউনলোড করা চেকলিস্টগুলিতে একটি গ্রেস পিরিয়ডে রিড-ওনলি এক্সেস দিন\n- এডিটগুলো কিউ করুন কিন্তু সিঙ্ক করার আগে রি-লগইন আবশ্যক করুন\n- একটি স্পষ্ট ব্যানার দেখান: “You’re offline—sign in required to sync”
ফটো/ফাইল অ্যাপ-প্রাইভেট স্টোরেজ পাথে রাখুন, শেয়ারড গ্যালারিতে নয়। প্রতিটি অ্যাটাচমেন্টকে সাইন-ইন করা ব্যবহারকারীর সাথে টায় করুন, অ্যাপ-ভিত্তিক অ্যাক্সেস চেক বাস্তবায়ন করুন, এবং লগআউটের সময় (এবং ঐচ্ছিকভাবে সেটিংসে “Remove offline data” থেকে) ক্যাশড ফাইল মুছুন।
একটি সিঙ্ক ফিচার যা অফিস Wi‑Fi-তে কাজ করে তা এভেলেভেটরে, গ্রামীণ এলাকায়, অথবা যেখানে OS ব্যাকগ্রাউন্ড কাজ থ্রোটল করে তাতে ব্যর্থ হতে পারে। “নেটওয়ার্ক”কে প্রাথমিকভাবে অবিশ্বাস্য ধরুন, এবং সিঙ্ককে নিরাপদভাবে ব্যর্থ ও দ্রুত পুনরুদ্ধারযোগ্যভাবে ডিজাইন করুন।
প্রতিটি নেটওয়ার্ক কলের টাইমবাউন্ড রাখুন। ২ মিনিট আটকে থাকা অ্যাপ ফ্রোজেন লাগায় এবং অন্যান্য কাজ ব্লক করতে পারে।\n\nট্রানজিয়েন্ট ত্রুটির (টাইমআউট, 502/503, অস্থায়ী DNS ইস্যু) জন্য রিট্রাই ব্যবহার করুন, কিন্তু সার্ভারকে হামলা করবেন না। এক্সপোনেনশিয়াল ব্যাকঅফ (উদাহরণ: 1s, 2s, 4s, 8s…) এবং সামান্য র্যান্ডম জিটার ব্যবহার করুন যাতে একসাথে অনেক ডিভাইস একবারে রিট্রাই না করে।
প্ল্যাটফর্ম অনুমতি দিলে ব্যাকগ্রাউন্ডে সিঙ্ক চালান যাতে চেকলিস্ট নীরবে আপলোড হয়। তবুও একটি দৃশ্যমান ম্যানুয়াল অ্যাকশন দিন “Sync now” আস্থা দেওয়ার জন্য এবং ব্যাকগ্রাউন্ড সিঙ্ক ডিলে হলে ব্যবহারকারীদের জন্য।\n\nএটাকে “Last synced 12 min ago”, “3 items pending” এবং একটি অনিয়মিত ব্যানারের সাথে জোড়া দিন যখন অফলাইন থাকে।
অফলাইন অ্যাপগুলো প্রায়ই একই অ্যাকশন বারবার রিটারাই করে। প্রতিটি কিউড পরিবর্তনে ইউনিক request ID (আপনার event_id) দিন এবং এটি রিকোয়েস্টের সঙ্গে পাঠান। সার্ভারে প্রক্রিয়াজাত আইডিগুলো সংরক্ষিত রাখুন এবং ডুপ্লিকেট উপেক্ষা করুন—এতে ব্যবহারকারী দুর্ঘটনাক্রমে দ্বিগুণ ইনস্পেকশন, দ্বিগুণ স্বাক্ষর, বা দ্বিগুণ চেক থেকে রক্ষা পায়।
সিঙ্ক ত্রুটিগুলো প্রসঙ্গে রেকর্ড করুন: কোন চেকলিস্ট, কোন ধাপ, এবং ব্যবহারকারী কী করতে পারে। “Sync failed”–এর বদলে ব্যবহারকারীকে বলুন “2 টি ফটো আপলোড করতে পারিনি—কানেকশন ধীর। অ্যাপ খোলা রাখুন এবং Sync now ট্যাপ করুন।” সহায়তার জন্য “Copy details” অপশনও দিন।
অফলাইন ফিচারগুলো প্রান্তে প্রায়ই ব্যর্থ হয়: একটি টানেল, দুর্বল সিগনাল, আংশিক সেভ, বা বিশাল চেকলিস্ট যা মধ্যেই বাধা পায়। একটি মনোযোগী টেস্ট প্ল্যান এই ইস্যুগুলো লঞ্চের আগে ধরবে।
ফিজিক্যাল ডিভাইসে airplane mode–এ end-to-end টেস্ট করুন, কেবল সিমুলেটরের উপর নয়। তারপর আরও এগোবেন: ক্রিয়াটির মাঝেই কানেকটিভিটি বদলান।
এমন সিচুয়েশন চেষ্টা করুন:\n\n- আইটেম চেক করতে শুরু করুন, তারপর Save চাপার আগে airplane mode চালু করুন।\n- একটি অ্যাটাচমেন্ট আপলোডের সময় কানেকটিভিটি বারবার অন/অফ করুন।\n- সেভ করার সময় অ্যাপ কিল করুন, পুনরায় খুলে ডেটা লস বা ডুপ্লিকেট না হয়েছে নিশ্চিত করুন।\n- লগআউট বা টোকেন এক্সপায়ার যখন অফলাইন—ব্যবহারকারী কী দেখতে ও এডিট করতে পারে তা যাচাই করুন।
আপনি যাচাই করছেন যে লেখাগুলো লোকালভাবে টেকসই, UI স্টেট কনসিস্টেন্ট, এবং অ্যাপ পেন্ডিং পরিবর্তন ভুলে যায় না।
আপনার সিঙ্ক কিউ একটি ব্যবসায়িক লজিক—তাই এটাকে একটি ব্যবসায়িক ইউনিটের মতো আচরণ করুন। অটোমেটেড টেস্ট যোগ করুন:\n\n- অর্ডারিং (oldest-first বনাম priority)\n- ব্যাকঅফসহ রিট্রাই ও “রিট্রাই না করা” ত্রুটি\n- আইডেমপটেন্সি (একই অপারেশন পুনরায় পাঠালে ডুপ্লিকেট না তৈরি হওয়া)\n- কনফ্লিক্ট কেস (সার্ভার একই আইটেম পরিবর্তন করেছে; প্রত্যাশিত রেজাল্ট নিশ্চিত করা)
এইগুলোর একটি ছোট সেট ডিটারমিনিস্টিক টেস্ট মিস্টের সবচেয়ে ব্যয়বহুল বাগগুলো থামায়।
বড়, বাস্তবসম্মত ডেটাসেট তৈরি করুন: দীর্ঘ চেকলিস্ট, অনেক সম্পন্ন আইটেম, এবং অ্যাটাচমেন্ট। পরিমাপ করুন:\n\n- একটি চেকলিস্ট খোলার সময়\n- দ্রুত অনেক আইটেম মার্ক করার সময়\n- শতাব্দীর ব্যবহারের পর স্টোরেজ বৃদ্ধિ ও কোয়েরি গতি
পর্দায় খারাপ ডিভাইস (লো-এন্ড Android, পুরনো iPhone)–এও টেস্ট করুন যেখানে ধীর I/O বটলনেক ফাঁস করে দেয়।
সিঙ্ক সাকসেস রেট ও টাইম-টু-সিঙ্ক (লোকাল পরিবর্তন থেকে সার্ভার কনফার্মেশন) ট্র্যাক করুন। রিলিজের পরে স্পাইক দেখলে সতর্ক হন এবং নেটওয়ার্ক টাইপ অনুসারে সেগমেন্ট করুন। এটি “সিঙ্ক ফ্ল্যাকি মনে হচ্ছে”কে সংখ্যায় পরিণত করে।
অফলাইন চেকলিস্ট অ্যাপ শিপ করা একবারের কাজ নয়—এটি একটি ফিডব্যাক লুপের শুরু। নিরাপদে রিলিজ করা, বাস্তব ব্যবহার দেখা, এবং সিঙ্ক ও ডেটা কোয়ালিটি বাড়ানো লক্ষ্য রাখুন যেন ব্যবহারকারীদের অবাক না করে।
রোলআউটে আগে সেই এন্ডপয়েন্টগুলো লক করুন যার উপরে অ্যাপ নির্ভর করে যাতে ক্লায়েন্ট ও সার্ভার পূর্বানুমেয়ভাবে эভোলভ করে:\n\n- Pull changes: শেষ সিঙ্ক থেকে সার্ভার আপডেটগুলো (কার্সর বা টাইমস্ট্যাম্প দ্বারা)\n- Push actions: লোকাল অ্যাকশনগুলোর ব্যাচ (create item, tick box, edit notes) স্টেবল ID সহ আপলোড করুন\n- Resolve conflicts: জয়ী ভার্সন (বা মার্জ রেজাল্ট) ফিরিয়ে দিন এবং পর্যাপ্ত প্রেক্ষাপট দিন কেন এমন হলো
রেসপন্সগুলো কনসিস্টেন্ট ও স্পষ্ট রাখুন (কি গৃহীত, প্রত্যাখ্যাত, রিট্রাই করা) যাতে অ্যাপ Gracefully recover করতে পারে।
অফলাইন ইস্যুগুলো অদৃশ্য যখন আপনি মাপেন না। ট্র্যাক করুন:\n\n- সিঙ্ক ফলিয়ারেট ও শীর্ষতর ত্রুটি কারণ (auth expired, timeout, payload too large)\n- কিউ গভীরতা ও টাইম-টু-সিঙ্ক (অ্যাকশনগুলো কতোক্ষণ অপেক্ষা করে থাকে)\n- ডেটা ইন্টিগ্রিটি সিগন্যাল (ডুপ্লিকেট আইটেম, অনুপস্থিত চেকলিস্ট এন্ট্রি, অপ্রত্যাশিত ডিলিট)
সিঙ্গেল এরর নয়—স্পাইক-এ এলার্ট করুন, এবং করিলেশন ID লগ করুন যাতে সাপোর্ট একজন ব্যবহারকারীর সিঙ্ক স্টোরি ট্রেস করতে পারে।
ফিচার ফ্ল্যাগ ব্যবহার করে সিঙ্গেল-হালি রোলআউট করুন এবং ভাঙা পথ দ্রুত ডিসেবল করার অপশন রাখুন। স্কিমা মাইগ্রেশনের জন্যও সাবধানতা রাখুন:\n\n- সম্ভব হলে ব্যাকওয়ার্ড-কম্প্যাটিবল মাইগ্রেশন\n- লোকাল DB আপগ্রেড ব্যর্থ হলে “সেফ মোড” ফলব্যাক
একটি হালকা ওজনের অনবোর্ডিং দিন: কিভাবে অফলাইন স্ট্যাটাস চিনবেন, “Queued” মানে কী, এবং কখন ডেটা সিঙ্ক হবে। একটি হেল্প আর্টিকেল প্রকাশ করুন এবং অ্যাপ থেকে লিংক দিন (দেখুন আইডিয়া /blog/)।
যদি আপনি দ্রুত এই অফলাইন প্যাটার্নগুলো যাচাই করতে চান (লোকাল স্টোর, আউটবক্স কিউ, এবং একটি বেসিক Go/PostgreSQL ব্যাকএন্ড), একটি ভিব-কোডিং প্ল্যাটফর্ম যেমন Koder.ai আপনাকে চ্যাট-ড্রিভেন স্পেক থেকে কার্যকর প্রোটোটাইপ দাঁড় করাতে সাহায্য করতে পারে। আপনি চেকলিস্ট UX ও সিঙ্ক নিয়মগুলো উন্নত করে বাস্তবে পরিক্ষা করতে পারবেন, এবং কোড এক্সপোর্ট করে যখন প্রস্তুত তখন উৎস কোড রাখতে পারবেন।
“অফলাইন” বলতে কয়েক সেকেন্ডের ড্রপআউট থেকেও শুরু করে কয়েক দিনের সম্পূর্ণ অনুপস্থিতি পর্যন্ত সবকিছু বোঝাতে পারে। নির্ধারণ করুন:
যদি ব্যবহারকারীদের কম/জিরো সিগনালে নির্ভর করে কাজ করতেই হয়, তাহলে বেছে নিন অফলাইন-প্রথম: ডিভাইসই প্রধান কাজের স্থান এবং সিঙ্ক ব্যাকগ্রাউন্ডে চলে।
যদি বেশিরভাগ কাজ অনলাইনে হয় এবং অফলাইনকে সীমিত রাখা যায় (প্রায়শই রিড-অনলি বা সীমিত সম্পাদনা), তখন অনলাইন-প্রথম + অফলাইন ফলব্যাক বিবেচনা করুন।
একটি ব্যবহারিক বেসলাইন হলো:
যদি কোনো ফিচার সীমাবদ্ধ (উদাহরণ: টিম মেম্বার আমন্ত্রণ), UI-তে ব্যাখ্যা দিন।
আপনার ডেটাকে দুইভাগে ভাগ করুন:
এটি টেমপ্লেট আপডেটে ইতিহাস নষ্ট হওয়া থেকে রক্ষা করে এবং অডিটিং সহজ করে।
অফলাইনে কাজকে সিঙ্কযোগ্য করে তোলার জন্য ক্লায়েন্ট-সাইড জেনারেট করা স্থায়ী ID ব্যবহার করুন (UUID), এবং এই ফিল্ডগুলো অন্তর্ভুক্ত করুন:
updated_at প্রতিটি রেকর্ডেversion/revision কাউন্টারtemplate_versionএকটি স্থানীয় আউটবক্স কিউ ব্যবহার করুন যা অ্যাকশনগুলো রেকর্ড করে (স্ক্রিন সিঙ্ক না করে)। প্রতিটি ইভেন্টে থাকতে পারে:
প্রতিটি পরিবর্তনকে আবার পাঠানো নিরাপদ করুন: প্রতিটি কিউড চেইঞ্জে event_id (idempotency key) পাঠান। সার্ভার প্রক্রিয়াজাত IDগুলো সংরক্ষণ করবে এবং ডুপ্লিকেট এন্ট্রি উপেক্ষা করবে।
এতে দুবার রিকোয়েস্ট হলে ডাবল-ক্রিয়েশন বা ডাবল-চেকিং বন্ধ হবে।
সাধারণত অ্যাপগুলো মিশ্র কৌশল ব্যবহার করে:
কনফ্লিক্ট ডিটেকশনের জন্য সার্ভার রিভিশন/ETag এবং ক্লায়েন্টের বেস রিভিশন ট্র্যাক করুন।
একটি পূর্বাভাসযোগ্য, কোয়েরি-সক্ষম স্টোর বেছে নিন:
আরও: প্রথম রিলিজ থেকেই স্কিমা ভার্সনিং ও মাইগ্রেশন রাখুন।
OS-প্রদানকৃত নিরাপদ স্টোর ব্যবহার করুন:
ডাটাবেস এনক্রিপশন দরকার হলে কী ম্যানেজমেন্ট বিবেচ্য রাখুন এবং লগআউট হলে অফলাইনে রাখা ফাইল মুছুন।
এইগুলো সিঙ্ক, রিট্রাই এবং কনফ্লিক্ট ডিটেকশনে অনেকটা সহায়ক।
event_id (UUID)type (যেমন CHECK_ITEM, ADD_NOTE)payloadcreated_atstatus (pending, sending, sent, failed)UI স্থানীয় DB থেকেই দ্রুত আপডেট হবে; আউটবক্স পরে ব্যাকগ্রাউন্ডে সিঙ্ক করবে।