Mengenal Prinsip SOLID Dalam Software Development

Daniel Saputra
Eureka Edutech
Published in
6 min readApr 21, 2022

Sahabat Pintar, sebagai developer kita memahami bahwa suatu bisnis berbasis teknologi sangat bergantung pada software sebagai tulang punggungnya.

Berkembangnya bisnis berbanding lurus dengan meningkatnya iterasi yang dilakukan pada software yang digunakan. Namun untuk membuat perubahan pada software dibutuhkan waktu, dimana waktu disini merupakan variabel penting ketika scale bisnis semakin besar.

Pada artikel ini kita akan membahas prinsip SOLID untuk membuat software lebih maintainable sehingga developer lebih produktif dan kecepatan iterasi software meningkat.

Prinsip SOLID pertama kali diperkenalkan oleh Robert J. Martin (Uncle Bob). Dimana prinsip ini berisi best practices dalam pengembangan software.

Maka dengan menerapkannya, kita bisa membuat software menjadi lebih mudah dikelola seiring dengan bertambahnya kompleksitas software tersebut.

SOLID merupakan singkatan dari:
S — Single Responsibility Principle (SRP)
O — Open-Closed Principle (OCP)
L — Liskov Substitution Principle (LSP)
I — Interface Segregation Principle (ISP)
D — Dependency Inversion Principle (DIP)

Secara konsep, prinsip SOLID dapat diterapkan kedalam banyak bahasa pemrograman. Kita akan coba mempelajari prinsip tersebut satu persatu, lalu melihat contoh penerapannya pada bahasa Java.

Single Responsibility Principle (SRP)

“A class should have one and only one reason to change, meaning that a class should have only one job.”

Class yang memiliki banyak tugas dapat mengakibatkan bug karena perubahan yang dilakukan pada salah satu tugasnya bisa berdampak juga ke bagian lain.

Untuk menghindarinya kita bisa menerapkan prinsip pertama dalam SOLID dimana suatu class hanya boleh memiliki satu alasan untuk berubah, dengan kata lain suatu class hanya boleh memiliki satu tugas.

Contoh Kasus

Misal kita mempunyai class Task. Class tersebut mempunyai banyak tugas diantaranya seperti mengunduh file hingga menyimpan data. Pada gambar di atas logic di dalam method persistTheData mempunyai ketergantungan ke method parseTheFile.

Ketika logic parseTheFile diubah, maka persistTheData akan terkena dampaknya sehingga bisa menimbulkan bug.

Solusi yang bisa kita gunakan untuk masalah di atas adalah membuat class terpisah untuk mengunduh dan menyimpan file sehingga ketika salah satu logic-nya diubah tidak berdampak ke bagian yang lain.

Open-Closed Principle (OCP)

Classes should open for extension but closed for modification

Secara umum ketika kita membuat method pada suatu class, lalu melakukan perubahan pada method tersebut, class lain yang menggunakan method tersebut akan terkena dampaknya.

Solusi ideal untuk masalah diatas yaitu menambah method baru sesuai kebutuhan bukan mengubah method lama yang sudah jalan.

Contoh Kasus

Misal, kita punya method yang berfungsi untuk menghitung luas area dari shapes.

Method di atas akan melakukan pengecekan shape untuk Rectangle dan Circle, bagaimana ketika kita ingin menambahkan bentuk lain?.

Solusi yang bisa kita lakukan yaitu membuat abstract class sebagai abstraksi dari shape/bentuk yang akan dihitung. Dimana pada abstract class tersebut terdapat method Area untuk menghitung luasnya.

Ketika ada shape baru yang ingin dibuat, kita hanya perlu membuat class dengan menerapkan abstraksi yang ada pada class Shape.

Dengan demikian kita telah menerapkan open for extension untuk membuat shape baru, dan close for modification yaitu mencegah perubahan pada shape existing yang sudah berjalan.

Liskov Substitution Principle (LSP)

If S is a subtype of T, then objects of type T in a program may be replaced with objects of type S without altering any of the desirable properties of that program.

Ketika child class tidak bisa melakukan aksi yang sama seperti parent class maka dapat terjadi bug.

Tujuan dari penerapan LSP adalah untuk menjaga konsistensi sehingga parent atau child class dapat bekerja dengan cara yang sama tanpa adanya error.

Contoh Kasus

Misal kita punya Rectangle class dengan setWidth dan setHeight method, kemudian kita membuat class Square yang ingin mengimplementasikan method yang sama seperti class Rectangle, instead membuat method yang sama berulang kita bisa melakukan extends class.

Masalahnya muncul ketika kita mencoba memasukan class Square pada method test dibawah. Perlu diperhatikan pada method setWidth pada class Square akan membuat kedua height dan width menjadi value inputan, hal ini berbeda dengan method pada class Rectangle.

Bisa kita pahami bahwa behaviour dari method setWidth pada class Rectangle dan class Square berbeda. Sehingga parent class tidak bisa digunakan untuk menggantikan child class.

Dari contoh diatas kita bisa menyimpulkan, gunakan inheritance ketika child class dapat digunakan untuk menggantikan parent class. Jangan gunakan inheritance hanya untuk mengurangi jumlah line of code.

Interface Segregation Principle

Clients should not be forced to depend on methods that they do not use.

Tujuan dari prinsip ISP yaitu suatu class hanya melaksanakan method yang dibutuhkan. Jika ada method yang tidak digunakan maka harus dihapus atau dipindah ke Class lainnya.

Contoh Kasus

Misal kita punya abstract class Animal, kemudian class Cat dan class Tiger sebagai implementasinya.

Ketika kita menambahkan method play, maka setiap class yang mengimplementasi class Animal harus menerapkan method play tersebut meskipun class Tiger tidak memerlukannya karena merupakan hewan liar. Berdasarkan konsep ISP yang kita lakukan disini merupakan bad practice.

Solusi yang bisa kita lakukan yaitu membuat class Pet di extends dari class Animal. Dimana method play kita letakan pada class Pet instead of class Animal.

Sehingga class Cat extends dari class Pet dan class Tiger extends dari class Animal. Dengan demikian kita bisa menghindari membuat method yang tidak dibutuhkan.

Sebagai catatan usahakan agar class tidak mengimplementasikan interface yang tidak dibutuhkan. Instead of fat interface lebih baik kita memecahnya menjadi interface yang lebih kecil sehigga bisa kita sesuaikan dengan class yang dimiliki.

Dependency Inversion Principle

High-level modules should not depend on low-level modules. Both should depend on abstractions. Abstractions should not depend on details. Details should depend on abstractions.

Prinsip DIP bertujuan untuk mengurangi ketergantungan dependency dari high-level Class kepada low-level Class melalu penggunaan interface.

Contoh Kasus

Misal kita punya method copy yang bertugas untuk meng-copy data ke output device (printer, disk). Ketika jumlah output device meningkat maka logic di dalam method akan terus diubah.

Solusi untuk masalah di atas adalah membuat interface untuk Reader dan Writer. Dengan demikian, method copy dapat membaca dari any Reader dan menulis ke any Writer, sehingga isi method tidak perlu diubah ketika ada source Reader maupun Writer baru.

Kesimpulan

Demikian kita telah membahas tujuan dan contoh kasus dari masing-masing prinsip SOLID. Dengan menerapkannya, kita bisa membuat software menjadi lebih maintainable dan sehingga kecepatan pengembangan software meningkat.

Jika ada hal yang ingin ditanyakan silahkan tinggalkan komentar!
Terima Kasih.

Referensi
- Software Design — Introduction to SOLID Principles in 8 Minutes

--

--

Daniel Saputra
Eureka Edutech

Software Engineer @Ralali. Writes about Computer Science, Software Engineering, Infrastructures, and Distributed System