def match(self): """Match observables against Yeti's intelligence repository. Takes an array of observables, expands them and tries to match them against specific indicators or known observables. To "expand" an observable means to enrich the query. For instance, if the arrays of observables contains the URL ``http://google.com``, the "expanded" observable array will also include the hostname ``google.com``. :<json [string] observables: An array of observables to be analyzed :>json [Entity] entities: Related ``Entity`` objects :>json [Observable] known: ``Observable`` objects that are already present in database :>json [Indicator] matches: ``Indicators`` that matched observables :>json Observable matches[].observable: The ``Observable`` object that matched the ``Indicator`` :>json string unknown: Array of observable strings that didn't match any ``Indicators`` and are unknown to Yeti """ params = request.json observables = params.pop("observables", []) fetch_neighbors = params.pop("fetch_neighbors", True) add_unknown = bool(params.pop("add_unknown", False)) if add_unknown and current_user.has_permission("observable", "write"): for o in observables: Observable.add_text(o) data = match_observables( observables, save_matches=add_unknown and current_user.has_permission("observable", "write"), fetch_neighbors=fetch_neighbors, ) return render(data)
def get_site_edit_form(site_name): # Needed to be able to change the form definition class _SiteEditForm(SiteEditForm): pass site = get_db_site(site_name) if not site: abort(404) # Load template from backend and populate form fields based on template template_vars = [] if site.template_content: template_string = gzip.decompress( base64.b64decode(site.template_content)) template_vars = get_template_string_variables(template_string) populate_form_from_template(_SiteEditForm, template_vars) # Load data from backend into form data = {'template_name': site.template_name} if site.template_parameters: data.update(json.loads(site.template_parameters)) if current_user.has_permission('site_update'): _SiteEditForm.update = SubmitField('Update Site') if current_user.has_permission('site_delete'): _SiteEditForm.commit = SubmitField('Commit to Conductor') if current_user.has_permission('site_delete'): _SiteEditForm.delete = SubmitField('Delete Site') form = _SiteEditForm(data=data) return form, template_vars
def user_scan(user_id): """Queue a job to check the solo MMR of the selected user. Args: user_id: user ID of the `User` to scan. Returns: Redirection to the user detail page. """ if current_user.id == user_id or current_user.has_permission( constants.PERMISSION_ADMIN): target_user = User.query.filter_by(id=user_id).first() if target_user is not None: if target_user.profile_scan_info is None: target_user.profile_scan_info = ProfileScanInfo( target_user) if current_user.has_permission(constants.PERMISSION_ADMIN) or \ datetime.utcnow() - target_user.profile_scan_info.last_scan_request > timedelta(minutes=5): target_user.profile_scan_info.last_scan_request = datetime.utcnow( ) db.session.commit() job_queue.produce(JobScan(steam_id=target_user.id)) return redirect(url_for('user_blueprint.user', steam_id=user_id))
def match(self): """Match observables against Yeti's intelligence repository. Takes an array of observables, expands them and tries to match them against specific indicators or known observables. To "expand" an observable means to enrich the query. For instance, if the arrays of observables contains the URL ``http://google.com``, the "expanded" observable array will also include the hostname ``google.com``. :<json [string] observables: An array of observables to be analyzed :>json [Entity] entities: Related ``Entity`` objects :>json [Observable] known: ``Observable`` objects that are already present in database :>json [Indicator] matches: ``Indicators`` that matched observables :>json Observable matches[].observable: The ``Observable`` object that matched the ``Indicator`` :>json string unknown: Array of observable strings that didn't match any ``Indicators`` and are unknown to Yeti """ params = request.json observables = params.pop('observables', []) fetch_neighbors = params.pop('fetch_neighbors', True) add_unknown = bool(params.pop('add_unknown', False)) if add_unknown and current_user.has_permission('observable', 'write'): for o in observables: Observable.add_text(o) data = match_observables(observables, save_matches=add_unknown and current_user.has_permission('observable', 'write'), fetch_neighbors=fetch_neighbors) return render(data)
def has_permission_to_edit_brief(brief=None): is_permitted = (current_user.has_permission('create_drafts') or current_user.has_permission('publish_opportunities')) if brief and brief_can_be_edited(brief): return is_permitted else: return is_permitted
def decorated_function(*args, **kwargs): if current_user.has_permission(permission): return f(*args, **kwargs) if current_user.has_permission('AUTH-PERMISSION_MISSING'): flash( _('Missing permission %(permission)s', permission=b(permission)), 'warning') abort(403)
def main(): if current_user.is_anonymous: return redirect(url_for('users.login', next=url_for('.main'))) if current_user.has_permission('volunteer:admin'): return redirect(url_for('.emailvolunteers')) if current_user.has_permission('admin'): return redirect(url_for('.emailvolunteers')) abort(404)
def main(): if current_user.is_anonymous: return redirect(url_for("users.login", next=url_for(".main"))) if current_user.has_permission("volunteer:admin"): return redirect(url_for(".emailvolunteers")) if current_user.has_permission("admin"): return redirect(url_for(".emailvolunteers")) abort(404)
def main(): if current_user.is_anonymous: return redirect(url_for('users.login', next=url_for('.main'))) if current_user.has_permission('cfp_admin'): return redirect(url_for('.proposals')) if current_user.has_permission('cfp_anonymiser'): return redirect(url_for('.anonymisation')) if current_user.has_permission('cfp_reviewer'): return redirect(url_for('.review_list')) abort(404)
def on_leave(data): try: deploymentId = data['deploymentId'] except KeyError: return if current_user.has_permission('supervisor'): join_room(f'{deploymentId}-supervisor') if current_user.has_permission('view_all_incidents'): leave_room(f'{deploymentId}-all') else: leave_room(f'{deploymentId}-{current_user.id}') if f'{deploymentId}-{current_user.id}' in assigned_rooms: assigned_rooms.remove(f'{deploymentId}-{current_user.id}') emit('ignoring_room', {'room': f'{deploymentId}-{current_user.id}'}, namespace='/', room=f'{deploymentId}-{current_user.id}', include_self=False)
def main(): if current_user.is_anonymous: return redirect(url_for("users.login", next=url_for(".main"))) if current_user.has_permission("cfp_admin"): return redirect(url_for(".proposals")) if current_user.has_permission("cfp_anonymiser"): return redirect(url_for(".anonymisation")) if current_user.has_permission("cfp_reviewer"): return redirect(url_for(".review_list")) abort(404)
def client_config(): if not current_user.is_api_user() and current_user.is_authenticated: client_config = { 'newVersionAvailable': bool(get_latest_version()), 'version': __version__ } else: client_config = {} if current_user.has_permission('admin') and current_org.get_setting('beacon_consent') is None: client_config['showBeaconConsentMessage'] = True defaults = { 'allowScriptsInUserInput': settings.ALLOW_SCRIPTS_IN_USER_INPUT, 'showPermissionsControl': current_org.get_setting("feature_show_permissions_control"), 'allowCustomJSVisualizations': settings.FEATURE_ALLOW_CUSTOM_JS_VISUALIZATIONS, 'autoPublishNamedQueries': settings.FEATURE_AUTO_PUBLISH_NAMED_QUERIES, 'extendedAlertOptions': settings.FEATURE_EXTENDED_ALERT_OPTIONS, 'mailSettingsMissing': not settings.email_server_is_configured(), 'dashboardRefreshIntervals': settings.DASHBOARD_REFRESH_INTERVALS, 'queryRefreshIntervals': settings.QUERY_REFRESH_INTERVALS, 'googleLoginEnabled': settings.GOOGLE_OAUTH_ENABLED, 'pageSize': settings.PAGE_SIZE, 'pageSizeOptions': settings.PAGE_SIZE_OPTIONS, 'tableCellMaxJSONSize': settings.TABLE_CELL_MAX_JSON_SIZE, } client_config.update(defaults) client_config.update({ 'basePath': base_href() }) client_config.update(date_time_format_config()) client_config.update(number_format_config()) return client_config
def before_request(self, *args, **kwargs): redir = UIView.before_request(self, *args, **kwargs) if redir: return redir if not current_user.has_permission('configs'): abort(404)
def add_comment(self, id): if comments_enabled(): f = File(get_or_404(current_user.files, _id=id)) if current_user.has_permission('add_probable_name'): probable_name = request.form.get('probable_name') else: probable_name = None comment = request.form.get('comment') analysis_id = request.form.get('analysis') notify = request.form.get('notify') if comment: # If there is an analysis ID, make sure it is accessible if analysis_id: get_or_404(current_user.analyses, _id=analysis_id) f.add_comment(current_user['_id'], comment, analysis_id, probable_name) if notify: self.notify_new_comment(f, analysis_id, current_user['_id'], comment) else: flash('Comment should not be empty', 'danger') return redirect(request.referrer)
def reset(what): if not current_user.has_permission('reset.{}'.format(what)): abort(403) form = ResetForm(request.form) user = User.objects(name=form.who.data).first() if user is None: abort(401) if form.validate(): if what == 'password': password = ''.join(random.choice('0123456789abcdefghijklmnopqrstuvxyzABCDEFGHIJKLMNOPQRSTUVWXYZ') for i in range(16)) user.hash = bcrypt.hashpw(password, bcrypt.gensalt()) user.save() return render_template('profile_reset_password_successful.html', user=user, password=password) elif what == 'tfa': user.tfa = False user.tfa_secret = '' user.save() return render_template('profile_reset_tfa_successful.html', user=user) else: abort(401) flash('Error in reset form. Make sure you are typing the confirmation token correctly.', category='alert') return redirect(user.get_profile_url()), 303
def wrapped(*args, **kwargs): if not current_user.has_permission(permission): raise Unauthorized( "The current user requires the '{}' permission.".format( str(permission.name))) r = f(*args, **kwargs) return r
def post(self, id): obs = self.objectmanager.objects.get(id=id) j = request.json if not current_user.has_permission('observable', 'tag') and 'tags' in j: abort(401) return render(self._modify_observable(obs, request.json))
def division_permissions(division_id, permission): division = Division.query.get_or_404(division_id) if not current_user.admin and not \ current_user.has_permission(PermissionType.admin, division): abort(403) permission = PermissionType.from_string(permission) # Can't use normal Entity JSON encoder as it doesn't include the # authentication source or their type (explicitly. Ain't nobody got time # for parsing the entity type out of the href). entities = [] for entity in map(lambda p: p.entity, division.permissions[permission]): entity_info = { u'name': entity.name, u'id': entity.id, u'source': str(entity.authmethod), } if hasattr(entity, u'users'): entity_info[u'type'] = u'Group' entity_info[u'length'] = len(entity.users) else: entity_info[u'type'] = u'User' entities.append(entity_info) return jsonify(entities=entities, name=permission.name, description=permission.description)
def get_work_order_links(brief): links = [] old_work_order_creator = use_old_work_order_creator(brief.published_at) has_permission = current_user.has_permission('create_work_orders') permission_needed = None if has_permission else 'create_work_orders' # No need for green ticks to indicate completion if brief.work_order: if old_work_order_creator: links.append( build_brief_link( False, get_path_for_brief_link(brief, '/work-orders/{work_order_id}'), 'Edit work order', permission_needed)) else: links.append( build_brief_link(True, '/2/buyer-award/{}'.format(brief.id), 'Download work order', permission_needed)) else: if old_work_order_creator: start_work_order_path = (get_path_for_brief_link( brief, '{path}/work-orders/create') if brief.status == 'closed' else None) links.append( build_brief_link(False, start_work_order_path, 'Start a work order', permission_needed)) else: links.append( build_brief_link(False, '/2/buyer-award/{}'.format(brief.id), 'Download work order', permission_needed)) return links
def division_permissions(division_id, permission): division = Division.query.get_or_404(division_id) if not current_user.admin and not \ current_user.has_permission(PermissionType.admin, division): abort(403) permission = PermissionType.from_string(permission) # Can't use normal Entity JSON encoder as it doesn't include the # authentication source or their type (explicitly. Ain't nobody got time # for parsing the entity type out of the href). entities = [] for entity in map(lambda p: p.entity, division.permissions[permission]): entity_info = { u'name': entity.name, u'id': entity.id, u'source': str(entity.authmethod), } if hasattr(entity, u'users'): entity_info[u'type'] = u'Group' entity_info[u'length'] = len(entity.users) else: entity_info[u'type'] = u'User' entities.append(entity_info) return jsonify( entities=entities, name=permission.name, description=permission.description)
def index(): form = PostForm() show_followed = False if current_user.is_authenticated: show_followed = request.cookies.get('show_followed') if current_user.has_permission(Permission.WRITE) \ and form.validate_on_submit(): # current_user 由 Flask-Login 提供,和所有上下文环境变量一样 # 也是通过线程的代理对象实现,这个对象的表现类似用户对象 # 但实际上却是一个轻度包装,它包含了真正的用户对象 # 数据库需要真正的用户对象,因此需要调用 _get_current_object 方法 post = Post(body=form.body.data, author=current_user._get_current_object()) db.session.add(post) db.session.commit() return redirect(url_for('.index')) if show_followed: query = current_user.followed_posts else: query = Post.query page = request.args.get('page', default=1, type=int) pagination = query.order_by(Post.timestamp.desc()).paginate( page, per_page=current_app.config.get('POST_PER_PAGE'), error_out=False) posts = pagination.items name = session.get('name') or 'Stranger' return render_template('index.html', name=name, form=form, posts=posts, Permission=Permission, pagination=pagination, show_followed=show_followed)
def get_user_payment_or_abort(payment_id, provider=None, valid_states=None, allow_admin=False): try: payment = Payment.query.get(payment_id) except Exception as e: app.logger.warning("Exception %r getting payment %s", e, payment_id) abort(404) if not payment: app.logger.warning("Payment %s does not exist.", payment_id) abort(404) if not (payment.user == current_user or (allow_admin and current_user.has_permission("admin"))): app.logger.warning("User not allowed to access payment %s", payment_id) abort(404) if provider and payment.provider != provider: app.logger.warning("Payment %s is of type %s, not %s", payment.provider, provider) abort(404) if valid_states and payment.state not in valid_states: app.logger.warning("Payment %s is %s, not one of %s", payment_id, payment.state, valid_states) abort(404) return payment
def reset(what): if not current_user.has_permission('reset.{}'.format(what)): abort(403) form = ResetForm(request.form) user = User.objects(name=form.who.data).first() if user is None: abort(401) if form.validate(): if what == 'password': password = ''.join( random.choice( '0123456789abcdefghijklmnopqrstuvxyzABCDEFGHIJKLMNOPQRSTUVWXYZ' ) for i in range(16)) user.hash = bcrypt.hashpw(password, bcrypt.gensalt()) user.save() return render_template('profile_reset_password_successful.html', user=user, password=password) elif what == 'tfa': user.tfa = False user.tfa_secret = '' user.save() return render_template('profile_reset_tfa_successful.html', user=user) else: abort(401) flash( 'Error in reset form. Make sure you are typing the confirmation token correctly.', category='alert') return redirect(user.get_profile_url()), 303
def list_transformers(division_id, attribute=None): """API method to get a list of transformers for a division. :param division_id int: the ID of the division to look up :param attribute str: a specific attribute to look up. Optional. :return: JSON """ division = Division.query.get_or_404(division_id) if not current_user.admin and not \ current_user.has_permission(PermissionType.admin, division): abort(403) if attribute is None: attrs = six.iterkeys(current_app.url_transformers) else: attrs = (attribute,) choices = {} for attr in attrs: raw_choices = transformer_choices(attr) current = division.transformers.get(attr, None) if current is not None: choices[attr] = \ [(c[0], c[1], c[1] == current.name) for c in raw_choices] else: choices[attr] = \ [(c[0], c[1], False) for c in raw_choices] return jsonify(choices)
def home(): app.logger.info('Here I am') if current_user.has_permission('volunteering'): return redirect(url_for('.schedule')) return redirect(url_for('.sign_up'))
def list_entities(): """Return a JSON object with a list of all of the specified entity type. Example output:: { entities: [ {name: 'Bar', id: 1, source: 'Auth Source', type: 'User'}, {name: 'Foo', id: 0, source: 'Another Auth Source', type: 'Group'}, {name: 'Baz', id: 20, source: 'Auth Source', type: 'Group'} ] } This method is only accesible to administrators. :param str entity_type: Either ``'user'`` or ``'group'``. """ if not current_user.admin and not \ current_user.has_permission(PermissionType.admin): abort(403) user_query = db.session.query(User.id, User.name, User.authmethod) group_query = db.session.query(Group.id, Group.name, Group.authmethod) users = map(lambda e: { u'id': e.id, u'name': e.name, u'type': u'User', u'source': e.authmethod}, user_query) groups = map(lambda e: { u'id': e.id, u'name': e.name, u'type': u'Group', u'source': e.authmethod}, group_query) return jsonify(entities=chain(users, groups))
def blog(id): if id is None: abort(404) blog = Blog.query.filter_by(id=int(id)).first() if blog is None: abort(404) form = CommentForm() if current_user.has_permission(Permission.COMMENT): if form.validate_on_submit(): comment = Comment() comment.blog_id = blog.id comment.author_id = current_user.id comment.body = form.comment.data comment.disabled = False db.session.add(comment) db.session.commit() return redirect(url_for('main.blog', id=blog.id)) # comments = Comment.query.filter_by(blog_id = blog.id).all() page = request.args.get('page', type=int, default=1) pagination = blog.comments.order_by(Comment.time.desc()).paginate( page, 3, False) comments = pagination.items return render_template('main/blog.html', blog=blog, form=form, comments=comments, pagination=pagination)
def widget(data): try: target = widgets[data['id']] except KeyError: # Widget is out of date. Force client reload send_message("Interface out of date; reloading", "warning") sleep(1) emit('reload') return if current_user.has_permission(target[3]): if target[0] == 'method': name = target[1].__name__ app.logger.info("({}) Execute {} on {} with config {}".format( current_user.username, name, target[3].name, target[2])) func = target[1] args = target[2] try: if target[3].driver.noserialize or type( target[3]) is MultiDevice: func(**args) else: run(func, **args) except Exception as e: app.logger.error("Error running {}: {}".format(name, str(e))) send_message("Error running \"{}\"!".format(name), 'danger') else: send_message("Successfully ran \"{}\".".format(name), 'success') elif target[0] == 'action': app.logger.info("({}) Execute action {}".format( current_user.username, target[1])) send_message("Executing action \"{}\"".format(target[1])) target[1].run() else: disconnect()
def get_request_details(request_id=None, srp_request=None): """Handles responding to all of the :py:class:`~.models.Request` detail functions. The various modifier functions all depend on this function to create the actual response content. Only one of the arguments is required. The ``srp_request`` argument is a conveniece to other functions calling this function that have already retrieved the request. :param int request_id: the ID of the request. :param srp_request: the request. :type srp_request: :py:class:`~.models.Request` """ if srp_request is None: srp_request = Request.query.get_or_404(request_id) # A user should always be able to access their own requests, but others # need fresh sessions. if current_user != srp_request.submitter and not login_fresh(): return login_manager.needs_refresh() # Different templates are used for different roles if current_user.has_permission(PermissionType.review, srp_request.division): template = 'request_review.html' elif current_user.has_permission(PermissionType.pay, srp_request.division): template = 'request_pay.html' elif current_user == srp_request.submitter or current_user.has_permission( PermissionType.audit): template = 'request_detail.html' else: abort(403) if request.is_json or request.is_xhr: return jsonify(**srp_request._json(True)) if request.is_xml: return xmlify('request.xml', srp_request=srp_request) return render_template( template, srp_request=srp_request, modifier_form=ModifierForm(formdata=None), payout_form=PayoutForm(formdata=None), action_form=ActionForm(formdata=None), void_form=VoidModifierForm(formdata=None), details_form=ChangeDetailsForm(formdata=None, obj=srp_request), note_form=AddNote(formdata=None), # TRANS: Title for the page showing the details about a single # TRANS: SRP request. title=gettext(u"Request #%(request_id)s", request_id=srp_request.id))
def wrapped(*args, **kwargs): if has_permission and check_device: raise AuthPluginMisuseError( "Cannot provide both `has_permission` and `check_device` to decorator." ) if current_user.is_authenticated: if has_permission and current_user.has_permission( group=has_permission): return f(*args, **kwargs) elif check_device: device = get_device(args[0]['device'].replace('-', ' ')) if current_user.has_permission(device): kwargs['device'] = device return f(*args, **kwargs) elif not has_permission and not check_device: return f(*args, **kwargs) disconnect()
def dispatch_request(self, filters='', **kwargs): if not current_user.has_permission(self.permissions): abort(403) else: return super(PermissionRequestListing, self).dispatch_request( filters, title=gettext(self.title), **kwargs)
def get_request_details(request_id=None, srp_request=None): """Handles responding to all of the :py:class:`~.models.Request` detail functions. The various modifier functions all depend on this function to create the actual response content. Only one of the arguments is required. The ``srp_request`` argument is a conveniece to other functions calling this function that have already retrieved the request. :param int request_id: the ID of the request. :param srp_request: the request. :type srp_request: :py:class:`~.models.Request` """ if srp_request is None: srp_request = Request.query.get_or_404(request_id) # A user should always be able to access their own requests, but others # need fresh sessions. if current_user != srp_request.submitter and not login_fresh(): return login_manager.needs_refresh() # Different templates are used for different roles if current_user.has_permission(PermissionType.review, srp_request.division): template = 'request_review.html' elif current_user.has_permission(PermissionType.pay, srp_request.division): template = 'request_pay.html' elif current_user == srp_request.submitter or current_user.has_permission( PermissionType.audit): template = 'request_detail.html' else: abort(403) if request.is_json or request.is_xhr: return jsonify(srp_request._json(True)) if request.is_xml: return xmlify('request.xml', srp_request=srp_request) return render_template(template, srp_request=srp_request, modifier_form=ModifierForm(formdata=None), payout_form=PayoutForm(formdata=None), action_form=ActionForm(formdata=None), void_form=VoidModifierForm(formdata=None), details_form=ChangeDetailsForm(formdata=None, obj=srp_request), note_form=AddNote(formdata=None), # TRANS: Title for the page showing the details about a single # TRANS: SRP request. title=gettext(u"Request #%(request_id)s", request_id=srp_request.id))
def dispatch_request(self, filters='', **kwargs): if not current_user.has_permission(self.permissions): abort(403) else: return super(PermissionRequestListing, self).dispatch_request(filters, title=gettext(self.title), **kwargs)
def index(self): if request.method == "POST": lines = [] obs = {} if request.files.get("bulk-file"): # request files lines = request.files.get("bulk-file").readlines() else: lines = request.form["bulk-text"].split("\n") invalid_observables = 0 if bool(request.form.get("add", False)) and current_user.has_permission( "observable", "write" ): tags = request.form.get("tags", "").split(",") for l in lines: try: txt = l.strip() if txt: if ( request.form["force-type"] and request.form["force-type"] in globals() and issubclass( globals()[request.form["force-type"]], Observable ) ): print(globals()[request.form["force-type"]]) o = globals()[request.form["force-type"]].get_or_create( value=txt ) else: o = Observable.add_text(txt) o.tag(tags) obs[o.value] = o except (ObservableValidationError, ValueError) as e: logging.error("Error validating {}: {}".format(txt, e)) invalid_observables += 1 continue else: for l in lines: obs[l.strip()] = l, None if len(obs) > 0: data = match_observables(obs.keys()) userLogger.info( "User %s add observable : value=%s", current_user.username, data ) return render_template("observable/search_results.html", data=data) else: if invalid_observables: flash( "Type guessing failed for {} observables. Try setting it manually.".format( invalid_observables ), "danger", ) return render_template("observable/search.html") return render_template("observable/search.html")
def clean_objects(instances, filters): for permission in filters: if permission != "": if not current_user.has_permission(permission): instances = remove_fields(instances, filters[permission]) else: instances = remove_fields(instances, filters[permission]) return instances
def role_admin_required(f, *args, **kwargs): """Check that current user has permissions to be RoleAdmin for role.id that is first entry in args""" if current_user.is_authenticated: if int(args[0]) in [ ra.role_id for ra in current_user.volunteer_admin_roles ] or current_user.has_permission("volunteer:admin"): return f(*args, **kwargs) abort(404) return app.login_manager.unauthorized()
def submit_request(): """Submit a :py:class:`~.models.Request`\. Displays a form for submitting a request and then processes the submitted information. Verifies that the user has the appropriate permissions to submit a request for the chosen division and that the killmail URL given is valid. Also enforces that the user submitting this requests controls the character from the killmail and prevents duplicate requests. """ if not current_user.has_permission(PermissionType.submit): abort(403) form = RequestForm() # Do it in here so we can access current_app (needs to be in an app # context) form.url.description = get_killmail_descriptions() form.details.description = current_app.config['SRP_DETAILS_DESCRIPTION'] # Create a list of divisions this user can submit to form.division.choices = current_user.submit_divisions() if len(form.division.choices) == 1: form.division.data = form.division.choices[0][0] if form.validate_on_submit(): mail = form.killmail # Prevent submitting other people's killmails pilot = Pilot.query.get(mail.pilot_id) if not pilot or pilot not in current_user.pilots: # TRANS: Error message shown when trying to submit a lossmail from # TRANS: A character not associated with your user account. flash(gettext(u"You can only submit killmails of characters you " u"control"), u'warning') return render_template('form.html', form=form) # Prevent duplicate killmails # The name 'request' is already used by Flask. # Hooray name collisions! srp_request = Request.query.get(mail.kill_id) if srp_request is None: division = Division.query.get(form.division.data) srp_request = Request(current_user, form.details.data, division, mail) srp_request.pilot = pilot db.session.add(srp_request) db.session.commit() return redirect(url_for('.get_request_details', request_id=srp_request.id)) else: # TRANS: Error message shown when trying to submit a killmail for # TRANS: SRP a second time. flash(gettext(u"This kill has already been submitted"), u'warning') return redirect(url_for('.get_request_details', request_id=srp_request.id)) return render_template('form.html', form=form, # TRANS: Title for the page showing the form for submitting SRP requests. title=gettext(u'Submit Request'))
def inner(*args, **kwargs): oname = object_name if not oname: oname = getattr(args[0], 'klass', getattr(args[0], 'objectmanager', args[0].__class__)).__name__.lower() # a user must have all permissions in order to be granted access for p in iterify(permissions): if not current_user.has_permission(oname, p): # improve this and make it redirect to login abort(401) else: return f(*args, **kwargs)
def dispatch_request(self, filters='', **kwargs): if hasattr(request, 'json_extended'): if isinstance(request.json_extended, bool): old_value = request.json_extended request.json_extended = defaultdict(lambda: old_value) else: request.json_extended = {} request.json_extended[Request] = True if not current_user.has_permission(self.permissions): abort(403) return super(PayoutListing, self).dispatch_request( filters, form=ActionForm())
def validate_division(form, field): division = Division.query.get(field.data) if division is None: # TRANS: Error message shown when trying to submit a request to a # TRANS: non-existant division. raise ValidationError(gettext(u"No division with ID '%(div_id)s'.", div_id=field.data)) if not current_user.has_permission(PermissionType.submit, division): # TRANS: Error message shown when trying to a submit a request to a # TRANS: division you do not have the submission permission in. raise ValidationError(gettext(u"You do not have permission to " u"submit to division '%(name)s'.", name=division.name))
def _change_payout(srp_request): form = PayoutForm() if not current_user.has_permission(PermissionType.review, srp_request): # TRANS: Error message when someone who does not have the reviewer # TRANS: permission tries to change the base payout of a request. flash(gettext(u"Only reviewers can change the base payout."), u'error') elif form.validate(): try: srp_request.base_payout = form.value.data * 1000000 db.session.commit() except ModifierError as e: flash(unicode(e), u'error') return get_request_details(srp_request=srp_request)
def index(self): if request.method == "POST": lines = [] obs = {} if request.files.get('bulk-file'): # request files lines = request.files.get('bulk-file').readlines() else: lines = request.form['bulk-text'].split('\n') invalid_observables = 0 if bool(request.form.get( 'add', False)) and current_user.has_permission("observable", "write"): tags = request.form.get('tags', "").split(',') for l in lines: try: txt = l.strip() if txt: if (request.form['force-type'] and request.form['force-type'] in globals() and issubclass( globals()[request.form['force-type']], Observable)): print globals()[request.form['force-type']] o = globals()[request.form[ 'force-type']].get_or_create(value=txt) else: o = Observable.add_text(txt) o.tag(tags) obs[o.value] = o except (ObservableValidationError, ValueError) as e: logging.error("Error validating {}: {}".format(txt, e)) invalid_observables += 1 continue else: for l in lines: obs[l.strip()] = l, None if len(obs) > 0: data = match_observables(obs.keys()) return render_template( "observable/search_results.html", data=data) else: if invalid_observables: flash( "Type guessing failed for {} observables. Try setting it manually.". format(invalid_observables), "danger") return render_template("observable/search.html") return render_template("observable/search.html")
def can_review_proposal(proposal): if proposal.state != 'anonymised': return False if current_user.has_permission('cfp_admin'): return True if proposal.user == current_user: return False if proposal.type == 'installation': # Only admins can review installations currently return False return True
def receipt(user_id=None): if current_user.has_permission('admin') and user_id is not None: user = User.query.get(user_id) else: user = current_user if not user.owned_purchases.filter_by(is_paid_for=True).all(): abort(404) png = bool(request.args.get('png')) pdf = bool(request.args.get('pdf')) page = render_receipt(user, png, pdf) if pdf: url = external_url('tickets.receipt', user_id=user_id) return send_file(render_pdf(url, page), mimetype='application/pdf', cache_timeout=60) return page
def division_detail(division_id): """Get the details of a division. :param int division_id: The ID of the division """ division = Division.query.get_or_404(division_id) if not current_user.admin and not \ current_user.has_permission(PermissionType.admin, division): abort(403) permissions = {} for perm in PermissionType.all: key = perm.name + '_href' permissions[key] = url_for('.division_permissions', division_id=division_id, permission=perm.name) return jsonify( name=division.name, requests=division.requests, permissions=permissions)
def _add_note(srp_request): form = AddNote() if not current_user.has_permission(PermissionType.elevated): # TRANS: Error message shown when someone without the proper # TRANS: permissions tries to add a note to a user. flash(gettext(u"You do not have permission to add a note to a user."), u'error') elif form.validate(): # Linkify killmail IDs note_content = Markup.escape(form.note.data) for match in killmail_re.findall(note_content): kill_id = int(match) check_request = db.session.query(Request.id).filter_by(id=kill_id) if db.session.query(check_request.exists()): link = u'<a href="{url}">#{kill_id}</a>'.format( url=url_for('.get_request_details', request_id=kill_id), kill_id=kill_id) link = Markup(link) note_content = note_content.replace(u'#' + match, link) # Create the note note = Note(srp_request.submitter, current_user, note_content) db.session.commit() return get_request_details(srp_request=srp_request)
def get_user_payment_or_abort(payment_id, provider=None, valid_states=None, allow_admin=False): try: payment = Payment.query.get(payment_id) except Exception as e: app.logger.warning('Exception %r getting payment %s', e, payment_id) abort(404) if not payment: app.logger.warning('Payment %s does not exist.', payment_id) abort(404) if not (payment.user == current_user or (allow_admin and current_user.has_permission('admin'))): app.logger.warning('User not allowed to access payment %s', payment_id) abort(404) if provider and payment.provider != provider: app.logger.warning('Payment %s is of type %s, not %s', payment.provider, provider) abort(404) if valid_states and payment.state not in valid_states: app.logger.warning("Payment %s is %s, not one of %s", payment_id, payment.state, valid_states) abort(404) return payment
def call(f, *args, **kwargs): if current_user.is_authenticated: if current_user.has_permission(permission): return f(*args, **kwargs) abort(404) return app.login_manager.unauthorized()
def request_change_division(request_id): srp_request = Request.query.get_or_404(request_id) if not current_user.has_permission(PermissionType.review, srp_request) and\ current_user != srp_request.submitter: current_app.logger.warn(u"User '{}' does not have permission to change" u" request #{}'s division".format( current_user, srp_request.id)) abort(403) if srp_request.finalized: msg = (u"Cannot change request #{}'s division as it is in a finalized" u" state").format(srp_request.id) current_app.logger.info(msg) # TRANS: Error message shown when a user tries to move a request but is # TRANS: unable to becuase the request has been paid or rejected. flash(gettext(u"Cannot change the division as this request is in a " u"finalized state"), u'error') return redirect(url_for('.get_request_details', request_id=request_id)) division_choices = srp_request.submitter.submit_divisions() try: division_choices.remove( (srp_request.division.id, srp_request.division.name)) except ValueError: pass if len(division_choices) == 0: current_app.logger.debug(u"No other divisions to move request #{} to."\ .format(srp_request.id)) # TRANS: Message shown when a user tries to change a request's division # TRANS: but they do not have access to any other divisions. flash(gettext(u"No other divisions to move to."), u'info') return redirect(url_for('.get_request_details', request_id=request_id)) form = DivisionChange() form.division.choices = division_choices # Default to the first value if there's only once choice. if len(division_choices) == 1: form.division.data = form.division.choices[0][0] if form.validate_on_submit(): new_division = Division.query.get(form.division.data) # TRANS: When a request is moved from one division to another, a # TRANS: comment is added noting the old division's name and the new # TRANS: division's name. This is the text of that note. archive_note = gettext(u"Moving from division '%(old_division)s' to " u"division '%(new_division)s'.", old_division=srp_request.division.name, new_division=new_division.name) if srp_request.status == ActionType.evaluating: type_ = ActionType.comment else: type_ = ActionType.evaluating archive_action = Action(srp_request, current_user, archive_note, type_) srp_request.division = new_division db.session.commit() # TRANS: Confirmation message shown when wa request has been # TRANS: successfully moved to a new division. flash(gettext(u"Request #%(request_id)d moved to %(division)s " u"division", request_id=srp_request.id, division=new_division.name), u'success') if current_user.has_permission(PermissionType.elevated, new_division) \ or current_user == srp_request.submitter: return redirect(url_for('.get_request_details', request_id=request_id)) else: return redirect(url_for('.list_pending_requests')) else: current_app.logger.warn(u"Form validation failed for division change:" u" {}.".format(form.errors)) form.division.data = srp_request.division.id return render_template('form.html', form=form, # TRANS: Title for the page showing the form for changing a # TRANS: request's division. title=lazy_gettext(u"Change #%(request_id)d's Division", request_id=srp_request.id))
def review_list(): form = ReviewListForm() if form.validate_on_submit(): app.logger.info('Clearing review order') session['review_order'] = None session['review_order_dt'] = datetime.utcnow() return redirect(url_for('.review_list')) review_order_dt = session.get('review_order_dt') last_visit = session.get('review_visit_dt') if not last_visit: last_vote_cast = CFPVote.query.filter_by(user_id=current_user.id) \ .order_by(CFPVote.modified.desc()).first() if last_vote_cast: last_visit = last_vote_cast.modified review_order_dt = last_vote_cast.modified proposal_query = Proposal.query.filter(Proposal.state == 'anonymised') if not current_user.has_permission('cfp_admin'): # reviewers shouldn't see their own proposals, and don't review installations # youth workshops are reviewed separately proposal_query = proposal_query.filter( Proposal.user_id != current_user.id, Proposal.type.in_(['talk', 'workshop'])) to_review_again = [] to_review_new = [] to_review_old = [] reviewed = [] user_votes = aliased(CFPVote, CFPVote.query.filter_by(user_id=current_user.id).subquery()) for proposal, vote in proposal_query.outerjoin(user_votes).with_entities(Proposal, user_votes).all(): proposal.user_vote = vote if vote: if vote.state in ['new', 'resolved', 'stale']: proposal.is_new = True to_review_again.append(proposal) else: reviewed.append(((vote.state, vote.vote or 0, vote.modified), proposal)) else: # modified doesn't really describe when proposals are "new", but it's near enough if last_visit is None or review_order_dt is None or proposal.modified < review_order_dt: to_review_old.append(proposal) else: proposal.is_new = True to_review_new.append(proposal) reviewed = [p for o, p in sorted(reviewed, reverse=True)] review_order = session.get('review_order') if review_order is None \ or not set([p.id for p in to_review_again]).issubset(review_order) \ or (to_review_new and (last_visit is None or datetime.utcnow() - last_visit > timedelta(hours=1))): random.shuffle(to_review_again) random.shuffle(to_review_new) random.shuffle(to_review_old) to_review_max = 30 # prioritise showing proposals that have been voted on before # after that, split new and old proportionally for fairness to_review = to_review_again[:] other_max = max(0, to_review_max - len(to_review)) other_count = len(to_review_old) + len(to_review_new) if other_count: old_max = int(float(len(to_review_old)) / other_count * other_max) new_max = other_max - old_max to_review += to_review_new[:new_max] + to_review_old[:old_max] session['review_order'] = [p.id for p in to_review] session['review_order_dt'] = last_visit session['review_visit_dt'] = datetime.utcnow() else: # Sort proposals based on the previous review order to_review_dict = dict((p.id, p) for p in to_review_again + to_review_new + to_review_old) to_review = [to_review_dict[i] for i in session['review_order'] if i in to_review_dict] session['review_visit_dt'] = datetime.utcnow() return render_template('cfp_review/review_list.html', to_review=to_review, reviewed=reviewed, form=form)
def admin_require_permission(): """ Require admin permission for everything under /admin """ if not current_user.is_authenticated or not current_user.has_permission('admin'): abort(404)
def decorated_view(*args, **kwargs): if current_user.has_permission(permission): return func(*args, **kwargs) else: return render_template("error.html", data="You are not authorized to view this page")
def set_mc_face_as_avatar_request(username): if not current_user.has_permission("avatar.reset"): abort(403) return str(set_avatar(username, get_mc_face(username)))
def is_accessible(self): if current_user.is_authenticated: if current_user.has_permission('volunteer:admin'): return True return False
def pay(flow=None): if flow is None: flow = 'main' view = ProductView.get_by_name(flow) if not view: abort(404) if view.token and session.get('ticket_token') != view.token: if not current_user.is_anonymous and current_user.has_permission('admin'): abort(404) if request.form.get("change_currency") in ('GBP', 'EUR'): currency = request.form.get("change_currency") app.logger.info("Updating currency to %s", currency) set_user_currency(currency) db.session.commit() return redirect(url_for('.pay', flow=flow)) basket = Basket.from_session(current_user, get_user_currency()) if not any(basket.values()): empty_baskets.inc() if current_user.is_authenticated: basket.load_purchases_from_db() if any(basket.values()): # We've lost the user's state, but we can still show them all # tickets they've reserved and let them empty their basket. flash("Your browser doesn't seem to be storing cookies. This may break some parts of the site.") app.logger.warn("Basket is empty, so showing reserved tickets (%s)", request.headers.get('User-Agent')) else: app.logger.info("Basket is empty, redirecting back to choose tickets") if view.type == 'tickets': flash("Please select at least one ticket to buy.") elif view.type == 'hire': flash("Please select at least one item to hire.") else: flash("Please select at least one item to buy.") return redirect(url_for('tickets.main', flow=flow)) if basket.requires_shipping: if current_user.is_authenticated: shipping = current_user.shipping else: shipping = None form = TicketPaymentShippingForm(obj=shipping) else: form = TicketPaymentForm() form.flow = flow if current_user.is_authenticated: form.name.data = current_user.name del form.email if current_user.name != current_user.email and not basket.requires_shipping: # FIXME: is this helpful? del form.name if form.validate_on_submit(): if Decimal(form.basket_total.data) != Decimal(basket.total): # Check that the user's basket approximately matches what we told them they were paying. price_changed.inc() app.logger.warn("User's basket has changed value %s -> %s", form.basket_total.data, basket.total) flash("""The items you selected have changed, possibly because you had two windows open. Please verify that you've selected the correct items.""") return redirect(url_for('tickets.pay', flow=flow)) user = current_user if user.is_anonymous: try: new_user = create_current_user(form.email.data, form.name.data) except IntegrityError as e: app.logger.warn('Adding user raised %r, possible double-click', e) return None user = new_user elif user.name == user.email: user.name = form.name.data if form.allow_promo.data: user.promo_opt_in = True if basket.requires_shipping: if not user.shipping: user.shipping = UserShipping() user.shipping.address_1 = form.address_1.data user.shipping.address_2 = form.address_2.data user.shipping.town = form.town.data user.shipping.postcode = form.postcode.data user.shipping.country = form.country.data if form.gocardless.data: payment_type = GoCardlessPayment elif form.banktransfer.data: payment_type = BankPayment elif form.stripe.data: payment_type = StripePayment basket.user = user payment = basket.create_payment(payment_type) basket.cancel_surplus_purchases() db.session.commit() Basket.clear_from_session() if not payment: empty_baskets.inc() app.logger.warn('User tried to pay for empty basket') flash("We're sorry, your session information has been lost. Please try ordering again.") return redirect(url_for('tickets.main', flow=flow)) if payment_type == GoCardlessPayment: return gocardless_start(payment) elif payment_type == BankPayment: return transfer_start(payment) elif payment_type == StripePayment: return stripe_start(payment) form.basket_total.data = basket.total return render_template('payment-choose.html', form=form, basket=basket, total=basket.total, flow=flow, view=view)
def has_permission_or_owner(permission, object_owner_id): return int(object_owner_id) == current_user.id or current_user.has_permission(permission)