SOLID: prinsiplər, 5 OOP qaydası və inkişafda tətbiqi

Müəllif: IT Sectr Dərc olunub: 2026-05-11 Oxuma vaxtı: 10 dəq

SOLID — Robert C. Martin (Uncle Bob) tərəfindən 2000-ci illərin əvvəlində formalaşdırılmış beş obyekt yönümlü proqramlaşdırma prinsipidir. DigitalOcean, 2024 məlumatlarına görə, SOLID Single Responsibility, Open-Closed, Liskov Substitution, Interface Segregation və Dependency Inversion kimi açılır. Bu prinsiplər Clean Architecture-ın əsasını təşkil edir və Android (MVP, MVVM, Clean Architecture) və iOS (VIPER, TCA) inkişafında tətbiq olunur.

Başlıca

  • SOLID — çevik və davamlı kod yaratmaq üçün Robert C. Martin tərəfindən formalaşdırılmış beş OOP prinsipinin akronimi: SRP, OCP, LSP, ISP, DIP.
  • SRP (Single Responsibility) — hər sinfin dəyişiklik üçün bir səbəbi var, modul üçün bir məsuliyyət.
  • OCP (Open-Closed) — siniflər genişlənməyə açıq, dəyişikliyə qapalıdır, miras və polimorfizm vasitəsilə həyata keçirilir.
  • LSP (Liskov Substitution) — alt siniflərin obyektləri proqramın düzgünlüyünü dəyişmədən baza sinfinin obyektlərini əvəz etməlidir.
  • ISP (Interface Segregation) — müştərilər istifadə etmədikləri interfeyslərdən asılı olmamalıdır, interfeyslər dar və spesifik olmalıdır.
  • DIP (Dependency Inversion) — yuxarı səviyyəli modullar aşağı səviyyəli modullardan asılı olmamalıdır, hər ikisi abstraksiyalardan asılıdır.

SOLID nədir? Beş prinsipə ümumi baxış

SOLID — beş obyekt yönümlü dizayn prinsipini ifadə edən mnemonic akronimdir. Termin Robert C. Martin tərəfindən “Design Principles and Design Patterns” (2000) məqaləsində təqdim edilmiş, sonra “Agile Software Development: Principles, Patterns, and Practices” (2002) kitabında populyarlaşdırılmışdır. SOLID çərçivə və ya kitabxana deyil — kodu daha az bağlı, daha test edilə bilən və dəyişikliklər üçün daha rahat edən təcrübələr toplusudur.

Clean Coder Blog, 2014 məlumatlarına görə, hər SOLID prinsipi müəyyən dizayn problemini həll edir: SRP God-siniflərlə mübarizə aparır, OCP — kaskad dəyişikliklərlə, LSP — yanlış mirasla, ISP — şişman interfeyslərlə, DIP — sıx bağlanmalarla. Birlikdə onlar MVP, MVVM və MVI ilə Android layihələrində istifadə olunan Clean Architecture-ın təməlini təşkil edir.

SRP: Single Responsibility Principle

Single Responsibility Principle (SRP) — vahid məsuliyyət prinsipi. Formula: “Sinfin dəyişiklik üçün yalnız bir səbəbi olmalıdır.” Bu o deməkdir ki, hər modul və ya sinf dəqiq bir funksionallığa və ya bir domenda bir varlığa cavabdehdir. Şərəf sinfi həm istifadəçiləri, həm də email göndərilməsini idarə edirsə — onun dəyişiklik üçün iki səbəbi var, bu da SRP-ni pozur.

Robert C. Martin, 2002 görə, SRP ən vacib və eyni zamanda ən çox pozulan prinsipdir. Mobil inkişafda SRP tez-tez Activity/Fragment-də UI mantiqini, naviqasiyanı, şəbəkə işini və biznes mantiqini birləşdirərək pozulur. Həll — hər təbəqəni ayrı sinfə ayırmaq: UI mantiqi üçün ViewModel, məlumatlar üçün Repository, naviqasiya üçün NavController.

SRP nümunəsi: UserManager bölgüsü

UserManager sinfini nəzərdən keçirək, o profili yükləyir, parametrləri saxlayır və email göndərir. Bunlar üç fərqli məsuliyyətdir, hər biri ayrı sinfə ayrılmalıdır: UserProfileRepository (yükləmə), UserSettingsStorage (saxlama) və EmailService (göndərmə). Müştəri kodu (ViewModel) hüçüsinə Dependency Injection vasitəsilə istifadə edir və hər sinf asanlıqla təcrid olunmuş şəkildə test edilir və digərlərinə təsir etmədən dəyişdirilir.

kotlin
// ❌ SRP-nin pozulması: Activity şəbəkə, BD və UI haqqında bilir
class ProfileActivity : AppCompatActivity() {
    fun loadProfile() {
        api.getUser() // Şəbəkə çağırışı
        db.saveUser()    // BD ilə iş
        updateUI()         // UI yenilənməsi
    }
}

// ✅ SRP gözlənilir: təbəqələr ayrılıb
class ProfileViewModel : ViewModel() {
    private val repo = UserRepository()
    fun loadProfile() { repo.getUser() }
}

SRP pozulmasının əlamətləri: sinf 200-dən çox sətir ehtiva edir, müxtəlf mövzu sahələrindən metodları var, tez-tez müxtəlf səbəblərdən dəyişir. Android inkişafı üçün qayda sadədir: Activity yalnız ekranın həyat dövrü üçün cavabdehdir, ViewModel — UI vəziyyəti üçün, Repository — məlumat mənbələri üçün.

SRP və mikroservis arxitekturası

SRP prinsipi təkcə siniflərə deyil, həm də xidmət səviyyəli arxitekturaya aiddir. Hər mikroservis bir domenda olan varlığa cavabdehdir: UserService — yalnız istifadəçilər, PaymentService — yalnız ödənişlər, NotificationService — yalnız bildirişlər. Bu, xidmətlərin müstəqil şəkildə miqyaslanmasına, yerləşdirilməsinə və test edilməsinə imkan verir. Mobil tətbiqdə mikroservis səviyyəsində SRP, API müştərilərinin domenlər üzrə bölünməsində özünü göstərir.

OCP: Open-Closed Principle

Open-Closed Principle (OCP) — açıqlıq/qapalılıq prinsipi. Siniflər genişlənməyə açıq (yeni davranış əlavə edilə bilər) və dəyişikliyə qapalı (mövcud kod dəyişmir) olmalıdır. Buna polimorfizm, abstrakt siniflər və interfeyslər vasitəsilə nail olunur. Mövcud metoda if-else əlavə etmək əvəzinə, interfeysin yeni tətbiqi yaradılır.

Clean Coder Blog, 2014 görə, OCP Strategy naxışı ilə birlikdə ən effektivdir. Məsələn, tətbiq müxtəlif ödəniş üsullarını (Google Pay, Apple Pay, PayPal) dəstəkləyirsə, ödəniş prosessoruna switch-case əlavə etməyə ehtiyac yoxdur. Hər ödəniş üsulu ümumi PaymentGateway interfeysini tətbiq edir və yeni ödəniş sistemi mövcud kodu dəyişmədən yeni sinf kimi əlavə edilir.

kotlin
// ✅ OCP: genişlənməyə açıq, dəyişikliyə qapalı
interface PaymentGateway {
    fun processPayment(amount: Double): Boolean
}

class GooglePayGateway : PaymentGateway {
    override fun processPayment(amount: Double) = true
}

// Yeni ödəniş sistemi — mövcud kodu dəyişmədən
class ApplePayGateway : PaymentGateway {
    override fun processPayment(amount: Double) = true
}

LSP: Liskov Substitution Principle

Liskov Substitution Principle (LSP) — Barbara Liskovun əvəzetmə prinsipi. Əgər S T-nin alt tipidirsə, onda T obyektləri proqramın xassələrini dəyişmədən S obyektləri ilə əvəz edilə bilər. Formal olaraq: baza sinfindən istifadə edən funksiya onun istənilən alt sinfi ilə düzgün işləməlidir. Alt sinf baza sinfinin atmadığı yerdə istisna atırsa — LSP pozulur.

Robert C. Martin, 2002 görə, LSP SOLID-in anlaşılması ən çətin prinsipidir. Pozulmanın klassik nümunəsi — Rectangle-dan (dördbucaq) miras alan Square sinfi (kvadrat). Square üçün setWidth həm eni, həm də hündürlüyü təyin edirsə, Rectangle davranışını gözləyən müştəri kodu gözlənilən nəticəni almayacaq. Mobil inkişafda LSP tez-tez ViewModel mirası alınarkən pozulur, o zaman ki, uşaq ViewModel məcburi asılılıqlar əlavə edir.

kotlin
// ❌ LSP-nin pozulması: Square Rectangle davranışını pozur
open class Rectangle(open var width: Int, open var height: Int)

class Square(side: Int) : Rectangle(side, side) {
    override var width
        get() = super.width
        set(value) { super.setBoth(value, value) }
}

ISP: Interface Segregation Principle

Interface Segregation Principle (ISP) — interfeyslərin ayrılması prinsipi. Müştərilər istifadə etmədikləri interfeyslərdən asılı olmamalıdır. Bir şişman interfeys əvəzinə bir neçə dar, ixtisaslaşdırılmış interfeys yaradılır. Əgər sinf interfeysi tətbiq edir, lakin metodların bir hissəsi UnsupportedOperationException atır və ya boş qalırsa — bu ISP pozulmasının açıq əlamətidir.

DigitalOcean, 2024 görə, ISP mobil inkişafda ViewModel və Repository dizaynı zamanı xüsusilə aktualdır. Bütün CRUD metodları ilə bir UserRepository interfeysi əvəzinə QueryUserRepository (yalnız oxu) və CommandUserRepository (yazı) yaratmaq daha yaxşıdır. O zaman oxuyan müştəri (UI elementi) yalnız Query interfeysindən asılı olur və yazı metodları haqqında bilmir.

kotlin
// ❌ Şişman interfeys — müştəri lazımsız metodları tətbiq etməyə məcburdur
interface UserOperations {
    fun getUser(id: String): User
    fun saveUser(user: User)
    fun deleteUser(id: String)
    fun exportUsers(): File
}

// ✅ ISP: ayrılmış interfeyslər
interface UserReader { fun getUser(id: String): User }
interface UserWriter { fun saveUser(user: User) }
interface UserDeleter { fun deleteUser(id: String) }

DIP: Dependency Inversion Principle

Dependency Inversion Principle (DIP) — asılılıqların tərsi prinsipi. Yuxarı səviyyəli modullar aşağı səviyyəli modullardan asılı olmamalıdır. Hər iki səviyyə abstraksiyalardan (interfeyslərdən) asılı olmalıdır. Abstraksiyalar detallardan asılı olmamalıdır — detallar abstraksiyalardan asılıdır. Bu Dependency Injection (asılılıqların daxil edilməsi) ilə eyni deyil, baxmayaraq ki, DI DIP-in həyata keçirilməsinin ümumi üsuludur.

Robert C. Martin, 2019 görə, DIP Clean Architecture-ın əsasıdır. ViewModel (yuxarı səviyyə) birbaşa RetrofitApi nümunəsi (detallar) yaratmamalıdır. Bunun əvəzinə ViewModel UserRepository interfeysindən asılıdır və Retrofit ilə konkret UserRepositoryImpl tətbiqi konstruktor vasitəsilə ötürülür. Android-də DIP Hilt/Dagger və ya Koin vasitəsilə həyata keçirilir: bütün asılılıqlar DI konteyneri vasitəsilə təmin edilir.

kotlin
// ✅ DIP: Modul abstraksiyadan asılıdır, detaldan yox
class UserRepositoryImpl(
    private val api: UserApi,   // Interfeysdən asılıdır
    private val db: UserDao     // Interfeysdən asılıdır
) : UserRepository {

    override suspend fun getUser(id: String): User {
        return api.fetchUser(id)
    }
}

// Hilt DI: detallar DI modulu vasitəsilə bağlanır
@Module
object NetworkModule {
    @Provides
    fun provideUserApi(retrofit: Retrofit): UserApi =
        retrofit.create(UserApi::class.java)
}

SOLID-in mobil inkişafda tətbiqi

Mobil inkişafda SOLID bütün səviyyələrdə tətbiq olunur: tətbiq arxitekturasından fərdi siniflərə qədər. Android layihələrində Clean Architecture kodu üç təbəqəyə ayırır: domain (biznes mantiqi — çərçivələrdən asılı deyil), data (repozitoriyalar, API, BD) və presentation (UI, ViewModel). Domain təbəqəsi SOLID prinsiplərindən istifadə edir: use case (SRP), repozitoriya interfeysləri (DIP), entity sinifləri (OCP + LSP).

Android Developers Guide, 2025 görə, SRP Android-də ViewModel, Repository və Mapper bölgüsündə özünü göstərir. OCP — DataSource interfeysi vasitəsilə yeni məlumat mənbələri əlavə edərkən. LSP — müxtəlif repozitoriyalardan Result-un vahid şəkildə işlənməsində. ISP — CQRS yanaşmasında (Read/Write repozitoriyalarının ayrılması). DIP — asılılıqların daxil edilməsi üçün Hilt/Koin vasitəsilə.

PrinsipOnsuz problemMobil layihədə həll
SRP1000+ sətir ActivityViewModel + UseCase + Repository
OCPÖdəniş növü üzrə switch-caseStrategy: PaymentGateway interfeysi
LSPBaseViewModel dəyişikliyində xətaAlt siniflərin müqaviləsinin yoxlanması
ISPUnsupportedOperationExceptionReader / Writer ayrılması
DIPViewModel əl ilə Retrofit yaradırHilt / Koin DI konteyneri

SOLID tətbiq edərkən tipik səhvlər

SOLID səhvləri ən çox kodun həddən artıq mürəkkəbləşməsilə bağlıdır. Birinci — konteksti nəzərə almadan prinsiplərə sözü sözbəsöz əməl etmək. Bir UserService sinfini təmiz ISP üçün 10 interfeysə və 15 sinfə bölmək overengineering-dir. SOLID bir alətdir, məqsəd deyil. İkinci səhv — SRP-ni bir metod = bir məsuliyyət ilə qarışdırmaq. Sinif bir neçə metoda malik ola bilər, əgər onların hamısı bir məsuliyyət sahəsinə aiddirsə.

Simple Thread, 2024 görə, üçüncü səhv — Android-də ViewModel mirası alınarkən LSP-yə məhəl qoymamaq. Əgər baza ViewModel LiveData gözləyirsə, uşaq isə StateFlow istifadə edirsə — LiveData-ya abunə olan müştəri kodu yenilənmələri almayacaq. Dördüncü — test etmək üçün DIP-in pozulması: RepositoryImpl birbaşa OkHttpClient nümunəsi yaradır, bu da vahid testləri qeyri-mümkün edir.

Qızıl orta qaydası: SOLID-i real problemi həll etdikdə tətbiq edin (tez-tez dəyişikliklər, test etmənin çətinliyi, təkrarlanma). Sadə CRUD ekranları üçün bütün beş prinsipə ciddi əməl etmək həddən artıqdır. Biznes mantiqi, maliyyə hesablamaları və API qarşılıqlı əlaqələri üçün SOLID məcburidir.

SOLID və Clean Architecture əlaqəsi

Clean Architecture (Robert C. Martin, 2012) — SOLID-in tətbiq təbəqəsi səviyyəsində birbaşa tətbiqidir. SRP use case sərhədlərini müyyənləşdirir (hər use case — bir sinif). OCP repozitoriya interfeysləri vasitəsilə həyata keçirilir (Data təbəqəsi Domain-i dəyişmədən dəyişə bilər). ISP Use Case-in giriş/çıxış boundary bölgüsünü təmin edir. DIP — asılılıqların Domain təbəqəsinin içinə doğru istiqaməti. LSP repozitoriyanın istənilən tətbiqinin use case-i pozmadan dəyişdirilə biləcəyini təmin edir.

Tez-tez verilən suallar

SOLID sadə sözlərlə nədir?

SOLID — kodu dəyişmək, test etmək və anlamaq asan olması üçün beş yazı qaydasıdır. Hər hər bir prinsipdir: böyük siniflər yazmayın (SRP), mövcud kodu dəyişməyin — yenisini əlavə edin (OCP), vərislərin davranışını pozmayın (LSP) və digərləri.

Hansı SOLID prinsipi ən vacibdir?

SRP (Single Responsibility) ən vacib sayılır, çünki onun pozulması God-siniflərə — test etməsi və dəyişməsi çətin olan nəhəng siniflərə gətirib çıxarır. Bununla belə, DIP (Dependency Inversion) olmadan kod sıx bağlı qalır, bu da kritikdir.

SOLID mobil inkişaf üçün məcburidir?

Məcburi deyil, lakin uzun həyat dövrü olan kommersiya layihələri üçün çox arzuolunandır. Sadə tətbiqlər (bir ekran, biznes mantiqi yoxdur) üçün SOLID həddən artıq ola bilər. 50+ ekran və 3+ tərtibatçı olan layihələr üçün SOLID zəruri minimumdur.

SOLID-ə əməl edilməsə nə olar?

Nəticələr: siniflər şişmanlaşır (1000+ sətir), bir yerdə dəyişiklik üç başqa yeri sındırır, vahid testlər yazmaq qeyri-mümkündür, yeni funksiyanın əlavə edilməsi günlər əvəzinə həftələr çəkir. Zamanla kod Big Ball of Mud — qarışıq və kövrək bir şeyə çevrilir.

Layihədə SOLID-ə əməl olunduğunu necə yoxlamaq olar?

Əməl əlamətləri: hər sinif 200 sətirdən azdır, funksiya dəyişikliyi 5+ fayla təsir etmir, testlər 10 asılılığı mock etmədən yazılır, yeni tərtibatçı strukturu bir günə başa düşür. SonarQube və detekt kimi alətlər SRP və DIP pozuntularını aşkarlamağa kömək edir.

Yekun

  • SOLID — çevik və davamlı kod yaratmaq üçün beş OOP prinsipi (SRP, OCP, LSP, ISP, DIP)
  • SRP — hər varlıq bir tapşırığa cavabdehdir, God-sinif problemlərini həll edir
  • OCP — mövcud kodu dəyişmədən polimorfizm vasitəsilə genişləndirmə
  • LSP — vərislər baza sinfinin davranışını pozmamalıdır
  • ISP — universal İsveçrə bıçağı əvəzinə dar interfeyslər
  • DIP — abstraksiyalardan asılılıq, Android-də Hilt/Koin vasitəsilə daxil etmə
  • SOLID Clean Architecture və kommersiya mobil layihələri üçün məcburidir

Açar təslim mobil tətbiq hazırlayacağıq

IT Sectr 2017-ci ildən startaplar və bizneslər üçün iOS və Android tətbiqləri yaradır. Sizə məsləhət verəcəyik və ən yaxşı həlli təklif edəcəyik.

Layihəni müzakirə et

Həm də oxuyun