Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Crash on Windows when opened from system tray #720

Closed
simonrob opened this issue Apr 28, 2021 · 6 comments
Closed

Crash on Windows when opened from system tray #720

simonrob opened this issue Apr 28, 2021 · 6 comments

Comments

@simonrob
Copy link
Contributor

Specification

  • pywebview version: 3.4
  • operating system: Windows 10
  • web renderer: Unknown - whatever is the default

Description

I use pywebview along with pystray (0.17.3) as part of a script that occasionally needs to pop up a login window. Because both pywebview and pystray need to run on the main thread, I open the webview from a click on the system tray icon, as shown in the basic example below. This action runs on the main thread, and on macOS and Ubuntu it works with no issues. On Windows it gives the following error:

Unhandled Exception: Python.Runtime.PythonException: OSError : [WinError 1402] Invalid cursor handle.
   at Python.Runtime.Dispatcher.Dispatch(ArrayList args)
   at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
   at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
   at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
   at System.Threading.ThreadHelper.ThreadStart()

A minimum example to demonstrate the issue is given below. Run this code on Windows and you will see a black square appear in the system tray. Right-click the icon and click the Webview option to trigger the crash. I've also added the thread names to show that both pystray and pywebview are running on the main thread:

import pystray, webview, threading
from PIL import Image

def click(icon, item):
    print('pywebview thread:', threading.current_thread().__class__.__name__)
    window = webview.create_window('Woah dude!', 'https://pywebview.flowrl.com')
    webview.start()

if __name__ == '__main__':
    print('pystray thread:', threading.current_thread().__class__.__name__)
    pystray.Icon('test', Image.new('RGB', (16, 16)), menu=pystray.Menu(pystray.MenuItem('Webview', click))).run()

Practicalities

  • YES/NO I am willing to work on this issue myself.
    Possibly, if you can point to where to begin

  • YES/NO I am prepared to support this issue financially.
    If needed

@NikitaKozlovtcev
Copy link

NikitaKozlovtcev commented May 2, 2021

Specification

  • pywebview version: 3.8.6
  • operating system: Windows 10
  • web renderer: Unknown - whatever is the default

I have same problem

import webview

webview.create_window('Hello world', 'https://pywebview.flowrl.com/')
webview.start()
python main.py

Необработанное исключение: Python.Runtime.PythonException: Exception : Сбой при удаленном вызове процедуры. (Исключение из HRESULT: 0x800706BE)
   в System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   в System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   в Microsoft.Toolkit.Win32.UI.Controls.Interop.WinRT.WebViewControlProcess.<CreateWebViewControlHostAsync>d__16.MoveNext()
--- Конец трассировка стека из предыдущего расположения, где возникло исключение ---
   в System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   в System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   в Microsoft.Toolkit.Forms.UI.Controls.WebViewControlProcessExtensions.CreateWebViewControlHost(WebViewControlProcess process, IntPtr hostWiНеобработанное исключение: Python.Runtime.PythonException: Exception : Сбой при удаленном вызове процедуры. (Исключение из HRESULT: 0x800706BE
)
   в System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   в System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   в Microsoft.Toolkit.Win32.UI.Controls.Interop.WinRT.WebViewControlProcess.<CreateWebViewControlHostAsync>d__16.MoveNext()
--- Конец трассировка стека из предыдущего расположения, где возникло исключение ---
   в System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   в System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   в Microsoft.Toolkit.Forms.UI.Controls.WebViewControlProcessExtensions.CreateWebViewControlHost(WebViewControlProcess process, IntPtr hostWi
ndowHandle, Rectangle bounds)
   в Microsoft.Toolkit.Forms   в Microsoft.Toolkit.Forms.UI.Controls.WebViewControlProcessExtensions.CreateWebViewControlHost(WebViewControlProcess process, IntPtr host
WindowHandle, Rectangle bounds)
   в Microsoft.Toolkit.Forms.UI.Controls.WebView.Initialize()
   в Microsoft.Toolkit.Forms.UI.Controls.WebView.System.ComponentModel.ISupportInitialize.EndInit()
   в Python.Runtime.Dispatcher.Dispatch(ArrayList args)
   в System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preser
veSyncCtx)
   в System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCt
x)
   в System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
   в System.Threading.ThreadHelper.ThreadStart()

   в Microsoft.Toolkit.Forms.UI.Controls.WebViewControlProcessExtensions.CreateWebViewControlHost(WebViewControlProcess process, IntPtrh
ostWindowHandle, Rectangle bounds)
   в Microsoft.Toolkit.Forms.UI.Controls.WebViewControlProcessExtensions.CreateWebViewControlHost(WebViewControlProcess process, IntPtr
   в System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   в Microsoft.Toolkit.Forms.UI.Controls.WebViewControlProcessExtensions.CreateWebViewControlHost(WebViewControlProcess process, IntPtr hostWin
dowHandle, Rectangle bounds)
   в Microsoft.Toolkit.Forms.UI.Controls.WebView.Initialize()
   в Microsoft.Toolkit.Forms.UI.Controls.WebView.System.ComponentModel.ISupportInitialize.EndInit()
   в Python.Runtime.Dispatcher.Dispatch(ArrayList args)
   в System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveS
yncCtx)
   в System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
   в System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
   в System.Threading.ThreadHelper.ThreadStart()

@r0x0r
Copy link
Owner

r0x0r commented May 4, 2021

@simonrob both libraries need to be run on a main thread. threading cannot do that, but using multiprocessing combined with a queue to pass data between processes might do the trick.

@simonrob
Copy link
Contributor Author

simonrob commented May 5, 2021

@r0x0r thanks, but as the example shows, both are running on the main thread, and work on Linux and macOS which has the same requirements. (I don't think the other reply in this issue is actually the same problem.)

@simonrob
Copy link
Contributor Author

simonrob commented May 9, 2021

I looked at this again and found that it may actually not be anything to do with the thread, but actually some underlying pywebview incompatibility with pystray on Windows.

On Windows, simply adding import pystray and trying to start the webview causes this crash.

Pystray itself works fine when both are imported together (in either order).

What could be going on here?

@simonrob
Copy link
Contributor Author

simonrob commented May 11, 2021

Just to follow up, as discussed in a pystray issue, this is caused by windll.user32.DestroyIcon(icon_handle) in winforms.py.

Should this call be conditional on icon_handle != 0 like the icon creation which happens a few lines above? The only documentation I can find seems to suggest that DestroyIcon should always be called after ExtractIcon, but presumably this is not the case if there is no handle returned.

@r0x0r
Copy link
Owner

r0x0r commented May 18, 2021

I have no idea about this either, but if this solves the problem then it is fine by me. Thanks for the PR!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants