| Trees | Indices | Help |
|---|
|
|
1 # -*- Mode: Python -*-
2 # vi:si:et:sw=4:sts=4:ts=4
3
4 # Flumotion - a streaming media server
5 # Copyright (C) 2004,2005,2006,2007,2008,2009 Fluendo, S.L.
6 # Copyright (C) 2010,2011 Flumotion Services, S.A.
7 # All rights reserved.
8 #
9 # This file may be distributed and/or modified under the terms of
10 # the GNU Lesser General Public License version 2.1 as published by
11 # the Free Software Foundation.
12 # This file is distributed without any warranty; without even the implied
13 # warranty of merchantability or fitness for a particular purpose.
14 # See "LICENSE.LGPL" in the source distribution for more information.
15 #
16 # Headers in this file shall remain intact.
17
18 """boostrapping functions for flumotion"""
19
20 import os
21 import sys
22
23 from flumotion.common.log import safeprintf
24
25 __version__ = "$Rev$"
26 # Keep in sync with configure.ac
27 PYGTK_REQ = (2, 10, 0)
28 KIWI_REQ = (1, 9, 13)
29 GST_REQ = {'0.10': {'gstreamer': (0, 10, 10),
30 'gst-python': (0, 10, 4)}}
31 USE_GOPTION_PARSER = False
32 USE_GTK = False
33 USE_GST = True
34
35
37 """
38 Initialize pygobject. A missing or too-old pygobject will cause a
39 SystemExit exception to be raised.
40 """
41 try:
42 import pygtk
43 pygtk.require('2.0')
44
45 import gobject
46 except ImportError:
47 raise SystemExit('ERROR: PyGTK could not be found')
48
49 if gobject.pygtk_version < PYGTK_REQ:
50 raise SystemExit('ERROR: PyGTK %s or higher is required'
51 % '.'.join(map(str, PYGTK_REQ)))
52
53 gobject.threads_init()
54
55
60
61 if gst_majorminor not in GST_REQ:
62 raise SystemExit('ERROR: Invalid FLU_GST_VERSION: %r (expected '
63 'one of %r)' % (gst_majorminor, GST_REQ.keys()))
64
65 pygst_req = GST_REQ[gst_majorminor]['gst-python']
66 gst_req = GST_REQ[gst_majorminor]['gstreamer']
67
68 try:
69 import pygst
70 pygst.require(gst_majorminor)
71 import gst
72 except ImportError:
73 return False
74 except AssertionError:
75 return False
76
77 try:
78 gst_version = gst.get_gst_version()
79 pygst_version = gst.get_pygst_version()
80 except AttributeError:
81 # get_foo_version() added in 0.10.4, fall back
82 gst_version = gst.gst_version
83 pygst_version = gst.pygst_version
84
85 if gst_req[:2] != gst_version[:2]:
86 raise SystemExit(
87 'ERROR: Expected GStreamer %s, but got incompatible %s'
88 % (gst_majorminor, tup2version(gst_version[:2])))
89
90 if gst_version < gst_req:
91 raise SystemExit(
92 'ERROR: GStreamer %s too old; install %s or newer'
93 % (tup2version(gst_version), tup2version(gst_req)))
94
95 if pygst_version < pygst_req:
96 raise SystemExit(
97 'ERROR: gst-python %s too old; install %s or newer'
98 % (tup2version(pygst_version), tup2version(pygst_req)))
99
100 return True
101
102
104 """
105 Initialize pygst. A missing or too-old pygst will cause a
106 SystemExit exception to be raised.
107 """
108 assert 'gobject' in sys.modules, "Run init_gobject() first"
109
110 gst_majorminor = os.getenv('FLU_GST_VERSION')
111
112 if gst_majorminor:
113 if not _init_gst_version(gst_majorminor):
114 raise SystemExit('ERROR: requested GStreamer version %s '
115 'not available' % gst_majorminor)
116 else:
117 majorminors = GST_REQ.keys()
118 majorminors.sort()
119 while majorminors:
120 majorminor = majorminors.pop()
121 if _init_gst_version(majorminor):
122 gst_majorminor = majorminor
123 break
124 if not gst_majorminor:
125 raise SystemExit('ERROR: no GStreamer available '
126 '(looking for versions %r)' % (GST_REQ.keys(), ))
127
128 return gst_majorminor
129
130
132 import gobject
133
134 try:
135 from kiwi.__version__ import version as kiwi_version
136 except ImportError:
137 return False
138
139 if kiwi_version < KIWI_REQ:
140 raise SystemExit('ERROR: Kiwi %s or higher is required'
141 % '.'.join(map(str, KIWI_REQ)))
142 elif gobject.pygobject_version > (2, 26, 0):
143 # Kiwi is not compatible yet with the changes introduced in
144 # http://git.gnome.org/browse/pygobject/commit/?id=84d614
145 # Basically, what we do is to revert the changes in _type_register of
146 # GObjectMeta at least until kiwi works properly with new pygobject
147 from gobject._gobject import type_register
148
149 def _type_register(cls, namespace):
150 ## don't register the class if already registered
151 if '__gtype__' in namespace:
152 return
153
154 if not ('__gproperties__' in namespace or
155 '__gsignals__' in namespace or
156 '__gtype_name__' in namespace):
157 return
158
159 # Do not register a new GType for the overrides, as this would sort
160 # of defeat the purpose of overrides...
161 if cls.__module__.startswith('gi.overrides.'):
162 return
163
164 type_register(cls, namespace.get('__gtype_name__'))
165
166 gobject.GObjectMeta._type_register = _type_register
167
168 return True
169
170
172 # We should only use the GOption parser if we are already going to
173 # import gobject, and if we can find a recent enough version of
174 # pygobject on our system. There were bugs in the GOption parsing
175 # until pygobject 2.15.0, so just revert to optparse if our
176 # pygobject is too old.
177 global USE_GOPTION_PARSER
178 if not gtk and not gst:
179 USE_GOPTION_PARSER = False
180 else:
181 import gobject
182 if getattr(gobject, 'pygobject_version', ()) >= (2, 15, 0):
183 USE_GOPTION_PARSER = True
184 else:
185 USE_GOPTION_PARSER = False
186
187
189 try:
190 import statprof
191 except ImportError, e:
192 print "Profiling requested, but statprof not available (%s)" % e
193 return main
194
195 def wrapped(*args, **kwargs):
196 statprof.start()
197 try:
198 return main(*args, **kwargs)
199 finally:
200 statprof.stop()
201 statprof.display(OUT=file(output_file, 'wb'))
202 return wrapped
203
204
206 try:
207 import cProfile as profile
208 except ImportError:
209 import profile
210
211 def wrapped(*args, **kwargs):
212 prof = profile.Profile()
213 try:
214 return prof.runcall(main, *args, **kwargs)
215 finally:
216 prof.dump_stats(output_file)
217 return wrapped
218
219
221
222 def generate_output_file():
223 import tempfile
224 return os.path.join(tempfile.gettempdir(),
225 'flustat.%s.%s.%d' %
226 (main.__module__, main.__name__, os.getpid()))
227
228 if os.getenv('FLU_PROFILE'):
229 return wrap_for_statprof(main, generate_output_file())
230 elif os.getenv('FLU_BUILTIN_PROFILE'):
231 return wrap_for_builtin_profiler(main, generate_output_file())
232 else:
233 return main
234
235
237 # python 2.5 and twisted < 2.5 don't work together
238 pythonMM = sys.version_info[0:2]
239 from twisted.copyright import version
240 twistedMM = tuple([int(n) for n in version.split('.')[0:2]])
241 if pythonMM >= (2, 5) and twistedMM < (2, 5):
242 raise SystemError(
243 "Twisted versions older than 2.5.0 do not work with "
244 "Python 2.5 and newer. "
245 "Please upgrade Twisted or downgrade Python.")
246
247 if gtk or gst:
248 init_gobject()
249
250 if gtk:
251 init_kiwi()
252
253 if gst:
254 from flumotion.configure import configure
255 configure.gst_version = init_gst()
256
257 global USE_GTK, USE_GST
258 USE_GTK=gtk
259 USE_GST=gst
260 init_option_parser(gtk, gst)
261
262 # installing the reactor could override our packager's import hooks ...
263 if installReactor:
264 from twisted.internet import gtk2reactor
265 try:
266 gtk2reactor.install(useGtk=gtk)
267 except RuntimeError, e:
268 safeprintf(sys.stderr, 'ERROR: %s\n', e)
269 sys.exit(1)
270 from twisted.internet import reactor
271
272 # ... so we install them again here to be safe
273 from flumotion.common import package
274 package.getPackager().install()
275
276 # this monkeypatched var exists to let reconnecting factories know
277 # when they should warn about a connection being closed, and when
278 # they shouldn't because the system is shutting down.
279 #
280 # there is no race condition here -- the reactor doesn't handle
281 # signals until it is run().
282 reactor.killed = False
283
284 def setkilled(killed):
285 reactor.killed = killed
286
287 reactor.addSystemEventTrigger('before', 'startup', setkilled, False)
288 reactor.addSystemEventTrigger('before', 'shutdown', setkilled, True)
289
290 from flumotion.twisted import reflect
291 from flumotion.common import errors
292 from flumotion.common import setup
293
294 setup.setup()
295
296 from flumotion.common import log
297 log.logTwisted()
298
299 main = reflect.namedAny(path)
300
301 wrapped = wrap_for_profiling(main)
302 wrapped.__name__ = main.__name__
303
304 try:
305 sys.exit(wrapped(sys.argv))
306 except (errors.FatalError, SystemError), e:
307 safeprintf(sys.stderr, 'ERROR: %s\n', e)
308 sys.exit(1)
309
| Trees | Indices | Help |
|---|
| Generated by Epydoc 3.0.1 on Mon May 11 00:19:53 2015 | http://epydoc.sourceforge.net |