Son zamanlarda dağıtımla ilgili işler yapıyorum, yetersiz insan gücünden dolayı sadece kendi başıma gelebiliyorum, bu dönemdeki fazla mesai programına bakmak berbat.
Ancak gelecekte paylaşmak için gelecekte karşılaşılan birçok ilginç şey de var, bugün hizmeti tartışmaya odaklanacağım Kayıt ve keşif .
Dağıtılmış sorunlar
İşim nispeten basit, şu anda hangi servis örneklerinin kullanılabileceğini bilmem gerekiyor (uzaktan aramalar için değil, sadece bilgi almam gerekiyor).
Bu işlevi elde etmenin en basit yolu, uygulamadaki tüm hizmet düğümlerini yapılandırmaktır, böylece her kullanımda belirli bir algoritma aracılığıyla yapılandırma listesinden yalnızca birini seçmeniz gerekir.
Ancak bunun çok ciddi bir sorunu olacak:
Uygulamanın, uygulama yüküne göre hizmet düğümlerinin sayısını esnek bir şekilde ayarlaması gerektiğinden, yapılandırmam sabit kodlanamaz.
Aksi takdirde, ya yeni eklenen düğüme erişilmez ya da kapatılan düğüm talep edilir ve bu kesinlikle kabul edilemez.
Genellikle bu tür dağıtılmış problemleri çözmek için, bu bilgiyi depolamak için halka açık bir alana ihtiyaç vardır Örneğin, Redis kullanılabilir mi?
Her düğüm, başlangıçtan sonra bilgileri Redis ile kaydeder ve kapatıldığında verileri siler.
Aslında, düğümün ip + bağlantı noktasını depolamaktır ve daha sonra hizmet düğümü bilgilerini bilmeniz gerektiğinde, yalnızca Redis'te almanız gerekir.
Aşağıda gösterildiği gibi:
Ancak bu, her kullanıldığında Redis'e sık sık sorgu gönderilmesine neden olacaktır.Bu sorunu önlemek için, her sorgudan sonra en son verilerin bir kopyasını yerel olarak önbelleğe alabiliriz. Bu, önce yerel olarak elde ederek verimliliği gerçekten artırabilir.
Ancak yeni sorunlar da olacak, servis sağlayıcının düğümü tüketicileri ekler veya silerse, bu taraf durumu bilmeyecektir.
Bu sorunu çözmek için akla gelen ilk şey, servis listesini düzenli olarak güncellemek için zamanlanmış görevleri kullanmaktır.
Yukarıdaki şema kesinlikle mükemmel ve zarif değil. Ana noktalar aşağıdaki gibidir:
Bu yüzden daha güvenilir bir çözüme ihtiyacımız var Bu senaryo aslında Dubbo'ya çok benziyor.
Onu kullanan öğrenciler bu resme aşina olmalıdır.
Dubbo resmi web sitesinden alıntılanmıştırTemel içeriklerden biri (kırmızıyla özetlenmiştir) hizmet kaydı ve keşiftir.
Genel olarak konuşursak, tüketicilerin uzaktan aramaları başlatmak için servis sağlayıcının ağ adresini (ip + portu) bilmeleri gerekir.Bu içerik aslında yukarıdaki gereksinimlerime çok benzer.
Dubbo, sorunu çözmek için Zookeeper'ı kullanır.
Zookeeper ne yapabilir
Nasıl uygulanacağını ayrıntılı olarak tartışmadan önce, Zookeeper'ın birkaç önemli özelliğine bir göz atalım.
Zookeeper, bir dosya sistemine benzer bir ağaç yapısı uygular:
Bu düğümlere znode adı verilir (isim önemli değildir) ve her bir düğüm belirli verileri depolayabilir.
Önemli olan, dört tür znode olmasıdır:
Yukarıdaki Redis kullanımıyla ilgili en büyük sorunun ne olduğunu düşünün.
Aslında, servis sağlayıcının bilgileri gerçek zamanlı olarak güncellenemez.
Zookeeper kullanılarak nasıl başarılır?
Esas olarak üçüncü özelliğe bakın: Geçici düğüm
Zookeeper, tipik bir gözlemci modudur.
Bu sayede servis düğümünün bilgilerini gerçek zamanlı olarak elde edebiliyoruz ve aynı zamanda listeyi ilk aldığımızda sadece yerel olarak önbelleğe almamız gerekiyor; Zookeeper ile sık sık etkileşim kurmamıza gerek yok, sadece bildirim güncellemelerini bekleyin.
Nedeni ne olursa olsun, düğüm kapatıldıktan sonra bilgiler Zookeeper'da silinecektir.
Etkisi gösterimi
Bu gerçekleştirme yolu şuna benzer.
Bunun için şunu göstermek için yeni bir uygulama oluşturdum:
https://github.com/crossoverJie/netty-action/tree/master/netty-action-zk
Basit bir SpringBoot uygulaması, sadece birkaç şey yapıyor.
Yerel olarak iki uygulamayı başlattım: 127.0.0.1:8083 ve 127.0.0.1:8084. Görüntülere bir göz atın.
İki uygulama başlatılır:
Zookeeper'ın mevcut görsel ağaç yapısı:
Tüm servis düğümü bilgilerini öğrenmek istediğinizde:
Kullanılabilir bir hizmet düğümü almak istediğinizde:
İşte basit bir oylama.
Bir düğüm çalışmadığında: uygulamaya yerel önbelleği güncellemesi bildirilecektir. Aynı zamanda, Zookeeper'daki düğümler otomatik olarak silinecektir.
En son düğümü tekrar alırken:
En son bilgiler, düğüm geri yüklendiğinde doğal olarak elde edilebilir. Yerel önbellek de zaman içinde güncellenecektir.
Kodlama uygulaması
Esas olarak ZKClient'ın API'sinin kullanılmasıyla uygulanması nispeten basittir.
Birkaç tane daha çekirdek yayınlayın.
kayıtlı
Zookeeper'ı kaydetmeye başlayın.Ana mantık bu başlıktadır.
Yerel önbelleğe göre
Servis değişiklikleri izlenir public void subscribeEvent (Dize yolu) { zkClient.subscribeChildChanges (yol, yeni IZkChildListener () { @Override public void handleChildChange (String parentPath, List < Dize > currentChilds) Exception {atar logger.info ("Yerel önbelleği temizle / güncelle parentPath = [{}], currentChilds = [{}]", parentPath, currentChilds.toString ()); // Önce tüm önbellekleri güncelleyin / silin ve ardından ekleyin serverCache.updateCache (currentChilds); } }); }Burada yerel önbelleğin güncellendiğini görebilirsiniz.Önbellek Guava tarafından sağlanan Önbelleği kullanır.İlgileniyorsanız, önceki kaynak kod analizini görüntüleyebilirsiniz.
/ ** * Önce tüm önbellekleri güncelleyin / silin ve ardından ekleyin * * @param currentChilds * / public void updateCache (Liste < Dize > currentChilds) { cache.invalidateAll (); for (String currentChild: currentChilds) { Dize anahtarı = currentChild.split ("-"); addCache (anahtar); } }İstemci yükü
Aynı zamanda istemcide bir yük algoritması sağlanır.Aslında bir yoklama uygulamasıdır:
/ ** * Sunucu seç * * @dönüş * / public String selectServer () { Liste < Dize > tümü = getAll (); eğer (all.size () == 0) { yeni RuntimeException ("Yönlendirme listesi boş"); } Uzun konum = index.incrementAndGet ()% all.size (); eğer (pozisyon < 0) { pozisyon = 0L; } all.get (position.intValue ()); }Elbette ağırlık, rastgele ve LRU gibi daha fazla algoritma burada genişletilebilir.
Zookeeper diğer avantajlar ve sorunlar
Zookeeper, doğal olarak büyük bir dağıtılmış koordinasyon aracıdır ve özelliklerinin başka işlevleri de olabilir.
Kaydı gerçekleştirirken ve bu gereksinimi keşfederken, Zookeeper aslında en çok tercih edilen değildir.
Zookeeper, CAP teorisinde CP'yi (tutarlılık, bölüm hatası toleransı) seçtiğinden, Zookeeper kümesindeki düğümlerin yarısı kullanılamadığında hiçbir veri elde edilemez.
Tutarlılık için bir sorun yoktur, ancak Eureka, Spring Cloud'da doğrulanan kayıt ve keşif senaryolarında daha çok önerilmektedir. Detaylar bu makalede tartışılmamaktadır.
Ancak kullanım senaryom göz önüne alındığında, Zookeeper zaten yetenekli.
sonuç olarak
Bu makalenin tüm kodu GitHub'da barındırılmaktadır.
https://github.com/crossoverJie/netty-action.
Görünüşte basit bir kayıt ve keşif işlevi gerçekleştirilir, ancak dağıtılmış uygulamalar bundan çok daha fazlasıdır.