Skip to content

Commit 8d63b8e

Browse files
authored
Display a messagebox when an error occurs during startup (#8196)
2 parents ca82531 + 35cc11e commit 8d63b8e

File tree

1 file changed

+94
-35
lines changed

1 file changed

+94
-35
lines changed

src/run_tribler.py

+94-35
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,67 @@
11
from __future__ import annotations
22

3-
import argparse
4-
import asyncio
5-
import encodings.idna # noqa: F401 (https://github.com/pyinstaller/pyinstaller/issues/1113)
6-
import logging.config
7-
import os
83
import sys
9-
import threading
10-
import typing
11-
import webbrowser
12-
from pathlib import Path
4+
import traceback
135

14-
from aiohttp import ClientSession
15-
from PIL import Image
166

17-
import tribler
18-
from tribler.core.session import Session
19-
from tribler.tribler_config import VERSION_SUBDIR, TriblerConfigManager
7+
def show_error(exc: Exception, shutdown: bool = True) -> None:
8+
"""
9+
Create a native pop-up without any third party dependency.
10+
11+
:param exc: the error to show to the user
12+
:param shutdown: whether to shut down after showing the error
13+
"""
14+
title = f"A {exc.__class__.__name__} occurred"
15+
text = "\n\n".join([str(a) for a in exc.args])
16+
sep = "*" * 80
17+
18+
print('\n'.join([sep, title, sep, traceback.format_exc(), sep]), file=sys.stderr) # noqa: T201, FLY002
19+
try:
20+
if sys.platform == 'win32':
21+
import win32api
22+
23+
win32api.MessageBox(0, text, title)
24+
elif sys.platform == 'Linux':
25+
import subprocess
26+
27+
subprocess.Popen(['xmessage', '-center', text]) # noqa: S603, S607
28+
elif sys.platform == 'Darwin':
29+
import subprocess
30+
31+
subprocess.Popen(['/usr/bin/osascript', '-e', text]) # noqa: S603
32+
else:
33+
print(f'cannot create native pop-up for system {sys.platform}') # noqa: T201
34+
except Exception as exception:
35+
# Use base Exception, because code above can raise many
36+
# non-obvious types of exceptions:
37+
# (SubprocessError, ImportError, win32api.error, FileNotFoundError)
38+
print(f'Error while showing a message box: {exception}') # noqa: T201
39+
40+
if shutdown:
41+
sys.exit(1)
42+
43+
44+
try:
45+
import argparse
46+
import asyncio
47+
import encodings.idna # noqa: F401 (https://github.com/pyinstaller/pyinstaller/issues/1113)
48+
import logging.config
49+
import os
50+
import sys
51+
import threading
52+
import typing
53+
import webbrowser
54+
from pathlib import Path
55+
56+
from aiohttp import ClientSession
57+
from PIL import Image
58+
59+
import tribler
60+
from tribler.core.session import Session
61+
from tribler.tribler_config import VERSION_SUBDIR, TriblerConfigManager
62+
63+
except Exception as e:
64+
show_error(e)
2065

2166
logger = logging.getLogger(__name__)
2267

@@ -66,6 +111,7 @@ async def start_download(config: TriblerConfigManager, server_url: str, torrent_
66111
else:
67112
logger.warning("Failed to start torrent %s: %s", torrent_uri, await response.text())
68113

114+
69115
def init_config(parsed_args: Arguments) -> TriblerConfigManager:
70116
"""
71117
Add environment variables to the configuration.
@@ -92,36 +138,49 @@ def init_config(parsed_args: Arguments) -> TriblerConfigManager:
92138
config.write()
93139
return config
94140

95-
async def main() -> None:
141+
142+
def load_torrent_uri(parsed_args: Arguments) -> str | None:
96143
"""
97-
The main script entry point.
144+
Loads the torrent URI.
98145
"""
99-
parsed_args = parse_args()
100-
config = init_config(parsed_args)
101-
102-
logger.info("Creating session. API port: %d. API key: %s.", config.get("api/http_port"), config.get("api/key"))
103-
session = Session(config)
104-
105146
torrent_uri = parsed_args.get('torrent')
106147
if torrent_uri and os.path.exists(torrent_uri):
107148
if torrent_uri.endswith(".torrent"):
108149
torrent_uri = Path(torrent_uri).as_uri()
109150
if torrent_uri.endswith(".magnet"):
110151
torrent_uri = Path(torrent_uri).read_text()
111-
server_url = await session.find_api_server()
152+
return torrent_uri
153+
154+
155+
async def main() -> None:
156+
"""
157+
The main script entry point.
158+
"""
159+
try:
160+
parsed_args = parse_args()
161+
config = init_config(parsed_args)
162+
163+
logger.info("Creating session. API port: %d. API key: %s.", config.get("api/http_port"), config.get("api/key"))
164+
session = Session(config)
165+
166+
torrent_uri = load_torrent_uri(parsed_args)
167+
server_url = await session.find_api_server()
168+
169+
headless = parsed_args.get('server')
170+
if server_url:
171+
logger.info("Core already running at %s", server_url)
172+
if torrent_uri:
173+
logger.info("Starting torrent using existing core")
174+
await start_download(config, server_url, torrent_uri)
175+
if not headless:
176+
webbrowser.open_new_tab(server_url + f"?key={config.get('api/key')}")
177+
logger.info("Shutting down")
178+
return
179+
180+
await session.start()
181+
except Exception as exc:
182+
show_error(exc)
112183

113-
headless = parsed_args.get('server')
114-
if server_url:
115-
logger.info("Core already running at %s", server_url)
116-
if torrent_uri:
117-
logger.info("Starting torrent using existing core")
118-
await start_download(config, server_url, torrent_uri)
119-
if not headless:
120-
webbrowser.open_new_tab(server_url + f"?key={config.get('api/key')}")
121-
logger.info("Shutting down")
122-
return
123-
124-
await session.start()
125184
server_url = await session.find_api_server()
126185
if server_url and torrent_uri:
127186
await start_download(config, server_url, torrent_uri)

0 commit comments

Comments
 (0)