Django डिफ़ॉल्ट रूप मान सेट करता है


241

मेरे पास एक मॉडल इस प्रकार है:

class TankJournal(models.Model):
    user = models.ForeignKey(User)
    tank = models.ForeignKey(TankProfile)
    ts = models.IntegerField(max_length=15)
    title = models.CharField(max_length=50)
    body = models.TextField()

मेरे पास उपरोक्त मॉडल के लिए एक मॉडल फॉर्म इस प्रकार है:

class JournalForm(ModelForm):
    tank = forms.IntegerField(widget=forms.HiddenInput()) 

    class Meta:
        model = TankJournal
        exclude = ('user','ts')

मैं जानना चाहता हूं कि उस टैंक छिपे हुए क्षेत्र के लिए डिफ़ॉल्ट मान कैसे सेट किया जाए। यहाँ अब तक फॉर्म को दिखाना / सहेजना मेरा कार्य है:

def addJournal(request, id=0):
    if not request.user.is_authenticated():
        return HttpResponseRedirect('/')

    # checking if they own the tank
    from django.contrib.auth.models import User
    user = User.objects.get(pk=request.session['id'])

    if request.method == 'POST':
        form = JournalForm(request.POST)
        if form.is_valid():
            obj = form.save(commit=False)

            # setting the user and ts
            from time import time
            obj.ts = int(time())
            obj.user = user

            obj.tank = TankProfile.objects.get(pk=form.cleaned_data['tank_id'])

            # saving the test
            obj.save()

    else:
        form = JournalForm()

    try:
        tank = TankProfile.objects.get(user=user, id=id)
    except TankProfile.DoesNotExist:
        return HttpResponseRedirect('/error/')

जवाबों:


402

आप प्रारंभिक का उपयोग कर सकते हैं जो यहां बताया गया है

फॉर्म निर्माणकर्ता को कॉल करते समय आपके पास दो विकल्प हैं

form = JournalForm(initial={'tank': 123})

या फॉर्म की परिभाषा में मूल्य निर्धारित करें:

tank = forms.IntegerField(widget=forms.HiddenInput(), initial=123) 

और उस चर initialको वास्तविक रूप में कैसे पारित किया जाता है? वास्तविक रूप मॉडल में, क्या हमें एक पैरामीटर / तर्क के रूप में लिखना है?
mgPePe

2
@ भारमल यह जादू है। ;-) (या बल्कि, Django फॉर्म कंस्ट्रक्टर विशेष "प्रारंभिक" वैरिएबल को समझते हैं और इसकी सामग्री के माध्यम से पुनरावृति करते हैं, इसके बिना आपको कुछ अतिरिक्त करने की आवश्यकता नहीं है)। व्यक्तिगत रूप से, मैं प्रपत्र परिभाषा में डिफ़ॉल्ट मान निर्दिष्ट करना पसंद करता हूं और केवल प्रारंभिक = ... तंत्र का उपयोग करता हूं यदि वांछित डिफ़ॉल्ट एक गतिशील मूल्य है (उदाहरण के लिए उपयोगकर्ता द्वारा दर्ज की गई कोई चीज़, या उनके लॉगिन, भौगोलिक स्थिति, आदि के आधार पर)
रिचर्ड जे फोस्टर

66
प्रारंभिक डिफ़ॉल्ट नहीं है। यदि फॉर्म बाउंड किया गया है तो प्रारंभिक मान लागू नहीं होता है :(।
क्लेम

4
एक और usecase का उल्लेख करने के लिए यहां टिप्पणी करना जहां प्रारंभिक परम के इस समाधान में मदद करेगा: किसी को पंजीकरण लिंक भेजते समय यदि आप ईमेल / आईडी या पंजीकरण फॉर्म पर किसी अन्य क्रेडेंशियल को पूर्वनिर्मित करना चाहते हैं तो उस स्थिति में आप इसे नहीं लिख सकते हैं मॉडल को इसके गतिशील के रूप में बल्कि आपको @ umnik700 द्वारा उल्लिखित प्रारंभिक परम के साथ निर्माता को कॉल करने की आवश्यकता है । बहुत अच्छा काम करता है!
केशव अग्रवाल

1
@Pipip: View.get_formप्रारंभिक डेटा सेट करने के लिए ओवरराइड न करें । FormMixin के साथ कोई भी CBV (मूल रूप से सभी CBV जो डेटा बनाते हैं या संपादित करते हैं) या तो एक क्लास-लेवल initialचर (अपरिवर्तित चूक के लिए) का उपयोग कर सकते हैं या आप FormMixin.get_initial()फॉर्म के कंस्ट्रक्टर (डायनामिक डिफॉल्ट्स) के लिए पारित किए जाने वाले प्रारंभिक मूल्यों का एक बड़ा हिस्सा वापस करने के लिए ओवरराइड कर सकते हैं ।)
GDorn

29

अन्य समाधान: फॉर्म बनाने के बाद प्रारंभिक सेट करें:

form.fields['tank'].initial = 123

मेरी जरूरत के लिए यह काम, फार्म में केवल एक क्षेत्र को सम्मिलित करता है। धन्यवाद।
bl4ckb1rd

15

यदि आप POST मूल्यों से मॉडलफॉर्म बना रहे हैं, तो प्रारंभिक को इस तरह से सौंपा जा सकता है:

form = SomeModelForm(request.POST, initial={"option": "10"})

https://docs.djangoproject.com/en/1.10/topics/forms/modelforms/#providing-initial-values


6
उस or Noneहिस्से की वास्तव में जरूरत नहीं है।
स्मेड सिप

11

मेरे पास यह दूसरा समाधान था (मैं इसे किसी और के रूप में पोस्ट कर रहा हूं क्योंकि मैं मॉडल से निम्नलिखित विधि का उपयोग कर रहा हूं):

class onlyUserIsActiveField(forms.ModelForm):
    def __init__(self, *args, **kwargs):
        super(onlyUserIsActiveField, self).__init__(*args, **kwargs)
        self.fields['is_active'].initial = False

    class Meta:
        model = User
        fields = ['is_active']
        labels = {'is_active': 'Is Active'}
        widgets = {
            'is_active': forms.CheckboxInput( attrs={
                            'class':          'form-control bootstrap-switch',
                            'data-size':      'mini',
                            'data-on-color':  'success',
                            'data-on-text':   'Active',
                            'data-off-color': 'danger',
                            'data-off-text':  'Inactive',
                            'name':           'is_active',

            })
        }

प्रारंभिक को __init__फ़ंक्शन के रूप में परिभाषित किया गया हैself.fields['is_active'].initial = False


0

मैं आशा करता हूं यह आपकी मदद कर सकते हैं:

form.instance.updatedby = form.cleaned_data['updatedby'] = request.user.id

0

जैसा कि Django डॉक्स में बताया गया है , initialनहीं हैdefault

  • प्रारंभिक एक फ़ील्ड का मान एक HTML में प्रदर्शित किया जा करने का इरादा है। लेकिन अगर उपयोगकर्ता इस मान को हटा देता है, और अंत में इस क्षेत्र के लिए एक रिक्त मान वापस भेज देता है, तो initialमान खो जाता है। तो आप वह नहीं प्राप्त करते हैं, जो किसी से अपेक्षित है डिफ़ॉल्ट व्यवहार ।

  • डिफ़ॉल्ट व्यवहार है: मूल्य कि सत्यापन प्रक्रिया करता है, तो ले जाएगाdata तर्क क्षेत्र के लिए किसी भी कीमत शामिल नहीं है।

इसे लागू करने के लिए, एक सीधा तरीका गठबंधन करना है initialऔर clean_<field>():

class JournalForm(ModelForm):
    tank = forms.IntegerField(widget=forms.HiddenInput(), initial=123) 

    (...)

    def clean_tank(self):
        if not self['tank'].html_name in self.data:
            return self.fields['tank'].initial
        return self.cleaned_data['tank']
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.