Ошибка: страница не найдена (404) django createview со встроенным набором форм - PullRequest
0 голосов
/ 05 мая 2019

Django 2.1 Python 3.6

Я пытаюсь использовать Django CreateView для создания и сохранения трех форм.Затем я хочу перенаправить обратно в подробный вид родительской модели.Однако, когда я отправляю форму, меня перенаправляют на рецепты / вместо рецептов / теста.Я получаю сообщение об ошибке «Страница не найдена» (404), потому что рецептов / не существует.

Нет отслеживания, которое помогло бы мне выяснить, что происходит.Может кто-нибудь, пожалуйста, покажите мне, что я делаю неправильно в моем коде?

models.py

from django.db import models
from django.utils.text import slugify
from django.urls import reverse 


class Recipe(models.Model):
    title = models.CharField(max_length=255)
    description = models.TextField()
    slug = models.SlugField(default='')

    def save(self, *args, **kwargs):
        self.slug = (slugify(self.title))
        super().save(*args, **kwargs)

    def get_absolute_url(self):
        return reverse('recipes:RecipeDetail',
                        kwargs = {'slug': self.slug})


class Ingredient(models.Model):
    recipe = models.ForeignKey(Recipe,
                                on_delete = models.CASCADE)
    description = models.CharField(max_length=255)


class Instruction(models.Model):
    recipe = models.ForeignKey(Recipe,
                                on_delete = models.CASCADE)
    number = models.PositiveSmallIntegerField()
    description = models.TextField()

views.py

Обновлен путем перемещения перенаправления на публикацию.Все еще не работает.

 def get(self, request, *args, **kwargs):
        """
        Handles GET requests and instantiates blank versions of the form
        and its inline formsets.
        """
        self.object = None
        form_class = self.get_form_class()
        form = self.get_form(form_class)
        ingredient_form = IngredientFormSet()
        instruction_form = InstructionFormSet()
        return self.render_to_response(
            self.get_context_data(form=form,
                                  ingredient_form=ingredient_form,
                                  instruction_form=instruction_form))

    def post(self, request, *args, **kwargs):
        """
        Handles POST requests, instantiating a form instance and its inline
        formsets with the passed POST variables and then checking them for
        validity.
        """
        self.object = None
        form_class = self.get_form_class()
        form = self.get_form(form_class)
        ingredient_form = IngredientFormSet(self.request.POST)
        instruction_form = InstructionFormSet(self.request.POST)
        if (form.is_valid() and ingredient_form.is_valid() and
            instruction_form.is_valid()):
            return self.form_valid(form, ingredient_form, instruction_form)
        else:
            return self.form_invalid(form, ingredient_form, instruction_form)
        return super(RecipeCreateView, self).form_valid(form, ingredient_form, instruction_form)

    def form_valid(self, form, ingredient_form, instruction_form):
        """
        Called if all forms are valid. Creates a Recipe instance along with
        associated Ingredients and Instructions and then redirects to a
        success page.
        """
        self.object = form.save()
        ingredient_form.instance = self.object
        ingredient_form.save()
        instruction_form.instance = self.object
        instruction_form.save()
        return super(RecipeCreateView, self).form_valid(form, ingredient_form, instruction_form)

    def form_invalid(self, form, ingredient_form, instruction_form):
        """
        Called if a form is invalid. Re-renders the context data with the
        data-filled forms and errors.
        """
        return self.render_to_response(
            self.get_context_data(form=form,
                                  ingredient_form=ingredient_form,
                                  instruction_form=instruction_form))

urls.py

from django.urls import path


from recipes.views import (RecipeCreateView,
                            RecipeDetail)


app_name = 'recipes'


urlpatterns = [
    path('add',
            RecipeCreateView.as_view(),
            name = 'AddRecipe'),


    path('<slug:slug>',
            RecipeDetail.as_view(),
            name = 'RecipeDetail'),

]

template.html

<!DOCTYPE html>
<html>
<head>
    <title>Multiformset Demo</title>
    <script src="https://code.jquery.com/jquery-3.4.1.min.js" integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo="   crossorigin="anonymous"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery.formset/1.2.2/jquery.formset.js"></script>
    <script type="text/javascript">
        $(function() {
            $(".inline.{{ ingredient_form.prefix }}").formset({
                prefix: "{{ ingredient_form.prefix }}",
            })
            $(".inline.{{ instruction_form.prefix }}").formset({
                prefix: "{{ instruction_form.prefix }}",
            })
        })
    </script>
</head>

<body>
    <div>
        <h1>Add Recipe</h1>
        <form action="." method="post">
            {% csrf_token %}
            <div>
                {{ form.as_p }}
            </div>
            <fieldset>
                <legend>Recipe Ingredient</legend>
                {{ ingredient_form.management_form }}
                {{ ingredient_form.non_form_errors }}
                {% for form in ingredient_form %}
                    {{ form.id }}
                    <div class="inline {{ ingredient_form.prefix }}">
                        {{ form.description.errors }}
                        {{ form.description.label_tag }}
                        {{ form.description }}
                    </div>
                {% endfor %}
            </fieldset>
            <fieldset>
                <legend>Recipe instruction</legend>
                {{ instruction_form.management_form }}
                {{ instruction_form.non_form_errors }}
                {% for form in instruction_form %}
                    {{ form.id }}
                    <div class="inline {{ instruction_form.prefix }}">
                        {{ form.number.errors }}
                        {{ form.number.label_tag }}
                        {{ form.number }}
                        {{ form.description.errors }}
                        {{ form.description.label_tag }}
                        {{ form.description }}
                    </div>
                {% endfor %}
            </fieldset>
            <input type="submit" value="Add recipe" class="submit" />
        </form>
    </div>
</body>
</html>

1 Ответ

0 голосов
/ 05 мая 2019

Я думаю, вам нужно указать перенаправление на рецепты / тест в конце метода POST (который будет вызываться при отправке формы), в противном случае Django будет перенаправлен на рецепты / по умолчанию как стандарт.

...