Mobile Development 22 min read

Applying Domain‑Driven Design to Large List Architecture in Android

This article describes how the Lofter team applied Domain‑Driven Design to refactor and govern complex, multi‑type RecyclerView lists on Android, progressing from a monolithic adapter through a split‑stage implementation to a full DDD‑based framework with reusable bars and context‑aware layout managers.

LOFTER Tech Team
LOFTER Tech Team
LOFTER Tech Team
Applying Domain‑Driven Design to Large List Architecture in Android

Domain‑Driven Design (DDD) was introduced in 2004 and has recently been adopted for backend and mobile architectures. The article uses the Lofter interest‑community app as a case study to illustrate the challenges of rendering massive RecyclerView lists that contain dozens of item types (text, photo, video, music, etc.) and many shared UI elements such as likes, comments, and menus.

1. Single‑Item Stage – Initially all item types were handled in a single LofterAdapter with a large switch‑case inside convert() . The adapter grew to over 8,000 lines, making maintenance and iteration costly.

public class LofterAdapter
extends BaseMultiItemQuickAdapter
{
    @Override
    public void convert(helper: K, item: T) {
        switch (item.type) {
            TEXT: ...; break;
            PHOTO: ...; break;
            VIDEO: ...; break;
            MUSIC: ...; break;
        }
    }
}

2. Divide‑and‑Conquer Stage – The team built a ComMultiItemAdapter that registers separate item‑holder controllers for each type, moving layout creation and data binding into dedicated render classes such as TextItemRender and PhotoItemRender . This reduced the monolithic switch but still suffered from a bloated base render class.

addItemHolderController(TEXT, R.layout.text, new TextItemRender(adapterController));
addItemHolderController(PHOTO, R.layout.photo, new PhotoItemRender(adapterController));

3. DDD Stage – By treating each UI fragment (called a “bar”) as a bounded context, the architecture separates concerns more cleanly. Bars encapsulate view lookup, click handling, data binding, and lifecycle management. Example of a simple bar implementation:

class DebugInfoBar : FrameLayout, ItemPartView {
    private var hintTv: TextView? = null
    init { View.inflate(context, R.layout.item_part_debug_info_bar, this) }
    override fun onCreate() { hintTv = findViewById(R.id.hint_tv) }
    override fun onUpdate(itemModel: Any?) { /* update UI */ }
}

Bars can communicate via a shared ItemPartLayoutMan that receives lifecycle events, broadcasts, and scroll callbacks. For example, PostOwnerItemPartLayoutMan listens for follow‑user broadcasts and triggers partial UI updates.

override fun onContextAttached() {
    adapterContext.registerLocalBroadcastReceiver(FOLLOW_FILTER, followUserReceiver)
    adapterContext.registerLocalBroadcastReceiver(COLLECT_FILTER, updateCollectionInfoReceiver)
}

The final DDD architecture is visualized as a hierarchy where each item’s XML only declares the list of bars it composes, dramatically simplifying layout files and enabling reuse across pages.

To adopt the framework, developers register the required ItemLayoutMan for each item type (text, photo, video, etc.) in the activity/fragment, and the framework assembles the appropriate bars at runtime.

fun createAdapter(): UnityAdapter {
    adapter = UnityAdapter(this, ArrayList
()).apply {
        registerItemLayoutMan(POST_CARD_TEXT, R.layout.post_card_item_text, PostTextItemLayoutMan::class.java)
        registerItemLayoutMan(POST_CARD_PHOTO, R.layout.post_card_item_photo, PostPhotoItemLayoutMan::class.java)
        // ... other types
    }
}

The article concludes that DDD‑driven large‑list governance improves maintainability, reduces merge conflicts, and enables multiple teams to collaborate efficiently on complex UI lists.

Mobile DevelopmentarchitectureandroidDDDRecyclerViewLarge List
LOFTER Tech Team
Written by

LOFTER Tech Team

Technical sharing and discussion from NetEase LOFTER Tech Team

0 followers
Reader feedback

How this landed with the community

login Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.