/
exaile_win.py
133 lines (103 loc) · 3.85 KB
/
exaile_win.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
#!/usr/bin/env python3
"""Launcher for Exaile on Windows"""
import builtins
import msvcrt
import sys
import os
from ctypes import windll
# Provide dummy sys.stdout and sys.stderr, which are None in noconsole/windowed
# mode (launched using pythonw.exe, or PyInstaller build).
if sys.stdout is None:
sys.stdout = open(os.devnull, "w")
if sys.stderr is None:
sys.stderr = open(os.devnull, "w")
__builtin__open = __builtins__.open
def __open_inheritance_hack(*args, **kwargs):
"""Make file handles not inheritable, that way we can restart on the fly"""
# From http://www.virtualroadside.com/blog/index.php/2013/02/06/problems-with-file-descriptors-being-inherited-by-default-in-python/
result = __builtin__open(*args, **kwargs)
handle = msvcrt.get_osfhandle(result.fileno())
windll.kernel32.SetHandleInformation(handle, 1, 0)
return result
builtins.open = __open_inheritance_hack
def error(message1, message2=None, die=True):
import logging
"""Show error message and exit.
If two message arguments are supplied, the first one will be used as title.
If `die` is true, exit after showing the message.
"""
logging.error(message1 + (('\r\n\r\n' + message2) if message2 else ''))
if sys.stdout.isatty():
if die:
print("\r\n[Press Enter to exit.]", file=sys.stderr)
input()
else:
import ctypes
if not message2:
message1, message2 = message2, message1
ctypes.windll.user32.MessageBoxW(None, message2, message1, 0x10)
if die:
sys.exit(1)
def main():
import logging
logging.basicConfig(
level=logging.INFO, datefmt="%H:%M:%S", format="%(levelname)-8s: %(message)s"
)
aio_message = (
"\r\n\r\nPlease run the 'All-In-One PyGI/PyGObject for "
"Windows Installer' and ensure that the following are selected:"
"\r\n\r\n"
"* GTK+ 3.x\r\n"
"* GStreamer 1.x and the gst-plugins package(s)\r\n"
"\r\n"
"The 'All-In-One PyGI/PyGObject for Windows Installer' "
"can be downloaded at\r\n"
"https://sourceforge.net/projects/pygobjectwin32/\r\n\r\n"
"See README.Windows for more information."
)
try:
import gi
except Exception:
error("PyGObject not found", "PyGObject could not be imported. " + aio_message)
else:
logging.info("PyGObject works")
try:
gi.require_version('Gtk', '3.0')
from gi.repository import Gtk
except Exception:
error("GTK+ not found", "GTK+ could not be imported. " + aio_message)
else:
logging.info("GTK+ works")
try:
gi.require_version('Gst', '1.0')
from gi.repository import Gst
except Exception:
error("GStreamer not found", "GStreamer could not be imported. " + aio_message)
else:
logging.info("GStreamer works")
try:
import mutagen
except Exception:
error(
"Mutagen not found",
"The Python module Mutagen could not be imported. For download "
"and installation instructions see "
"https://mutagen.readthedocs.io/en/latest/\r\n\r\n"
"See README.Windows for more information.",
)
else:
logging.info("Mutagen works")
# disable the logging before starting exaile.. otherwise it gets
# configured twice and we get double the log messages!
logging = None
del sys.modules['logging']
try:
sys.argv[1:1] = ['--startgui', '--no-dbus', '--no-hal']
import exaile
exaile.main()
except Exception:
import traceback
error("Error while running exaile.main()", traceback.format_exc())
if __name__ == '__main__':
main()
# vi: et sts=4 sw=4 ts=4