def watch(conf): '''Set up file watchers''' from . import watcher events = { 'on_modified', 'on_created', 'on_deleted', 'on_moved', 'on_any_event' } for name, config in conf.items(): _key = cache_key('watch', config) if _key in _cache: watcher.watch(name, **_cache[_key]) continue if 'paths' not in config: app_log.error('watch:%s has no "paths"', name) continue if not set(config.keys()) & events: app_log.error('watch:%s has no events (on_modified, ...)', name) continue if not isinstance(config['paths'], (list, set, tuple)): config['paths'] = [config['paths']] for event in events: if event in config: if not callable(config[event]): config[event] = locate(config[event], modules=['gramex.transforms']) if not callable(config[event]): app_log.error('watch:%s.%s is not callable', name, event) config[event] = lambda event: None _cache[_key] = config watcher.watch(name, **_cache[_key])
def alert(conf): from . import scheduler _stop_all_tasks(info.alert) schedule_keys = 'minutes hours dates months weekdays years startup utc'.split( ) for name, alert in conf.items(): _key = cache_key('alert', alert) if _key in _cache: task = info.alert[name] = _cache[_key] task.call_later() continue app_log.info('Initialising alert: %s', name) schedule = {key: alert[key] for key in schedule_keys if key in alert} if 'thread' in alert: schedule['thread'] = alert['thread'] schedule['function'] = create_alert(name, alert) if schedule['function'] is not None: try: _cache[_key] = scheduler.Task(name, schedule, info.threadpool, ioloop=info._main_ioloop) info.alert[name] = _cache[_key] except Exception: app_log.exception('Failed to initialize alert: %s', name)
def email(conf): '''Set up email service''' for name, config in conf.items(): _key = cache_key('email', config) if _key in _cache: info.email[name] = _cache[_key] continue info.email[name] = _cache[_key] = SMTPMailer(**config)
def sms(conf): '''Set up SMS service''' for name, config in conf.items(): _key = cache_key('sms', config) if _key in _cache: info.sms[name] = _cache[_key] continue notifier_type = config.pop('type') if notifier_type not in sms_notifiers: raise ValueError('sms: %s: Unknown type: %s' % (name, notifier_type)) info.sms[name] = _cache[_key] = sms_notifiers[notifier_type](**config)
def schedule(conf): '''Set up the Gramex PeriodicCallback scheduler''' # Create tasks running on ioloop for the given schedule, store it in info.schedule from . import scheduler _stop_all_tasks(info.schedule) for name, sched in conf.items(): _key = cache_key('schedule', sched) if _key in _cache: task = info.schedule[name] = _cache[_key] task.call_later() continue try: app_log.info('Initialising schedule:%s', name) _cache[_key] = scheduler.Task(name, sched, info.threadpool, ioloop=info._main_ioloop) info.schedule[name] = _cache[_key] except Exception as e: app_log.exception(e)
def url(conf): '''Set up the tornado web app URL handlers''' handlers = [] # Sort the handlers in descending order of priority specs = sorted(conf.items(), key=_sort_url_patterns, reverse=True) for name, spec in specs: _key = cache_key('url', spec) if _key in _cache: handlers.append(_cache[_key]) continue if 'handler' not in spec: app_log.error('url: %s: no handler specified') continue app_log.debug('url: %s (%s) %s', name, spec.handler, spec.get('priority', '')) urlspec = AttrDict(spec) handler = locate(spec.handler, modules=['gramex.handlers']) if handler is None: app_log.error('url: %s: ignoring missing handler %s', name, spec.handler) continue # Create a subclass of the handler with additional attributes. class_vars = {'name': name, 'conf': spec} # If there's a cache section, get the cache method for use by BaseHandler if 'cache' in urlspec: class_vars['cache'] = _cache_generator(urlspec['cache'], name=name) else: class_vars['cache'] = None # PY27 type() requires the class name to be a string, not unicode urlspec.handler = type(str(spec.handler), (handler, ), class_vars) # If there's a setup method, call it to initialize the class kwargs = urlspec.get('kwargs', {}) if hasattr(handler, 'setup'): try: urlspec.handler.setup_default_kwargs() urlspec.handler.setup(**kwargs) except Exception: app_log.exception('url: %s: setup exception in handler %s', name, spec.handler) # Since we can't set up the handler, all requests must report the error instead class_vars['exc_info'] = sys.exc_info() error_handler = locate('SetupFailedHandler', modules=['gramex.handlers']) urlspec.handler = type(str(spec.handler), (error_handler, ), class_vars) urlspec.handler.setup(**kwargs) try: handler_entry = tornado.web.URLSpec( name=name, pattern=_url_normalize(urlspec.pattern), handler=urlspec.handler, kwargs=kwargs, ) except re.error: app_log.error('url: %s: pattern: %s is invalid', name, urlspec.pattern) continue except Exception: app_log.exception('url: %s: invalid', name) continue _cache[_key] = handler_entry handlers.append(handler_entry) info.app.clear_handlers() info.app.add_handlers('.*$', handlers)