Rumah pembangunan bahagian belakang Golang Pemutus Litar dalam Go: Hentikan Kegagalan Lata

Pemutus Litar dalam Go: Hentikan Kegagalan Lata

Jul 17, 2024 pm 05:41 PM

Circuit Breakers in Go: Stop Cascading Failures

Pemutus Litar

Pemutus litar mengesan kegagalan dan merangkum logik pengendalian kegagalan tersebut dengan cara yang menghalang kegagalan daripada terus berulang. Contohnya, ia berguna apabila berurusan dengan panggilan rangkaian ke perkhidmatan luaran, pangkalan data, atau benar-benar, mana-mana bahagian sistem anda yang mungkin gagal buat sementara waktu. Dengan menggunakan pemutus litar, anda boleh mengelakkan kegagalan melata, mengurus ralat sementara dan mengekalkan sistem yang stabil dan responsif di tengah-tengah kerosakan sistem.

Kegagalan Lata

Kegagalan berlatarkan berlaku apabila kegagalan dalam satu bahagian sistem mencetuskan kegagalan di bahagian lain, yang membawa kepada gangguan yang meluas. Contohnya ialah apabila perkhidmatan mikro dalam sistem teragih menjadi tidak bertindak balas, menyebabkan perkhidmatan bergantung tamat masa dan akhirnya gagal. Bergantung pada skala aplikasi, impak kegagalan ini boleh menjadi malapetaka yang akan merendahkan prestasi dan mungkin juga memberi kesan kepada pengalaman pengguna.

Corak Pemutus Litar

Pemutus litar itu sendiri ialah teknik/corak dan terdapat tiga keadaan berbeza ia beroperasi yang akan kita bincangkan:

  1. Keadaan Tertutup: Dalam keadaan tertutup, pemutus litar membenarkan semua permintaan melalui perkhidmatan sasaran seperti biasa. Jika permintaan berjaya, litar tetap ditutup. Walau bagaimanapun, jika ambang kegagalan tertentu dicapai, litar beralih ke keadaan terbuka. Anggap ia seperti perkhidmatan yang beroperasi sepenuhnya di mana pengguna boleh log masuk dan mengakses data tanpa masalah. Semuanya berjalan lancar.

Circuit Breakers in Go: Stop Cascading Failures

2. Keadaan Terbuka : Dalam keadaan terbuka, pemutus litar serta-merta gagal semua permintaan masuk tanpa cuba menghubungi perkhidmatan sasaran. Negeri itu dimasukkan untuk mengelakkan lebihan beban perkhidmatan yang gagal dan memberi masa untuk pulih. Selepas tamat masa yang telah ditetapkan, pemutus litar bergerak ke keadaan separuh terbuka. Contoh yang boleh dikaitkan ialah ini; Bayangkan kedai dalam talian mengalami isu mendadak di mana setiap percubaan pembelian gagal. Untuk mengelak daripada membebankan sistem, kedai berhenti menerima sebarang permintaan pembelian baharu buat sementara waktu.

Circuit Breakers in Go: Stop Cascading Failures

3. Keadaan Separuh Terbuka : Dalam keadaan separuh terbuka, pemutus litar membenarkan bilangan permintaan ujian terhad (boleh dikonfigurasikan) untuk melalui perkhidmatan sasaran. Dan jika permintaan ini berjaya, litar beralih kembali ke keadaan tertutup. Jika gagal, litar kembali ke keadaan terbuka. Dalam contoh kedai dalam talian yang saya berikan dalam keadaan terbuka di atas, di sinilah kedai dalam talian mula membenarkan beberapa percubaan pembelian untuk melihat sama ada isu itu telah dibetulkan. Jika beberapa percubaan ini berjaya, kedai akan membuka semula perkhidmatannya sepenuhnya untuk menerima permintaan pembelian baharu.

Rajah ini menunjukkan apabila pemutus litar cuba untuk melihat sama ada permintaan untuk Perkhidmatan B berjaya dan kemudian ia gagal/putus:

Circuit Breakers in Go: Stop Cascading Failures

Rajah susulan kemudian menunjukkan apabila ujian meminta Perkhidmatan B berjaya, litar ditutup dan semua panggilan selanjutnya dihalakan ke Perkhidmatan B sekali lagi:

Circuit Breakers in Go: Stop Cascading Failures

Nota : Konfigurasi utama untuk pemutus litar termasuk ambang kegagalan (bilangan kegagalan yang diperlukan untuk membuka litar), tamat masa untuk keadaan terbuka dan bilangan permintaan ujian dalam separuh terbuka negeri.

Melaksanakan Pemutus Litar dalam Go

Adalah penting untuk menyatakan bahawa pengetahuan awal tentang Go diperlukan untuk diikuti dalam artikel ini.

Seperti mana-mana corak kejuruteraan perisian, pemutus litar boleh dilaksanakan dalam pelbagai bahasa. Walau bagaimanapun, artikel ini akan menumpukan pada pelaksanaan di Golang. Walaupun terdapat beberapa perpustakaan yang tersedia untuk tujuan ini, seperti goresilience, go-resiliency dan gobreaker, kami secara khusus akan menumpukan pada menggunakan perpustakaan gobreaker.

Petua Pro : Anda boleh melihat pelaksanaan dalaman pakej gobreaker, semak di sini.

Mari kita pertimbangkan aplikasi Golang mudah di mana pemutus litar dilaksanakan untuk mengendalikan panggilan ke API luaran. Contoh asas ini menunjukkan cara membungkus panggilan API luaran dengan teknik pemutus litar:

Mari kita sentuh beberapa perkara penting:

  1. Fungsi gobreaker.NewCircuitBreaker memulakan pemutus litar dengan tetapan tersuai kami
  2. Kaedah cb.Execute membungkus permintaan HTTP, mengurus keadaan litar secara automatik.
  3. Permintaan Maksimum ialah bilangan maksimum permintaan yang dibenarkan untuk dilalui apabila keadaan separuh terbuka
  4. Selang ialah tempoh kitaran keadaan tertutup untuk pemutus litar mengosongkan kiraan dalaman
  5. Tamat masa ialah tempoh sebelum beralih daripada keadaan terbuka kepada separuh terbuka.
  6. ReadyToTrip dipanggil dengan salinan kiraan apabila permintaan gagal dalam keadaan tertutup. Jika ReadyToTrip kembali benar, pemutus litar akan diletakkan dalam keadaan terbuka. Dalam kes kami di sini, ia kembali benar jika permintaan telah gagal lebih daripada tiga kali berturut-turut.
  7. OnStateChange dipanggil apabila keadaan pemutus litar berubah. Anda biasanya ingin mengumpulkan metrik perubahan keadaan di sini dan melaporkan kepada mana-mana pengumpul metrik pilihan anda.

Mari kita tulis beberapa ujian unit untuk mengesahkan pelaksanaan pemutus litar kami. Saya hanya akan menerangkan ujian unit yang paling kritikal untuk difahami. Anda boleh menyemak di sini untuk kod penuh.

  1. Kami akan menulis ujian yang mensimulasikan permintaan gagal berturut-turut dan menyemak sama ada pemutus litar bergerak ke keadaan terbuka. Pada asasnya, selepas 3 kegagalan, apabila kegagalan keempat berlaku, kami menjangkakan pemutus litar akan tersandung (terbuka) kerana keadaan kami berkata penting.Kegagalan Berturut-turut > 3 . Begini rupa ujian itu:
 t.Run("FailedRequests", func(t *testing.T) {
         // Override callExternalAPI to simulate failure
         callExternalAPI = func() (int, error) {
             return 0, errors.New("simulated failure")
         }

         for i := 0; i < 4; i++ {
             _, err := cb.Execute(func() (interface{}, error) {
                 return callExternalAPI()
             })
             if err == nil {
                 t.Fatalf("expected error, got none")
             }
         }

         if cb.State() != gobreaker.StateOpen {
             t.Fatalf("expected circuit breaker to be open, got %v", cb.State())
         }
     })
Salin selepas log masuk
  1. Kami akan menguji terbuka > separuh - terbuka > ditutup menyatakan. Tetapi kita akan mula-mula mensimulasikan litar terbuka dan memanggil tamat masa. Selepas tamat masa, kita perlu membuat sekurang-kurangnya satu permintaan kejayaan untuk litar beralih kepada separuh terbuka. Selepas keadaan separuh terbuka, kita perlu membuat satu lagi permintaan kejayaan untuk litar ditutup sepenuhnya semula. Jika atas sebarang sebab, tiada rekod permintaan kejayaan dalam kes itu, ia akan kembali dibuka. Begini rupa ujian itu:
     //Simulates the circuit breaker being open, 
     //wait for the defined timeout, 
     //then check if it closes again after a successful request.
         t.Run("RetryAfterTimeout", func(t *testing.T) {
             // Simulate circuit breaker opening
             callExternalAPI = func() (int, error) {
                 return 0, errors.New("simulated failure")
             }
    
             for i := 0; i < 4; i++ {
                 _, err := cb.Execute(func() (interface{}, error) {
                     return callExternalAPI()
                 })
                 if err == nil {
                     t.Fatalf("expected error, got none")
                 }
             }
    
             if cb.State() != gobreaker.StateOpen {
                 t.Fatalf("expected circuit breaker to be open, got %v", cb.State())
             }
    
             // Wait for timeout duration
             time.Sleep(settings.Timeout + 1*time.Second)
    
             //We expect that after the timeout period, 
             //the circuit breaker should transition to the half-open state. 
    
             // Restore original callExternalAPI to simulate success
             callExternalAPI = func() (int, error) {
                 resp, err := http.Get(server.URL)
                 if err != nil {
                     return 0, err
                 }
                 defer resp.Body.Close()
                 return resp.StatusCode, nil
             }
    
             _, err := cb.Execute(func() (interface{}, error) {
                 return callExternalAPI()
             })
             if err != nil {
                 t.Fatalf("expected no error, got %v", err)
             }
    
             if cb.State() != gobreaker.StateHalfOpen {
                 t.Fatalf("expected circuit breaker to be half-open, got %v", cb.State())
             }
    
             //After verifying the half-open state, another successful request is simulated to ensure the circuit breaker transitions back to the closed state.
             for i := 0; i < int(settings.MaxRequests); i++ {
                 _, err = cb.Execute(func() (interface{}, error) {
                     return callExternalAPI()
                 })
                 if err != nil {
                     t.Fatalf("expected no error, got %v", err)
                 }
             }
    
             if cb.State() != gobreaker.StateClosed {
                 t.Fatalf("expected circuit breaker to be closed, got %v", cb.State())
             }
         })
    
    Salin selepas log masuk
    1. Mari kita uji keadaan ReadyToTrip yang tercetus selepas 2 permintaan kegagalan berturut-turut. Kami akan mempunyai pembolehubah yang menjejaki kegagalan berturut-turut. Panggilan balik ReadyToTrip dikemas kini untuk memeriksa sama ada pemutus litar terputus selepas 2 kegagalan ( dikira.ConsecutiveFailures > 2). Kami akan menulis ujian yang mensimulasikan kegagalan dan mengesahkan kiraan dan peralihan pemutus litar ke keadaan terbuka selepas bilangan kegagalan yang ditentukan.
       t.Run("ReadyToTrip", func(t *testing.T) {
               failures := 0
               settings.ReadyToTrip = func(counts gobreaker.Counts) bool {
                   failures = int(counts.ConsecutiveFailures)
                   return counts.ConsecutiveFailures > 2 // Trip after 2 failures
               }
      
               cb = gobreaker.NewCircuitBreaker(settings)
      
               // Simulate failures
               callExternalAPI = func() (int, error) {
                   return 0, errors.New("simulated failure")
               }
               for i := 0; i < 3; i++ {
                   _, err := cb.Execute(func() (interface{}, error) {
                       return callExternalAPI()
                   })
                   if err == nil {
                       t.Fatalf("expected error, got none")
                   }
               }
      
               if failures != 3 {
                   t.Fatalf("expected 3 consecutive failures, got %d", failures)
               }
               if cb.State() != gobreaker.StateOpen {
                   t.Fatalf("expected circuit breaker to be open, got %v", cb.State())
               }
           })
      
      Salin selepas log masuk

      Strategi Lanjutan

      Kami boleh melangkah lebih jauh dengan menambahkan strategi mundur eksponen pada pelaksanaan pemutus litar kami. Kami akan memastikan artikel ini ringkas dan ringkas dengan menunjukkan contoh strategi mundur eksponen. Walau bagaimanapun, terdapat strategi lanjutan lain untuk pemutus litar yang patut disebut, seperti penumpahan beban, sekat, mekanisme sandaran, konteks dan pembatalan. Strategi ini pada asasnya meningkatkan keteguhan dan kefungsian pemutus litar. Berikut ialah contoh menggunakan strategi mundur eksponen:

      Penyingkiran Eksponen

      Pemutus litar dengan mundur eksponen

      Mari kita jelaskan beberapa perkara:

      Fungsi Backoff Tersuai: Fungsi ExponentialBackoff melaksanakan strategi backoff eksponen dengan jitter. Ia pada asasnya mengira masa mundur berdasarkan bilangan percubaan, memastikan bahawa kelewatan meningkat secara eksponen dengan setiap percubaan mencuba semula.

      Mengendalikan Percubaan Semula: Seperti yang anda lihat dalam pengendali /api, logik kini termasuk gelung yang cuba memanggil API luaran sehingga bilangan percubaan yang ditentukan ( percubaan := 5). Selepas setiap percubaan yang gagal, kami menunggu tempoh yang ditentukan oleh fungsi ExponentialBackoff sebelum mencuba semula.

      Perlaksanaan Pemutus Litar: Pemutus litar digunakan dalam gelung. Jika panggilan API luaran berjaya ( err == nil), gelung pecah, dan hasil yang berjaya dikembalikan. Jika semua percubaan gagal, ralat HTTP 503 (Perkhidmatan Tidak Tersedia) dikembalikan.

      Mengintegrasikan strategi mundur tersuai dalam pelaksanaan pemutus litar sememangnya bertujuan untuk mengendalikan ralat sementara dengan lebih anggun. Kelewatan yang semakin meningkat antara percubaan semula membantu mengurangkan beban pada perkhidmatan yang gagal, memberikan masa untuk pulih. Seperti yang terbukti dalam kod kami di atas, fungsi ExponentialBackoff kami telah diperkenalkan untuk menambah kelewatan antara percubaan semula apabila memanggil API luaran.

      Selain itu, kami boleh menyepadukan metrik dan pengelogan untuk memantau perubahan keadaan pemutus litar menggunakan alat seperti Prometheus untuk pemantauan dan amaran masa nyata. Berikut ialah contoh mudah:

      Melaksanakan corak pemutus litar dengan strategi lanjutan semasa

      Seperti yang anda akan lihat, kini kami telah melakukan perkara berikut:

      1. Dalam L16–21, kami mentakrifkan vektor pembilang prometheus untuk menjejaki bilangan permintaan dan keadaannya (berjaya, kegagalan, perubahan keadaan pemutus litar).
      2. Dalam L25–26, metrik yang ditakrifkan didaftarkan dengan Prometheus dalam fungsi init.

      Petua Pro : Fungsi init dalam Go digunakan untuk memulakan keadaan pakej sebelum fungsi utama atau mana-mana kod lain dalam pakej dilaksanakan. Dalam kes ini, fungsi init mendaftarkan metrik requestCount dengan Prometheus. Dan ini pada asasnya memastikan bahawa Prometheus mengetahui metrik ini dan boleh mula mengumpul data sebaik sahaja aplikasi mula berjalan.

      1. Kami mencipta pemutus litar dengan tetapan tersuai, termasuk fungsi ReadyToTrip yang meningkatkan pembilang kegagalan dan menentukan masa untuk mengelirukan litar.

      2. OnStateChange untuk mencatat perubahan keadaan dan menambah metrik prometheus yang sepadan

      3. Kami mendedahkan metrik Prometheus pada titik akhir /metrics

      Membungkus

      Untuk mengakhiri artikel ini, saya harap anda melihat bagaimana pemutus litar memainkan peranan yang besar dalam membina sistem yang berdaya tahan dan boleh dipercayai. Dengan secara proaktif mencegah kegagalan melata, mereka mengukuhkan kebolehpercayaan perkhidmatan mikro dan sistem yang diedarkan, memastikan pengalaman pengguna yang lancar walaupun dalam menghadapi kesukaran.

      Perlu diingat, mana-mana sistem yang direka untuk skalabiliti mesti menggabungkan strategi untuk menangani kegagalan dengan anggun dan pulih dengan pantas —  Oluwafemi , 2024

      Asalnya diterbitkan di https://oluwafemiakinde.dev pada 7 Jun 2024.

      Atas ialah kandungan terperinci Pemutus Litar dalam Go: Hentikan Kegagalan Lata. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan Laman Web ini
Kandungan artikel ini disumbangkan secara sukarela oleh netizen, dan hak cipta adalah milik pengarang asal. Laman web ini tidak memikul tanggungjawab undang-undang yang sepadan. Jika anda menemui sebarang kandungan yang disyaki plagiarisme atau pelanggaran, sila hubungi admin@php.cn

Alat AI Hot

Undresser.AI Undress

Undresser.AI Undress

Apl berkuasa AI untuk mencipta foto bogel yang realistik

AI Clothes Remover

AI Clothes Remover

Alat AI dalam talian untuk mengeluarkan pakaian daripada foto.

Undress AI Tool

Undress AI Tool

Gambar buka pakaian secara percuma

Clothoff.io

Clothoff.io

Penyingkiran pakaian AI

Video Face Swap

Video Face Swap

Tukar muka dalam mana-mana video dengan mudah menggunakan alat tukar muka AI percuma kami!

Artikel Panas

<🎜>: Bubble Gum Simulator Infinity - Cara Mendapatkan dan Menggunakan Kekunci Diraja
4 minggu yang lalu By 尊渡假赌尊渡假赌尊渡假赌
Nordhold: Sistem Fusion, dijelaskan
4 minggu yang lalu By 尊渡假赌尊渡假赌尊渡假赌
Mandragora: Whispers of the Witch Tree - Cara Membuka Kunci Cangkuk Bergelut
3 minggu yang lalu By 尊渡假赌尊渡假赌尊渡假赌

Alat panas

Notepad++7.3.1

Notepad++7.3.1

Editor kod yang mudah digunakan dan percuma

SublimeText3 versi Cina

SublimeText3 versi Cina

Versi Cina, sangat mudah digunakan

Hantar Studio 13.0.1

Hantar Studio 13.0.1

Persekitaran pembangunan bersepadu PHP yang berkuasa

Dreamweaver CS6

Dreamweaver CS6

Alat pembangunan web visual

SublimeText3 versi Mac

SublimeText3 versi Mac

Perisian penyuntingan kod peringkat Tuhan (SublimeText3)

Topik panas

Tutorial Java
1670
14
Tutorial PHP
1276
29
Tutorial C#
1256
24
Golang vs Python: Prestasi dan Skala Golang vs Python: Prestasi dan Skala Apr 19, 2025 am 12:18 AM

Golang lebih baik daripada Python dari segi prestasi dan skalabiliti. 1) Ciri-ciri jenis kompilasi Golang dan model konkurensi yang cekap menjadikannya berfungsi dengan baik dalam senario konvensional yang tinggi. 2) Python, sebagai bahasa yang ditafsirkan, melaksanakan perlahan -lahan, tetapi dapat mengoptimumkan prestasi melalui alat seperti Cython.

Golang dan C: Konvensyen vs kelajuan mentah Golang dan C: Konvensyen vs kelajuan mentah Apr 21, 2025 am 12:16 AM

Golang lebih baik daripada C dalam kesesuaian, manakala C lebih baik daripada Golang dalam kelajuan mentah. 1) Golang mencapai kesesuaian yang cekap melalui goroutine dan saluran, yang sesuai untuk mengendalikan sejumlah besar tugas serentak. 2) C Melalui pengoptimuman pengkompil dan perpustakaan standard, ia menyediakan prestasi tinggi yang dekat dengan perkakasan, sesuai untuk aplikasi yang memerlukan pengoptimuman yang melampau.

Bermula dengan Go: Panduan Pemula Bermula dengan Go: Panduan Pemula Apr 26, 2025 am 12:21 AM

GoisidealforbeginnersandSuekableforcloudandnetworkservicesduetoitssimplicity, kecekapan, danconcurrencyfeatures.1) installgofromtheofficialwebsiteandverifywith'goversion'.2)

Golang vs C: Perbandingan Prestasi dan Kelajuan Golang vs C: Perbandingan Prestasi dan Kelajuan Apr 21, 2025 am 12:13 AM

Golang sesuai untuk pembangunan pesat dan senario serentak, dan C sesuai untuk senario di mana prestasi ekstrem dan kawalan peringkat rendah diperlukan. 1) Golang meningkatkan prestasi melalui pengumpulan sampah dan mekanisme konvensional, dan sesuai untuk pembangunan perkhidmatan web yang tinggi. 2) C mencapai prestasi muktamad melalui pengurusan memori manual dan pengoptimuman pengkompil, dan sesuai untuk pembangunan sistem tertanam.

Impak Golang: Kelajuan, Kecekapan, dan Kesederhanaan Impak Golang: Kelajuan, Kecekapan, dan Kesederhanaan Apr 14, 2025 am 12:11 AM

Goimpactsdevelopmentpositivielythroughspeed, efficiency, andsimplicity.1) Speed: goCompilesquicklyandrunsefficiently, idealforlargeproject.2) Kecekapan: ITSComprehensivestandardlibraryraryrarexternaldependencies, enhingdevelyficiency.

Golang vs Python: Perbezaan dan Persamaan Utama Golang vs Python: Perbezaan dan Persamaan Utama Apr 17, 2025 am 12:15 AM

Golang dan Python masing -masing mempunyai kelebihan mereka sendiri: Golang sesuai untuk prestasi tinggi dan pengaturcaraan serentak, sementara Python sesuai untuk sains data dan pembangunan web. Golang terkenal dengan model keserasiannya dan prestasi yang cekap, sementara Python terkenal dengan sintaks ringkas dan ekosistem perpustakaan yang kaya.

Golang dan C: Perdagangan dalam prestasi Golang dan C: Perdagangan dalam prestasi Apr 17, 2025 am 12:18 AM

Perbezaan prestasi antara Golang dan C terutamanya ditunjukkan dalam pengurusan ingatan, pengoptimuman kompilasi dan kecekapan runtime. 1) Mekanisme pengumpulan sampah Golang adalah mudah tetapi boleh menjejaskan prestasi, 2) Pengurusan memori manual C dan pengoptimuman pengkompil lebih cekap dalam pengkomputeran rekursif.

Perlumbaan Prestasi: Golang vs C Perlumbaan Prestasi: Golang vs C Apr 16, 2025 am 12:07 AM

Golang dan C masing-masing mempunyai kelebihan sendiri dalam pertandingan prestasi: 1) Golang sesuai untuk kesesuaian tinggi dan perkembangan pesat, dan 2) C menyediakan prestasi yang lebih tinggi dan kawalan halus. Pemilihan harus berdasarkan keperluan projek dan tumpukan teknologi pasukan.

See all articles