zauberzeug / nicegui

Create web-based user interfaces with Python. The nice way.
https://nicegui.io
MIT License
8.74k stars 532 forks source link

pyinstaller and cpu_bound issue #3034

Open Wananrd opened 4 months ago

Wananrd commented 4 months ago

Description

I need to use pyinstaller to generate exe file, when i run the exe file, there's a question about cpu_bound, I guess it may be connected with muti-thread.

I want to know how to solve it.

My demo.py code

from nicegui import ui, run
import time

def compute_sum(a: float, b: float) -> float:
    time.sleep(1)  # simulate a long-running computation
    return a + b

@ui.page('/')
def main_page() -> None:
    async def handle_click():
        result = await run.cpu_bound(compute_sum, 1, 2)
        ui.notify(f'Sum is {result}')

    ui.button('Compute', on_click=handle_click)

ui.run(reload=False)

my build code

import os
import subprocess
from pathlib import Path
import nicegui

cmd = [
    'python',
    '-m', 'PyInstaller',
    'demo.py', # your main file with ui.run()
    '--name', 'demo', # name of your app
    '--onefile',
    '--add-data', f'{Path(nicegui.__file__).parent}{os.pathsep}nicegui'
]
subprocess.call(cmd)

This is error info

D:\code\Ai\pic_to_cad\demo\dist>demo.exe
NiceGUI ready to go on http://localhost:8080, http://169.254.171.137:8080, http://169.254.246.197:8080, http://169.254.30.91:8080, http://169.254.46.222:8080, http://169.254.47.165:8080, http://169.254.5.247:8080, http://192.168.147.75:8080, http://192.168.189.1:8080, and http://192.168.19.1:8080
NiceGUI ready to go on http://localhost:8080, http://169.254.171.137:8080, http://169.254.246.197:8080, http://169.254.30.91:8080, http://169.254.46.222:8080, http://169.254.47.165:8080, http://169.254.5.247:8080, http://192.168.147.75:8080, http://192.168.189.1:8080, and http://192.168.19.1:8080
ERROR:    [Errno 10048] error while attempting to bind on address ('0.0.0.0', 8080): 通常每个套接字地址(协议/网络地址/端口)只允许使用一次。
A process in the process pool was terminated abruptly while the future was running or pending.
Traceback (most recent call last):
  File "nicegui\events.py", line 413, in wait_for_result
    await result
  File "demo.py", line 14, in handle_click
  File "nicegui\run.py", line 40, in cpu_bound
    return await _run(process_pool, callback, *args, **kwargs)
  File "nicegui\run.py", line 23, in _run
    return await loop.run_in_executor(executor, partial(callback, *args, **kwargs))
concurrent.futures.process.BrokenProcessPool: A process in the process pool was terminated abruptly while the future was running or pending.
Wananrd commented 4 months ago

I want to know how to handle this issue?

rodja commented 4 months ago

Does your code run fine when not packaged with pyinstaller? Is the exception happening whenever you start the program, or have you pressed CTRL-C or something else?

Wananrd commented 4 months ago

Does your code run fine when not packaged with pyinstaller? Is the exception happening whenever you start the program, or have you pressed CTRL-C or something else?

No packaged it works. When after I packaged it and exeacute it, it could show the right page. However, I clicked the button, it appears this error. I don't do any other operation.

rodja commented 4 months ago

Can anyone reproduce this?

rodja commented 4 months ago

Besides a confirmation from another windows user I would like to know if the error also happens if you use nicegui-pack (see https://nicegui.io/documentation/section_configuration_deployment#package_for_installation).

Wananrd commented 4 months ago

Besides a confirmation from another windows user I would like to know if the error also happens if you use nicegui-pack (see https://nicegui.io/documentation/section_configuration_deployment#package_for_installation).

It has the same error even i use the nicegui-pack

afullerx commented 3 months ago

I was able to replicate this error. However, after further investigation, it doesn't appear to be an issue with NiceGUI. From the PyInstaller documentation:

Currently, the only supported multi-processing framework is the multiprocessing module from the Python standard library, and even that requires you to make a multiprocessing.freeze_support() call before using any multiprocessing functionality.

I modified demp.py to include:

multiprocessing.freeze_support()
ui.run(reload=False)

This prevented the error.

@Wananrd, does this also resolve the issue for you?