Reputation:
I'm getting a NoClassDefFoundError with my app. I'm using dnsjava, okhttp3 and retrofit. My min API is 19.
I read that the java.time package was added in API 26. Does this mean that I can't use dnsjava for Android API lower than 26? Or does something else cause this error (proguard for example)? Can using an older dnsjava version help? I couldn't find any information about the minimum API of dnsjava.
Edit: I found this on the dnsjava Github page.
Migrating from version 2.1.x to v3
Methods using java.util.Date are deprecated. Use the new versions with java.time.Instant or java.time.Duration instead
So does this mean I can use version 2.1.x?
FATAL EXCEPTION: OkHttp Dispatcher
Process: de.url.myproject, PID: 10723
java.lang.NoClassDefFoundError: Failed resolution of: Ljava/time/Duration;
at org.xbill.DNS.ExtendedResolver.<clinit>(ExtendedResolver.java)
at org.xbill.DNS.Lookup.refreshDefault(Lookup.java:1)
at org.xbill.DNS.Lookup.<clinit>(Lookup.java:1)
at org.xbill.DNS.Lookup.getDefaultResolver(Lookup.java)
at de.url.myproject.MyDNS.init(MyDNS.java)
at de.url.myproject.MyDNS.lookup(MyDNS.java)
at okhttp3.internal.connection.RouteSelector.resetNextInetSocketAddress(RouteSelector.java:19)
at okhttp3.internal.connection.RouteSelector.nextProxy(RouteSelector.java:19)
at okhttp3.internal.connection.RouteSelector.next(RouteSelector.java:19)
at okhttp3.internal.connection.StreamAllocation.findConnection(StreamAllocation.java:19)
at okhttp3.internal.connection.StreamAllocation.e(StreamAllocation.java)
at okhttp3.internal.connection.StreamAllocation.newStream(StreamAllocation.java:10)
at okhttp3.internal.connection.ConnectInterceptor.intercept(ConnectInterceptor.java:10)
at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:2)
at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:103)
at okhttp3.internal.cache.CacheInterceptor.intercept(CacheInterceptor.java:103)
at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:2)
at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:27)
at okhttp3.internal.http.BridgeInterceptor.intercept(BridgeInterceptor.java:27)
at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:2)
at okhttp3.internal.http.RetryAndFollowUpInterceptor.intercept(RetryAndFollowUpInterceptor.java:7)
at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:2)
at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java)
at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.java:12)
at okhttp3.RealCall$AsyncCall.a(RealCall.java)
at okhttp3.internal.NamedRunnable.run(NamedRunnable.java)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607)
at java.lang.Thread.run(Thread.java:776)
Caused by: java.lang.ClassNotFoundException: Didn't find class "java.time.Duration" on path: DexPathList[[zip file "/system/framework/android.test.runner.jar", zip file "/data/app/androidx.test.tools.crawler-1/base.apk", zip file "/data/app/de.url.myproject-1/base.apk", zip file "/data/app/de.url.myproject-1/split_config.xxhdpi.apk"],nativeLibraryDirectories=[/data/app/androidx.test.tools.crawler-1/lib/arm64, /data/app/de.url.myproject-1/lib/arm64, /system/lib64, /vendor/lib64, /system/vendor/lib64, /product/lib64]]
at dalvik.system.BaseDexClassLoader.findClass(BaseDexClassLoader.java:56)
at java.lang.ClassLoader.loadClass(ClassLoader.java:380)
at java.lang.ClassLoader.loadClass(ClassLoader.java:312)
... 22 more
Suppressed: java.io.IOException: No original dex files found for dex location /data/app/de.url.myproject-1/split_config.xxhdpi.apk
at dalvik.system.DexFile.openDexFileNative(DexFile.java)
at dalvik.system.DexFile.openDexFile(DexFile.java:373)
at dalvik.system.DexFile.<init>(DexFile.java:113)
at dalvik.system.DexFile.<init>(DexFile.java:78)
at dalvik.system.DexPathList.loadDexFile(DexPathList.java:359)
at dalvik.system.DexPathList.makeElements(DexPathList.java:323)
at dalvik.system.DexPathList.makeDexElements(DexPathList.java:263)
at dalvik.system.DexPathList.<init>(DexPathList.java:126)
at dalvik.system.BaseDexClassLoader.<init>(BaseDexClassLoader.java:48)
at dalvik.system.PathClassLoader.<init>(PathClassLoader.java:64)
at com.android.internal.os.PathClassLoaderFactory.createClassLoader(PathClassLoaderFactory.java:43)
at android.app.ApplicationLoaders.getClassLoader(ApplicationLoaders.java:58)
at android.app.LoadedApk.createOrUpdateClassLoaderLocked(LoadedApk.java:540)
at android.app.LoadedApk.getClassLoader(LoadedApk.java:573)
at android.app.ActivityThread.getTopLevelResources(ActivityThread.java:1990)
at android.app.LoadedApk.getResources(LoadedApk.java:799)
at android.app.ContextImpl.<init>(ContextImpl.java:2217)
at android.app.ContextImpl.createAppContext(ContextImpl.java:2162)
at android.app.ActivityThread.handleBindApplication(ActivityThread.java:5547)
at android.app.ActivityThread.-wrap2(ActivityThread.java)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1637)
at android.os.Handler.dispatchMessage(Handler.java:105)
at android.os.Looper.loop(Looper.java:156)
at android.app.ActivityThread.main(ActivityThread.java:6524)
at java.lang.reflect.Method.invoke(Method.java)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:941)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:831)
My code:
package de.url.myproject;
import android.util.Log;
import androidx.annotation.NonNull;
import org.xbill.DNS.Address;
import org.xbill.DNS.ExtendedResolver;
import org.xbill.DNS.Lookup;
import org.xbill.DNS.Resolver;
import org.xbill.DNS.SimpleResolver;
import java.net.InetAddress;
import java.net.UnknownHostException;
import java.util.Collections;
import java.util.List;
import okhttp3.Dns;
public class MyDNS implements Dns {
private static final String LIVE_API_HOST = "api.myproject.de";
private static final String LIVE_API_IP = "12.345.67.890";
private boolean mInitialized;
private InetAddress mLiveApiStaticIpAddress;
@NonNull
@Override
public List<InetAddress> lookup(@NonNull String hostname) throws UnknownHostException {
// I'm initializing the DNS resolvers here to take advantage of this method being called in a background-thread managed by OkHttp
init();
try {
return Collections.singletonList(Address.getByName(hostname));
} catch (UnknownHostException e) {
// fallback to the API's static IP
if (LIVE_API_HOST.equals(hostname) && mLiveApiStaticIpAddress != null) {
return Collections.singletonList(mLiveApiStaticIpAddress);
} else {
throw e;
}
}
}
private void init() {
if (mInitialized) return; else mInitialized = true;
try {
mLiveApiStaticIpAddress = InetAddress.getByName(LIVE_API_IP);
} catch (UnknownHostException e) {
Log.w("DNS", "Couldn't initialize static IP address");
}
try {
// configure the resolvers, starting with the default ones (based on the current network connection)
Resolver defaultResolver = Lookup.getDefaultResolver();
// use Google's public DNS services
Resolver googleFirstResolver = new SimpleResolver("8.8.8.8");
Resolver googleSecondResolver = new SimpleResolver("8.8.4.4");
// also try using Amazon
Resolver amazonResolver = new SimpleResolver("205.251.198.30");
Lookup.setDefaultResolver(new ExtendedResolver(new Resolver[]{
defaultResolver, googleFirstResolver, googleSecondResolver, amazonResolver}));
} catch (UnknownHostException e) {
Log.w("DNS", "Couldn't initialize custom resolvers");
}
}
}
Upvotes: 2
Views: 2203
Reputation: 1
I met the same problem and solved it by adding try ... catch
. If you want to keep the function going, you can switch to another downloading method when Android is under 1.8.
try {
if (client == null) {
notifyFail("System does not support")
} else {
val result = client?.startStreamTranscription(getRequest(22000), AudioStreamPublisher(FileInputStream(File(fileName))), getResponseHandler())
if (NetworkUtils.isAvailable(BaseApp.context)) {
result?.get()
client?.close()
}
}
} catch (e: Exception) {
logee { "startTrans ${e.message}" }
}
Another way is that you can copy the whole time package into local:
Upvotes: 0
Reputation: 1
I had the same trouble yet,not i use the "minidns" to replaced,It's friendly to android.
implementation 'de.measite.minidns:minidns:0.1.7'
Upvotes: 0