2015-11-05 2 views
0

Я пытаюсь устранить потерю данных при обновлении страницы, когда проверка не удалась. Когда форма обновляется после ошибки проверки, все поля пусты, за исключением полей, в которых произошла ошибка. Как я могу обновить страницу, отобразить ошибки проверки и все еще иметь все поля во всех заполненных divs?Только часть формы сохраняется после ошибки проверки

Заранее благодарен!

Мой код показан ниже:

views.py

class CreateListingView(CreateView): 
    template_name = 'listing/listing.html' 
    model = Listing 
    form_class = ListingForm 
    # success_url = '/add-listing/' 

def get_success_url(self): 
    return reverse('store') + "?success=true" 

def dispatch(self, request, *args, **kwargs): 
    if self.request.user.is_authenticated(): 
     if not self.request.user.has_company(): 
      return HttpResponseRedirect(reverse('get_paid')) 
     elif not self.request.user.has_shipping(): 
      return HttpResponseRedirect(reverse('get_paid')) 
     elif not self.request.user.has_bank(): 
      return HttpResponseRedirect(reverse('get_paid')) 
     else: 
      return super(CreateListingView, self).dispatch(request, *args, **kwargs) 
    else: 
     return HttpResponseRedirect(reverse('create_user')) 

def get_initial(self): 
    return {'company_profile': self.request.user.company} 

def get_form_kwargs(self): 
    kwargs = super(CreateListingView, self).get_form_kwargs() 
    if self.request.method in ('POST', 'PUT'): 
     kwargs['data']['price'] = kwargs['data']['price'].replace(',','') 
    return kwargs 

forms.py

class ListingForm(forms.ModelForm): 
    caliber_firearm = forms.CharField(required=False,  widget=forms.TextInput(attrs={'class': 'req'})) 
    caliber_ammo = forms.CharField(required=False) 

tags = forms.CharField(required=False) 
img_0 = forms.ImageField(required=False, widget=forms.FileInput(attrs={'class': 'image-input'})) 
img_1 = forms.ImageField(required=False, widget=forms.FileInput(attrs={'class': 'image-input'})) 
img_2 = forms.ImageField(required=False, widget=forms.FileInput(attrs={'class': 'image-input'})) 
img_3 = forms.ImageField(required=False, widget=forms.FileInput(attrs={'class': 'image-input'})) 
img_4 = forms.ImageField(required=False, widget=forms.FileInput(attrs={'class': 'image-input'})) 

class Meta: 
    model = Listing 
    exclude = ['copy', 'caliber'] 
    widgets = { 
     'title': forms.TextInput(attrs={'class': 'title-listing'}), 
     'listing_type': forms.RadioSelect(), 
     'upc': forms.TextInput(attrs={'class': 'upc'}), 
     'category': forms.Select(attrs={'class': 'short-input', 'required': 'True'}), 
     'price': forms.TextInput(attrs={'class': 'price dollar req'}), 
     'list_price': forms.TextInput(attrs={'class': 'list_price_input'}), 
     'quantity': forms.TextInput(attrs={'class': 'qty req'}), 
     'description': forms.Textarea(attrs={'class': 'description req'}), 
     'estimated_ship_days': forms.TextInput(attrs={'class': 'qty req', 'placeholder': 'Days'}), 
     'capacity': forms.TextInput(attrs={'class': 'req'}), 
     'weight_pounds': forms.TextInput(attrs={'class': 'weight req', 'placeholder': 'Pounds'}), 
     'weight_ounces': forms.TextInput(attrs={'class': 'weight', 'placeholder': 'Ounces'}), 
     'barrel_length': forms.TextInput(attrs={'class': 'req', 'placeholder': 'Inches'}), 
     'overall_length': forms.TextInput(attrs={'class': 'req', 'placeholder': 'Inches'}), 
     'company_profile': forms.HiddenInput(), 
     'shipping_zip_code': forms.TextInput(attrs={'placeholder': 'Your shipping zip code'}), 
    } 

    error_messages = empty_errors 

def clean(self): 
    listing_type = self.cleaned_data.get('listing_type') 
    if self.cleaned_data.get('img_0') is None and \ 
        self.cleaned_data.get('img_1') is None and \ 
        self.cleaned_data.get('img_2') is None and \ 
        self.cleaned_data.get('img_3') is None and \ 
        self.cleaned_data.get('img_4') is None: 

     self.add_error('img_0', 'One photo must be uploaded') 

    if listing_type == 'Firearm': 
     if self.cleaned_data.get('caliber_firearm', None) is None: 
      self.add_error('caliber_firearm', 'This field is required') 
     else: 
      self.cleaned_data['caliber'] = self.cleaned_data.get('caliber_firearm') 
     if self.cleaned_data.get('capacity', None) is None: 
      self.add_error('capacity', 'This field is required') 
     if self.cleaned_data.get('weight_pounds', None) is None: 
      self.add_error('weight_pounds', 'This field is required') 
     if self.cleaned_data.get('weight_ounces', None) is None: 
      self.add_error('weight_ounces', 'This field is required') 
     if self.cleaned_data.get('barrel_length', None) is None: 
      self.add_error('barrel_length', 'This field is required') 
     if self.cleaned_data.get('overall_length', None) is None: 
      self.add_error('overall_length', 'This field is required') 
    elif listing_type == 'Ammo': 
     if self.cleaned_data.get('caliber_ammo', None) is not None: 
      self.cleaned_data['caliber'] = self.cleaned_data.get('caliber_ammo') 

    if self.cleaned_data.get('shipping_zip_code') is None or \ 
        self.cleaned_data.get('shipping_weight') is None or \ 
        self.cleaned_data.get('shipping_height') is None or \ 
        self.cleaned_data.get('shipping_length') is None or \ 
        self.cleaned_data.get('shipping_width') is None: 

     self.add_error('shipping_weight', 'Shipping information is not complete') 

    return self.cleaned_data 

Шаблон

{% extends 'base.html' %} 
{% load staticfiles %} 
{% block head %} 

    <title>Dealer Direct by FFL Design</title> 
    <meta name="viewport" content="width=device-width, initial-scale=1"> 
    <link rel="stylesheet" 
      type="text/css" 
      href="{% static 'listing/css/listing.css' %}"> 
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script> 
    <script src="{% static 'listing/js/listing.js' %}"></script> 

    <!-- Start of ffldesign Zendesk Widget script --> 
    <script>/*<![CDATA[*/window.zEmbed||function(e,t){var n,o,d,i,s,a=[],r=document.createElement("iframe");window.zEmbed=function(){a.push(arguments)},window.zE=window.zE||window.zEmbed,r.src="javascript:false",r.title="",r.role="presentation",(r.frameElement||r).style.cssText="display: none",d=document.getElementsByTagName("script"),d=d[d.length-1],d.parentNode.insertBefore(r,d),i=r.contentWindow,s=i.document;try{o=s}catch(c){n=document.domain,r.src='javascript:var d=document.open();d.domain="'+n+'";void(0);',o=s}o.open()._l=function(){var o=this.createElement("script");n&&(this.domain=n),o.id="js-iframe-async",o.src=e,this.t=+new Date,this.zendeskHost=t,this.zEQueue=a,this.body.appendChild(o)},o.write('<body onload="document._l();">'),o.close()}("https://assets.zendesk.com/embeddable_framework/main.js","ffldesign.zendesk.com");/*]]>*/</script> 
    <!-- End of ffldesign Zendesk Widget script --> 

{% endblock %} 
{% block body %} 
<body> 
    <div class="listing"> 
     <p class="ffl">Add a new listing</p> 
     <form action="{% url 'add-listing' %}" method="post" enctype="multipart/form-data"> 
      <div class="errors">{{ form.shipping_weight.errors }}</div> 
      {% csrf_token %} 
      <div class="photos"> 
       <p class="ffl-small">Photos</p> 
       <p class="desc" id="photos-desc">Must add at least one photo.</p> 
       <ul> 
        <li id="photo_0"> 
         <div id="input_photo_0"> 
          <img src="{% static 'listing/images/add-photo.png' %}" class="add-photo"> 
          <p><button type="button" class="active-button">Add Photo</button></p> 
          {{ form.img_0 }} 
         </div> 
         <div id="display_photo_0" class="hidden"> 
          <img src="" width="143" height="105" id="img_view_0" class="item-image"> 
          <button type="button" class="remove-zoom active-button magnify"><img src="{% static 'listing/images/zoom.png' %}" width="18" height="18"></button><button type="button" class="remove-zoom active-button delete_photo"><img src="{% static 'listing/images/remove.png' %}"></button> 
         </div> 
        </li> 
        <li id="photo_1"> 
         <div id="input_photo_1"> 
          <img src="{% static 'listing/images/add-photo.png' %}" class="add-photo"> 
          <p><button type="button" class="active-button">Add Photo</button></p> 
          {{ form.img_1 }} 
         </div> 
         <div id="display_photo_1" class="hidden"> 
          <img src="" width="143" height="105" id="img_view_1" class="item-image"> 
          <button type="button" class="remove-zoom active-button magnify"><img src="{% static 'listing/images/zoom.png' %}" width="18" height="18"></button><button type="button" class="remove-zoom active-button delete_photo"><img src="{% static 'listing/images/remove.png' %}"></button> 
         </div> 
        </li> 
        <li id="photo_2"> 
         <div id="input_photo_2"> 
          <img src="{% static 'listing/images/add-photo.png' %}" class="add-photo"> 
          <p><button type="button" class="active-button">Add Photo</button></p> 
          {{ form.img_2 }} 
         </div> 
         <div id="display_photo_2" class="hidden"> 
          <img src="" width="143" height="105" id="img_view_2" class="item-image"> 
          <button type="button" class="remove-zoom active-button magnify"><img src="{% static 'listing/images/zoom.png' %}" width="18" height="18"></button><button type="button" class="remove-zoom active-button delete_photo"><img src="{% static 'listing/images/remove.png' %}"></button> 
         </div> 
        </li> 
        <li id="photo_3"> 
         <div id="input_photo_3"> 
          <img src="{% static 'listing/images/add-photo.png' %}" class="add-photo"> 
          <p><button type="button" class="active-button">Add Photo</button></p> 
          {{ form.img_3 }} 
         </div> 
         <div id="display_photo_3" class="hidden"> 
          <img src="" width="143" height="105" id="img_view_3" class="item-image"> 
          <button type="button" class="remove-zoom active-button magnify"><img src="{% static 'listing/images/zoom.png' %}" width="18" height="18"></button><button type="button" class="remove-zoom active-button delete_photo"><img src="{% static 'listing/images/remove.png' %}"></button> 
         </div> 
        </li> 
        <li id="photo_4"> 
         <div id="input_photo_4"> 
          <img src="{% static 'listing/images/add-photo.png' %}" class="add-photo"> 
          <p><button type="button" class="active-button">Add Photo</button></p> 
          {{ form.img_4 }} 
         </div> 
         <div id="display_photo_4" class="hidden"> 
          <img src="" width="143" height="105" id="img_view_4" class="item-image"> 
          <button type="button" class="remove-zoom active-button magnify"><img src="{% static 'listing/images/zoom.png' %}" width="18" height="18"></button><button type="button" class="remove-zoom active-button delete_photo"><img src="{% static 'listing/images/remove.png' %}"></button> 
         </div> 
        </li> 
        <li class="desc"> 
         For best results, use high quality jpeg or gif files that are at least 570 px wide. 
        </li> 
       </ul> 
      </div> 
      <div class="select-type"> 
       <p class="ffl-small">Select listing type</p> 
       {% for radio in form.listing_type %} 
        {{ radio }} 
       {% endfor %} 
{#    <label><input type="radio" name="listing" checked>Firearms</label>#} 
{#    <label><input type="radio" name="listing">Ammo</label>#} 
{#    <label><input type="radio" name="listing">Optics</label>#} 
{#    <label><input type="radio" name="listing">Apparel</label>#} 
{#    <label><input type="radio" name="listing">Other</label>#} 
      </div> 
      <div class="details"> 
       <p class="ffl-small">Listing Details</p> 
       <p><label for="id_title">Title<span>&#42;</span></label><input type="text" id="id_title" name="title" class="title-listing" required><span class="desc">Describe your item using words and phrases people would use in a search.</span> 
        <span class="title-error">Error: you cannot use a period in the title name.</span> 
       </p> 
       <p><label for="id_upc">UPC</label><input type="text" name="upc" id="id_upc" class="upc" maxlength="12"></p> 
       <p><label for="id_category">Category<span>&#42;</span></label> 
        {{form.category}} 
       </p> 
       <p> 
        <label for="id_price">Cost<span>&#42;</span></label><input type="number" name="price" id="id_price" class="price dollar req" min=0 step="0.01"> 
        <span class="list_price_text">List Price:<input type="number" name="list_price" id="id_list_price" class="list_price_input" step="0.01" readonly></span> 
        <span class="list_price_desc">The "List Price" is automatically calculated with Dealer Direct seller fees. This price is what the dealer will see. The "Cost" field is the amount you will be paid.</span> 
       </p> 
       <p><label for="id_quantity">Quantity<span>&#42;</span></label><input type="text" name="quantity" id="id_quantity" class="qty req"></p> 
       <p><label for="id_description" class="textarea-label">Description<span>&#42;</span></label><textarea name="description" id="id_description" class="description req"></textarea></p> 
       <p><label for="id_estimated_ship_days">Days to ship:<span>&#42;</span></label><input type="text" name="estimated_ship_days" id="id_estimated_ship_days" class="qty req" placeholder="days"></p> 

       {% for field in form.hidden_fields %} 
        {{ field }} 
       {% endfor %} 
      </div> 
      <div class="details ammo type-ammo"> 
       <p class="ffl-small">Ammo Details</p> 
       <p><label for="id_rounds">Rounds per box</label>{{ form.rounds }}</p> 
       <p><label for="id_caliber_ammo">Caliber/Gauge</label>{{ form.caliber_ammo }}</p> 
       <p><label for="id_weight">Weight</label>{{ form.weight }}</p> 
       <p><label for="id_muzzle_velocity">Muzzle Velocity</label>{{ form.muzzle_velocity }}</p> 
       <p><label for="id_length">Length</label>{{ form.length }}</p> 
       <p><label for="id_ammo_type">Type</label>{{ form.ammo_type }}</p> 
      </div> 
      <div class="details ammo type-firearm"> 
       <p class="ffl-small">Firearm Details</p> 
       <p><label for="id_caliber_firearm">Caliber<span>&#42;</span></label>{{ form.caliber_firearm }}</p> 
       <p><label for="id_capacity">Capacity<span>&#42;</span></label>{{ form.capacity }}</p> 
       <p><label for="id_weight_pounds">Weight<span>&#42;</span></label>{{ form.weight_pounds }}<label for="id_weight_ounces" class="weight-label"></label>{{ form.weight_ounces }}</p> 
       <p><label for="id_barrel_length">Barrel Length<span>&#42;</span></label>{{ form.barrel_length }}</p> 
       <p><label for="id_overall_length">Overall Length<span>&#42;</span></label>{{ form.overall_length }}</p> 
       <p><label for="id_finish">Finish</label>{{ form.finish }}</p> 
      </div> 
      <div class="details optics type-optics"> 
       <p class="ffl-small">Optics Details</p> 
       <p><label for="id_magnification">Magnification</label><input id="id_magnification" name="magnification" type="text"></p> 
       <p><label for="id_field_of_view">Field of View</label><input id="id_field_of_view" name="field_of_view" type="text"></p> 
       <p><label for="id_reticle">Reticle</label><input id="id_reticle" name="reticle" type="text"></p> 
       <p><label for="id_objective_lens">Objective Lens</label><input id="id_objective_lens" name="objective_lens" type="text"></p> 
       <p><label for="id_eye_relief">Eye Relief</label><input id="id_eye_relief" name="eye_relief" type="text"></p> 
       <p><label for="id_max_elevation_adjustment">Max Elevation Adjustment</label><input id="id_max_elevation_adjustment" name="max_elevation_adjustment" type="text"></p> 
       <p><label for="id_max_windage_adjustment">Max Windage<br/>Adjustment</label><input id="id_max_windage_adjustment" name="max_windage_adjustment" type="text"></p> 
       <p><label for="id_length_optics">Length</label><input id="id_length_optics" name="length" type="text"></p> 
       <p><label for="id_weight_optics">Weight</label><input id="id_weight_optics" name="weight" type="text"></p> 
       <p><label for="id_battery">Battery</label><input id="id_battery" name="battery" type="text"></p> 
       <p><label for="id_dot_size">DOT Size</label><input id="id_dot_size" name="dot_size" type="text"></p> 
       <p><label for="id_finish_optics">Finish</label><input id="id_finish_optics" name="finish" type="text"></p> 
      </div> 
      <div class="details apparel type-apparel"> 
       <p class="ffl-small">Apparel Details</p> 
       <p><label for="id_shirt_size">Size</label> 
        {{ form.shirt_size }} 
       </p> 
       <p><label for="id_shirt_color">Color</label><input id="id_shirt_color" name="shirt_color" type="text"></p> 
      </div> 
      <div class="search"> 
       <p class="ffl-small">Search Terms</p> 
       <p class="desc">Help dealers find this product by using accurate and descriptive words or phrases.</p> 
       <ul class="search-ul"> 
        <li> 
         <span class="tags"><label for="id_tags">Tags</label></span> 
         <span class="desc">Optional</span> 
        </li> 
        <li> 
         <label><input type="text" name="tags" id="id_tags" placeholder="example: ar15, iron sights, glock holster, etc" class="tag-input"><span class="desc left">10 left</span></label> 
         <p class="tags-wrapper">must separate each tag by a comma</p> 
         <p id="tag-list"></p> 
        </li> 
        <li> 
         <span class="desc"> 
          We highly recommend using all 10 tags for<br />your listing to get 
          found. Use words you think<br />dealers would use to search for this product. 
         </span> 
        </li> 
       </ul> 
      </div> 
      <div class=" details shipping"> 
       <p class="ffl-small">Shipping</p> 
       <p class="desc">For realistic shipping expectations, please provide accurate product shipping information below.</p> 
       <div class="errors">{{ form.shipping_zip_code.errors }}{{ form.shipping_weight.errors }}</div> 
       {% comment %} 
       <p class="zip"><label for="">Zip Code</label><input name="" type="text" placeholder="Your shipping zip code"></p> 
       <p class="shipping-weight"><label for="">Weight</label><input name="" type="text"><label for=""></label><input name="" type="text"></p> 
       <p class="dimensions"><label for="">Dimensions</label><input name="" type="text"><label for=""></label><input name="" type="text"><label for=""></label><input name="" type="text"></p> 
       {% endcomment %} 
       <p class="zip"> 
        <label for="id_shipping_zip_code">Zip Code</label> 
        {{form.shipping_zip_code}} 
       </p> 
       <p class="shipping-weight"> 
        <label for="id_shipping_weight">Weight</label> 
        {{form.shipping_weight}} 
       </p> 
       <p class="dimensions"> 
        <label for="">Dimensions</label> 
        {{form.shipping_length}} 
        <label for=""></label> 
        {{form.shipping_width}} 
        <label for=""></label> 
        {{form.shipping_height}} 
       </p> 
      </div> 
      <button class="submit-btn active-button">Submit Listing</button> 
     </form> 
     <div class="wrapper"> 
      <div class=""> 
       <button class="active-button">Close</button> 
       <img src="{% static 'listing/images/example-img.png' %}"> 
      </div> 
     </div> 
    </div> 

    <div id="spacer"></div> 
</body> 
{% endblock %} 

ответ

0

Намного проще, чем я предполагал. Просто нужно добавить 'value = "{{form.field_name.value}}" "к каждому входу.

<input type="text" class="foo" value="{{ form.field_name.value }}"/> 

Я также обнаружил, что каждый тег шаблона django был сохранен. Замена каждого тега <input> переменной django {{ form.field_name }} также решила проблему.

Смежные вопросы