2012-01-19 93 views
23
if request.method == 'POST': 
    userf = UsersModelForm(request.POST) 
    username = userf.data['username'] 
    password = userf.data['password'] 
    passwordrepeat = userf.data['passwordrepeat'] 
    email = userf.data['email'] 

我嘗試這樣做:如何更改保存之前Django的表單字段的值?

tempSalt = bcrypt.gensalt() 
    password = bcrypt.hashpw(password,tempSalt) 
    passwordrepeat = bcrypt.hashpw(passwordrepeat,tempSalt) 

    userf.data['password'] = password 
    userf.data['passwordrepeat'] = passwordrepeat 

但我得到的錯誤。我怎樣才能在保存之前改變userf.data['password']userf.data['passwordrepeat']價值?

錯誤:

AttributeError at /register 

This QueryDict instance is immutable 

Request Method:  POST 
Request URL: http://127.0.0.1:8000/register 
Django Version:  1.3.1 
Exception Type:  AttributeError 
Exception Value:  

This QueryDict instance is immutable 

Exception Location:  /usr/local/lib/python2.6/dist-packages/django/http/__init__.py in _assert_mutable, line 359 
Python Executable: /usr/bin/python 
Python Version:  2.6.6 
Python Path:  

['/home/user1/djangoblog', 
'/usr/lib/python2.6', 
'/usr/lib/python2.6/plat-linux2', 
'/usr/lib/python2.6/lib-tk', 
'/usr/lib/python2.6/lib-old', 
'/usr/lib/python2.6/lib-dynload', 
'/usr/local/lib/python2.6/dist-packages', 
'/usr/lib/python2.6/dist-packages', 
'/usr/lib/python2.6/dist-packages/gst-0.10', 
'/usr/lib/pymodules/python2.6', 
'/usr/lib/pymodules/python2.6/gtk-2.0'] 
+0

你有什麼樣的錯誤?驗證錯誤,完整性錯誤?您必須始終發佈錯誤消息。總是。 –

+0

我已更新錯誤,請再次參閱以瞭解。 – shibly

+0

我們需要你想做的事情:設置一個默認值,如果不存在值,則設置一個值,如果值不好,則更正一個值等。在Django表單中有幾個鉤子。 –

回答

29

文檔如果你需要在保存前需要做一些數據,只需創建一個功能,如:

def clean_nameofdata(self): 
    data = self.cleaned_data['nameofdata'] 
    # do some stuff 
    return data 

所有你需要的是創造一個函數名稱爲** clean _ *** nameofdata *其中nameofdata是該字段的名稱,所以如果要修改密碼字段,則需要:

def clean_password(self): 

,如果你需要修改passwordrepeat

def clean_passwordrepeat(self): 

所以裏面就有,只是CRIPT您的密碼,並返回一個cripted。

我的意思是:

def clean_password(self): 
    data = self.cleaned_data['password'] 
    # cript stuff 
    return data 

所以當你有效的形式,密碼會被cripted。

+0

我不明白你的問題。哪裏?在clean_foo裏面,你得到了簡單的密碼並對其進行了轉換。 –

+2

我的意思是在哪裏創建那些'def clean_password(self):'functions? – shibly

+0

哦,真的,在你創建的表單類中。 –

5

覆蓋_clean方法,並把your checks in them。您可以從那裏修改cleaned_data

E.g:

def clean_password(self): 
    self.cleaned_data['password'] = new1 
    return new1 

在表單字段的每個將具有由Django的自動創建的field_name_clean()方法。當您執行form.is_valid()時會調用此方法。

+0

我聽不懂。你可以發佈完整的代碼與解釋。這將有所幫助。 – shibly

+0

它是ModelForm,而不是Form,是Cleaning_data可用於ModelForm? – shibly

+0

什麼時候調用了'clean_passwor(self):'函數? – shibly

8

請參閱save()方法

if request.method == 'POST': 
    userf = UsersModelForm(request.POST) 
    new_user = userf.save(commit=False) 

    username = userf.cleaned_data['username'] 
    password = userf.cleaned_data['password'] 
    passwordrepeat = userf.cleaned_data['passwordrepeat'] 
    email = userf.cleaned_data['email'] 

    new_user.password = new1 
    new_user.passwordrepeat = new2 

    new_user.save() 
+3

這是一種更新。是否可以在保存前更改/修改值? – shibly

5

,如果你需要從POST填寫表格,更改任何表單字段值,並再次渲染形式您將有問題。 下面是它的解決方案:

class StudentSignUpForm(forms.Form): 
    step = forms.IntegerField() 

    def set_step(self, step): 
    data = self.data.copy() 
    data['step'] = step 
    self.data = data 

然後:

form = StudentSignUpForm(request.POST) 
if form.is_valid() and something(): 
    form.set_step(2) 
    return render_to_string('form.html', {'form': form}) 
+0

我有一個類似的問題,我有兩個提交按鈕。第一個創建預覽,第二個是實際提交。通過使用POST數據創建表單(自然),未提交的按鈕的值將被清除。此方法非常適合恢復未點擊的按鈕的值。 – Scott

+0

這很好,很靈活 –

0

與以前的解決方案的問題是,如果驗證失敗,將無法正常工作。爲了避免驗證,您可以使用如下實例:

instance = form.instance 
instance.user = request.user 
instance.save() 

但是要小心,這不檢查is_valid()。如果你想這樣做,你可以用新值來實例化表單:

# NOT TESTED, NOT SURE IF THIS WORKS... 
form = MyForm(instance=instance) 
if form.is_valid(): 
    form.save() 
相關問題