Depuis que j'ai passé deux heures patauger dans la pylônes/routes/bécher/etc Je pensais que je partagerais ma solution.
D'abord un peu de contexte. J'utilise un équilibreur de charge élastique (ELB) sur AWS avec terminaison SSL. L'application est conçue pour fonctionner uniquement sur https; c'est un monde post-incendiaire après tout. Il est en couches comme ceci:
ELB -> nginx -> pasteWSGI -> pylons
ELB est joyeux bonne en termes de simplicité, mais tout appel à pylons.controllers.util.redirect déclencherait une redirection 302 « http: // monsite/». L'ELB ne changerait pas cela sur le chemin du retour (aucune raison de) et ainsi mon navigateur serait renvoyé au port 80 et il n'y a aucune ELB écoutant sur ce port.
J'ai essayé de mettre à jour le mappeur comme suggéré ci-dessus.
- cela n'a pas fonctionné,
- Je voulais que mes réoriente être relatif. Le passage à https dans Pylônes signifie que le générateur d'URL va chercher l'hôte pour créer une nouvelle URL (https: // localhost/....)
Notez que Mapper.redirect_to fonctionne hors de la boîte et les utilisations redirections relatives, il n'y a donc pas besoin de gâcher avec ça. Le problème fondamental est que controllers.redirect utilise un chemin de code légèrement différent. En particulier, dans Routes, le controllers.util.redirect n'est pas une redirection (il y a un "if routes et routes.redirect" qui correspond à False).
Ma solution: remplacer tous les appels à rediriger par une nouvelle méthode de contrôleur (appelée aussi redirection) pour changer les redirections de redirections absolues à relatives.
Le code est le suivant:
lib/aides.py
def relative_redirect(to_url, start_response):
"""Returns a redirect that is compatible with AWS ELB (no absolute http responses)
Using pylons.controllers.util.redirect triggers an exception that'll be turned into a 302
But with an absolute path so the response does not contains https but simple http
"""
start_response("302 Found", [("Content-Type", "text/plain; charset=utf-8"), ("Location", url(to_url))])
return ["You are being redirected to {0}".format(url(to_url))]
Avec ce bit appelé à partir de la classe de base de mes contrôleurs:
class BaseController(WSGIController):
...
def redirect(self, to_url):
"""Force a relative redirection, to work with AWS ELB"""
return relative_redirect(to_url, self.start_response)