Пример #1
0
def modify_poll(
    id: int,
    choices: Dict[str, list] = None,
    closed: bool = None,
    featured: bool = None,
) -> flask.Response:
    """
    This is the endpoint for forum poll editing. The ``modify_forum_polls``
    permission is required to access this endpoint. The choices can be edited
    here, as well as the closed and featured statuses.

    .. :quickref: ForumPoll; Edit a forum poll.

    **Example request**:

    .. parsed-literal::

       PUT /forums/polls/6 HTTP/1.1

       {
         "id": 1,
         "choices": {
           "add": ["Yes", "No"],
           "delete": ["Placeholder1", "Placeholder2"]
         },
         "closed": true,
         "featured": false
       }


    **Example response**:

    .. parsed-literal::

       {
         "status": "success",
         "response": "<ForumPoll>"
       }

    :>json dict response: The edited forum poll

    :statuscode 200: Editing successful
    :statuscode 400: Editing unsuccessful
    :statuscode 404: Forum poll does not exist
    """
    poll = ForumPoll.from_pk(id, _404=True)
    if featured is not None:
        if featured is True:
            ForumPoll.unfeature_existing()
        poll.featured = featured
    if closed is not None:
        poll.closed = closed
    if choices:
        change_poll_choices(poll, choices['add'], choices['delete'])
    db.session.commit()
    return flask.jsonify(poll)
Пример #2
0
def test_poll_no_permissions(app, authed_client):
    db.engine.execute(
        """DELETE FROM users_permissions
                      WHERE permission = 'forumaccess_forum_2'"""
    )
    db.engine.execute(
        """DELETE FROM users_permissions
                      WHERE permission = 'forumaccess_thread_3'"""
    )
    with pytest.raises(_403Exception):
        ForumPoll.from_pk(3, error=True)
Пример #3
0
def test_modify_poll_closed_featured(app, authed_client):
    add_permissions(app, 'forums_view', 'modify_forum_polls')
    ForumPoll.from_pk(3)  # cache it
    response = authed_client.put('/polls/1',
                                 data=json.dumps({
                                     'closed': True,
                                     'featured': True
                                 }))
    check_json_response(response, {'id': 1, 'featured': True, 'closed': True})
    poll = ForumPoll.from_pk(1)
    assert poll.closed is True
    assert poll.featured is True
    assert ForumPoll.from_pk(3).featured is False
Пример #4
0
def test_forum_poll_new(app, authed_client):
    poll = ForumPoll.new(thread_id=5, question='Una pregunta')
    assert poll.id == 5
    assert poll.thread_id == 5
    assert poll.question == 'Una pregunta'
    assert poll.closed is False
    assert poll.featured is False
Пример #5
0
def view_poll(id: int) -> flask.Response:
    """
    This endpoint allows users to view details about a poll.

    .. :quickref: ForumPoll; View a forum poll.

    **Example response**:

    .. parsed-literal::

       {
         "status": "success",
         "response": [
           "<ForumPoll>",
           "<ForumPoll>"
         ]
       }

    :>json list response: A forum poll

    :statuscode 200: View successful
    :statuscode 403: User does not have permission to view thread
    :statuscode 404: Thread does not exist
    """
    return flask.jsonify(ForumPoll.from_pk(id, error=True, _404=True))
Пример #6
0
def change_poll_choices(poll: ForumPoll, add: List[str],
                        delete: List[int]) -> None:
    """
    Change the choices to a poll. Create new choices or delete existing ones.
    The choices parameter should contain a dictionary of answer name keys and
    their status as booleans. True = Add, False = Delete.

    :param poll:    The forum poll to alter
    :param choices: The choices to edit
    """
    poll_choice_choices = {c.choice for c in poll.choices}
    poll_choice_ids = {c.id for c in poll.choices}
    errors = {
        'add': {choice
                for choice in add if choice in poll_choice_choices},
        'delete':
        {choice
         for choice in delete if choice not in poll_choice_ids},
    }

    error_message = []
    if errors['add']:
        error_message.append(
            f'The following poll choices could not be added: '  # type: ignore
            f'{", ".join(errors["add"])}.')
    if errors['delete']:
        error_message.append(
            f'The following poll choices could not be deleted: '  # type: ignore
            f'{", ".join([str(d) for d in errors["delete"]])}.')
    if error_message:
        raise APIException(' '.join(error_message))

    for choice in delete:
        choice = ForumPollChoice.from_pk(choice)
        choice.delete_answers()  # type: ignore
        db.session.delete(choice)
    for choice_new in add:
        db.session.add(ForumPollChoice(poll_id=poll.id, choice=choice_new))
    cache.delete(ForumPollChoice.__cache_key_of_poll__.format(poll_id=poll.id))
    poll.del_property_cache('choices')
    db.session.commit()
Пример #7
0
def test_modify_poll_unfeature(app, authed_client):
    add_permissions(app, 'forums_view', 'modify_forum_polls')
    authed_client.put('/polls/3', data=json.dumps({'featured': False}))
    assert ForumPoll.get_featured() is None
    assert not cache.get(ForumPoll.__cache_key_featured__)
Пример #8
0
def test_forum_poll_from_id(app, authed_client):
    poll = ForumPoll.from_pk(1)
    assert poll.question == 'Question 1'
Пример #9
0
def test_poll_new_choice(app, authed_client):
    choice = ForumPollChoice.new(poll_id=3, choice='user_three!')
    assert choice.id == 7
    assert choice.poll_id == 3
    assert choice.choice == 'user_three!'
    assert {6, 7} == set(c.id for c in ForumPoll.from_pk(3).choices)
Пример #10
0
def test_poll_choices(app, authed_client):
    choices = ForumPoll.from_pk(1).choices
    assert {1, 2, 3} == set(c.id for c in choices)
Пример #11
0
def test_unfeature_poll(app, authed_client):
    ForumPoll.unfeature_existing()
    assert not ForumPoll.get_featured()
    assert ForumPoll.from_pk(3).featured is False
    ForumPoll.unfeature_existing()  # Validate no errors here
Пример #12
0
def test_forum_poll_new_nonexistent_thread(app, authed_client):
    with pytest.raises(APIException):
        ForumPoll.new(thread_id=10, question='.')
Пример #13
0
def test_forum_poll_from_featured(app, authed_client):
    poll = ForumPoll.get_featured()
    assert poll.id == 3
Пример #14
0
def test_forum_poll_from_thread(app, authed_client):
    poll = ForumPoll.from_thread(1)
    assert poll.id == 1