Support Native Media Gallery Indexing / scanFile API on Android (Serious Python)
还没有人认领这个 Issue。
评估
调研方向
首先跟踪 Flutter 客户端的 Dart 端 handler 和提议的 MethodChannel 入口点,然后检查 Serious Python 如何向 Python 暴露服务。当跨平台媒体扫描 API 被暴露,并且 Android 文件无需 PyJNIus 变通方案即可对原生 MediaStore 可见时,即表示完成。
由索引模型根据 Issue 内容生成。
描述
Context
When building multi-platform Python applications with Flet and compiling them for Android using Serious Python, apps often need to download or save media files (videos, photos, audio) to public user directories (such as the standard Download/ folder).
The Problem
When a file is downloaded or created directly on the filesystem under public storage (e.g., /storage/emulated/0/Download/), other Android apps (like WhatsApp, Instagram, TikTok) and the native system Gallery do not show the new file automatically.
The files are technically present on disk, but they remain invisible to other apps until the user manually opens the Android system File Manager. Opening the File Manager forces a system-level ContentObserver folder scan, which finally registers the files in the Android MediaStore database.
What We Tried (And the JNI / PyJNIus Traps)
We attempted to solve this within Python code using PyJNIus (jnius) to manually trigger the Android MediaScannerConnection.scanFile() API. However, doing this from Python runs into several major JNI and Serious Python structural blocks:
1. PyJNIus Background Thread Attachment Trap
Flet events and background tasks run on Python background worker threads (like asyncio or threading loops). PyJNIus calling Java methods from a background thread fails silently or crashes unless jnius.attach_thread() is explicitly called beforehand.
import jnius
jnius.attach_thread() # Required, but undocumented and highly prone to runtime errors
2. Changing Host Activity Class Names
To initialize MediaScannerConnection, we need the application Context. In Serious Python, finding the host activity via class lookups is brittle because class names vary between Serious Python versions:
- Older:
com.flet.serious_python_android.PythonActivity - Newer:
com.flet.serious_python.PythonActivity - Fallback lookups like
android.app.ActivityThread.currentApplication()frequently returnnullwhen called from Python worker threads.
3. JNI Signature Matching Failures
PyJNIus has trouble converting Python list structures to Java String[] array signatures expected by scanFile(Context, String[], String[], OnScanCompletedListener). Developers have to construct Java arrays manually via JNI reflection:
Array = autoclass('java.lang.reflect.Array')
String = autoclass('java.lang.String')
paths_arr = Array.newInstance(String, len(file_paths)) # Brittle reflection setup
4. Android 9+ Implicit Intent Blocks
Fallback intent broadcasts like android.intent.action.MEDIA_SCANNER_SCAN_FILE are ignored on Android 9+ unless explicitly targeted to the Media Provider package (-p com.android.providers.media), making shell-based workarounds highly complex and security-restricted.
Proposed Solution (Feature Request)
To make Flet a truly first-class framework for mobile development, Flet should expose a native, cross-platform media indexing API (for example, page.scan_media(path) or a new page.storage_paths.scan_file(path) service method).
How it should work under the hood:
- The Flet Flutter client should handle the media scanner connection natively on the Dart side.
- In Dart, triggering a media scan on Android is extremely simple and does not suffer from classloader or background-thread JNI issues:
// Dart side handler import 'package:flutter/services.dart'; // Native MethodChannel triggers MediaScannerConnection.scanFile on the Android Activity thread - By delegating this to the Flutter shell, Python developers wouldn't need to write brittle PyJNIus wrappers, deal with JNI JVM thread-attachments, or worry about changing package class names between Serious Python releases.
This feature is essential for any Flet application that downloads user-facing files (photos, videos, PDF documents, audio) to public directories on Android.
- 主要语言
- Dart
- 星标
- 325
- 派生
- 46
- 平均合并
- 14 小时 53 分钟
- 30 天内合并 PR
- 5
环境准备
- 没有 Dockerfile 或 Docker Compose 文件
- 没有 Pull Request 模板
- 阅读贡献指南
从这里开始
- 先读完整个 Issue,再读项目的贡献指南。
- 在 Issue 下留言说明你要接手 —— 这能避免两个人做同样的事。
- Fork 仓库,在一个分支上完成修改。
- 提交 Pull Request,并在描述里引用这个 Issue 编号。
flet-dev/serious-python 的其他 Issue
-
难度 4/5 3-5 天 新手友好度 35/100
flet-dev/serious-python#169 ·
-
iOS Build Failure: Missing site-xcframeworks Directory in serious_python_darwin PhaseScriptExecution未关闭
难度 3/5 1-2 天 新手友好度 42/100
flet-dev/serious-python#168 ·
-
Update docs for site-packages可能重新可做 @FeodorFitsner 于 558 天前认领,目前没有进行中的 PR。 未关闭documentation
flet-dev/serious-python#157 · 1 条评论 · 已指派 1 人 ·
-
难度 4/5 3-5 天 新手友好度 35/100
flet-dev/serious-python#133 · 2 条评论 ·
-
难度 4/5 3-5 天 新手友好度 35/100
flet-dev/serious-python#117 ·
查看 flet-dev/serious-python 的全部 Issue
相似的 Issue
-
Smart charging: USB charger re-assert is starved during BLE scans, so the tablet never discharges未关闭bug ready-for-agent
难度 2/5 1-3 小时 新手友好度 86/100
decentespresso/decaid#931 ·
维护者通常 1 天内回复
-
bug
难度 1/5 1 小时以内 新手友好度 92/100
flame-engine/flame#4067 ·
维护者通常 1 天内回复
-
难度 2/5 1-3 小时 新手友好度 78/100
维护者通常 1 天内回复
-
难度 2/5 1-3 小时 新手友好度 88/100
google/skills_lint.dart#58 ·
维护者通常 1 天内回复
-
难度 2/5 1-3 小时 新手友好度 84/100
nvim-flutter/flutter-tools.nvim#557 ·
维护者通常 1 天内回复