Facade: mga batayan ng pattern ng facade sa mobile na arkitektura

May-akda: IT Sectr Nai-publish: 2026-02-18 Oras ng pagbabasa: 9 min

Facade ay isang istruktural na pattern ng disenyo na nagbibigay ng pinasimpleng interface sa isang kumplikadong subsystem ng mga klase. Sa mobile development, ang Facade ay kadalasang ipinapatupad bilang Service Layer o UseCase, na nagtatago ng interaksyon sa network, database, at analytics. Ayon kay Martin Fowler (Patterns of Enterprise Application Architecture, 2003), ang Facade ay isa sa mga pangunahing pattern para sa pag-oorganisa ng layer ng serbisyo.

Mga pangunahing punto

  • Facade — istruktural na pattern na nagbibigay ng simpleng interface sa isang kumplikadong sistema ng mga klase, library, o framework
  • Service Layer — pagpapatupad ng Facade sa mobile na arkitektura, na nagtatago ng API, cache, at analytics mula sa UI
  • Hindi itinatago ng Facade ang subsystem — maaaring direktang ma-access ito ng kliyente kung kinakailangan
  • UseCase sa Clean Architecture — isang variant ng Facade na nag-oorkestra ng isang business scenario
  • Facade vs Adapter: pinapasimple ng Facade ang interface, pinapalitan ng Adapter ang isang interface sa isa pa

Ano ang pattern ng Facade?

Facade — istruktural na pattern na nagbibigay ng pinag-isang interface sa isang grupo ng mga interface ng subsystem. Tinutukoy nito ang isang interface sa mataas na antas na nagpapasimple sa paggamit ng subsystem. Hindi nagdaragdag ng bagong functionality ang Facade — inoorkestra nito ang mga umiiral na component at itinatago ang pagiging kumplikado ng kanilang interaksyon mula sa kliyente.

Kotlin
// Kumplikadong subsystem
class AuthApi {
    suspend fun login(email: String, pass: String): TokenResponse
}

class UserDao {
    suspend fun saveUser(user: UserEntity)
    suspend fun getUser(id: Long): UserEntity?
}

class AnalyticsTracker {
    fun track(event: String, params: Map)
}

// Facade — simpleng interface para sa UI
class AuthService(
    private val api: AuthApi,
    private val dao: UserDao,
    private val analytics: AnalyticsTracker
) {
    suspend fun loginUser(email: String, password: String): Result {
        return runCatching {
            val token = api.login(email, password)
            val user = User(token.userId, email, token.accessToken)
            dao.saveUser(user.toEntity())
            analytics.track("login_success", mapOf("method" to "email"))
            user
        }
    }
}

AuthService — Facade na nagtatago ng AuthApi, UserDao, at AnalyticsTracker mula sa ViewModel. Tumatawag ang UI ng loginUser(email, password) sa halip na tatlong hiwalay na kahilingan sa API, database, at analytics. Binabawasan nito ang coupling: kung bukas ay magiging FirebaseAuth ang AuthApi o magmi-migrate ang UserDao sa Room, ang Facade lamang ang magbabago, hindi ang UI.

Facade sa mobile na arkitektura: Service Layer

Service Layer — karaniwang pagpapatupad ng Facade sa mga mobile application. Ine-encapsulate nito ang business logic at ang koordinasyon sa pagitan ng mga layer. Sa Android, ang Service Layer ay kadalasang ipinapatupad sa pamamagitan ng UseCase (Clean Architecture), sa iOS — sa pamamagitan ng Manager o mga Service protocol.

ComponentPapel sa subsystemAno ang itinatago ng Facade
AuthApiNetwork request sa serverFormat ng kahilingan, endpoint, paghawak ng mga error sa HTTP
UserDaoLokal na pag-iimbak ng tokenSchema ng database, mga SQL query, migrasyon
AnalyticsTrackerPaghahatid ng mga event ng analyticsFirebase/AppMetrica SDK, format ng mga event
NetworkMonitorPagsusuri ng availability ng networkConnectivityManager, BroadcastReceiver

AuthService pinag-iisa ang lahat ng apat na component. Tumatawag ang ViewModel ng isang method, nang hindi nalalaman na sa ilalim ng hood ay nangyayari ang isang network request, pagsulat sa database, tracking, at pagsusuri ng network. Sa pag-test, maaaring palitan ang AuthService ng mock, na sinusuri ang buong lohika ng pagpapatotoo nang walang integrasyon sa mga totoong component.

Facade vs Adapter vs Mediator

Facade, Adapter, at Mediator — mga istruktural na pattern, ngunit nilulutas nila ang iba't ibang problema. Madalas silang napagkakamalan, dahil lahat ng tatlo ay nagpapakilala ng isang tagapamagitang object. Tingnan natin ang mga pagkakaiba gamit ang halimbawa ng isang mobile application.

AspektoFacadeAdapterMediator
LayuninPasimplehin ang interface ng subsystemPalitan ang interfaceBawasan ang coupling ng mga component
DireksyonIsang interface → subsystemKliyente → AdapteeN component ↔ Mediator
Pagbabago ng interfaceLumilikha ng bago, pinasimplePinapalitan ang umiiralHindi binabago, kinoordina
Alam ba ng subsystem ang pattern?HindiHindiOo, nakikipag-ugnayan sa pamamagitan ng Mediator
Halimbawa sa mobile developmentUseCase / Service LayerRecyclerView.AdapterCoordinator sa iOS

Facade ay hindi itinatago ang subsystem — maaaring direktang ma-access ng kliyente ang AuthApi kung kinakailangan. Adapter ay sapilitang binabago ang interface ng Adaptee. Mediator ay kinoordina ang mga kumplikadong interaksyon sa pagitan ng maraming object na maaaring hindi kilala ang isa't isa.

Pagpapatupad ng Facade sa Kotlin para sa Android

Ang pagpapatupad ng Facade sa Kotlin para sa Android na may Clean Architecture ay gumagamit ng UseCase bilang entry point para sa bawat business scenario. Ang UseCase ay isang Facade na nagtatago ng repository, mapper, at iba pang dependencies mula sa UI layer.

Kotlin
// Repository — Facade din, ngunit isang antas na mas mababa
class UserRepositoryImpl(
    private val local: UserLocalDataSource,
    private val remote: UserRemoteDataSource,
    private val mapper: UserMapper
) : UserRepository {
    override suspend fun getUserProfile(id: String): UserProfile {
        val cached = local.getUser(id)
        if (cached != null && !cached.isStale) {
            return mapper.toProfile(cached)
        }
        val dto = remote.fetchUser(id)
        val entity = mapper.toEntity(dto)
        local.saveUser(entity)
        return mapper.toProfile(entity)
    }
}

// UseCase — Facade para sa business scenario
class LoadUserProfileUseCase(
    private val repo: UserRepository,
    private val analytics: AnalyticsTracker
) {
    suspend operator fun invoke(userId: String): Result {
        return runCatching {
            val profile = repo.getUserProfile(userId)
            analytics.track("profile_loaded", mapOf("user_id" to userId))
            profile
        }
    }
}

LoadUserProfileUseCase — Facade para sa scenario ng pag-load ng profile. Itinatago nito ang lohika ng caching (local → remote), ang pagmamapa ng DTO → Entity → Profile, at ang pagsubaybay ng analytics. Tumatawag ang ViewModel ng invoke(userId) at tumatanggap ng handa nang UserProfile o isang error. Maaaring i-test ang UseCase nang nakahiwalay sa pamamagitan ng pagpapalit ng repository ng mock object.

Pagpapatupad ng Facade sa Swift para sa iOS

Ang Facade sa iOS ay kadalasang ipinapatupad bilang Manager o Service. Hindi tulad ng Android, gumagamit ang iOS ng mga protocol upang tukuyin ang interface ng Facade, na ginagawang madali ang pagpapalit ng mga pagpapatupad sa mga test. Tingnan natin ang isang Facade para sa pagtatrabaho sa media — pag-load, pag-cache, at pagpapakita.

Swift
protocol MediaServiceProtocol {
    func loadImage(from url: URL) async -> Result<UIImage, Error>
}

final class MediaService: MediaServiceProtocol {
    private let cache: ImageCache
    private let downloader: ImageDownloader
    private let decoder: ImageDecoder
    
    func loadImage(from url: URL) async -> Result<UIImage, Error> {
        // 1. Suriin ang cache
        if let cached = cache.image(for: url) {
            return .success(cached)
        }
        // 2. I-load ang data
        let result = await downloader.download(from: url)
        guard case let .success(data) = result else {
            return .failure(MediaError.downloadFailed)
        }
        // 3. I-decode
        guard let image = decoder.decode(data) else {
            return .failure(MediaError.decodeFailed)
        }
        // 4. I-save sa cache
        cache.setImage(image, for: url)
        return .success(image)
    }
}

MediaService ay ine-encapsulate ang isang proseso na may tatlong hakbang: cache → pag-load → pag-decode. Tumatawag ang UI ng isang method na loadImage(from:) sa halip na pamahalaan ang ImageCache, URLSession, at ImageDecoder. Sa pag-test, maaaring palitan ang MediaServiceProtocol ng mock na nagbabalik ng mga itinakdang imahe nang walang totoong pag-load.

Mga karaniwang pagkakamali sa paggamit ng Facade

Ang mga pagkakamali sa pagdidisenyo ng Facade ay sumisira sa mga bentahe nito: sa halip na pagpapasimple, lumilitaw ang isang God Object na pinagkakatiwalaan ng buong sistema. Tingnan natin ang tatlong pangunahing problema.

God Facade — labis na responsibilidad

Kapag ang isang Facade ay naglalaman ng mga method para sa pagpapatotoo, pag-load ng profile, pagpapadala ng mensahe, at pag-sync — ito ay isang God Object. Tanda: higit sa 15 pampublikong method sa isang klase. Solusyon: hatiin sa ilang espesyalisadong Facade ayon sa mga lugar ng responsibilidad — AuthService, ProfileService, MessagingService.

Facade na may paglabas ng mga detalye ng subsystem

Kung ang Facade ay nagbabalik ng mga type na tiyak sa subsystem (halimbawa, FirebaseUser o RealmObject), ang kliyente ay nakatali pa rin sa isang partikular na pagpapatupad. Solusyon: ang Facade ay dapat magbalik lamang ng sarili nitong mga type (data class / struct), na ganap na ina-abstrakta ang kliyente mula sa mga detalye ng subsystem.

Facade bilang nag-iisang entry point

Kapag ipinagbabawal ng Facade ang direktang pag-access sa subsystem, ito ay nagiging bottleneck. Minsan kailangan ng kliyente ang isang partikular na method ng subsystem, at ang pagpilit sa kanya na dumaan sa Facade ay labis. Ang Facade ay hindi dapat maging mahigpit na gatekeeper: nagbibigay ito ng maginhawang interface, ngunit hindi hinaharangan ang direktang pag-access sa mga component.

Mga madalas itanong

Ano ang pagkakaiba sa pagitan ng Facade at Proxy?

Facade ay nagbibigay ng pinasimpleng interface sa subsystem, madalas na lumilikha ng bagong hanay ng mga method. Proxy ay pinapanatili ang parehong interface ng orihinal na object, ngunit nagdaragdag ng kontrol sa pag-access o lazy loading. Facade — para sa pagpapasimple, Proxy — para sa kontrol.

Ang Facade ba ay kapareho ng Service Layer?

Service Layer — ito ang pagpapatupad ng pattern ng Facade sa antas ng arkitektura ng application. Tinutukoy nito ang hangganan sa pagitan ng UI at ng business logic, itinatago ang mga detalye ng pagpapatupad ng mga serbisyo. Sa Android, ang Service Layer ay kadalasang ipinapatupad sa pamamagitan ng UseCase, sa iOS — sa pamamagitan ng Manager o mga Service protocol.

Kailan nagiging God Object ang Facade?

God Facade ay lumilitaw kapag ang isang klase ay kumukuha ng responsibilidad para sa ilang hindi magkaugnay na subsystem. Tanda: higit sa 15 pampublikong method, mga method mula sa iba't ibang domain (pagpapatotoo + pagbabayad + mga notification), isang klase na mahirap i-test (higit sa 10 dependencies). Solusyon: hatiin sa mga Facade ayon sa domain.

Kailangan ba ang Facade sa isang maliit na application?

Sa isang application na may 1-2 screen, ang Facade ay labis — ang direktang pagtawag ng API at database mula sa UI ay mas simple at mas malinaw. Nagbabayad ang Facade sa higit sa 5 screen at higit sa 3 subsystem. Sa mga katamtaman at maliliit na proyekto, sapat na ang Repository bilang nag-iisang layer ng Facade, nang walang dagdag na wrapper ng UseCase.

Paano i-test ang code na gumagamit ng Facade?

Pinapasimple ng Facade ang pag-test, dahil pinapalitan nito ang buong subsystem ng isang mock object. Sa halip na i-mock ang tatlong component (network + database + analytics), sapat na ang i-mock ang isang Facade. Sa Swift para dito ay ginagamit ang protocol, sa Kotlin — ang interface. Ang Facade ay maginhawa rin para sa integration test, kung saan sinusuri ang orkestrasyon ng mga component.

Buod

  • Facade — istruktural na pattern na nagbibigay ng simpleng interface sa isang kumplikadong subsystem
  • Service Layer at UseCase — karaniwang pagpapatupad ng Facade sa mobile na arkitektura
  • Facade ay hindi itinatago ang subsystem: maaaring direktang ma-access ng kliyente ang mga component kung kinakailangan
  • Facade vs Adapter: pinapasimple ng Facade, pinapalitan ng Adapter; Facade vs Mediator: one-way ang Facade, two-way ang Mediator
  • God Facade — antipattern: ang higit sa 15 method sa isang klase ay senyales ng paglabag sa Single Responsibility
  • Protokol/interface para sa Facade ay kinakailangan — ito ang tanging paraan ng mock-testing ng subsystem
  • Rekomendasyon: ipakilala ang Facade sa higit sa 5 screen at higit sa 3 subsystem; para sa maliliit na proyekto, sapat na ang Repository

Gagawa kami ng mobile application na turnkey

Gumagawa ang IT Sectr ng mga iOS at Android application para sa mga startup at negosyo mula noong 2017. Magpapayo kami sa iyo at magmumungkahi ng pinakamahusay na solusyon.

Pag-usapan ang proyekto

Basahin din