1
2 """
3 Plugin for our configuring the OMERO.web installation
4
5 Copyright 2009 University of Dundee. All rights reserved.
6 Use is subject to license terms supplied in LICENSE.txt
7
8 """
9
10 from exceptions import Exception
11 from omero.cli import BaseControl, CLI
12 import omero.java
13 import time
14 import sys
15 import os
16
17 HELP="""omero web settings
18
19 OMERO.web tools:
20
21 settings - Configuration for web
22
23 For advance use:
24 custom_settings - Creates only custom_settings.py
25 server - Set to 'default' for django internal webserver
26 or 'fastcgi'
27 config - output a config template for server (only 'nginx'
28 for the moment)
29 syncmedia - creates needed symlinks for static media files
30 enableapp - TODO: document
31 gateway
32 test
33 seleniumtest
34 call
35
36 """
38
72
73 - def help(self, args = None):
75
76 - def _setup_server(self, email_server=None, app_host=None, sender_address=None, smtp_server=None):
77 settings = dict()
78
79 while not app_host or len(app_host) < 1:
80 app_host = self.ctx.input("Please enter the domain you want to run OMERO.web on (http://www.domain.com:8000/):")
81 if app_host == None or app_host == "":
82 self.ctx.err("Domain cannot be empty")
83 continue
84 settings["APPLICATION_HOST"] = app_host
85 break
86
87 while not sender_address or len(sender_address) < 1 :
88 sender_address = self.ctx.input("Please enter the Email address you want to send from (omero_admin@example.com): ")
89 if sender_address == None or sender_address == "":
90 self.ctx.err("Email cannot be empty")
91 continue
92 break
93
94 while not smtp_server or len(smtp_server) < 1 :
95 smtp_server = self.ctx.input("Please enter the SMTP server host you want to send from (smtp.example.com): ")
96 if smtp_server == None or smtp_server == "":
97 self.ctx.err("SMTP server host cannot be empty")
98 continue
99
100 smtp_port = self.ctx.input("Optional: please enter the SMTP server port (default 25): ")
101 smtp_user = self.ctx.input("Optional: Please enter the SMTP server username: ")
102 smtp_password = self.ctx.input("Optional: Password: ", hidden=True)
103 smtp_tls = self.ctx.input("Optional: TSL? (yes/no): ")
104 if smtp_tls == "yes":
105 smtp_tls = True
106 else:
107 smtp_tls = False
108 break
109
110 settings["SERVER_EMAIL"] = sender_address
111 settings["EMAIL_HOST"] = smtp_server
112
113 if smtp_port:
114 settings["EMAIL_PORT"] = smtp_port
115 if smtp_user:
116 settings["EMAIL_HOST_USER"] = smtp_user
117 if smtp_password:
118 settings["EMAIL_HOST_PASSWORD"] = smtp_password
119 if smtp_tls:
120 settings["EMAIL_USE_TLS"] = smtp_tls
121
122 return settings
123
125 output = open(location, 'w')
126
127 try:
128 output.write("""#!/usr/bin/env python
129 #
130 # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
131 # # Django custom settings for OMERO.web project. # #
132 # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
133 #
134 #
135 # Copyright (c) 2009 University of Dundee.
136 #
137 # This program is free software: you can redistribute it and/or modify
138 # it under the terms of the GNU Affero General Public License as
139 # published by the Free Software Foundation, either version 3 of the
140 # License, or (at your option) any later version.
141 #
142 # This program is distributed in the hope that it will be useful,
143 # but WITHOUT ANY WARRANTY; without even the implied warranty of
144 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
145 # GNU Affero General Public License for more details.
146 #
147 # You should have received a copy of the GNU Affero General Public License
148 # along with this program. If not, see <http://www.gnu.org/licenses/>.
149 #
150 # Author: Aleksandra Tarkowska <A(dot)Tarkowska(at)dundee(dot)ac(dot)uk>, 2008.
151 #
152 # Version: 1.0
153
154 # Notification
155 # Application allows to notify user about new shares
156
157 SERVER_LIST = (
158 ('localhost', 4064, 'omero'),
159 )
160
161 ADMINS = (
162 # ('Name', 'email'),
163 )
164
165 """)
166 if settings.has_key('SERVER_EMAIL'):
167 output.write("""SERVER_EMAIL = '%s'
168 """ % settings["SERVER_EMAIL"])
169 if settings.has_key('EMAIL_HOST'):
170 output.write("""EMAIL_HOST = '%s'
171 """ % settings["EMAIL_HOST"])
172 if settings.has_key('EMAIL_PORT'):
173 output.write("""EMAIL_PORT = %s
174 """ % settings["EMAIL_PORT"])
175 if settings.has_key('EMAIL_HOST_USER'):
176 output.write("""EMAIL_HOST_USER = '%s'
177 """ % settings["EMAIL_HOST_USER"])
178 if settings.has_key('EMAIL_HOST_PASSWORD'):
179 output.write("""EMAIL_HOST_PASSWORD = '%s'
180 """ % settings["EMAIL_HOST_PASSWORD"])
181 if settings.has_key('EMAIL_USE_TLS'):
182 if settings["EMAIL_USE_TLS"]:
183 output.write("""EMAIL_USE_TLS = 'True'
184 """)
185 else:
186 output.write("""EMAIL_USE_TLS = 'False'
187 """)
188
189 output.write("""
190 APPLICATION_HOST='%s'
191 """ % settings["APPLICATION_HOST"])
192 finally:
193 output.flush()
194 output.close()
195
196 self.ctx.out("Saved to " + location)
197 sys.path_importer_cache.pop(self.ctx.dir / "var" / "lib", None)
198 self.ctx.out("PYTHONPATH updated.")
199
201 while answer != "yes" and answer != "no":
202 answer = self.ctx.input("%s already exist. Do you want to ovewrite it? (yes/no)" % file_name)
203 if answer != "yes" and answer != "no":
204 self.ctx.err("Answer yes or no")
205 continue
206 break
207 return answer
208
210 location = self.ctx.dir / "var" / "lib" / "custom_settings.py"
211
212 if location.exists():
213 if self._get_yes_or_no("%s" % location) == 'no':
214 if hasattr(args, "no_exit") and args.no_exit:
215 return
216 else:
217 sys.exit()
218 else:
219 self.ctx.out("You just installed OMERO, which means you didn't have settings configured in OMERO.web.")
220
221 if not os.path.exists(self.ctx.dir / "var" / "lib"):
222 os.mkdir(self.ctx.dir / "var" / "lib")
223
224 settings = self._setup_server()
225 self._update_settings(location, settings)
226
234
236 if not args.server:
237 self.ctx.out("OMERO.web application is served by 'default'")
238 else:
239 location = self.ctx.dir / "var" / "lib" / "custom_settings.py"
240 settings = file(location, 'rb').read().split('\n')
241 if settings[-1] == '':
242 settings = settings[:-1]
243 cserver = 'default'
244 for l in settings:
245 if l.startswith('APPLICATION_SERVER'):
246 cserver = l.split('=')[-1].strip().replace("'",'').replace('"','')
247 server = args.server
248 if server == cserver:
249 self.ctx.out("OMERO.web was already configured to be served by '%s'" % server)
250 elif server in ('default', 'fastcgi'):
251 if server == 'fastcgi':
252 import flup
253 out = file(location, 'wb')
254 wrote = False
255 for l in settings:
256 if l.startswith('APPLICATION_SERVER'):
257 wrote = True
258 out.write("APPLICATION_SERVER = '%s'\n" % server)
259 else:
260 out.write(l + '\n')
261 if not wrote:
262 out.write("APPLICATION_SERVER = '%s'\n" % server)
263 self.ctx.out("OMERO.web has been configured to be served by '%s'" % server)
264 else:
265 self.ctx.err("Unknown server '%s'" % server)
266
268 if not args.type:
269 self.ctx.out("Available configuration helpers:\n - nginx\n")
270 else:
271 from omeroweb.settings import APPLICATION_HOST
272 host = APPLICATION_HOST.split(':')
273 try:
274 port = int(host[-1])
275 except ValueError:
276 port = 8000
277 server = args.type
278 if server == "nginx":
279 c = file(self.ctx.dir / "etc" / "nginx.conf.template").read()
280 d = {
281 "ROOT":self.ctx.dir,
282 "OMEROWEBROOT":self.ctx.dir / "lib" / "python" / "omeroweb",
283 "HTTPPORT":port,
284 }
285 self.ctx.out(c % d)
286
306
308 from omeroweb.settings import INSTALLED_APPS
309 location = self.ctx.dir / "lib" / "python" / "omeroweb"
310 if not args.appname:
311 apps = [x.name for x in filter(lambda x: x.isdir() and (x / 'scripts' / 'enable.py').exists(), location.listdir())]
312 iapps = map(lambda x: x.startswith('omeroweb.') and x[9:] or x, INSTALLED_APPS)
313 apps = filter(lambda x: x not in iapps, apps)
314 self.ctx.out('[enableapp] available apps:\n - ' + '\n - '.join(apps) + '\n')
315 else:
316 for app in args.appname:
317 args = ["python", location / app / "scripts" / "enable.py"]
318 rv = self.ctx.call(args, cwd = location)
319 if rv != 0:
320 self.ctx.die(121, "Failed to enable '%s'.\n" % app)
321 else:
322 self.ctx.out("App '%s' was enabled\n" % app)
323 args = ["python", "manage.py", "syncdb", "--noinput"]
324 rv = self.ctx.call(args, cwd = location)
325 self.syncmedia(None)
326
328 location = self.ctx.dir / "lib" / "python" / "omeroweb"
329 args = ["python", "-i", location / "../omero/gateway/scripts/dbhelpers.py"]
330 os.environ['ICE_CONFIG'] = self.ctx.dir / "etc" / "ice.config"
331 os.environ['PATH'] = os.environ.get('PATH', '.') + ':' + self.ctx.dir / 'bin'
332 os.environ['DJANGO_SETTINGS_MODULE'] = os.environ.get('DJANGO_SETTINGS_MODULE', 'omeroweb.settings')
333 rv = self.ctx.call(args, cwd = location)
334
335 - def test(self, args):
336 location = self.ctx.dir / "lib" / "python" / "omeroweb"
337 cargs = ["coverage","-x", "manage.py", "test"]
338 if args.arg:
339 cargs.append(args.arg)
340 os.environ['ICE_CONFIG'] = self.ctx.dir / "etc" / "ice.config"
341 os.environ['PATH'] = os.environ.get('PATH', '.') + ':' + self.ctx.dir / 'bin'
342 rv = self.ctx.call(cargs, cwd = location)
343
345 location = self.ctx.dir / "lib" / "python" / "omeroweb"
346 cargs = ["python", "seleniumtests.py"]
347 location = location / args.djangoapp / "tests"
348 print location
349 rv = self.ctx.call(cargs, cwd = location )
350
351 - def call (self, args):
352 try:
353 location = self.ctx.dir / "lib" / "python" / "omeroweb"
354 cargs = []
355 appname = args.appname
356 scriptname = args.scriptname.split(' ')
357 if len(scriptname) > 1:
358 cargs.append(scriptname[0])
359 scriptname = ' '.join(scriptname[1:])
360 else:
361 scriptname = scriptname[0]
362 cargs.extend([location / appname / "scripts" / scriptname] + args.arg)
363 print cargs
364 os.environ['DJANGO_SETTINGS_MODULE'] = 'omeroweb.settings'
365 os.environ['ICE_CONFIG'] = self.ctx.dir / "etc" / "ice.config"
366 os.environ['PATH'] = os.environ.get('PATH', '.') + ':' + self.ctx.dir / 'bin'
367 rv = self.ctx.call(cargs, cwd = location)
368 except:
369 import traceback
370 print traceback.print_exc()
371
373 host = args.host is not None and args.host or "0.0.0.0"
374 port = args.port is not None and args.port or "8000"
375 link = ("%s:%s" % (host, port))
376 location = self.ctx.dir / "lib" / "python" / "omeroweb"
377 self.ctx.out("Starting django development webserver... \n")
378 import omeroweb.settings as settings
379 deploy = getattr(settings, 'APPLICATION_SERVER', 'default')
380 if deploy == 'fastcgi':
381 cmd = "python manage.py runfcgi workdir=./"
382 cmd += " method=prefork socket=%(base)s/var/django_fcgi.sock"
383 cmd += " pidfile=%(base)s/var/django.pid daemonize=false"
384 cmd += " maxchildren=5 minspare=1 maxspare=5 maxrequests=400"
385 django = (cmd % {'base': self.ctx.dir}).split()+list(args.arg)
386 else:
387 django = ["python","manage.py","runserver", link, "--noreload"]
388 rv = self.ctx.call(django, cwd = location)
389
390 try:
391 register("web", WebControl, HELP)
392 except NameError:
393 if __name__ == "__main__":
394 cli = CLI()
395 cli.register("web", WebControl, HELP)
396 cli.invoke(sys.argv[1:])
397