অ্যান্ড্রয়েড আর্কিটেকচারের জন্য সুপারিশ

এই পৃষ্ঠাটি বেশ কয়েকটি আর্কিটেকচার সেরা অনুশীলন এবং সুপারিশ উপস্থাপন করে। আপনার অ্যাপের গুণমান, দৃঢ়তা এবং মাপযোগ্যতা উন্নত করতে সেগুলি গ্রহণ করুন। তারা আপনার অ্যাপকে রক্ষণাবেক্ষণ এবং পরীক্ষা করা আরও সহজ করে তোলে।

নীচের সেরা অনুশীলনগুলি বিষয় অনুসারে গোষ্ঠীবদ্ধ করা হয়েছে৷ প্রতিটির একটি অগ্রাধিকার রয়েছে যা প্রতিফলিত করে যে দলটি কতটা দৃঢ়ভাবে সুপারিশ করে। অগ্রাধিকার তালিকা নিম্নরূপ:

  • দৃঢ়ভাবে সুপারিশ করা হয়েছে: আপনার এই অনুশীলনটি বাস্তবায়ন করা উচিত যদি না এটি আপনার পদ্ধতির সাথে মৌলিকভাবে সংঘর্ষ হয়।
  • প্রস্তাবিত: এই অনুশীলনটি আপনার অ্যাপ উন্নত করতে পারে।
  • ঐচ্ছিক: এই অনুশীলনটি নির্দিষ্ট পরিস্থিতিতে আপনার অ্যাপকে উন্নত করতে পারে।

স্তরযুক্ত স্থাপত্য

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

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

UI স্তরের উপাদান যেমন কম্পোজেবল, অ্যাক্টিভিটি, বা ভিউমডেলগুলি সরাসরি ডেটা উত্সের সাথে ইন্টারঅ্যাক্ট করা উচিত নয়৷ তথ্য উৎসের উদাহরণ হল:

  • ডেটাবেস, ডেটাস্টোর, শেয়ার করা পছন্দ, ফায়ারবেস এপিআই।
  • GPS অবস্থান প্রদানকারী।
  • ব্লুটুথ ডেটা প্রদানকারী।
  • নেটওয়ার্ক সংযোগ স্থিতি প্রদানকারী.
coroutines এবং প্রবাহ ব্যবহার করুন. স্তরগুলির মধ্যে যোগাযোগ করতে coroutines এবং ফ্লো ব্যবহার করুন৷

আরও কোরোটিন সেরা অনুশীলন এখানে

একটি ডোমেইন স্তর ব্যবহার করুন। একটি ডোমেন স্তর ব্যবহার করুন , কেস ব্যবহার করুন, যদি আপনি একাধিক ভিউমডেল জুড়ে ডেটা স্তরের সাথে ইন্টারঅ্যাক্ট করে এমন ব্যবসায়িক যুক্তি পুনঃব্যবহার করতে চান বা আপনি একটি নির্দিষ্ট ভিউমডেলের ব্যবসায়িক যুক্তি জটিলতাকে সহজ করতে চান

UI স্তর

UI স্তরের ভূমিকা হল স্ক্রিনে অ্যাপ্লিকেশন ডেটা প্রদর্শন করা এবং ব্যবহারকারীর ইন্টারঅ্যাকশনের প্রাথমিক পয়েন্ট হিসাবে পরিবেশন করা। UI স্তরের জন্য এখানে কিছু সেরা অনুশীলন রয়েছে:

সুপারিশ বর্ণনা
ইউনিডাইরেশনাল ডেটা ফ্লো (UDF) অনুসরণ করুন। ইউনিডাইরেশনাল ডেটা ফ্লো (UDF) নীতিগুলি অনুসরণ করুন, যেখানে ভিউ মডেলগুলি পর্যবেক্ষক প্যাটার্ন ব্যবহার করে UI অবস্থা প্রকাশ করে এবং মেথড কলের মাধ্যমে UI থেকে অ্যাকশন গ্রহণ করে।
AAC ViewModels ব্যবহার করুন যদি তাদের সুবিধাগুলি আপনার অ্যাপে প্রযোজ্য হয়। ব্যবসায়িক যুক্তি পরিচালনা করতে AAC ViewModels ব্যবহার করুন এবং UI-তে UI অবস্থা প্রকাশ করতে অ্যাপ্লিকেশন ডেটা আনুন (কম্পোজ বা Android Views)।

এখানে আরও ViewModel সেরা অনুশীলন দেখুন।

এখানে ViewModels এর সুবিধা দেখুন।

জীবনচক্র-সচেতন UI রাজ্য সংগ্রহ ব্যবহার করুন। উপযুক্ত লাইফসাইকেল-সচেতন কোরোটিন নির্মাতা ব্যবহার করে UI থেকে UI অবস্থা সংগ্রহ করুন: ভিউ সিস্টেমে repeatOnLifecycle এবং Jetpack Compose-এ collectAsStateWithLifecycle

repeatOnLifecycle সম্পর্কে আরও পড়ুন।

collectAsStateWithLifecycle সম্পর্কে আরও পড়ুন।

ViewModel থেকে UI এ ইভেন্ট পাঠাবেন না। ViewModel-এ অবিলম্বে ইভেন্টটি প্রক্রিয়া করুন এবং ইভেন্ট পরিচালনার ফলাফল সহ একটি রাষ্ট্রীয় আপডেট করুন৷ UI ইভেন্ট সম্পর্কে আরও এখানে
একটি একক কার্যকলাপ অ্যাপ্লিকেশন ব্যবহার করুন. আপনার অ্যাপে একাধিক স্ক্রিন থাকলে স্ক্রিন এবং আপনার অ্যাপের গভীর লিঙ্কের মধ্যে নেভিগেট করতে নেভিগেশন ফ্র্যাগমেন্ট বা নেভিগেশন কম্পোজ ব্যবহার করুন।
জেটপ্যাক কম্পোজ ব্যবহার করুন। ফোন, ট্যাবলেট এবং ফোল্ডেবল এবং Wear OS-এর জন্য নতুন অ্যাপ তৈরি করতে Jetpack Compose ব্যবহার করুন।

নিচের স্নিপেটে লাইফসাইকেল-সচেতন পদ্ধতিতে কীভাবে UI স্টেট সংগ্রহ করা যায় তার রূপরেখা দেওয়া হয়েছে:

ভিউ

class MyFragment : Fragment() {

    private val viewModel: MyViewModel by viewModel()

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)

        viewLifecycleOwner.lifecycleScope.launch {
            viewLifecycleOwner.repeatOnLifecycle(Lifecycle.State.STARTED) {
                viewModel.uiState.collect {
                    // Process item
                }
            }
        }
    }
}

রচনা করুন

@Composable
fun MyScreen(
    viewModel: MyViewModel = viewModel()
) {
    val uiState by viewModel.uiState.collectAsStateWithLifecycle()
}

মডেল দেখুন

ViewModels UI অবস্থা এবং ডেটা স্তরে অ্যাক্সেস প্রদানের জন্য দায়ী। ভিউমডেলের জন্য এখানে কিছু সেরা অনুশীলন রয়েছে:

সুপারিশ বর্ণনা
ভিউ মডেলগুলিকে অ্যান্ড্রয়েড জীবনচক্রের অজ্ঞেয়বাদী হওয়া উচিত। ViewModels কোনো লাইফসাইকেল-সম্পর্কিত প্রকারের রেফারেন্স রাখা উচিত নয়। নির্ভরতা হিসাবে Activity, Fragment, Context বা Resources পাস করবেন না। যদি ViewModel-এ কোনো Context প্রয়োজন হয়, তাহলে সেটি সঠিক স্তরে থাকলে আপনার দৃঢ়ভাবে মূল্যায়ন করা উচিত।
coroutines এবং প্রবাহ ব্যবহার করুন.

ভিউমডেল ব্যবহার করে ডেটা বা ডোমেন স্তরগুলির সাথে ইন্টারঅ্যাক্ট করে:

  • কোটলিন অ্যাপ্লিকেশন ডেটা প্রাপ্তির জন্য প্রবাহিত হয়,
  • viewModelScope ব্যবহার করে কর্ম সঞ্চালনের জন্য ফাংশন suspend
পর্দা স্তরে ViewModels ব্যবহার করুন.

UI এর পুনঃব্যবহারযোগ্য টুকরোগুলিতে ViewModels ব্যবহার করবেন না। আপনার ভিউ মডেলগুলি এতে ব্যবহার করা উচিত:

  • স্ক্রীন-স্তরের কম্পোজেবল,
  • দৃশ্যের মধ্যে কার্যকলাপ/খন্ড,
  • জেটপ্যাক নেভিগেশন ব্যবহার করার সময় গন্তব্য বা গ্রাফ।
পুনরায় ব্যবহারযোগ্য UI উপাদানগুলিতে প্লেইন স্টেট হোল্ডার ক্লাস ব্যবহার করুন। পুনঃব্যবহারযোগ্য UI উপাদানগুলিতে জটিলতা পরিচালনার জন্য প্লেইন স্টেট হোল্ডার ক্লাস ব্যবহার করুন। এতে করে রাষ্ট্রকে বাহ্যিকভাবে উত্তোলন ও নিয়ন্ত্রণ করা যায়।
AndroidViewModel ব্যবহার করবেন না। ViewModel ক্লাস ব্যবহার করুন, AndroidViewModel নয়। ViewModel-এ Application ক্লাস ব্যবহার করা উচিত নয়। পরিবর্তে, নির্ভরতাকে UI বা ডেটা স্তরে সরান৷
একটি UI অবস্থা প্রকাশ করুন। ভিউমডেলগুলিকে uiState নামক একটি একক সম্পত্তির মাধ্যমে UI-তে ডেটা প্রকাশ করা উচিত। যদি UI একাধিক, অসংলগ্ন ডেটার টুকরো দেখায়, VM একাধিক UI স্টেট বৈশিষ্ট্য প্রকাশ করতে পারে।
  • আপনি uiState একটি StateFlow করা উচিত.
  • আপনি uiState তৈরি করতে হবে stateIn অপারেটর ব্যবহার করে WhileSubscribed(5000) নীতি (উদাহরণ) যদি ডেটা ক্রমানুসারের অন্যান্য স্তর থেকে ডেটার স্ট্রিম হিসাবে আসে।
  • ডেটা স্তর থেকে ডেটার কোনও স্ট্রিম না থাকা সহজ ক্ষেত্রে, একটি অপরিবর্তনীয় StateFlow (উদাহরণ) হিসাবে প্রকাশ করা একটি MutableStateFlow ব্যবহার করা গ্রহণযোগ্য।
  • আপনি ${Screen}UiState ডেটা ক্লাস হিসাবে বেছে নিতে পারেন যাতে ডেটা, ত্রুটি এবং লোডিং সংকেত থাকতে পারে৷ বিভিন্ন রাজ্য একচেটিয়া হলে এই শ্রেণীটি একটি সীলমোহরযুক্ত শ্রেণীও হতে পারে।

নিম্নলিখিত স্নিপেটটি একটি ভিউমডেল থেকে কীভাবে UI অবস্থা প্রকাশ করতে হয় তার রূপরেখা দেয়:

@HiltViewModel
class BookmarksViewModel @Inject constructor(
    newsRepository: NewsRepository
) : ViewModel() {

    val feedState: StateFlow<NewsFeedUiState> =
        newsRepository
            .getNewsResourcesStream()
            .mapToFeedState(savedNewsResourcesState)
            .stateIn(
                scope = viewModelScope,
                started = SharingStarted.WhileSubscribed(5_000),
                initialValue = NewsFeedUiState.Loading
            )

    // ...
}

জীবনচক্র

অ্যান্ড্রয়েড লাইফসাইকেলের সাথে কাজ করার জন্য নিম্নলিখিত কিছু সেরা অনুশীলনগুলি রয়েছে:

সুপারিশ বর্ণনা
অ্যাক্টিভিটিস বা ফ্র্যাগমেন্টে লাইফসাইকেল পদ্ধতি ওভাররাইড করবেন না। লাইফসাইকেল পদ্ধতিগুলিকে ওভাররাইড করবেন না যেমন ক্রিয়াকলাপগুলিতে onResume বা ফ্র্যাগমেন্টস৷ পরিবর্তে LifecycleObserver ব্যবহার করুন। লাইফসাইকেল একটি নির্দিষ্ট Lifecycle.State এ পৌঁছালে অ্যাপটিকে কাজ করার প্রয়োজন হলে, repeatOnLifecycle API ব্যবহার করুন।

নিম্নলিখিত স্নিপেটে একটি নির্দিষ্ট লাইফসাইকেল অবস্থার প্রেক্ষিতে কীভাবে ক্রিয়াকলাপ সম্পাদন করতে হয় তার রূপরেখা দেয়:

ভিউ

class MyFragment: Fragment() {
    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)

        viewLifecycleOwner.lifecycle.addObserver(object : DefaultLifecycleObserver {
            override fun onResume(owner: LifecycleOwner) {
                // ...
            }
            override fun onPause(owner: LifecycleOwner) {
                // ...
            }
        }
    }
}

রচনা করুন

@Composable
fun MyApp() {

    val lifecycleOwner = LocalLifecycleOwner.current
    DisposableEffect(lifecycleOwner, ...) {
        val lifecycleObserver = object : DefaultLifecycleObserver {
            override fun onStop(owner: LifecycleOwner) {
                // ...
            }
        }

        lifecycleOwner.lifecycle.addObserver(lifecycleObserver)
        onDispose {
            lifecycleOwner.lifecycle.removeObserver(lifecycleObserver)
        }
    }
}

নির্ভরতা পরিচালনা করুন

উপাদানগুলির মধ্যে নির্ভরতা পরিচালনা করার সময় আপনাকে বেশ কয়েকটি সর্বোত্তম অনুশীলন পর্যবেক্ষণ করা উচিত:

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

টেস্টিং

নিম্নলিখিত পরীক্ষার জন্য কিছু সেরা অনুশীলন আছে:

সুপারিশ বর্ণনা
কি পরীক্ষা করতে হবে তা জেনে নিন

যতক্ষণ না প্রকল্পটি হ্যালো ওয়ার্ল্ড অ্যাপের মতো মোটামুটি সহজ না হয়, আপনার এটি পরীক্ষা করা উচিত, সর্বনিম্ন এর সাথে:

  • ইউনিট পরীক্ষা ViewModels, প্রবাহ সহ।
  • ইউনিট পরীক্ষা ডেটা স্তর সত্তা. অর্থাৎ রিপোজিটরি এবং ডেটা সোর্স।
  • UI নেভিগেশন পরীক্ষা যা CI-তে রিগ্রেশন পরীক্ষা হিসাবে কার্যকর।
উপহাসের চেয়ে নকল পছন্দ করুন। অ্যান্ড্রয়েড ডকুমেন্টেশনে পরীক্ষা দ্বিগুণ ব্যবহারে আরও পড়ুন।
স্টেটফ্লো পরীক্ষা করুন। StateFlow পরীক্ষা করার সময়:

আরও তথ্যের জন্য, অ্যান্ড্রয়েড ড্যাক গাইডে কী পরীক্ষা করতে হবে তা দেখুন।

মডেল

আপনার অ্যাপ্লিকেশানগুলিতে মডেলগুলি তৈরি করার সময় আপনার এই সর্বোত্তম অনুশীলনগুলি পালন করা উচিত:

সুপারিশ বর্ণনা
জটিল অ্যাপে লেয়ার প্রতি একটি মডেল তৈরি করুন।

জটিল অ্যাপ্লিকেশানগুলিতে, বিভিন্ন স্তর বা উপাদানে নতুন মডেল তৈরি করুন যখন এটি বোধগম্য হয়৷ নিম্নলিখিত উদাহরণ বিবেচনা করুন:

  • একটি দূরবর্তী ডেটা উত্স নেটওয়ার্কের মাধ্যমে প্রাপ্ত মডেলটিকে একটি সহজ শ্রেণিতে ম্যাপ করতে পারে শুধুমাত্র অ্যাপটির প্রয়োজনীয় ডেটা সহ
  • সংগ্রহস্থলগুলি DAO মডেলগুলিকে সহজ ডেটা ক্লাসে ম্যাপ করতে পারে কেবলমাত্র UI স্তরের প্রয়োজনীয় তথ্য দিয়ে।
  • ViewModel UiState ক্লাসে ডেটা লেয়ার মডেল অন্তর্ভুক্ত করতে পারে।

নামকরণের রীতি

আপনার কোডবেস নামকরণ করার সময়, আপনাকে নিম্নলিখিত সেরা অনুশীলনগুলি সম্পর্কে সচেতন হওয়া উচিত:

সুপারিশ বর্ণনা
নামকরণ পদ্ধতি।
ঐচ্ছিক
পদ্ধতি একটি ক্রিয়া বাক্যাংশ হতে হবে. উদাহরণস্বরূপ, makePayment()
নামকরণের বৈশিষ্ট্য।
ঐচ্ছিক
বৈশিষ্ট্য একটি বিশেষ্য বাক্যাংশ হতে হবে. উদাহরণস্বরূপ, inProgressTopicSelection
ডেটার স্ট্রীম নামকরণ।
ঐচ্ছিক
যখন একটি ক্লাস একটি ফ্লো স্ট্রীম, লাইভডেটা বা অন্য কোন স্ট্রীম প্রকাশ করে, তখন নামকরণের নিয়ম হল get{model}Stream() । উদাহরণস্বরূপ, getAuthorStream(): Flow<Author> যদি ফাংশনটি মডেলের একটি তালিকা প্রদান করে তাহলে মডেলের নামটি বহুবচনে থাকা উচিত: getAuthorsStream(): Flow<List<Author>>
নামকরণ ইন্টারফেস বাস্তবায়ন।
ঐচ্ছিক
ইন্টারফেস বাস্তবায়নের জন্য নাম অর্থপূর্ণ হওয়া উচিত। একটি ভাল নাম পাওয়া না গেলে উপসর্গ হিসাবে Default রাখুন। উদাহরণস্বরূপ, একটি NewsRepository ইন্টারফেসের জন্য, আপনার কাছে একটি OfflineFirstNewsRepository বা InMemoryNewsRepository থাকতে পারে। যদি আপনি কোন ভাল নাম খুঁজে না পান, তাহলে DefaultNewsRepository ব্যবহার করুন। FakeAuthorsRepository তে যেমন ফেক ইমপ্লিমেন্টেশন Fake এর সাথে প্রিফিক্স করা উচিত।
,

এই পৃষ্ঠাটি বেশ কয়েকটি আর্কিটেকচার সেরা অনুশীলন এবং সুপারিশ উপস্থাপন করে। আপনার অ্যাপের গুণমান, দৃঢ়তা এবং মাপযোগ্যতা উন্নত করতে সেগুলি গ্রহণ করুন। তারা আপনার অ্যাপকে রক্ষণাবেক্ষণ এবং পরীক্ষা করা আরও সহজ করে তোলে।

নীচের সেরা অনুশীলনগুলি বিষয় অনুসারে গোষ্ঠীবদ্ধ করা হয়েছে৷ প্রতিটির একটি অগ্রাধিকার রয়েছে যা প্রতিফলিত করে যে দলটি কতটা দৃঢ়ভাবে সুপারিশ করে। অগ্রাধিকার তালিকা নিম্নরূপ:

  • দৃঢ়ভাবে সুপারিশ করা হয়েছে: আপনার এই অনুশীলনটি বাস্তবায়ন করা উচিত যদি না এটি আপনার পদ্ধতির সাথে মৌলিকভাবে সংঘর্ষ হয়।
  • প্রস্তাবিত: এই অনুশীলনটি আপনার অ্যাপ উন্নত করতে পারে।
  • ঐচ্ছিক: এই অনুশীলনটি নির্দিষ্ট পরিস্থিতিতে আপনার অ্যাপকে উন্নত করতে পারে।

স্তরযুক্ত স্থাপত্য

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

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

UI স্তরের উপাদান যেমন কম্পোজেবল, অ্যাক্টিভিটি, বা ভিউমডেলগুলি সরাসরি ডেটা উত্সের সাথে ইন্টারঅ্যাক্ট করা উচিত নয়৷ তথ্য উৎসের উদাহরণ হল:

  • ডেটাবেস, ডেটাস্টোর, শেয়ার করা পছন্দ, ফায়ারবেস এপিআই।
  • GPS অবস্থান প্রদানকারী।
  • ব্লুটুথ ডেটা প্রদানকারী।
  • নেটওয়ার্ক সংযোগ স্থিতি প্রদানকারী.
coroutines এবং প্রবাহ ব্যবহার করুন. স্তরগুলির মধ্যে যোগাযোগ করতে coroutines এবং ফ্লো ব্যবহার করুন৷

আরও কোরোটিন সেরা অনুশীলন এখানে

একটি ডোমেইন স্তর ব্যবহার করুন। একটি ডোমেন স্তর ব্যবহার করুন , কেস ব্যবহার করুন, যদি আপনি একাধিক ভিউমডেল জুড়ে ডেটা স্তরের সাথে ইন্টারঅ্যাক্ট করে এমন ব্যবসায়িক যুক্তি পুনঃব্যবহার করতে চান বা আপনি একটি নির্দিষ্ট ভিউমডেলের ব্যবসায়িক যুক্তি জটিলতাকে সহজ করতে চান

UI স্তর

UI স্তরের ভূমিকা হল স্ক্রিনে অ্যাপ্লিকেশন ডেটা প্রদর্শন করা এবং ব্যবহারকারীর ইন্টারঅ্যাকশনের প্রাথমিক পয়েন্ট হিসাবে পরিবেশন করা। UI স্তরের জন্য এখানে কিছু সেরা অনুশীলন রয়েছে:

সুপারিশ বর্ণনা
ইউনিডাইরেশনাল ডেটা ফ্লো (UDF) অনুসরণ করুন। ইউনিডাইরেশনাল ডেটা ফ্লো (UDF) নীতিগুলি অনুসরণ করুন, যেখানে ভিউ মডেলগুলি পর্যবেক্ষক প্যাটার্ন ব্যবহার করে UI অবস্থা প্রকাশ করে এবং মেথড কলের মাধ্যমে UI থেকে অ্যাকশন গ্রহণ করে।
AAC ViewModels ব্যবহার করুন যদি তাদের সুবিধাগুলি আপনার অ্যাপে প্রযোজ্য হয়। ব্যবসায়িক যুক্তি পরিচালনা করতে AAC ViewModels ব্যবহার করুন এবং UI-তে UI অবস্থা প্রকাশ করতে অ্যাপ্লিকেশন ডেটা আনুন (কম্পোজ বা Android Views)।

এখানে আরও ViewModel সেরা অনুশীলন দেখুন।

এখানে ViewModels এর সুবিধা দেখুন।

জীবনচক্র-সচেতন UI রাজ্য সংগ্রহ ব্যবহার করুন। উপযুক্ত লাইফসাইকেল-সচেতন কোরোটিন নির্মাতা ব্যবহার করে UI থেকে UI অবস্থা সংগ্রহ করুন: ভিউ সিস্টেমে repeatOnLifecycle এবং Jetpack Compose-এ collectAsStateWithLifecycle

repeatOnLifecycle সম্পর্কে আরও পড়ুন।

collectAsStateWithLifecycle সম্পর্কে আরও পড়ুন।

ViewModel থেকে UI এ ইভেন্ট পাঠাবেন না। ViewModel-এ অবিলম্বে ইভেন্টটি প্রক্রিয়া করুন এবং ইভেন্ট পরিচালনার ফলাফল সহ একটি রাষ্ট্রীয় আপডেট করুন৷ UI ইভেন্ট সম্পর্কে আরও এখানে
একটি একক কার্যকলাপ অ্যাপ্লিকেশন ব্যবহার করুন. আপনার অ্যাপে একাধিক স্ক্রিন থাকলে স্ক্রিন এবং আপনার অ্যাপের গভীর লিঙ্কের মধ্যে নেভিগেট করতে নেভিগেশন ফ্র্যাগমেন্ট বা নেভিগেশন কম্পোজ ব্যবহার করুন।
জেটপ্যাক কম্পোজ ব্যবহার করুন। ফোন, ট্যাবলেট এবং ফোল্ডেবল এবং Wear OS-এর জন্য নতুন অ্যাপ তৈরি করতে Jetpack Compose ব্যবহার করুন।

নিচের স্নিপেটে লাইফসাইকেল-সচেতন পদ্ধতিতে কীভাবে UI স্টেট সংগ্রহ করা যায় তার রূপরেখা দেওয়া হয়েছে:

ভিউ

class MyFragment : Fragment() {

    private val viewModel: MyViewModel by viewModel()

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)

        viewLifecycleOwner.lifecycleScope.launch {
            viewLifecycleOwner.repeatOnLifecycle(Lifecycle.State.STARTED) {
                viewModel.uiState.collect {
                    // Process item
                }
            }
        }
    }
}

রচনা করুন

@Composable
fun MyScreen(
    viewModel: MyViewModel = viewModel()
) {
    val uiState by viewModel.uiState.collectAsStateWithLifecycle()
}

মডেল দেখুন

ViewModels UI অবস্থা এবং ডেটা স্তরে অ্যাক্সেস প্রদানের জন্য দায়ী। ভিউমডেলের জন্য এখানে কিছু সেরা অনুশীলন রয়েছে:

সুপারিশ বর্ণনা
ভিউ মডেলগুলিকে অ্যান্ড্রয়েড জীবনচক্রের অজ্ঞেয়বাদী হওয়া উচিত। ViewModels কোনো লাইফসাইকেল-সম্পর্কিত প্রকারের রেফারেন্স রাখা উচিত নয়। নির্ভরতা হিসাবে Activity, Fragment, Context বা Resources পাস করবেন না। যদি ViewModel-এ কোনো Context প্রয়োজন হয়, তাহলে সেটি সঠিক স্তরে থাকলে আপনার দৃঢ়ভাবে মূল্যায়ন করা উচিত।
coroutines এবং প্রবাহ ব্যবহার করুন.

ভিউমডেল ব্যবহার করে ডেটা বা ডোমেন স্তরগুলির সাথে ইন্টারঅ্যাক্ট করে:

  • কোটলিন অ্যাপ্লিকেশন ডেটা প্রাপ্তির জন্য প্রবাহিত হয়,
  • viewModelScope ব্যবহার করে কর্ম সঞ্চালনের জন্য ফাংশন suspend
পর্দা স্তরে ViewModels ব্যবহার করুন.

UI এর পুনঃব্যবহারযোগ্য টুকরোগুলিতে ViewModels ব্যবহার করবেন না। আপনার ভিউ মডেলগুলি এতে ব্যবহার করা উচিত:

  • স্ক্রীন-স্তরের কম্পোজেবল,
  • দৃশ্যের মধ্যে কার্যকলাপ/খন্ড,
  • জেটপ্যাক নেভিগেশন ব্যবহার করার সময় গন্তব্য বা গ্রাফ।
পুনরায় ব্যবহারযোগ্য UI উপাদানগুলিতে প্লেইন স্টেট হোল্ডার ক্লাস ব্যবহার করুন। পুনঃব্যবহারযোগ্য UI উপাদানগুলিতে জটিলতা পরিচালনার জন্য প্লেইন স্টেট হোল্ডার ক্লাস ব্যবহার করুন। এতে করে রাষ্ট্রকে বাহ্যিকভাবে উত্তোলন ও নিয়ন্ত্রণ করা যায়।
AndroidViewModel ব্যবহার করবেন না। ViewModel ক্লাস ব্যবহার করুন, AndroidViewModel নয়। ViewModel-এ Application ক্লাস ব্যবহার করা উচিত নয়। পরিবর্তে, নির্ভরতাকে UI বা ডেটা স্তরে সরান৷
একটি UI অবস্থা প্রকাশ করুন। ভিউমডেলগুলিকে uiState নামক একটি একক সম্পত্তির মাধ্যমে UI-তে ডেটা প্রকাশ করা উচিত। যদি UI একাধিক, অসংলগ্ন ডেটার টুকরো দেখায়, VM একাধিক UI স্টেট বৈশিষ্ট্য প্রকাশ করতে পারে।
  • আপনি uiState একটি StateFlow করা উচিত.
  • আপনি uiState তৈরি করতে হবে stateIn অপারেটর ব্যবহার করে WhileSubscribed(5000) নীতি (উদাহরণ) যদি ডেটা ক্রমানুসারের অন্যান্য স্তর থেকে ডেটার স্ট্রিম হিসাবে আসে।
  • ডেটা স্তর থেকে ডেটার কোনও স্ট্রিম না থাকা সহজ ক্ষেত্রে, একটি অপরিবর্তনীয় StateFlow (উদাহরণ) হিসাবে প্রকাশ করা একটি MutableStateFlow ব্যবহার করা গ্রহণযোগ্য।
  • আপনি ${Screen}UiState ডেটা ক্লাস হিসাবে বেছে নিতে পারেন যাতে ডেটা, ত্রুটি এবং লোডিং সংকেত থাকতে পারে৷ বিভিন্ন রাজ্য একচেটিয়া হলে এই শ্রেণীটি একটি সীলমোহরযুক্ত শ্রেণীও হতে পারে।

নিম্নলিখিত স্নিপেটটি একটি ভিউমডেল থেকে কীভাবে UI অবস্থা প্রকাশ করতে হয় তার রূপরেখা দেয়:

@HiltViewModel
class BookmarksViewModel @Inject constructor(
    newsRepository: NewsRepository
) : ViewModel() {

    val feedState: StateFlow<NewsFeedUiState> =
        newsRepository
            .getNewsResourcesStream()
            .mapToFeedState(savedNewsResourcesState)
            .stateIn(
                scope = viewModelScope,
                started = SharingStarted.WhileSubscribed(5_000),
                initialValue = NewsFeedUiState.Loading
            )

    // ...
}

জীবনচক্র

অ্যান্ড্রয়েড লাইফসাইকেলের সাথে কাজ করার জন্য নিম্নলিখিত কিছু সেরা অনুশীলনগুলি রয়েছে:

সুপারিশ বর্ণনা
অ্যাক্টিভিটিস বা ফ্র্যাগমেন্টে লাইফসাইকেল পদ্ধতি ওভাররাইড করবেন না। লাইফসাইকেল পদ্ধতিগুলিকে ওভাররাইড করবেন না যেমন ক্রিয়াকলাপগুলিতে onResume বা ফ্র্যাগমেন্টস৷ পরিবর্তে LifecycleObserver ব্যবহার করুন। লাইফসাইকেল একটি নির্দিষ্ট Lifecycle.State এ পৌঁছালে অ্যাপটিকে কাজ করার প্রয়োজন হলে, repeatOnLifecycle API ব্যবহার করুন।

নিম্নলিখিত স্নিপেটে একটি নির্দিষ্ট লাইফসাইকেল অবস্থার প্রেক্ষিতে কীভাবে ক্রিয়াকলাপ সম্পাদন করতে হয় তার রূপরেখা দেয়:

ভিউ

class MyFragment: Fragment() {
    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)

        viewLifecycleOwner.lifecycle.addObserver(object : DefaultLifecycleObserver {
            override fun onResume(owner: LifecycleOwner) {
                // ...
            }
            override fun onPause(owner: LifecycleOwner) {
                // ...
            }
        }
    }
}

রচনা করুন

@Composable
fun MyApp() {

    val lifecycleOwner = LocalLifecycleOwner.current
    DisposableEffect(lifecycleOwner, ...) {
        val lifecycleObserver = object : DefaultLifecycleObserver {
            override fun onStop(owner: LifecycleOwner) {
                // ...
            }
        }

        lifecycleOwner.lifecycle.addObserver(lifecycleObserver)
        onDispose {
            lifecycleOwner.lifecycle.removeObserver(lifecycleObserver)
        }
    }
}

নির্ভরতা পরিচালনা করুন

উপাদানগুলির মধ্যে নির্ভরতা পরিচালনা করার সময় আপনাকে বেশ কয়েকটি সর্বোত্তম অনুশীলন পর্যবেক্ষণ করা উচিত:

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

টেস্টিং

নিম্নলিখিত পরীক্ষার জন্য কিছু সেরা অনুশীলন আছে:

সুপারিশ বর্ণনা
কি পরীক্ষা করতে হবে তা জেনে নিন

যতক্ষণ না প্রকল্পটি হ্যালো ওয়ার্ল্ড অ্যাপের মতো মোটামুটি সহজ না হয়, আপনার এটি পরীক্ষা করা উচিত, সর্বনিম্ন এর সাথে:

  • ইউনিট পরীক্ষা ViewModels, প্রবাহ সহ।
  • ইউনিট পরীক্ষা ডেটা স্তর সত্তা. অর্থাৎ রিপোজিটরি এবং ডেটা সোর্স।
  • UI নেভিগেশন পরীক্ষা যা CI-তে রিগ্রেশন পরীক্ষা হিসাবে কার্যকর।
উপহাসের চেয়ে নকল পছন্দ করুন। অ্যান্ড্রয়েড ডকুমেন্টেশনে পরীক্ষা দ্বিগুণ ব্যবহারে আরও পড়ুন।
স্টেটফ্লো পরীক্ষা করুন। StateFlow পরীক্ষা করার সময়:

আরও তথ্যের জন্য, অ্যান্ড্রয়েড ড্যাক গাইডে কী পরীক্ষা করতে হবে তা দেখুন।

মডেল

আপনার অ্যাপ্লিকেশানগুলিতে মডেলগুলি তৈরি করার সময় আপনার এই সর্বোত্তম অনুশীলনগুলি পালন করা উচিত:

সুপারিশ বর্ণনা
জটিল অ্যাপে লেয়ার প্রতি একটি মডেল তৈরি করুন।

জটিল অ্যাপ্লিকেশানগুলিতে, বিভিন্ন স্তর বা উপাদানে নতুন মডেল তৈরি করুন যখন এটি বোধগম্য হয়৷ নিম্নলিখিত উদাহরণ বিবেচনা করুন:

  • একটি দূরবর্তী ডেটা উত্স নেটওয়ার্কের মাধ্যমে প্রাপ্ত মডেলটিকে একটি সহজ শ্রেণিতে ম্যাপ করতে পারে শুধুমাত্র অ্যাপটির প্রয়োজনীয় ডেটা সহ
  • সংগ্রহস্থলগুলি DAO মডেলগুলিকে সহজ ডেটা ক্লাসে ম্যাপ করতে পারে কেবলমাত্র UI স্তরের প্রয়োজনীয় তথ্য দিয়ে।
  • ViewModel UiState ক্লাসে ডেটা লেয়ার মডেল অন্তর্ভুক্ত করতে পারে।

নামকরণের রীতি

আপনার কোডবেস নামকরণ করার সময়, আপনাকে নিম্নলিখিত সেরা অনুশীলনগুলি সম্পর্কে সচেতন হওয়া উচিত:

সুপারিশ বর্ণনা
নামকরণ পদ্ধতি।
ঐচ্ছিক
পদ্ধতি একটি ক্রিয়া বাক্যাংশ হতে হবে. উদাহরণস্বরূপ, makePayment()
নামকরণের বৈশিষ্ট্য।
ঐচ্ছিক
বৈশিষ্ট্য একটি বিশেষ্য বাক্যাংশ হতে হবে. উদাহরণস্বরূপ, inProgressTopicSelection
ডেটার স্ট্রীম নামকরণ।
ঐচ্ছিক
যখন একটি ক্লাস একটি ফ্লো স্ট্রীম, লাইভডেটা বা অন্য কোন স্ট্রীম প্রকাশ করে, তখন নামকরণের নিয়ম হল get{model}Stream() । উদাহরণস্বরূপ, getAuthorStream(): Flow<Author> যদি ফাংশনটি মডেলের একটি তালিকা প্রদান করে তাহলে মডেলের নামটি বহুবচনে থাকা উচিত: getAuthorsStream(): Flow<List<Author>>
নামকরণ ইন্টারফেস বাস্তবায়ন।
ঐচ্ছিক
ইন্টারফেস বাস্তবায়নের জন্য নাম অর্থপূর্ণ হওয়া উচিত। একটি ভাল নাম পাওয়া না গেলে উপসর্গ হিসাবে Default রাখুন। উদাহরণস্বরূপ, একটি NewsRepository ইন্টারফেসের জন্য, আপনার কাছে একটি OfflineFirstNewsRepository বা InMemoryNewsRepository থাকতে পারে। যদি আপনি কোন ভাল নাম খুঁজে না পান, তাহলে DefaultNewsRepository ব্যবহার করুন। FakeAuthorsRepository তে যেমন ফেক ইমপ্লিমেন্টেশন Fake এর সাথে প্রিফিক্স করা উচিত।