2015-08-02 9 views
5

Ho un obbligo di creare un modulo di indagine. Diversi tipi di utenti avranno una serie diversa di domande a cui rispondere nel sondaggio.Come utilizzare i formati di django per creare un'app di sondaggio con domande e risposte?

models.py

from django.contrib.auth.models import Group, User 

from django.db import models 

ANSWER_CHOICES = (
    ('0', 'No'), 
    ('1', 'Yes') 
) 


class Survey(models.Model): 
    name = models.CharField(max_length=100) 
    group = models.ForeignKey(Group) 

    def __str__(self): 
     return self.name 


class Feature(models.Model): 
    name = models.CharField(max_length=150) 
    survey = models.ForeignKey(Survey) 

    def __str__(self): 
     return self.name 


class Rating(models.Model): 
    rating = models.IntegerField(choices=ANSWER_CHOICES) 
    feature = models.ForeignKey(Feature) 
    rating_for = models.ForeignKey(User, related_name='rated_user') 
    rating_by = models.ForeignKey(User, related_name='rated_by') 

    def __str__(self): 
     return str.format("%s - %s", self.feature, self.rating) 

La risposta (valutazione) per ogni domanda (funzione) o è un sì o un no, rappresentano da pulsanti di opzione. Una volta che l'utente invia il modulo, salva le risposte nella tabella di valutazione.

Qual è il modo django per raggiungere questo obiettivo?

Grazie


forms.py

from django import forms 
from django.forms import modelformset_factory, TextInput 

from survey.models import Rating, Feature 


class FeatureForm(forms.ModelForm): 
    class Meta: 
     model = Feature 


class RatingForm(forms.ModelForm): 
    class Meta: 
    model = Rating 


FeatureFormSetBase = modelformset_factory(Feature, extra=0, 
             widgets={'name': TextInput(attrs={'readonly': True, })} 
            ) 


class FeatureFormSet(FeatureFormSetBase): 
    def add_fields(self, form, index): 
     super(FeatureFormSet, self).add_fields(form, index) 
     form.fields['is_checked'] = forms.BooleanField(required=False) 

survey.html

<form action="." method="post" accept-charset="utf-8"> 
     <ul class="list-group"> 
      {% for form in formset.forms %} 
       <li class="list-group-item"> 
        <div class="hidden"> {{ form.survey }}</div> 
        <span> {{ form.name }} </span> 
        <span> {{ form.id }} </span> 
        <span> {{ form.is_checked }} </span> 
       </li> 
      {% endfor %} 

     </ul> 
     <p> 
      {{ formset.management_form }} 
      {% csrf_token %} 
      <button type="submit" name="action" value="save" class="btn btn-success">SAVE</button> 
     </p> 
    </form> 

Questo è il codice che ho e funziona ora, ma non sono sicuro se il migliore modo per risolvere questo problema? Ho un sacco di codice in views.py per analizzare i dati del post ... c'è un modo più pulito per raggiungere questo obiettivo?

view.py

def questionnaire(request): 
q = Feature.objects.filter(survey__group=request.user.groups.all()[0]).select_related('survey') 
if request.method == 'POST': 
    action = request.POST.get('action') 
    formset = FeatureFormSet(request.POST, queryset=q) 

    if formset.is_valid(): 
     # iterate over all forms in the formset 
     for form in formset.forms: 
      if action == u'save': 
       answer = form.cleaned_data.get('is_checked') 
       print("Saving answer...") 
       rating = Rating() 
       rating.rating = answer 
       rating.feature = form.cleaned_data.get('id') 
       rating.rating_for = request.user 
       rating.rating_by = request.user 
       rating.save() 

     redirect('useraccount_dashboard') 

else: 
    formset = FeatureFormSet(queryset=q) 

return render_to_response('account_survey.html', {'formset': formset}, context_instance=RequestContext(request)) 

AGGIORNAMENTO views.py

def questionnaire(request, instance_id): 
try: 
    instance = SurveyInstance.objects.get(pk=instance_id, completed=False) 
except SurveyInstance.DoesNotExist: 
    raise Http404 

if instance.rating_by != request.user: 
    return HttpResponse('Unauthorized', status=401) 

q = Feature.objects.filter(survey=instance.survey) 
if request.method == 'POST': 
    action = request.POST.get('action') 
    formset = FeatureFormSet(request.POST, queryset=q) 

    if formset.is_valid(): 
     # iterate over all forms in the formset 
     for form in formset.forms: 
      if action == u'save': 
       answer = form.cleaned_data.get('is_checked') 
       print("Saving answer...") 
       rating = Rating() 
       rating.rating = answer 
       rating.feature = form.cleaned_data.get('id') 
       rating.survey_instance = instance 
       rating.save() 

     instance.completed = True 
     instance.save() 
     messages.add_message(request, messages.INFO, 'Thank you for your feedback.') 
     return redirect('useraccount_dashboard') 

else: 
    formset = FeatureFormSet(queryset=q) 

return render_to_response('account_survey.html', {'formset': formset}, context_instance=RequestContext(request)) 
+0

Il tuo codice sembra a posto. Cosa intendi * "modo django per raggiungere questo" *, però? – xyres

+1

Per i principianti, non hai pubblicato alcun codice del tuo 'views.py' che causa la tua preoccupazione e in secondo luogo - se stai cercando suggerimenti per l'ottimizzazione; allora potrebbe essere meglio postarlo su [codereview.stackexchange.com] (http://codereview.stackexchange.com) –

risposta

1

Prova a utilizzare form.save() invece di creare dell'oggetto Rating, compilazione è campi e quindi risparmio.

+0

Con la leggera modifica, ho capito di fare ciò che volevo. –

Problemi correlati