def submit_comment(request, post): """Used by the form on `get_comments` to submit the form data to the database. Returns partial data for the remote side. """ if not request.is_xhr: raise BadRequest() post = Post.query.get(post) if post is None: raise NotFound() # not even moderators can submit comments for deleted posts. if post.is_deleted: message = _(u'You cannot submit comments for deleted posts') return json_response(success=False, form_errors=[message]) form = _get_comment_form(post) if form.validate(): comment = form.create_comment() session.commit() comment_box = get_macro('kb/_boxes.html', 'render_comment') comment_link = get_macro('kb/_boxes.html', 'render_comment_link') return json_response(html=comment_box(comment), link=comment_link(post), success=True) return json_response(success=False, form_errors=form.as_widget().all_errors)
def vote(request, post): """Votes on a post.""" # TODO: this is currently also fired as GET if JavaScript is # not available. Not very nice. post = Post.query.get(post) if post is None: raise NotFound() # you cannot cast votes on deleted shit if post.is_deleted: message = _(u"You cannot vote on deleted posts.") if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) # otherwise val = request.args.get("val", 0, type=int) if val == 0: request.user.unvote(post) elif val == 1: # users cannot upvote on their own stuff if post.author == request.user: message = _(u"You cannot upvote your own post.") if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) # also some reputation is needed if not request.user.is_admin and request.user.reputation < settings.REPUTATION_MAP["UPVOTE"]: message = _(u"In order to upvote you " u"need at least %d reputation") % settings.REPUTATION_MAP["UPVOTE"] if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) request.user.upvote(post) elif val == -1: # users need some reputation to downvote. Keep in mind that # you *can* downvote yourself. if not request.user.is_admin and request.user.reputation < settings.REPUTATION_MAP["DOWNVOTE"]: message = ( _(u"In order to downvote you " u"need at least %d reputation") % settings.REPUTATION_MAP["DOWNVOTE"] ) if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) request.user.downvote(post) else: raise BadRequest() session.commit() # standard requests are answered with a redirect back if not request.is_xhr: return redirect(url_for(post)) # others get a re-rendered vote box box = get_macro("kb/_boxes.html", "render_vote_box") return json_response(html=box(post, request.user))
def accept(request, post): """Accept a post as an answer.""" # TODO: this is currently also fired as GET if JavaScript is # not available. Not very nice. post = Post.query.get(post) if post is None: raise NotFound() # just for sanity. It makes no sense to accept the question # as answer. The UI does not allow that, so the user must have # tampered with the data here. if post.is_question: raise BadRequest() # likewise you cannot accept a deleted post as answer if post.is_deleted: message = _(u'You cannot accept deleted posts as answers') if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) topic = post.topic # if the post is already the accepted answer, we unaccept the # post as answer. if post.is_answer: if not request.user.can_unaccept_as_answer(post): message = _(u'You cannot unaccept this reply as an answer.') if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) topic.accept_answer(None, request.user) session.commit() if request.is_xhr: return json_response(accepted=False) return redirect(url_for(post)) # otherwise we try to accept the post as answer. if not request.user.can_accept_as_answer(post): message = _(u'You cannot accept this reply as answer.') if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) topic.accept_answer(post, request.user) session.commit() if request.is_xhr: return json_response(accepted=True) return redirect(url_for(post))
def get_tags(request): """A helper that returns the tags for the language.""" limit = max(0, min(request.args.get("limit", 10, type=int), 20)) query = Tag.query.filter((Tag.locale == request.view_lang) & (Tag.tagged > 0)) q = request.args.get("q") if q: query = query.filter(Tag.name.like("%%%s%%" % q)) query = query.order_by(Tag.tagged.desc(), Tag.name) return json_response(tags=[(tag.name, tag.tagged) for tag in query.limit(limit).all()])
def update_csrf_token(request): """Updates the CSRF token. Required for forms that are submitted multiple times using JavaScript. This updates the token. """ if not request.is_xhr: raise BadRequest() elif not request.method == 'POST': raise MethodNotAllowed(valid=['POST']) token = get_csrf_token(request, request.form['url'], force_update=True) return json_response(token=token)
def get_tags(request): """A helper that returns the tags for the language.""" limit = max(0, min(request.args.get('limit', 10, type=int), 20)) query = Tag.query.filter((Tag.locale == request.view_lang) & (Tag.tagged > 0)) q = request.args.get('q') if q: query = query.filter(Tag.name.like('%%%s%%' % q)) query = query.order_by(Tag.tagged.desc(), Tag.name) return json_response(tags=[(tag.name, tag.tagged) for tag in query.limit(limit).all()])
def get_comments(request, post, form=None): """Returns the partial comment template. This is intended to be used on by XHR requests. """ if not request.is_xhr: raise BadRequest() post = Post.query.get(post) if post is None: raise NotFound() # sanity check. This should not happen because the UI does not provide # a link to retrieve the comments, but it could happen if the user # accesses the URL directly or if he requests the comments to be loaded # after a moderator deleted the post. if post.is_deleted and not (request.user and request.user.is_moderator): raise Forbidden() form = _get_comment_form(post) return json_response(html=render_template("kb/_comments.html", post=post, form=form.as_widget()))
def get_comments(request, post, form=None): """Returns the partial comment template. This is intended to be used on by XHR requests. """ if not request.is_xhr: raise BadRequest() post = Post.query.get(post) if post is None: raise NotFound() # sanity check. This should not happen because the UI does not provide # a link to retrieve the comments, but it could happen if the user # accesses the URL directly or if he requests the comments to be loaded # after a moderator deleted the post. if post.is_deleted and not (request.user and request.user.is_moderator): raise Forbidden() form = _get_comment_form(post) return json_response(html=render_template( 'kb/_comments.html', post=post, form=form.as_widget()))
def request_exchange_token(request): """Return the exchange token.""" token = get_exchange_token(request) return json_response(token=token)
def vote(request, post): """Votes on a post.""" # TODO: this is currently also fired as GET if JavaScript is # not available. Not very nice. post = Post.query.get(post) if post is None: raise NotFound() # you cannot cast votes on deleted shit if post.is_deleted: message = _(u'You cannot vote on deleted posts.') if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) # otherwise val = request.args.get('val', 0, type=int) if val == 0: request.user.unvote(post) elif val == 1: # users cannot upvote on their own stuff if post.author == request.user: message = _(u'You cannot upvote your own post.') if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) # also some reputation is needed if not request.user.is_admin and \ request.user.reputation < settings.REPUTATION_MAP['UPVOTE']: message = _(u'In order to upvote you ' u'need at least %d reputation') % \ settings.REPUTATION_MAP['UPVOTE'] if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) request.user.upvote(post) elif val == -1: # users need some reputation to downvote. Keep in mind that # you *can* downvote yourself. if not request.user.is_admin and \ request.user.reputation < settings.REPUTATION_MAP['DOWNVOTE']: message = _(u'In order to downvote you ' u'need at least %d reputation') % \ settings.REPUTATION_MAP['DOWNVOTE'] if request.is_xhr: return json_response(message=message, error=True) request.flash(message, error=True) return redirect(url_for(post)) request.user.downvote(post) else: raise BadRequest() session.commit() # standard requests are answered with a redirect back if not request.is_xhr: return redirect(url_for(post)) # others get a re-rendered vote box box = get_macro('kb/_boxes.html', 'render_vote_box') return json_response(html=box(post, request.user))