Example #1
0
 def post(self, session: Session = None) -> Response:
     """ Manage server operations """
     data = request.json
     if data['operation'] == 'reload':
         try:
             self.manager.load_config(output_to_console=False)
         except YAMLError as e:
             if isinstance(e, MarkedYAMLError):
                 error: Dict[str, int] = {}
                 if e.problem is not None:
                     error.update({'reason': e.problem})
                 if e.context_mark is not None:
                     error.update(
                         {'line': e.context_mark.line, 'column': e.context_mark.column}
                     )
                 if e.problem_mark is not None:
                     error.update(
                         {'line': e.problem_mark.line, 'column': e.problem_mark.column}
                     )
                 raise APIError(message='Invalid YAML syntax', payload=error)
         except ConfigError as e:
             errors = []
             for er in e.errors:
                 errors.append({'error': er.message, 'config_path': er.json_pointer})
             raise APIError('Error loading config: %s' % e.args[0], payload={'errors': errors})
         response = 'Config successfully reloaded from disk'
     else:
         self.manager.shutdown(data.get('force'))
         response = 'Shutdown requested'
     return success_response(response)
Example #2
0
 def get(self, session=None):
     """ Reload Flexget config """
     log.info('Reloading config from disk.')
     try:
         self.manager.load_config(output_to_console=False)
     except YAMLError as e:
         if hasattr(e, 'problem') and hasattr(
                 e, 'context_mark') and hasattr(e, 'problem_mark'):
             error = {}
             if e.problem is not None:
                 error.update({'reason': e.problem})
             if e.context_mark is not None:
                 error.update({
                     'line': e.context_mark.line,
                     'column': e.context_mark.column
                 })
             if e.problem_mark is not None:
                 error.update({
                     'line': e.problem_mark.line,
                     'column': e.problem_mark.column
                 })
             raise APIError(message='Invalid YAML syntax', payload=error)
     except ValueError as e:
         errors = []
         for er in e.errors:
             errors.append({
                 'error': er.message,
                 'config_path': er.json_pointer
             })
         raise APIError('Error loading config: %s' % e.args[0],
                        payload={'errors': errors})
     return success_response('Config successfully reloaded from disk')
Example #3
0
    def post(self, session: Session = None) -> Response:
        """ Update config """
        config = {}
        data = request.json
        try:
            raw_config = base64.b64decode(data['raw_config'])
        except (TypeError, binascii.Error):
            raise BadRequest(message='payload was not a valid base64 encoded string')

        try:
            config = yaml.safe_load(raw_config)
        except YAMLError as e:
            if isinstance(e, MarkedYAMLError):
                error: Dict[str, int] = {}
                if e.problem is not None:
                    error.update({'reason': e.problem})
                if e.context_mark is not None:
                    error.update({'line': e.context_mark.line, 'column': e.context_mark.column})
                if e.problem_mark is not None:
                    error.update({'line': e.problem_mark.line, 'column': e.problem_mark.column})
                raise BadRequest(message='Invalid YAML syntax', payload=error)

        try:
            backup_path = self.manager.update_config(config)
        except ConfigError as e:
            errors = []
            for er in e.errors:
                errors.append({'error': er.message, 'config_path': er.json_pointer})
            raise BadRequest(
                message=f'Error loading config: {e.args[0]}', payload={'errors': errors}
            )

        try:
            self.manager.backup_config()
        except Exception as e:
            raise APIError(
                message='Failed to create config backup, config updated but NOT written to file',
                payload={'reason': str(e)},
            )

        try:
            with open(self.manager.config_path, 'w', encoding='utf-8') as f:
                f.write(raw_config.decode('utf-8').replace('\r\n', '\n'))
        except Exception as e:
            raise APIError(
                message='Failed to write new config to file, please load from backup',
                payload={'reason': str(e), 'backup_path': backup_path},
            )
        return success_response('Config was loaded and successfully updated to file')
Example #4
0
    def post(self, session=None):
        """ Add new task """
        data = request.json

        task_name = data['name']

        if task_name in self.manager.user_config.get('tasks', {}):
            raise Conflict('task already exists')

        if 'tasks' not in self.manager.user_config:
            self.manager.user_config['tasks'] = {}
        if 'tasks' not in self.manager.config:
            self.manager.config['tasks'] = {}

        task_schema_processed = copy.deepcopy(data)
        errors = process_config(
            task_schema_processed, schema=task_input_schema.__schema__, set_defaults=True
        )

        if errors:
            raise APIError('problem loading config, raise a BUG as this should not happen!')

        self.manager.user_config['tasks'][task_name] = data['config']
        self.manager.config['tasks'][task_name] = task_schema_processed['config']

        self.manager.save_config()
        self.manager.config_changed()
        rsp = jsonify({'name': task_name, 'config': self.manager.user_config['tasks'][task_name]})
        rsp.status_code = 201
        return rsp
Example #5
0
    def post(self, session=None):
        """ Add new schedule """
        data = request.json

        schedules = self.manager.config.get('schedules', [])

        # Checks for boolean config
        if schedules is True:
            schedules = DEFAULT_SCHEDULES
        elif schedules is False:
            raise Conflict('Schedules are disables in config')

        self.manager.config['schedules'] = schedules

        self.manager.config['schedules'].append(data)
        schedules = self.manager.config['schedules']
        new_schedule, _ = _schedule_by_id(id(data), schedules)

        if not new_schedule:
            raise APIError('schedule went missing after add')

        self.manager.save_config()
        self.manager.config_changed()
        resp = jsonify(new_schedule)
        resp.status_code = 201
        return resp
Example #6
0
 def get(self, session=None):
     """ Cache remote resources """
     args = cached_parser.parse_args()
     url = args.get('url')
     force = args.get('force')
     try:
         file_path, mime_type = cached_resource(url, self.manager.config_base, force=force)
     except RequestException as e:
         raise BadRequest('Request Error: {}'.format(e.args[0]))
     except OSError as e:
         raise APIError('Error: {}'.format(str(e)))
     return send_file(file_path, mimetype=mime_type)
Example #7
0
    def put(self, task, session: Session = None) -> Response:
        """ Update tasks config """
        data = request.json

        new_task_name = data['name']

        if task not in self.manager.user_config.get('tasks', {}):
            raise NotFoundError(f'task `{task}` not found')

        if 'tasks' not in self.manager.user_config:
            self.manager.user_config['tasks'] = {}
        if 'tasks' not in self.manager.config:
            self.manager.config['tasks'] = {}

        if task != new_task_name:
            # Rename task
            if new_task_name in self.manager.user_config['tasks']:
                raise BadRequest('cannot rename task as it already exist')

            del self.manager.user_config['tasks'][task]
            del self.manager.config['tasks'][task]

        # Process the task config
        task_schema_processed = copy.deepcopy(data)
        errors = process_config(task_schema_processed,
                                schema=task_return_schema.__schema__,
                                set_defaults=True)

        if errors:
            raise APIError(
                'problem loading config, raise a BUG as this should not happen!'
            )

        self.manager.user_config['tasks'][new_task_name] = data['config']
        self.manager.config['tasks'][new_task_name] = task_schema_processed[
            'config']

        self.manager.save_config()
        self.manager.config_changed()

        rsp = jsonify({
            'name':
            new_task_name,
            'config':
            self.manager.user_config['tasks'][new_task_name]
        })
        rsp.status_code = 200
        return rsp