Как вернуть относительный заголовок местоположения URI с помощью Flask?

Flask заменяет содержимое моего заголовка Location при построении моего HTTP-ответа. Он меняет мой фактический заголовок относительного местоположения URI на абсолютный.

@app.route('/votes', methods=['POST'])
def votes():
    return jsonify(), 201, {'location': '/votes/1'}

мой тест:

def test_vote_creation(self):
    response = self.app.post('/votes',
                             data=json.dumps({
                                 'name': 'Test vote'
                             }), content_type='application/json')
    print(response.headers['location'])

вернуть http://localhost/votes/1 вместо /votes/1

Как вернуть относительный заголовок местоположения URI с помощью Flask jsonify?

Изменить: в соответствии с текущей версией стандарта HTTP/1.1, RFC 2616, значение заголовка Location должно быть абсолютный URI. Но RCF собирается измениться, чтобы разрешить относительные URI. Поэтому я хочу изменить поведение моего API по умолчанию, чтобы он отвечал относительным URI в заголовке моего местоположения.

подробнее в этом сообщении


person Guillaume Vincent    schedule 26.03.2014    source источник
comment
Что вы пытаетесь сделать именно? Извините, ваш пост не очень понятен, по крайней мере для меня   -  person codegeek    schedule 26.03.2014
comment
@codegeek Я отредактировал свой вопрос, надеюсь, стало понятнее   -  person Guillaume Vincent    schedule 27.03.2014
comment
Это обсуждается в этом проблеме werkzeug на Github.   -  person snakecharmerb    schedule 13.01.2021


Ответы (1)


HTTP RFC указывает, что заголовок Location должен быть абсолютным URI:

14.30 Локация

Поле заголовка ответа Location используется для перенаправления получателя в место, отличное от Request-URI, для выполнения запроса или идентификации нового ресурса. Для ответов 201 (Создано) Location соответствует местоположению нового ресурса, который был создан по запросу. Для ответов 3xx в местоположении СЛЕДУЕТ указывать предпочтительный URI сервера для автоматического перенаправления на ресурс. Значение поля состоит из одного абсолютного URI.

Location       = "Location" ":" absoluteURI

Таким образом, объект ответа Flask / Werkzeug преобразует любой заголовок относительного URL-адреса Location в абсолютный URL-адрес.

Вы можете переопределить это поведение, хотя я бы не рекомендовал вам этого делать. Чтобы переопределить его, установите атрибут autocorrect_location_header объекта Response. до False. jsonify() возвращает объект ответа, измените его:

@app.route('/votes', methods=['POST'])
def votes():
    response = jsonify()
    response.status_code = 201
    response.headers['location'] = '/votes/1'
    response.autocorrect_location_header = False
    return response

но обратите внимание, что ваш сервер WSGI по-прежнему может применять абсолютный URL-адрес, даже если Flask этого не делает.

person Martijn Pieters    schedule 28.03.2014
comment
Спасибо @martijn-pieters за объяснение. Я знаю для RFC. Я просто хочу знать, есть ли решение, потому что RFC будет меняться. Но пока я изменю свой интерфейс для обработки абсолютного URI. - person Guillaume Vincent; 28.03.2014
comment
@martijn-pieters на момент написания этого комментария местоположение не обязательно должно быть абсолютным. › Синтаксис поля заголовка Location был изменен, чтобы разрешить все ссылки URI, включая относительные ссылки и фрагменты, а также некоторые пояснения относительно того, когда использование фрагментов нецелесообразно. (Раздел 7.1.2) — исходная страница 92 - person cianmce; 13.04.2015
comment
@cianmce Итак, я предполагаю, что текущий ответ еще не поддерживается Flask? - person Franklin Yu; 09.08.2017
comment
Вот обновленный RFC: tools.ietf.org/html/rfc7231 — он позволяет относительный путь. - person Danny Dulai; 07.01.2021