[Python] How to display local HTML files in Flet's WebView in Android device?

Discussão em 'Python' iniciado por Stack, Março 7, 2025.

  1. Stack

    Stack Membro Participativo

    I have problems with the WebView element in Android. I would like to display local HTML files with JavaScript and CSS.

    My first attempt was to use directly local files: When I use file:// scheme, it seems not to work.

    So I've created a local server with http.server and I call http://localhost:8000/file.html.

    import flet as ft
    import http.server
    import socketserver
    import threading
    import sys
    import ssl

    SERVER = "localhost"
    PORT = 8000
    HTML_DIRECTORY = "assets/html"


    class HookHandler(http.server.SimpleHTTPRequestHandler):
    def __init__(self, *args, **kwargs):
    super().__init__(*args, directory=HTML_DIRECTORY, **kwargs)

    class ThreadedTCPServer(socketserver.ThreadingMixIn, socketserver.TCPServer):
    pass

    def start_server():
    with ThreadedTCPServer((SERVER, PORT), HookHandler) as httpd:
    httpd.serve_forever()


    def main(page: ft.Page):
    wv = ft.WebView(
    f"http://{SERVER}:{PORT}/file.html",
    expand=True
    )
    page.add(wv)

    server_thread = threading.Thread(target=start_server)
    server_thread.daemon = True
    server_thread.start()
    app = ft.app(main)


    But when I access the files, there is a security error ERR_CLEARTEXT_NOT_PERMITTED. I find no way to disable this security in the WebView component.

    So I've added SSL to my server, with self signed certificate for localhost and I call http://localhost:8000/file.html.

    import flet as ft
    import http.server
    import socketserver
    import threading
    import sys
    import ssl

    SERVER = "localhost"
    PORT = 8000
    HTML_DIRECTORY = "assets/html"


    class HookHandler(http.server.SimpleHTTPRequestHandler):
    def __init__(self, *args, **kwargs):
    super().__init__(*args, directory=HTML_DIRECTORY, **kwargs)

    class ThreadedTCPServer(socketserver.ThreadingMixIn, socketserver.TCPServer):
    pass

    def get_ssl_context(certfile, keyfile):
    context = ssl.SSLContext(ssl.PROTOCOL_TLS_SERVER)
    context.load_cert_chain(certfile, keyfile)
    return context

    def start_server():
    with ThreadedTCPServer((SERVER, PORT), HookHandler) as httpd:
    context = get_ssl_context("cert.pem", "key.pem")
    httpd.socket = context.wrap_socket(httpd.socket, server_side=True)
    print("Serving at port", PORT)
    httpd.serve_forever()


    def main(page: ft.Page):
    wv = ft.WebView(
    f"https://{SERVER}:{PORT}/file.html",
    expand=True,
    )
    page.add(url_input, submit_btn, wv)


    server_thread = threading.Thread(target=start_server)
    server_thread.daemon = True
    server_thread.start()
    app = ft.app(main)



    When I open my application, it's blank. If I open the same URL in my Android's Firefox browser, I see a security alert (because the certificate is self signed), but I can check "I'm OK, continue" and the HTML file is well rendered.

    My question : How can I display local files with Flet's WebView?

    After a lot of searching, I've found a workaround that does't satisfy me: modify the Androidmanifest.xml to add a android:usesCleartextTraffic="true" property. But this implies to decompile APK, modify the file by hand, compile a new APK, sign this APK. Is there a way to add custom elements / properties in this file automatically in the flet build apkcommand?

    Continue reading...

Compartilhe esta Página