Comment les variables POST et GET sont-elles gérées en Python?

135

En PHP, vous pouvez simplement utiliser $_POSTpour POST et $_GETpour les variables GET (Query string). Quel est l'équivalent en Python?

Cliquez sur Upvote
la source
Êtes-vous en train d'écrire un script CGI, mod_python ou une application Django (ou un autre framework)? La réponse dépend d'un peu plus d'informations ...
Rob
pouvez-vous fournir un exemple de code pour chacun d'entre eux?
Cliquez sur Upvote le
2
CGI, mod_python, Django, CherryPy et Pylons ne sont pas des exemples de code. Ce sont des frameworks Web Python qui gèrent GET et POST. Voir wiki.python.org/moin/WebFrameworks pour plus d'informations. Votre question - telle que posée - ne peut pas recevoir de réponse.
S.Lott

Réponses:

246

supposons que vous publiez un formulaire html avec ceci:

<input type="text" name="username">

Si vous utilisez un CGI brut :

import cgi
form = cgi.FieldStorage()
print form["username"]

Si vous utilisez Django , Pylons , Flask ou Pyramid :

print request.GET['username'] # for GET form method
print request.POST['username'] # for POST form method

Utilisation de Turbogears , Cherrypy :

from cherrypy import request
print request.params['username']

Web.py :

form = web.input()
print form.username

Werkzeug :

print request.form['username']

Si vous utilisez Cherrypy ou Turbogears, vous pouvez également définir votre fonction de gestionnaire en prenant directement un paramètre:

def index(self, username):
    print username

Google App Engine :

class SomeHandler(webapp2.RequestHandler):
    def post(self):
        name = self.request.get('username') # this will get the value from the field named username
        self.response.write(name) # this will write on the document

Vous devrez donc vraiment choisir l'un de ces cadres.

nosklo
la source
18
Utilisation import cgi, n'est-ce pas print form["username"].value?
J.Katzwinkel
J'utilise Bottlece que je crois utilise wsgi, quelqu'un pourrait-il publier l'équivalent à utiliser dans ce scénario? La réponse ci-dessus est l'explication la plus claire que j'ai rencontrée, elle n'inclut tout simplement pas mon scénario.
user1063287
2
FieldStorage est cassé dans python3, vous pouvez rencontrer des problèmes avec lui. bugs.python.org/issue6234
NuclearPeon
2
Permettez-moi de clarifier mon commentaire précédent; cette page: lucumr.pocoo.org/2013/7/2/the-updated-guide-to-unicode l' explique mieux. N'utilisez pas FieldStorage () dans Python 3 en raison de problèmes d'encodage.
NuclearPeon
Pour Flask, c'est un peu différent: request.args.get ('username')
Damjan Pavlica
35

Je sais que c'est une vieille question. Pourtant, il est surprenant qu'aucune bonne réponse n'ait été donnée.

Tout d'abord, la question est tout à fait valable sans mentionner le cadre. Le CONTEXTE est une équivalence de langage PHP. Bien qu'il existe de nombreuses façons d'obtenir les paramètres de chaîne de requête en Python, les variables de structure sont simplement remplies de manière pratique. En PHP, $_GETet $_POSTsont également des variables de commodité. Ils sont analysés respectivement à partir des entrées QUERY_URI et php: //.

En Python, ces fonctions seraient os.getenv('QUERY_STRING')et sys.stdin.read(). N'oubliez pas d'importer les modules os et sys.

Il faut être prudent avec le mot «CGI» ici, surtout quand on parle de deux langues et de leurs points communs lors de l’interfaçage avec un serveur web. 1. CGI, en tant que protocole, définit le mécanisme de transport de données dans le protocole HTTP. 2. Python peut être configuré pour s'exécuter en tant que script CGI dans Apache. 3. Le module CGI en Python offre des fonctions pratiques.

Étant donné que le protocole HTTP est indépendant du langage et que l'extension CGI d'Apache est également indépendante du langage, l'obtention des paramètres GET et POST ne devrait supporter que les différences de syntaxe entre les langages.

Voici la routine Python pour remplir un dictionnaire GET:

GET={}
args=os.getenv("QUERY_STRING").split('&')

for arg in args: 
    t=arg.split('=')
    if len(t)>1: k,v=arg.split('='); GET[k]=v

et pour POST:

POST={}
args=sys.stdin.read().split('&')

for arg in args: 
    t=arg.split('=')
    if len(t)>1: k, v=arg.split('='); POST[k]=v

Vous pouvez maintenant accéder aux champs comme suit:

print GET.get('user_id')
print POST.get('user_name')

Je dois également souligner que le module CGI ne fonctionne pas bien. Considérez cette requête HTTP:

POST / test.py?user_id=6

user_name=Bob&age=30

L'utilisation CGI.FieldStorage().getvalue('user_id')provoquera une exception de pointeur nul car le module vérifie aveuglément les données POST, ignorant le fait qu'une requête POST peut également transporter des paramètres GET.

Schien
la source
J'ai eu cette erreur: AttributeError: 'NoneType' object has no attribute 'split'utilisation CGIavec Python2.7
candlejack
1
À propos de l'erreur de @candlejack, essayez d'obtenir les arguments comme celui-ci POST.get('user_name', 'default_value').
George Siggouroglou
@GeorgeSiggouroglou Le problème 'default_value' a résolu mon problème. Merci!
umbe1987
1
Certainement ma réponse préférée jusqu'à présent! +1
umbe1987
QUERY_STRING n'est pas un index valide sur Mac
Samuel Ev
31

J'ai trouvé la réponse de nosklo très complète et utile! Pour ceux, comme moi, qui pourraient trouver l'accès direct aux données de demande brutes également utile, j'aimerais ajouter la façon de le faire:

import os, sys

# the query string, which contains the raw GET data
# (For example, for http://example.com/myscript.py?a=b&c=d&e
# this is "a=b&c=d&e")
os.getenv("QUERY_STRING")

# the raw POST data
sys.stdin.read()
À M
la source
J'essaye d' appeler une méthode dans un fichier cgi. Un exemple d'URL est http://www.myserver.com/cgi-bin/cgi.py/ThisIsMyMethod. Les variables d'environnement suivantes sont liées: os.environ.get('PATH_INFO')qui obtient le nom de la méthode (par exemple: / ThisIsMyMethod) et os.environ.get('SCRIPT_NAME')qui fournit le chemin vers le script depuis le dossier racine de l'hôte Web (par exemple: /cgi-bin/cgi.py). Dans mon cas, QUERY_STRING est vide, car j'utilise POST.
NuclearPeon
28

Ils sont stockés dans l'objet CGI fieldstorage.

import cgi
form = cgi.FieldStorage()

print "The user entered %s" % form.getvalue("uservalue")
Evan Fosmark
la source
2
-1. il existe un certain nombre de représentations de l'objet de requête, selon les bibliothèques / framework utilisés.
bruno desthuilliers
10
Je ne sais pas pourquoi vous avez fait -1. Je veux dire, ce que j'ai donné fonctionne. Peut-être est-il incapable d'utiliser un framework. De plus, la plupart des frameworks ne l'utilisent-ils pas simplement en arrière-plan?
Evan Fosmark le
4
C'était stupide de faire -1, j'ai +1 pour l'équilibrer, plus je pense que c'est la meilleure méthode car elle renvoie une piqûre (ce qui est demandé)
joedborg
1
@Liam Je ne sais pas pourquoi vous obtenez None, mais ce post a plus de 6 ans, donc je ne doute pas que les choses aient changé.
Evan Fosmark
@EvanFosmark J'obtiens des valeurs None en utilisant ceci. Lorsque j'imprime la valeur renvoyée par cgi.FeildStorage, c'est ce que la sortie est FieldStorage (None, None, []). J'ai posté une question complète ici stackoverflow.com/questions/38024516/… Toute aide sera appréciée.
Chor Sipahi
1

Cela dépend un peu de ce que vous utilisez comme framework CGI, mais ils sont disponibles dans des dictionnaires accessibles au programme. Je vous indiquerais la documentation, mais je ne parviens pas à accéder à python.org pour le moment. Mais cette note sur mail.python.org vous donnera un premier pointeur . Regardez les bibliothèques Python CGI et URLLIB pour en savoir plus.

Mettre à jour

D'accord, ce lien a éclaté. Voici la référence wsgi de base

Charlie Martin
la source
Si vous n'êtes pas assez ambitieux pour suivre un lien, je ne suis pas assez ambitieux pour couper et coller si à partir du lien.
Charlie Martin
1
et maintenant le lien est mort et c'est pourquoi tout le monde déteste les réponses comme celle-ci et les évalue. Toutes nos félicitations.
John Tyree
2
Vous savez, chaque fois que je reçois un commentaire de quelqu'un qui me dit qu'une réponse vieille de cinq à presque six ans a maintenant un lien rompu, sans, par exemple, ajouter un lien de remplacement, je peux parier que c'est quelqu'un avec un représentant <1000.
Charlie Martin
Si je savais où aller pour le lien de remplacement (indice, je ne l'ai pas fait parce que votre lien ne fonctionnait pas), je n'aurais pas cherché cette question.
John Tyree
Vous pouvez toujours essayer l'astuce sur les «bibliothèques python CGI et URLLIB», je suppose.
Charlie Martin
0

Python n'est qu'un langage, pour obtenir des données GET et POST, vous avez besoin d'un framework Web ou d'un toolkit écrit en Python. Django en est un, comme le souligne Charlie, les modules standard cgi et urllib en sont d'autres. Sont également disponibles Turbogears, Pylons, CherryPy, web.py, mod_python, fastcgi, etc., etc.

Dans Django, vos fonctions d'affichage reçoivent un argument de requête qui a request.GET et request.POST. D'autres cadres le feront différemment.

Ned Batchelder
la source
13
"pour obtenir des données GET et POST, vous avez besoin d'un framework Web ou d'une boîte à outils écrite en Python" - Tout simplement faux
James Tomasino
2
Je suis d'accord avec James, s'ils sont écrits en Python, ils peuvent clairement être réécrits selon vos préférences.
Robin Sandström
Ok, je suis un nouveau venu en python et je pensais qu'il n'était pas possible que je doive utiliser un framework. Ma question est de savoir quel est le chemin? Je n'utilise aucun framework et j'ai demandé à apache2 de servir un script python. Ce sera bien de montrer une manière très simple comme l'utilisation de $ _GET ou $ _POST en php.
black sensei
1
@JamesTomasino Dans le contexte de la question, c'est vrai.
peterh