MTV newbie issues with Python Django
Question: I am kinda new with the MVC and MTV concept and i am trying to learn Python
Django. I want to make catalog with books, must have add and delete
functionality. I am trying to follow best practices and working with Generic
views, but kinda stuck at the end, i feel that i am missing something very
small but i cant figure it out - to be honest i am very exhausted at this
moment and i dont have much time. So this is my code: Models:

    
    
    class Books(models.Model):
        title = models.CharField(max_length=200)
        author = models.CharField(max_length=200)
        isbn = models.CharField(max_length=200)
        pages = models.IntegerField(default=0)
    
        def __unicode__(self):
            return self.title
    
    
    class BooksForm(ModelForm):
        class Meta:
            model = Books
    

Views:

    
    
    # coding: utf-8
    
    from django.core.urlresolvers import reverse_lazy
    from django.views.generic import ListView, UpdateView, CreateView, DetailView
    
    
    from models import Book
    
    
    class BooksDetailView(DetailView):
        model = Book
        template_name = "books_portal/details.html"
    
    
    class BooksCreateView(CreateView):
        model = Book
        template_name = "books_portal/add.html"
        success_url = reverse_lazy('books_portal')
    
    
    class BooksUpdateView(UpdateView):
        model = Book
        template_name = "books_portal/add.html"
        success_url = reverse_lazy('books_portal')
    
    
    class BooksListView(ListView):
        model = Book
        context_object_name = 'books_list'
        template_name = "books_portal/index.html"
    
        def get_queryset(self):
            return Book.objects.order_by('author')[:5]
    

Templates: add.html

    
    
    {% extends "books_portal/base.html" %}
    
    {% block title %}Add books{% endblock %}
    
    {% block extracss %}
    <style>
        .top-buffer { margin-top:20px; }
        .bs-docs-nav { background-color: #563d7c; }
    </style>
    {% endblock extracss %}
    
    {% block content %}
            <form action="" method="post" class="form-horizontal" role="form">{% csrf_token %}
                <div class="row top-buffer">
                    <div class="col-md-1">
                        {{form.title.label_tag}}
                        <input type="text" value="" class=""/>
                    </div>
                </div>
                <div class="row top-buffer">
                    <div class="col-md-1">
                        {{form.author.label_tag}}
                        <input type="text" value="" class=""/>
                    </div>
                </div>
                <div class="row top-buffer">
                    <div class="col-md-2 col-md-offset-1">
                        <input type="submit" value="Save" class="btn btn-primary btn-lg"/>
                    </div>
                </div>
            </form>
    {% endblock %}
    

base.html

    
    
    <!DOCTYPE html>
        <html>
            <head>
                <title>{% block title %}{{title|default:"Book Library"}}{% endblock %}</title>
                <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
                {% block extracss %}{% endblock extracss %}
            </head>
            <body>
                <div class="container">
                    <div class="navbar-header">
                        <a href="{% url 'books_portal' %}" class="navbar-brand">Books Portal</a>
                    </div>
                    {% block content %}
                    {% endblock %}
                </div>
    
                {% block extrajs %}{% endblock extrajs %}
            </body>
        </html>
    

details.html

    
    
    {% extends "books_portal/base.html" %}
    
    {% block title %}Details{% endblock %}
    
    {% block extracss %}
    <style>
        .top-buffer { margin-top:20px; }
        .bs-docs-nav { background-color: #4CD085; }
    </style>
    {% endblock extracss %}
    
    {% block content %}
             <div class="row top-buffer">
                    <div class="col-md-1">
                        <strong>Title:</strong>
                    </div>
                    <div class="col-md-2">
                        {{book.title}}
                    </div>
                </div>
                <div class="row top-buffer">
                    <div class="col-md-1">
                        <strong>Author:</strong>
                    </div>
                    <div class="col-md-2">
                        {{book.author}}
                    </div>
                </div>
                <div class="row top-buffer">
                    </div>
            <div class="row">
                <div class="col-md-1 col-md-offset-1 text-center"><a href="{% url 'books_portal' %}" class="btn btn-primary btn-lg">OK</a></div>
            </div>
    {% endblock %}
    

index.html

    
    
    {% extends "books_portal/base.html" %}
    
        {% block title %}Collection of books{% endblock %}
    
        {% block extracss %}
        <style>
            .top-buffer { margin-top:20px; }
            .bs-docs-nav { background-color: #563d7c; }
        </style>
        {% endblock extracss %}
    
        {% block content %}
            <table class="table table table-hover">
                <tr>
                    <th class="text-center">Title</th>
                    <th class="text-center">Author</th>
                    <th class="text-center">Edit</th>
                </tr>
                {% for book in books_list %}
                <tr>
                    <td class="text-center"><a href="{% url 'books_details' pk=book.id%}">{{ book.title }}</a></td>
                    <td class="text-center">{{ book.author }}</td>
                    <td class="text-center"><a href="{% url 'books_edit' pk=book.id%}" class="btn btn-default">Delete</a></td>
                </tr>
                {% endfor %}
            </table>
            <div class="row">
                <div class="col-md-2 col-md-offset-5 text-center"><a href="{% url 'books_add' %}" class="btn btn-primary btn-lg">Add</a></div>
            </div>
        {% endblock %}
    

Currently i cant add or delete any books, any help will be appreciated. Thank
you.


Answer: I've cut and pasted all your code, plus a relevant urls.py, into a new
project. The immediate problem is that you're not showing any form errors in
your add.html. You can just add `{{ form.errors }}` at the top of the
template.

Once you've done that, you'll see the actual issue: you're not providing all
relevant fields when creating your book. In fact, Django can't see _any_
fields, because you haven't given any of the inputs `name` attributes. Really,
you shouldn't create the `input` elements manually: you should get Django to
do that, because then it also takes responsibility for prepopulating the field
with the existing value either when re-showing the form with errors, or when
editing an existing Book. It should look like this:

    
    
    {{ form.title.label_tag }}
    {{ form.title }}
    {{ form.title.errors }}
    

Then the outstanding issue is that you're not including the `isbn` or `pages`
fields, which your model is treating as required. You can either set them as
`blank=False` in the model, or use an `exclude` list in the ModelForm. Either
way, you'll need `null=False` in the model field for `pages`.

Or, of course, you can add them to the form. To be honest, the easiest thing
for you to do now, while you're learning, is to replace all the HTML inside
your `<form>` tag with just `{{ form.as_p }}`, so that Django outputs
everything for you.

