I'm building a KivyMD python app for Android. I try to access the DeepL API. It works perfectly on my desktop and on my android device (when compiled with buildozer) when I use 'requests'. But it works on my desktop but not on my android device when I use the 'deepl' library instead of 'requests'. I want to use the 'deepl' library because the translations are better than when I use the 'requests' library.
My android device is Xiaomi Mi 9T
MIUI version : MIUI Global 12.0.5 Stable 12.0.5.0(QFJEUXM)
Android version : 10 QKQ1.190825.002
I'm using :
kivy 2.1.0
kivymd 1.1.1
deepl 1.14.0
Here is my code :
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
import traceback
import requests
import deepl
import ssl
ssl._create_default_https_context = ssl._create_unverified_context
class DeeplTranslator:
def __init__(self):
self.auth_key = "my_auth_key"
self.url = 'https://api-free.deepl.com/v2/translate'
self.translator = deepl.Translator(self.auth_key)
def translate(self, text_to_translate, target_lang, source_lang):
# Requests method
"""
params = {
'auth_key': self.auth_key,
'text': text_to_translate,
'target_lang': target_lang
}
try:
response = requests.post(self.url, data=params)
response.raise_for_status() # Raise an exception for 4xx or 5xx response status codes
source_lang = response.json()['translations'][0]['detected_source_language']
translation = response.json()['translations'][0]['text']
return source_lang, translation
except (requests.exceptions.RequestException, KeyError, IndexError) as e:
print(f"An error occurred while translating the text: {e}")
return None, None
"""
# DeepL method
try:
result = self.translator.translate_text(text_to_translate, target_lang=target_lang, source_lang=source_lang, formality='less')
translation = result.text
return source_lang, translation
except Exception as e:
traceback.print_exc()
print(str(e))
return None, None
class FlasholatorApp(MDApp):
def build(self):
return Builder.load_file("main.kv")
def on_start(self):
self.deepl_translator = DeeplTranslator()
if platform == 'android':
from android.permissions import request_permissions, Permission
request_permissions([
Permission.WRITE_EXTERNAL_STORAGE,
Permission.READ_EXTERNAL_STORAGE,
Permission.INTERNET
])
self.device_root_path = "/storage/emulated/0" if platform=='android' else os.environ['HOME']
def translate(self, text_to_translate, target_lang, source_lang):
if text_to_translate!=self.text_to_translate and text_to_translate!="":
self.translate_tab.ids.translate_button.disabled = True
source_lang, translation = self.deepl_translator.translate(text_to_translate, target_lang, source_lang)
self.translate_tab.ids.translate_button.disabled = False
else:
source_lang, translation = None, None
if source_lang and translation:
self.translate_tab.ids.translated_text.text = translation
self.text_to_translate, self.target_lang = text_to_translate, target_lang
self.translation, self.source_lang = translation, source_lang
Here is my buildozer.spec file permissions :
android.permissions = WRITE_EXTERNAL_STORAGE, READ_EXTERNAL_STORAGE, INTERNET, SSL
Here is the error I'm getting :
Traceback (most recent call last):
04-26 01:08:16.114 5121 5497 D PowerCheckerService: onBatteryChanged, mBatteryLevel = 58, status = 2, level = 58, plug = 2, scale = 100
04-26 01:08:16.115 3396 3396 I BatteryInfoReceiver: ACTION_BATTERY_CHANGED
04-26 01:08:16.115 23866 24365 I python : File "/media/felix/2bbafeba-9213-47d8-8cff-0f44dd5ad585/home/felix/Documents/Informatique/Python/Flasholator/.buildozer/android/platform/build-armeabi-v7a/build/python-installs/flasholatorApp/armeabi-v7a/deepl/http_client.py", line 110, in request_with_backoff
04-26 01:08:16.115 23866 24365 I python : File "/media/felix/2bbafeba-9213-47d8-8cff-0f44dd5ad585/home/felix/Documents/Informatique/Python/Flasholator/.buildozer/android/platform/build-armeabi-v7a/build/python-installs/flasholatorApp/armeabi-v7a/deepl/http_client.py", line 251, in _generate_user_agent
04-26 01:08:16.115 23866 24365 I python : File "/media/felix/2bbafeba-9213-47d8-8cff-0f44dd5ad585/home/felix/Documents/Informatique/Python/Flasholator/.buildozer/android/platform/build-armeabi-v7a/build/other_builds/python3/armeabi-v7a__ndk_target_21/python3/Lib/platform.py", line 1235, in platform
04-26 01:08:16.115 23866 24365 I python : File "/media/felix/2bbafeba-9213-47d8-8cff-0f44dd5ad585/home/felix/Documents/Informatique/Python/Flasholator/.buildozer/android/platform/build-armeabi-v7a/build/other_builds/python3/armeabi-v7a__ndk_target_21/python3/Lib/platform.py", line 196, in libc_ver
04-26 01:08:16.115 23866 24365 I python : IsADirectoryError: [Errno 21] Is a directory: '/data/data/org.felixmortas.flasholatorapp/files/app'
04-26 01:08:16.115 23866 24365 I python :
04-26 01:08:16.115 23866 24365 I python : The above exception was the direct cause of the following exception:
04-26 01:08:16.115 23866 24365 I python :
04-26 01:08:16.116 23866 24365 I python : Traceback (most recent call last):
04-26 01:08:16.116 23866 24365 I python : File "/media/felix/2bbafeba-9213-47d8-8cff-0f44dd5ad585/home/felix/Documents/Informatique/Python/Flasholator/.buildozer/android/app/DeeplTranslator.py", line 44, in translate
04-26 01:08:16.116 23866 24365 I python : File "/media/felix/2bbafeba-9213-47d8-8cff-0f44dd5ad585/home/felix/Documents/Informatique/Python/Flasholator/.buildozer/android/platform/build-armeabi-v7a/build/python-installs/flasholatorApp/armeabi-v7a/deepl/translator.py", line 823, in translate_text
04-26 01:08:16.116 23866 24365 I python : File "/media/felix/2bbafeba-9213-47d8-8cff-0f44dd5ad585/home/felix/Documents/Informatique/Python/Flasholator/.buildozer/android/platform/build-armeabi-v7a/build/python-installs/flasholatorApp/armeabi-v7a/deepl/translator.py", line 535, in _api_call
04-26 01:08:16.116 23866 24365 I python : File "/media/felix/2bbafeba-9213-47d8-8cff-0f44dd5ad585/home/felix/Documents/Informatique/Python/Flasholator/.buildozer/android/platform/build-armeabi-v7a/build/python-installs/flasholatorApp/armeabi-v7a/deepl/http_client.py", line 121, in request_with_backoff
04-26 01:08:16.116 23866 24365 I python : deepl.exceptions.DeepLException: Error occurred while preparing request: [Errno 21] Is a directory: '/data/data/org.felixmortas.flasholatorapp/files/app'
04-26 01:08:16.116 23866 24365 I python : Error occurred while preparing request: [Errno 21] Is a directory: '/data/data/org.felixmortas.flasholatorapp/files/app'
Here are my android logs :
04-25 00:00:22.639 12716 12716 V GrantPermissionsActivity: Permission grant result requestId=292789256274468049 callingUid=10501 callingPackage=org.felixmortas.flasholatorapp permission=android.permission.WRITE_EXTERNAL_STORAGE isImplicit=false result=5
04-25 00:00:22.641 1686 1935 W ActivityManager: setHasOverlayUi called on unknown pid: 12318
04-25 00:00:22.642 1686 2303 I MiuiNetworkPolicy: removeUidState uid = 10501
04-25 00:00:22.642 1686 2303 I MiuiNetworkPolicy: updateMLUid uid:10501,old:2,new:20
04-25 00:00:22.642 1686 2303 I MiuiNetworkPolicy: isMLEnabled state:2,uid:10501,connect:CONNECTED
04-25 00:00:22.642 1686 2303 I MiuiNetworkPolicy: isMLEnabled state:20,uid:10501,connect:CONNECTED
04-25 00:00:22.642 1686 2303 I MiuiNetworkPolicy: updateUidState uid = 10096, uidState = 2
04-25 00:00:22.642 1686 2303 I MiuiNetworkPolicy: updateMLUid uid:10096,old:6,new:2
04-25 00:00:22.642 1686 2303 I MiuiNetworkPolicy: isMLEnabled state:6,uid:10096,connect:CONNECTED
04-25 00:00:22.642 1686 2303 I MiuiNetworkPolicy: isMLEnabled state:2,uid:10096,connect:CONNECTED
04-25 00:00:22.643 2509 2509 D EventBus: [2509, u0] send(AppTransitionFinishedEvent)
04-25 00:00:22.643 2509 2509 D EventBus: [2509, u0] -> ForcedResizableInfoActivityController [0x77137cc, P1] onBusEvent(AppTransitionFinishedEvent)
04-25 00:00:22.643 522 522 I hwservicemanager: getTransport: Cannot find entry vendor.qti.hardware.servicetracker@1.0::IServicetracker/default in either framework or device manifest.
04-25 00:00:22.643 2509 2509 D EventBus: [2509, u0] onBusEvent(AppTransitionFinishedEvent) duration: 48 microseconds, avg: 60
04-25 00:00:22.647 1686 4701 V LocSvc_HIDL_IzatProvider_jni: [onRemoveRequest][180] [HC] =>> [HS]
04-25 00:00:22.647 718 718 V LocSvc_HIDL_IzatProvider: [onRemoveRequest][210] [HS] <<<<= [HC]
04-25 00:00:22.647 718 718 I IzatSvc_IzatManager: LocTech-Label :: IZATMANAGER :: Remove Request In
04-25 00:00:22.647 718 718 I IzatSvc_IzatManager: LocTech-Value :: Provider: 2, Num Updates: 2147483647, TTFF: 0, Interval: 1000, Displacement: 0.000000, Horizontal Accuracy: 1, Altitude Accuracy: 2, Bearing Accuracy: 2
04-25 00:00:22.647 1686 1946 V LocSvc_HIDL_OsNpGlue_jni: [onStopRequest][73] [HC] <<= [HS]
04-25 00:00:22.654 1686 1936 I Timeline: Timeline: App_transition_ready time:781897641
04-25 00:00:22.655 4784 5146 I FusedLocationProvider: onSetRequest
04-25 00:00:22.655 4784 5189 I AbsoluteLocationDispatcher: request type:0
04-25 00:00:22.655 12716 12716 V GrantPermissionsActivity: Permission grant result requestId=292789256274468049 callingUid=10501 callingPackage=org.felixmortas.flasholatorapp permission=android.permission.READ_EXTERNAL_STORAGE isImplicit=false result=5
When building the app on my android device, it asks me if I'm OK to give access to my storage and I say yes.
Also, my MDFileManager is not opening on my android device but is on my desktop. Maybe the problem is related ?
Here is the code for my MDFileManager in my class FlasholatorApp(MDApp):
class FlasholatorApp(MDApp):
...
def open_save_database_folder_selector(self):
def save_database(path):
print("Sauvegarde du paquet de carte ...")
# Pass the file path to save_database() method
self.flashcard_collection.save_database(path)
print("Paquet de cartes sauvegardé avec succès !")
# Close the file manager
file_manager.close()
# Create a file manager instance
file_manager = MDFileManager(
exit_manager=lambda x: file_manager.close(),
select_path=save_database,
ext=[".db"],
selector="folder"
)
# Open the file manager
file_manager.show(self.device_root_path) # Starting path
When I try to open my MDFileManager by clicking on a button, it doesn't crash but doesn't do anything.
Does anyone knows what is really causing the problem ?
Also, based on this post : https://stackoverflow.com/questions/64849485/why-is-filemanager-not-working-on-android-kivymd
I changed the self.device_root_path
of my MDFileManager to self.primary_ext_storage
.
self.primary_ext_storage
is defined as this :
from android.storage import primary_external_storage_path
self.primary_ext_storage = os.environ['HOME'] if platform!='android' else primary_external_storage_path()
But that doesn't change anything. When I try to open my MDFileManager by clicking on a button, it doesn't crash but doesn't do anything.
Thank you
The library is trying to figure out which platform is running on, which causes the issue you observed (platform.platform()
is throwing). Changing the way you instantiate your deepl.Translator
should fix the issue.
From
self.translator = deepl.Translator(self.auth_key)
to
self.translator = deepl.Translator(self.auth_key, send_platform_info=False)