Aracılığıyla paylaş


Bağımlılık sürümü çakışmalarını giderme

Bu makalede bağımlılık sürümü çakışmaları ve bunların nasıl giderilir açıklanmaktadır.

Java için Azure istemci kitaplıkları, aşağıdakiler gibi popüler üçüncü taraf kitaplıklarına bağlıdır:

Birçok Java uygulaması ve çerçevesi bu kitaplıkları doğrudan veya geçişli olarak kullanır ve bu da sürüm çakışmalarına yol açar. Maven ve Gradle gibi bağımlılık yöneticileri, tüm bağımlılıkları çözümleyip sınıf yolu üzerindeki her bağımlılığın yalnızca tek bir sürümünü oluşturur. Ancak, çözümlenen bağımlılık sürümünün uygulamanızdaki bu bağımlılığın tüm tüketicileriyle uyumlu olduğu garanti değildir. Daha fazla bilgi için Maven belgelerindeki Bağımlılık Mekanizmasına Giriş ve Gradle belgelerindeki Bağımlılık çözümünü anlama konularına bakın.

Doğrudan bağımlılıkların API uyumsuzluğu derleme hatalarına neden olur. Elmas bağımlılığı uyumsuzluğu genellikle NoClassDefFoundError, NoSuchMethodError veya diğer LinkageError gibi çalışma zamanı hatalarına neden olur. Tüm kitaplıklar semantik sürüm oluşturma işlemini kesinlikle izlemez ve hataya neden olan değişiklikler bazen aynı ana sürümde gerçekleşir.

Sürüm uyuşmazlığı sorunlarını tanılama

Aşağıdaki bölümlerde, sürüm uyuşmazlığı sorunlarını tanılama yöntemleri açıklanmaktadır.

Java için Azure SDK derleme aracını kullanma

Azure SDK ve Apache Maven ile çalışmaya başlama konusunda kullanıma sunulan Java için Azure SDK derleme aracı, yaygın olarak karşılaşılan sorunların belirlenmesine yardımcı olur. Bu derleme aracını projenize eklemenizi ve maven hedefini azure:run normal derleme sürecinize ekleyerek çalıştırmanızı öneririz. Uygun yapılandırmayla, bağımlılık çakışmalarını çalışma zamanında sorun haline gelmeden önce daha proaktif bir şekilde tanımlayabilir ve çözebilirsiniz.

Bağımlılık ağacını görüntüleme

Uygulamanızın tam bağımlılık ağacını sürüm numaralarıyla göstermek için veya gradle dependencies --scan komutunu çalıştırınmvn dependency:tree. mvn dependency:tree -Dverbose daha fazla bilgi verir, ancak yanıltıcı olabilir. Daha fazla bilgi için Maven belgelerindeki Apache Maven Bağımlılık Ağacı'na bakın. Sürüm çakışması olduğundan şüphelendiğiniz her kitaplık için sürüm numarasını not edin ve hangi bileşenlerin buna bağlı olduğunu belirleyin.

Geliştirme ve üretim ortamlarında bağımlılık çözümü farklı çalışabilir. Apache Spark, Apache Flink, Databricks ve IDE eklentilerinin özel bağımlılıklar için ek yapılandırmaya ihtiyacı vardır. Ayrıca kendi Azure İstemci kitaplıklarını veya ortak bileşenlerini de getirebilirler. Daha fazla bilgi için aşağıdaki makaleleri inceleyin:

Bu tür ortamlarda çakışma çözümü hakkında daha fazla bilgi için bu makalenin devamında Yer alan Fat JAR oluşturma bölümüne bakın.

Azure İşlevleri yapılandırma

Azure İşlevleri'da iç bağımlılık sürümü (yalnızca Java 8 çalıştıran) kullanıcı tarafından sağlanan sürümden önceliklidir. Bu bağımlılık özellikle Jackson, Netty ve Reactor ile sürüm çakışmalarını neden olur.

Bu sorunu çözmek için ortam değişkenini FUNCTIONS_WORKER_JAVA_LOAD_APP_LIBS veya 1olarak true ayarlayın. Azure İşlev Araçları'nı (v2 veya v3) en son sürüme güncelleştirin.

Not

Bu yapılandırma yalnızca Java 8 çalıştıran Azure İşlevleri için geçerlidir. Java 11 çalıştıran işlevler için özel yapılandırma gerekmez.

Apache Spark'ı yapılandırma

Java için Azure SDK, Jackson'ın birden çok sürümünü destekler, ancak bazen derleme araçlarınıza ve bağımlılık çözümleme sıralamanıza bağlı olarak sorunlar ortaya çıkabilir. Bu sorunun iyi bir örneği, Jackson 2.10'a bağlı olan Apache Spark, sürüm 3.0.0 ve üzeridir. Java için Azure SDK ile uyumlu olsa da geliştiriciler genellikle jackson'ın daha yeni bir sürümünün kullanıldığını keşfeder ve bu da uyumsuzluklara neden olur. Bu sorunu azaltmak için Jackson'ın (Spark ile uyumlu olan) belirli bir sürümünü sabitlemeniz gerekir. Daha fazla bilgi için bu makaledeki Birden çok Jackson sürümü için destek bölümüne bakın.

Spark'ın önceki sürümlerini kullanıyorsanız veya kullandığınız başka bir kitaplık, Java için Azure SDK'sının desteklemediği daha da eski bir Jackson sürümünü gerektiriyorsa, olası risk azaltma adımları için bu makaleyi okumaya devam edin.

Jackson çalışma zamanı sürümünü algılama

Azure Core 1.21.0'da jackson çalışma zamanı sürümünün çalışma zamanı algılamasını ve daha iyi tanılamasını ekledik.

Jackson API'siyle ilgili (veya alt sınıflarından herhangi birini) görüyorsanız LinkageError , çalışma zamanı sürüm bilgileri için özel durum iletisini denetleyin. Örneğin: com.azure.core.implementation.jackson.JacksonVersionMismatchError: com/fasterxml/jackson/databind/cfg/MapperBuilder Package versions: jackson-annotations=2.9.0, jackson-core=2.9.0, jackson-databind=2.9.0, jackson-dataformat-xml=2.9.0, jackson-datatype-jsr310=2.9.0, azure-core=1.19.0-beta.2

uyarı ve hata günlüklerini arayın JacksonVersion. Daha fazla bilgi için bkz . Java için Azure SDK'da günlüğe kaydetmeyi yapılandırma. Örneğin: [main] ERROR com.azure.core.implementation.jackson.JacksonVersion - Version '2.9.0' of package 'jackson-core' is not supported (too old), please upgrade.

Not

Tüm Jackson paketlerinin aynı sürüme sahip olup olmadığını kontrol edin.

Azure SDK tarafından kullanılan paketlerin listesi ve desteklenen Jackson sürümleri için Birden çok Jackson sürümü için destek bölümüne bakın.

Sürüm uyuşmazlığı sorunlarını azaltma

Aşağıdaki bölümlerde sürüm uyuşmazlığı sorunlarının nasıl azaltıldığı açıklanmaktadır.

Azure SDK BOM kullanma

En son kararlı Azure SDK BOM'unu kullanın ve POM dosyanızda Azure SDK ve bağımlılık sürümlerini belirtmeyin. Uygun olduğunda Azure Spring Boot BOM'u kullanın.

Azure SDK ürün reçetesinde listelenen bağımlılıklar, bağımlılık çakışmalarını önlemek için sıkı bir şekilde test edilir.

Gereksiz bağımlılıklardan kaçının

Yapabilirseniz bağımlılıkları kaldırın. Bazen, bir uygulamanın temelde aynı işlevselliği sağlayan birden çok kitaplıkta bağımlılıkları vardır. Bu tür gereksiz bağımlılıklar uygulamaları güvenlik açıklarına, sürüm çakışmalarına ve destek ve bakım maliyetlerine maruz bırakır.

Bağımlılık sürümlerini güncelleştirme

En son Azure SDK ürün reçetesine geçmek işe yaramazsa çakışmalara neden olan kitaplıkları ve bunları kullanan bileşenleri belirleyin. (Daha fazla bilgi için bkz. Bu makalenin önceki bölümlerinden bir bağımlılık ağacı bölümünü görüntüleyin.) Güvenlik açıklarına karşı koruma sağlayan ve genellikle yeni özellikler, performans iyileştirmeleri ve hata düzeltmeleri getiren daha yeni bir sürüme güncelleştirmeyi deneyin.

Uygulamanızı bilinen güvenlik açıklarına ve sorunlara maruz bırakabileceğinden Azure SDK sürümünü düşürmekten kaçının.

Kitaplıkları gölgelendirme

Bazen birlikte çalışan kitaplıkların birleşimi yoktur ve gölgelendirme son çare olarak gelir.

Not

Gölgelendirmenin önemli dezavantajları vardır: sınıf yolundaki paket boyutunu ve sınıf sayısını artırır, kod gezintisini ve hata ayıklamayı zorlaştırır, JNI kodunun yerini değiştirmez, yansımayı keser ve diğer şeylerin arasında kod lisanslarını ihlal edebilir. Yalnızca diğer seçenekler tükendikten sonra kullanılmalıdır.

Gölgelendirme, derleme zamanında JAR'a bağımlılıklar eklemenize, ardından paketleri yeniden adlandırmanıza ve uygulama kodunu gölgeli konumdaki kodu kullanacak şekilde güncelleştirmenize olanak tanır. Bir bağımlılığın iki farklı kopyası olduğundan baklava bağımlılık çakışması artık sorun oluşturmaz. Aşağıdaki listede açıklandığı gibi, çakışan geçişli bağımlılığı veya doğrudan uygulama bağımlılığı olan bir kitaplığı gölgelendirmeniz gerekebilir:

  • Geçişli bağımlılık çakışması: Örneğin, üçüncü taraf kitaplığı A için Azure SDK'larının desteklemediği Jackson 2.9 gerekir ve güncelleştirilemez A. Jackson 2.9 ve isteğe bağlı olarak diğer bağımlılıklarını Aiçeren A ve gölgelendiren (yeniden yer alan) yeni bir modül oluşturun.
  • Uygulama bağımlılığı çakışması: Uygulamanız doğrudan Jackson 2.9 kullanıyor. Kodunuzu güncelleştirmeye çalışırken Jackson 2.9'u yeniden konumlandırılmış Jackson sınıflarıyla yeni bir modülde gölgeleyebilir ve yeniden konumlandırabilirsiniz.

Not

Yeniden konumlandırılmış Jackson sınıfları ile yağ JAR'i oluşturmak bu örneklerde bir sürüm çakışması çözmez- yalnızca Jackson'ın tek bir gölgeli sürümünü zorlar.

Yağ JAR'i oluşturma

Databricks veya Apache Spark gibi ortamlar özel bağımlılık yönetimine sahiptir ve Jackson gibi ortak kitaplıklar sağlar. Sağlanan kitaplıklarla çakışmayı önlemek için tüm bağımlılıkları içeren bir fat JAR oluşturmak isteyebilirsiniz. Daha fazla bilgi için bkz . Apache Maven Shade Eklentisi. Çoğu durumda Jackson sınıflarını (com.fasterxml.jackson) yeniden konumlandırmak sorunu azaltır. Bazen bu tür ortamlar kendi Azure SDK'larını da getirir, bu nedenle ad alanını sürüm çakışmalarına geçici bir çözüm olarak yeniden taşımak com.azure zorunda olabilirsiniz.

Uyumlu bağımlılık sürümlerini anlama

Özel bağımlılıklar ve sürümleri hakkında azure-corebilgi için Maven Central Repository'de azure-core bölümüne bakın. Aşağıdaki tabloda bazı genel noktalar gösterilmektedir:

Dependency Desteklenen sürümler
Jackson 2.10.0 ve daha yeni ikincil sürümler uyumludur. Daha fazla bilgi için Birden çok Jackson sürümü için destek bölümüne bakın.
SLF4J 1.7.*
netty-tcnative-boringssl-static 2.0.*
netty-common 4.1.*
reaktör çekirdeği 3.X.* - Ana ve ikincil sürüm numaraları, sürümünüzün azure-core bağımlı olduğu numaralarla tam olarak eşleşmelidir. Daha fazla bilgi için bkz. Kullanımdan kaldırmalarla ilgili Project Reactor ilkesi.

Birden çok Jackson sürümü desteği

Java için Azure SDK, çeşitli Jackson sürümleriyle çalışmayı destekler. Desteklenen en düşük sürüm Jackson 2.10.0 sürümüdür. Java için Azure SDK istemci kitaplıkları, çalışma zamanında algılanan sürüme bağlı olarak yapılandırmalarını ve Jackson kullanımını ayarlar. Bu ayar Spring çerçevesinin, Apache Spark'ın ve diğer yaygın ortamların eski sürümleriyle daha fazla uyumluluk sağlar. Uygulamalar, Java istemci kitaplıkları için Azure SDK'sını bozmadan Jackson sürümlerini (2.10.0 veya üzeri) düşürebilir.

Not

Jackson'ın eski sürümlerini kullanmak uygulamaları bilinen güvenlik açıklarına ve sorunlara maruz bırakabilir. Daha fazla bilgi için Jackson kitaplıkları için bilinen güvenlik açıklarının listesine bakın.

Jackson'ın belirli bir sürümünü sabitlerken, aşağıdaki listede gösterilen Azure SDK tarafından kullanılan tüm modüller için bunu yaptığınızdan emin olun:

  • jackson-annotations
  • jackson-core
  • jackson-databind
  • jackson-dataformat-xml
  • jackson-datatype-jsr310

Jackson'dan azure-json'a geçiş

Java için Azure istemci kitaplıkları, üçüncü taraf bileşenlerine bağımlı olmayan ve JSON için paylaşılan temel öğeler, soyutlamalar ve yardımcılar sunan azure-json'a geçiş sürecindedir.

Apache Spark, Apache Flink ve Databricks gibi ortamlar, henüz bağımlı azure-jsonolmayan eski sürümlerini azure-core getirebilir. Sonuç olarak, bu tür ortamlarda Azure kitaplıklarının daha yeni sürümlerini kullanırken gibi java.lang.NoClassDefFoundError: com/azure/json/JsonSerializablehatalar alabilirsiniz. üzerinde azure-jsonaçık bir bağımlılık ekleyerek bu hatayı azaltabilirsiniz.

Sonraki adımlar

Artık bağımlılık sürümü çakışmalarını ve bunların sorunlarını gidermeyi bildiğinize göre, bunları önlemenin en iyi yolu hakkında bilgi için bkz . Java için Bağımlılık Yönetimi.