Circuit Breaker Pada Microservice
In Case of Overload just Break the Circuit
Sekilas istilahnya seperti suatu istilah yang ada pada dunia kelistrikan (electricity). Memang benar sekali istilah Cicuit Breaker pada microsercvice arsitektur tidak jauh dengan pengertian Circuit Breaker pada istilah kelistrikan.
Dalam ilmu kelistrikan yang dimaksud dengan circuit breaker adalah sebuah alat yang dirancang untuk memutuskan arus listrik secara otomatis ketika terjadi korsleting (short circuit) atau kelebihan beban. Tujuan dari circuit breaker atau sikring adalah untuk melindungi peralatan kita dari kerusakan yang mungkin tejadi ketika kelebihan beban atau korsleting terjadi.
Principles of Resiliency
Berikut adalah beberapa prinsip utama yang saya pegang dan usahakan ketika membuat API yang lebih tangguh.
- Kegagalan dalam ketergantungan terhadap service seharusnya tidak merusak pengalaman pengguna (baik itu end-user atau pun service)
- API harus secara otomatis mengambil tindakan korektif ketika salah satu dependensi servicenya gagal.
- API harus dapat menunjukkan kepada kita apa yang terjadi sekarang, selain apa yang terjadi 15–30 menit yang lalu, kemarin, minggu lalu, dll.
Circuit Breaker Pattern
Circuit breaker sendiri dalam dunia software khsusnya dalam microservice arsitektur merupakan salah satu dari sekian banyak design pattern yang ada. Apabila kita telah menggunakan microservice arsitektur pada sistem kita maka umumnya satu service akan berkolaborasi dengan service lainnya.
Ketika suatu service secara synchronous memanggil service lainnya maka akan selalu ada kemungkinan service yang dipanggil tadi mati, tidak tersedia, atau mengalami latency yang tinggi sehingga time out dan kegagalan request pun terjadi.
Pada service yang memanggil kita sebut saja Service A pasti ketika melakukan serangkaian proses akan terdapat resource dari server yang digunakan (memori dan procesor).
Umumnya suatu thread akan digunakan oleh Service A sambil menunggu respon dari Service yang dipanggil kita sebut Service B. Apabila ini terjadi terus (Seriver A akan terus menerus menahan resource karena menunggu respon dari service B) maka ketika Service A berjalan, lama kelamaan Service A akan kehabisan Resource juga, Pada akhirnya Service A mengalami kegalaan dan tidak dapat memberikan layanan.
Apabil dalam microservice arsiterkur dan hal ini terjadi maka akan ada kemungkinan besar kegalaan service yang terjadi berantai dan pada akhirnya semua service menjadi down.
Berikut adalah penjelasan dari gambar diatas.
- Kita memiliki empat service berbeda yaitu Service A, B, C, dan D.
- Karena permintaan dari luar, Service A akan terhubung dengan Service B dan B ke C dan C ke D.
- Ketika, Service D gagal karena beberapa alasan.
- Jadi, koneksi yang dibuat ke Service D oleh Service lain akan menunggu selama Service D yang tidak responsif akan tetap dalam keadaan yang sama.
- Oleh karena itu, Service C akan terus mencoba membuat koneksi dengan Service D. Demikian pula, Service B dan Service A.
- Ini akan menyebabkan kegagalan Cascade dan seluruh aplikasi, atau sebagian dari Service tidak akan tersedia.
Solution
Agar dapat terhindar dari cascade failure ini maka client harus menggunakan atau melalui proxy sebelum memanggil service yang di tuju. Proxy ini bertindak layaknya seperti pemutus aliran listrik.
Circuit breaker pattern adalah solusi untuk masalah ini. Ide dasar dibalik pemutus sirkuit sangat sederhana. Kita membungkus panggilan fungsi yang dilindungi dalam objek pemutus sirkuit, yang memantau kegagalan.
Setelah kegagalan mencapai ambang tertentu, pemutus sirkuit akan trip, dan semua panggilan lebih lanjut ke pemutus sirkuit kembali dengan kesalahan atau dengan di alihkan ke beberapa service alternatif atau pesan default, tanpa memanggil fungsi yang dilindungi sama sekali. Ini akan memastikan sistem responsif dan thread tidak menunggu panggilan yang tidak responsif.
Contoh sederhana penggunakan circuit breaker menggunakan Netflix Hystrix.
package hello;import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.bind.annotation.RequestMapping;@RestController
@SpringBootApplication
public class BookstoreApplication {@RequestMapping(value = "/recommended")
public String readingList(){
return "The legennd, Help Engineering Build Better Software";
}public static void main(String[] args) {
SpringApplication.run(BookstoreApplication.class, args);
}
}package hello;import java.net.URI;import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;@Service
public class BookService {private final RestTemplate restTemplate;public BookService(RestTemplate rest) {
this.restTemplate = rest;
}@HystrixCommand(fallbackMethod = "reliable")
public String readingList() {
URI uri = URI.create("http://localhost:8090/recommended");
return this.restTemplate.getForObject(uri, String.class);
}public String http://localhost:8090/recommended"() {
return "Cloud Native Java";
}}
Apabila http://localhost:8090/recommended" bermasalah maka secara otomatis methode reliable() akan dipanggil.
State Pada Circuit Breaker
Para ahli telah mendefinisikan ada 3 kedaan atau state dari 2 state yang secara natural pasti terjadi. State-state tersebur adalah.
- Closed, ketika semua berjalan dengan normal circuit breaker ini akan tetap dapam keadaan terturup (closed) dan semua request akan di teruskan ke service-service yang dituju. Apabila terjadi sejumlah kegagalan yang melebihi ambang batas makan akan masuk ke state Open.
- Open,circuit breaker akan menggembalikan error untuk setiap request tanpa harus mengeksekusi atau meneruskan ke service-service yang bermasalah.
- Half-Open, setelah beberapa waktu (time out), circuit breaker akan masuk ke kondisi setengah terbuka untuk menguji apakah masalah yang terjadi masih ada? Jika pada state ini request gagal maka state kembali ke status Open dan jika berhasil circuit akan kembali ke keadaan normar (closed).