2015-12-26 2 views
1

Я хочу добавить функции в свое приложение для Android. Однако я страдал «java.lang.ClassNotFoundException». Какие вещи мне не хватает?Загрузка динамического класса в Android

  1. Простой класс (только .class файл)
  2. Layout и ресурсы
  3. Деятельность

Прежде всего я хочу сделать 1. Но есть так много способов реализации, Я путаюсь, как это реализовать.

Допущение:

1.File загружается в локальное хранилище данных.

2.targetClassName - com.example.mari.myandroid.TestDinamicLoad.

3.SDK & Строительные инструменты версия, (без ProGuard) compileSdkVersion 22 buildToolsVersion "21.1.2"

Pattern A: Использование URLClassLoader

Compile: Gradle компиляцию и это просто сырец файл класса

URL: https://drive.google.com/file/d/0B0Hrot21k8nYZ2pWNXBBMU5Qd2M/view?usp=sharing

private void urlLoader(final File file){ 
     try { 
      URL myurl[] = {new URL("file:" + file.toString())}; 
      URLClassLoader x = new URLClassLoader(myurl); 
      Class c = x.loadClass(this.targetClassName); 
      for (Field f : c.getDeclaredFields()) { 
       Log.v(TAG, f.getName() + " : " + f.toString()); 
      } 
     }catch(Exception e){ 
      Log.v(TAG, e.toString()); 
     } 
    } 

шаблон Б: Используя dexLoader

Вкомпилировать:

javac -classpath /Applications/adt-bundle-mac/sdk/platforms/android-22/android.jar TestDinamicLoad.java 
    dx --dex --output TestDinamicLoad.jar TestDinamicLoad.java 

URL: https://drive.google.com/file/d/0B0Hrot21k8nYdG9wdHhiOWJIVE0/view?usp=sharing

private void dexLoader(final File file){ 
    try { 
     Context ctx  = getApplicationContext(); 
     String   dex_dir = ctx.getDir("dex", 0).getAbsolutePath(); 
     ClassLoader parent = getClass().getClassLoader(); 
     DexClassLoader loader = new DexClassLoader(file.getPath(), dex_dir, null, parent); 
     Class   c  = loader.loadClass(this.targetClassName); 
     Object   o  = c.newInstance(); 
     Method m  = c.getMethod("func"); 

     m.invoke(o); 
    } catch (Exception e) { 
     Log.v(TAG, e.toString()); 
    } 

} 

Ошибки:

12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani: urlLoader------ 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani: java.lang.ClassNotFoundException: com.example.mari.myandroid.TestDinamicLoad 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.net.URLClassLoader.findClass(URLClassLoader.java:753) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:511) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:469) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.MainActivity.urlLoader(MainActivity.java:109) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.MainActivity.access$200(MainActivity.java:23) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.MainActivity$1.postExecute(MainActivity.java:69) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.AsyncFileDownload.doInBackground(AsyncFileDownload.java:78) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.AsyncFileDownload.doInBackground(AsyncFileDownload.java:19) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at android.os.AsyncTask$2.call(AsyncTask.java:288) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.util.concurrent.FutureTask.run(FutureTask.java:237) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.Thread.run(Thread.java:818) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani: Suppressed: java.lang.ClassNotFoundException: Didn't find class "com.example.mari.myandroid.TestDinamicLoad" on path: DexPathList[[directory "."],nativeLibraryDirectories=[/vendor/lib, /system/lib]] 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.BaseDexClassLoader.findClass(BaseDexClassLoader.java:56) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:511) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:504) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:   ... 12 more 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  Suppressed: java.lang.ClassNotFoundException: com.example.mari.myandroid.TestDinamicLoad 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.Class.classForName(Native Method) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.BootClassLoader.findClass(ClassLoader.java:781) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.BootClassLoader.loadClass(ClassLoader.java:841) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:504) 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani:    ... 13 more 
    12-26 23:20:34.817 19078-19264/com.example.mari.myandorid2 V/murotani: Caused by: java.lang.NoClassDefFoundError: Class not found using the boot class loader; no stack available 


    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani: dexLoader------ 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani: java.lang.ClassNotFoundException: Didn't find class "com.example.mari.myandroid.TestDinamicLoad" on path: DexPathList[[zip file "/data/data/com.example.mari.myandorid2/files/TestDinamicLoad.class"],nativeLibraryDirectories=[/vendor/lib, /system/lib]] 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.BaseDexClassLoader.findClass(BaseDexClassLoader.java:56) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:511) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:469) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.MainActivity.dexLoader(MainActivity.java:91) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.MainActivity.access$300(MainActivity.java:23) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.MainActivity$1.postExecute(MainActivity.java:70) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.AsyncFileDownload.doInBackground(AsyncFileDownload.java:78) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.AsyncFileDownload.doInBackground(AsyncFileDownload.java:19) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at android.os.AsyncTask$2.call(AsyncTask.java:288) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.util.concurrent.FutureTask.run(FutureTask.java:237) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.Thread.run(Thread.java:818) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani: Suppressed: java.io.IOException: Expected valid zip or dex file: '/data/data/com.example.mari.myandorid2/files/TestDinamicLoad.class' 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.DexFile.openDexFileNative(Native Method) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.DexFile.openDexFile(DexFile.java:295) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.DexFile.<init>(DexFile.java:111) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.DexFile.loadDex(DexFile.java:151) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.DexPathList.loadDexFile(DexPathList.java:265) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.DexPathList.makeDexElements(DexPathList.java:231) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.DexPathList.<init>(DexPathList.java:109) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.BaseDexClassLoader.<init>(BaseDexClassLoader.java:48) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.DexClassLoader.<init>(DexClassLoader.java:57) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at com.example.mari.myandorid2.MainActivity.dexLoader(MainActivity.java:90) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:   ... 10 more 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani: Suppressed: java.lang.ClassNotFoundException: Didn't find class "com.example.mari.myandroid.TestDinamicLoad" on path: DexPathList[[zip file "/data/app/com.example.mari.myandorid2-2/base.apk"],nativeLibraryDirectories=[/vendor/lib, /system/lib]] 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at dalvik.system.BaseDexClassLoader.findClass(BaseDexClassLoader.java:56) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:511) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:504) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:   ... 12 more 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  Suppressed: java.lang.ClassNotFoundException: com.example.mari.myandroid.TestDinamicLoad 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.Class.classForName(Native Method) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.BootClassLoader.findClass(ClassLoader.java:781) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.BootClassLoader.loadClass(ClassLoader.java:841) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:  at java.lang.ClassLoader.loadClass(ClassLoader.java:504) 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani:    ... 13 more 
    12-26 23:20:34.837 19078-19264/com.example.mari.myandorid2 V/murotani: Caused by: java.lang.NoClassDefFoundError: Class not found using the boot class loader; no stack available 

Refered: ClassNotFoundException during Dynamic Class loading in android http://tech.co/android-security-2014-07 http://larshamren.blogspot.jp/2012/02/android-dynamically-loading-classes.html

+1

Динамически загружать задание? Я не считаю, что это возможно. –

+1

Для точки номер 1, пожалуйста, отправьте полную трассировку стека исключения, а также сообщите, соответствует ли это шаблону A или B.Что касается номера 2, вы можете легко добавить все XML-файлы и ресурсы, которые хотите, но сделайте это до начала процесса сборки, потому что в APK XML-ресурсы находятся в двоичном формате. Точка № 3 невозможна без трюка: когда приложение установлено, все действия, объявленные в манифесте, «зарегистрированы». Итак, если вы загружаете во время выполнения Activity, которая не присутствовала в манифесте во время установки, вы получите исключение. – fasteque

+1

см. [Динамическая структура нагрузки для android] (https://github.com/singwhatiwanna/dynamic-load-apk/blob/master/README-en.md) – pskink

ответ

0

Я думаю, что вы хотите, чтобы динамическому загрузить APK:

  1. Динамические классы нагрузки
  2. Динамические нагрузки андроид ресурсы
  3. Динамические деятельности регистра

Это теперь можно на [email protected], вы можете попробовать и развлечься.

Смежные вопросы