Questo è in realtà un problema interessante, e il modo in cui risolve WTForms è intenzionalmente qualcosa che richiede esplicitazione, perché ha a che fare con la sicurezza e non permettendo agli utenti di inserire falso.
Quindi l'intento è che i "gestori" non possono modificare il nome, mentre "amministratori" possono.
A prima vista questo sembra ovvio, basta disabilitare il campo in HTML, e scrivere il panorama come questo:
def edit_team():
form = TeamForm(request.POST, obj=team)
if request.POST and form.validate():
form.populate_obj(team) # <-- This is the dangerous part here
return redirect('/teams')
return render('edit_team.html')
Come scritto, questo è un grande rischio per la sicurezza, perché la proprietà disabile in moduli HTML è lato client solo. Chiunque con un ispettore HTML (ad esempio Firebug, WebKit Controllo documento, ecc) può rimuovere questa proprietà, o qualcuno potrebbe semplicemente fare una richiesta in questo modo:
POST /edit_team/7 HTTP/1.0
Content-Type: application/x-urlencoded
team=EVILTEAMNAME&title=foo
Il problema allora è, naturalmente, come facciamo a porta questo correttamente sul lato server, corrispondente al modo appropriato di farlo? L'approccio corretto con WTForms è a non avere il campo in primo luogo. Ci sono alcuni modi per farlo, uno è usare la composizione del modulo e avere ad es. ManagerTeamForm e AdminTeamForm (a volte è meglio), ma altre volte è più semplice da eseguire su use del to remove specific fields.
Quindi, ecco come si può scrivere la vostra vista, e non hanno i problemi di convalida:
def edit_team():
form = TeamForm(request.POST, obj=team)
if user.role == 'manager':
del form.name
if request.POST and form.validate():
form.populate_obj(team)
return redirect('/teams')
return render('edit_team.html')
e una rapida modifica al modello:
<html>
<body>
<form action="" method=POST>
{% if 'name' in form %}
{{ form.name() }}
{% else %}
{{ team.name|e }}
{% endif %}
{{ form.title }}
-- submit button --
</form>
</body>
</html>
Alcuni pezzi di riferimento per wtforms best- pratiche:
puoi condividere il tuo codice dei moduli per favore? – codegeek
@codegeek: aggiornato con il codice dei moduli. – rajpy
Puoi fornire qualche informazione su quale sia il tuo obiettivo? 'name' è un campo obbligatorio, ma non stai permettendo che venga fornito un valore. Stai programmando di iniettarne uno a livello di programmazione? – dirn