# Debugging and troubleshooting In this section you can find effective debugging and troubleshooting techniques, common issues, and instructions how to generate insightful logs. ## Common issues When you run into trouble, be sure to check first the [minimum requirements](introduction-requirements.md#supported-versions), [supported devices](introduction-requirements.md#supported-devices), and the list of known issues in the [changelog](https://www.here.com/docs/category/sdk-changelog). * **I see only a blank white map:** Make sure that your HERE credentials are valid and set as described in the [Get started](get-started.md) topic. Also, make sure that your device is able to make an internet connection. With slower internet connections, it may take a while until you see the first map tiles loaded. Please also make sure that your device time is set correctly. In rare cases, a wrongly set device time can lead to authentication issues with some backend services. * **In the logs I see "No map content will be displayed until valid config is provided.":** Make sure that your code is really calling `loadScene()`. * **The app crashes and in the logs I see "CL\_magma - Couldn't load the default shader.":** Your device must support OpenGL ES 3.0. If you are running a simulator, edit your emulator settings via **Settings** -> **Advanced** -> **OpenGL ES API level**. If it is set to **Autoselect**, try to change it to **Renderer Maximum**. This happens mostly on Windows machines. * **I am unable to resolve dependency for ':app\@debug/compileClasspath': Could not find :heresdk-YOUR\_SDK\_VERSION:** Make sure that your HERE SDK AAR matches the name in your application's build gradle file. Note: This is only needed, if you reference the version explicitly. If you follow the steps above, you don't have to do that as we use `*.aar` as wildcard to match any version. * **I get the error "License for package Android SDK Platform not accepted." or similar:** Make sure you have accepted all Android licenses, for example by installing the required tools and clicking the license button or by calling `cd /d "%ANDROID_SDK_ROOT%/tools/bin"` and `sdkmanager --licenses` from your terminal. * **I am seeing the following in a crash log: "Exception was thrown in Java and it was not handled.":** The HERE SDK cannot handle runtime exceptions that are thrown on app side inside a callback. In such a case you will see this error log. It means that your code throws an exception in one of the HERE SDK callbacks that are handled by your application. * **I am getting a crash due to a cache lock:** If an application crashes due to a `Storage.LevelDB` error or a `FAILED_TO_LOCK_CACHE_FOLDER` error, follow [this instruction](tips-troubleshooting.md#how-to-destroy-a-locking-process) to prevent such a crash from happening again. * **I see no map and/or my HERE SDK calls do nothing:** If you see the following log message "These credentials do not authorize access" then your credentials are not valid. Make sure you use a working set of credentials. Credentials from the 3.x versions are not compatible. Credentials from Explore are not compatible with Navigate. * **I see graphical glitches on the map view:** For some Android versions this may happen and it can be fixed by using the `MapRenderMode.texture`. Find more details in the [maps](maps.md) guide. * **I see a blank map after reopening an app on Android Emulator:** This is a known issue with Android Emulator 34.2.14 and 34.2.13. Please use Android Emulator 34.1.20 or earlier from the stable channel until Google fixes the [issue](https://issuetracker.google.com/issues/345674553). Sometimes, this issue may also appear with Android emulators using an image with API Level 28. * Android Studio does not compile my app and I get this build error **Your project's Gradle version is incompatible with the Java version for Gradle.** Such an error can happen when you are switching to a newer Android Studio version. Either build a new app from scratch following the [Get started](integrate-here-sdk.md) guide, or update Gradle via `gradle-wrapper-properties` by setting a newer `distributionURL` and update AGP via `classpath` in the `dependencies` closure of the project's `build.gradle` file. Make sure that the [AGP plugin and Gradle versions](https://developer.android.com/build/releases/gradle-plugin) do match. * **How should offline maps be handled to avoid large updates and storage spikes?** When using the Navigate license, you can query installed `Regions` with the `MapDownloader` to monitor downloaded regions, estimate update sizes, and avoid unnecessary downloads. Try to compare existing region sizes before triggering updates. If you want more control, avoid automatic updates. You can find more information [here](offline-maps-installation.md). ## How to destroy a locking process In rare cases an application using the HERE SDK may crash due to a `Storage.LevelDB` error or the initialization of the HERE SDK may fail with a `FAILED_TO_LOCK_CACHE_FOLDER` error. This may happen when a second instance of a `SDKNativeEngine` is created with the same `access_key_id` as an existing one. Then the local map cache directory is locked by the current process. This locked cache folder crash can be fixed by setting the following option before initializing the HERE SDK: ```java // Set your credentials for the HERE SDK. AuthenticationMode authenticationMode = AuthenticationMode.withKeySecret("YOUR_ACCESS_KEY_ID", "YOUR_ACCESS_KEY_SECRET"); SDKOptions sdkOptions = new SDKOptions(authenticationMode); // Defaults to SDKOptions.ActionOnCacheLock.WAIT_LOCKING_APP_FINISH. sdkOptions.actionOnCacheLock = SDKOptions.ActionOnCacheLock.KILL_LOCKING_APP; // Now, use these options to initialize the HERE SDK and destroy a locking process (if any). try { SDKNativeEngine.makeSharedInstance(context, sdkOptions); } catch (InstantiationErrorException e) { throw new RuntimeException("Initialization of HERE SDK failed: " + e.error.name()); } ``` If there is a cache lock, this will kill the locking process and the app can start normally. If no cache lock occurred, the code will only initialize the HERE SDK. Beside `KILL_LOCKING_APP`, also the following values can be set: * `NO_ACTION`: Nothing will be done. * `WAIT_LOCKING_APP_FINISH`: The app will wait until the locking process has ended. Note that this may happen never. This is the default behavior. Alternatively, the following snippet can be used to detect and to prevent the cache lock issue. This has the same effect as `KILL_LOCKING_APP` as `makeSharedInstance()` calls internally `destroyLockingProcess()` when this flag is set, but it provides more flexibility: ```java // Check if there is a lock on the cache. Integer processID = LockingProcess.getLockingProcessId(sdkOptions); if (processID != null) { // Warning: The cache is locked. // This may kill another process that is trying to attempt to lock the current map cache. // If this happens, the method will try to gracefully repair the cache. // If no problem was detected, the method will do nothing. long maxTimeoutInMilliseconds = 300; LockingProcess.destroyLockingProcess(sdkOptions, maxTimeoutInMilliseconds); } // Now, proceed to initialize the HERE SDK. ``` `getLockingProcessId()` provides the process ID of the locking process from the Android OS. If no lock occurred, the method will return `null`. By calling `destroyLockingProcess()` the problem will be gone. You can keep this code to solve sporadic crashes at application start. If no cache lock is detected, `destroyLockingProcess()` will do nothing. ## Specify the log level The `LogControl` class allows to log HERE SDK messages for various predefined `LogLevel` values - even for release builds of your app. Make sure to call the `LogControl` before initializing the HERE SDK: ```java // Disable any logs from HERE SDK. // Make sure to call this before initializing the HERE SDK. LogControl.disableLoggingToConsole(); ``` The above allows to silence all HERE SDK related console logs. Note that this is not recommended for debug builds, as you may miss important log messages when you want to investigate issues. A log level can be specified like so: ```java LogControl.enableLoggingToConsole(LogLevel.LOG_LEVEL_INFO); ``` When you provide a `LogLevel`, you set a minimal level of messages which will be reported, based on the below hierarchy: 1. `LOG_LEVEL_INFO` 2. `LOG_LEVEL_WARNING` 3. `LOG_LEVEL_ERROR` 4. `LOG_LEVEL_FATAL` For example, if you set `LOG_LEVEL_ERROR`, then `LOG_LEVEL_INFO` and `LOG_LEVEL_WARNING` will be excluded from the logs. All others will be logged. Setting `LOG_LEVEL_OFF` silences all logs. All log messages are prefixed with "hsdk-" to help you easily identify messages originating from the HERE SDK. You can also use the `LogAppender` interface to insert your own logging class to the `LogControl` class. This enables you to filter log messages based on different runtime conditions. For instance, you could choose to log only errors of type `LOG_LEVEL_ERROR`. By default, this selective logging isn’t possible, as only the log hierarchy determines which messages are allowed through, and you cannot adjust this minimum level after initializing the HERE SDK. By adding your own logging class, however, you gain complete control. ## Generate meaningful logs For many issues, the logs you see in your IDE's console are containing already the most relevant information. For crashes and ANRs you may want to dig deeper and take a look at the device logs. When you use `logcat`, use a timestamp to log only the most recent logs. Example: `adb logcat -t '06-30 16:30:00.820' > /Users/name/Desktop/log.txt` Preferably, use `adb logcat -c` to clear all logs before starting to reproduce the issue. ## Symbolication of crash logs with Google Play Console For apps that are deployed to Google Play Store you must upload the symbols files for each version of your app to get the crash reports as follows: 1. Open Google Play Console and open your app. 2. On the left menu, select **Release** -> **App bundle explorer**. 3. Using the picker in the top-right-hand corner, choose the ZIP archive with debug symbols. 4. Select the **Downloads** tab, and scroll down to the **Assets** section. 5. Click the upload arrow for the debug symbols as applicable to upload the symbols file for the version of your app. See [here](https://support.google.com/googleplay/android-developer/answer/9848633?sjid=13558197468535295314-EU#upload_file\&zippy=%2Cupload-files-using-the-google-play-developer-api) for more details. 6. Afterwards, crashes and ANRs will be deobfuscated. To view deobfuscated stack traces for individual crashes and ANRs on your app, go to your **Crashes & ANRs** page in the Google Play Console. ## Symbolication of crash logs can be done also locally Follow the below steps to symbolicate a native crash locally: 1. Use Logcat or ADB, gather the crash log and save it to a .txt file: ``` adb logcat -d > your_crashlog_filename.txt ``` 2. Get the symbols `.so` file that we ship with the release package. You can find these `.so` files inside `debug-symbols` ZIP file. 3. Depending upon your build architecture copy the file path, either `arm64-v8a` or `armeabi-v7a`. 4. Run the `ndk-stack` tool command : ``` path-to-Andorid-sdk/Android/sdk/ndk/24.0.8215888/ndk-stack -sym path-to-directory-with-binary-of-desired-architecture -dump path-to-crash.txt ``` Note that for this release, please use NDK 24.0.8215888.