2014-06-19 11 views
5

İki kitaplık modülüyle bir ana proje oluştururken, aynı libc++_shared.so paylaşılan kitaplığından yararlanan bir "yinelenen dosyalar" çakışması alıyorum.Çoklu Proje Android Yapılandırmasında Çoğaltılmış C Paylaşılan Kitaplıklarını (.so) Nasıl Harcalıyorsunuz?

(NOT:.. Bu bir "yinelenen soru" düşünmüyoruz Lütfen ben bu kadar Ancak, hiçbir mesaj karıştığı benim durumumda çalışan bir cevap vermiş bana bulmada yardımcı oluyorlar birkaç ilgili mesajları, okudum NDK eserler.)

Yapı, bu tür bir kitaplık modülüne sahip olduğumda doğru bir şekilde çalışıyordu. İkinci kütüphane modülünün eklenmesi şimdi çatışmayı yaratıyor.

aşağıdaki proje yapısını düşünün: 1 ana proje, 2 "çocuk" projesi - ama her proje

ProjectA/ (Parent) 
    LibraryModuleA1/ 
     build/exploded-aar/com.package.name/ 
      LibraryModuleB1/<version>/jni/armeabi-v7a/libc++_shared.so 
      LibraryModuleC1/<version>/jni/armeabi-v7a/libc++_shared.so 
     build.gradle (bgA1) 
    Test_APK_Module A1T/ 
     build.gradle (bgA1T) 
    build.gradle (bgPA) 

ProjectB/ 
    LibraryModuleB1/ (Uses NDK) 
     build/lib/armeabi-v7a/libc++_shared.so 
     build.gradle (bgB1) 
    build.gradle (bgPB) 

ProjectC/ 
    LibraryModuleC1/ (Uses NDK) 
     build/lib/armeabi-v7a/libc++_shared.so 
     build.gradle (bgC1) 
    build.gradle (bgPC) 

Kütüphane Modül A1 hem Library bağlıdır (yani hiyerarşik yuvalanmış değil) aynı dizin düzeyinde bulunduğu Modüller B1 & C1.
A1 -> B1
A1 -> C1

Projeler B ve C, her iki NDK tabanlı kodu ve doğru bir şekilde/test oluşturmak. Her ikisi de libc++_shared.so paylaşılan kütüphaneye bağlıdır.

Proje A inşa Ancak, ben :LibraryModuleA1:packageDebugTest görev sırasında aşağıdaki hatayı olsun :

Error: duplicate files during packaging of APK /ProjectA/LibraryModuleA1/build/apk/LibraryModuleA1-debug-test-unaligned.apk 
    Path in archive: lib/armeabi-v7a/libc++_shared.so 
    Origin 1: /ProjectA/LibraryModuleA1/build/exploded-aar/com.package.name/LibraryModuleB1/<version>/jni/armeabi-v7a/libc++_shared.so 
    Origin 2: /ProjectA/LibraryModuleA1/build/exploded-aar/com.package.name/LibraryModuleC1/<version>/jni/armeabi-v7a/libc++_shared.so 
You can ignore those files in your build.gradle: 
    android { 
     packagingOptions { 
     exclude 'lib/armeabi-v7a/libc++_shared.so' 
     } 
    } 

* What went wrong: 
Execution failed for task ':LibraryModuleA1:packageDebugTest'. 
> Duplicate files copied in APK lib/armeabi-v7a/libc++_shared.so 
    File 1: /ProjectA/LibraryModuleA1/build/exploded-aar/com.package.name/LibraryModuleC1/<version>/jni/armeabi-v7a/libc++_shared.so 
    File 2: /ProjectA/LibraryModuleA1/build/exploded-aar/com.package.name/LibraryModuleC1/<version>/jni/armeabi-v7a/libc++_shared.so 

:LibraryModuleA1:packageDebugTest FAILED 

Ben Far

  1. ben önerdi ekleme girişiminde Yani çalıştı ettik ne build.gradle dosyama kapatma, ancak hangi build.gradle dosyasını ekleyebilirim? Kapatma işlemini hiçbir başarı olmadan bgA1, bgB1 ve bgC1 (birer birer) ekledim.
  2. Önerilen kapatma, exclude 'lib/armeabi-v7a/libc++_shared.so''u kullanmayı bildiriyor. Her "alt" kitaplık modülü, libc++_shared.so dosyasını build/lib yolunun altına kurar. Ancak, ana kütüphane modülünün libc++_shared.so dosyasını build/exploded-aar dizin yapısının içinde jni/armeabi-v7a/libc++_shared.so altında kopyalar olduğunu fark ettim. (Yukarı bakın) Kapatma yerine exclude 'jni/armeabi-v7a/libc++_shared.so (yani jni vs lib) okunuyor mu?
  3. Gradle eklentisi 0.9.1 kullandığım için, 'u exclude yerine kullanmayı denedim, ancak bu da başarılı olmadı.

Birisi, benim verilen vaka için `packagingOptions 'kapanışını nasıl yapılandırmam gerektiğini belirleyebilir mi?

Yardımlarınız için teşekkür ederiz!

cevap

1

Aynı soruna rastladım ve hariç tut veya pickFirst ile hiç şansım olmadı. Bu yüzden biraz çirkin bir çözüm kullandım. Buradaki fikir, ana projenin derleme dizininde bir 'native-libs' klasörü oluşturmak, gerekli tüm * .so dosyalarını ndk kütüphane projelerinden kopyalamak ve daha sonra inşa sistemini bu lib'leri apk'de paketlemek için anlatmaktır.benim ana proje (app projesi), ben explicitely ben

// Ndk stuff. We have to explicitely manage our NDK dependencies 
ext.jniProjects = [project(':ndklib1'), project(':ndklib2'), project(':ndklib3')] 
apply from: '../depend_ndk.gradle' 

Ve sonra, 'depend_ndk.gradle' bağımlı olduğu ndk kodları içeriyor modüllerin listesini tanımlamak ise

bir gradle dış komut olduğundan

// Build helper for projects that depends on a native library with a NDK part 
// Define the list of ndk library you depend on in project main file : 
// ext.jniProjects = [project(':ndklib1')] 
// apply from : 'depend_ndk.gradle' 
buildscript { 
    repositories { 
     jcenter() 
     mavenCentral() 
    } 
    dependencies { 
     classpath 'com.android.tools.build:gradle:0.12.+' 
    } 
} 
import com.android.build.gradle.tasks.PackageApplication 

// As a workaround, we create a new 'native-libs' folder in the current project and 
// copy all the .so we depend on into it 
def ndkLibsDir = new File(buildDir, 'native-libs') 
ndkLibsDir.mkdir() 

task copyDependingNativeLibs(type: Copy) { 
    // Doc for copy http://www.gradle.org/docs/current/dsl/org.gradle.api.tasks.Copy.html 
    println 'jniProjects ' + jniProjects 
    jniProjects.each { 
     from(new File(it.buildDir, 'native-libs')) { 
      include '**/*.so' 
     } 
    } 
    into ndkLibsDir 
} 

tasks.withType(PackageApplication) { pkgTask -> 
    pkgTask.jniFolders = new HashSet<File>() 
    pkgTask.jniFolders.add(ndkLibsDir) 
    pkgTask.dependsOn copyDependingNativeLibs 
} 
+0

Paket Uygulaması nasıl tetiklenir? App - Ben hata ayıklama yapıları üzerinde göremiyorum ... böylece hata ayıklama APK's dahil ... Teşekkürler. –

+0

Haklısın, copyDependingNativeLibs'in otomatik olarak çalışması için sıkıntı yaşıyorum. PkgTask için bağımlılık olarak eklemenin doğru bir şey olmadığını düşünüyorum. Gerçekten bir çözüm bulmaya zamanım olmadı, bu yüzden şimdilik bazı yerel parçaları değiştirdiğimde './gradlew app: copyDependingNativeLibs' komutunu çalıştırıyorum. – Julien

İlgili konular