stark——增刪改頁面

1、製做添加頁面

一、前置準備

(1)修改增刪改的視圖函數名

class ModelStark(object):

    def add_view(self, request):
        return HttpResponse("add")

    def delete_view(self, request, id):
        return HttpResponse("delete")

    def change_view(self, request, id):
        return HttpResponse("change")

(2)調整路由對應的視圖函數

class ModelStark(object):

    def get_urls_2(self):
        temp = []

        # 用name取別名app名+model名+操做名能夠保證別名不會重複
        model_name = self.model._meta.model_name
        app_label = self.model._meta.app_label
        temp.append(url(r"^add/", self.add_view, name="%s_%s_add" % (app_label, model_name)))
        temp.append(url(r"^(\d+)/delete/", self.delete_view, name="%s_%s_delete" % (app_label, model_name)))
        temp.append(url(r"^(\d+)/change/", self.change_view, name="%s_%s_change" % (app_label, model_name)))
        temp.append(url(r"^$", self.list_view, name="%s_%s_list" % (app_label, model_name)))
        return temp

(3)在查看頁面添加add按鈕

  首先在list_view中獲取add_url:css

class ModelStark(object):
    '''代碼省略'''
    def get_add_url(self):
        model_name = self.model._meta.model_name
        app_label = self.model._meta.app_label
        _url = reverse("%s_%s_add" % (app_label, model_name))
        return _url

    def list_view(self, request):
        '''代碼省略'''
        # 構建一個查看url
        add_url = self.get_add_url()

        return render(request, "list_view.html", locals())

  在list_view.html中添加「添加數據」按鈕:html

<body>
<h4>數據列表</h4>
<div class="container">
    <div class="row">
        <div class="col-md-9">
            {# <a href="add/" class="btn btn-primary">添加數據</a> #}
            <a href="{{ add_url }}" class="btn btn-primary">添加數據</a>
    """代碼省略"""
</body>
</html>

(4)重構模型

  因爲以前的表結構過於簡單,在進行添加操做時不少問題沒法發現,在這裏從新構造模型(一對1、一對多、多對多都有)。python

from django.db import models


# Create your models here.


class Author(models.Model):
    nid = models.AutoField(primary_key=True)
    name = models.CharField(max_length=32)
    age = models.IntegerField()

    # 與AuthorDetail創建一對一的關係
    authorDetail = models.OneToOneField(to="AuthorDetail", on_delete=models.CASCADE)

    def __str__(self):
        return self.name


class AuthorDetail(models.Model):
    nid = models.AutoField(primary_key=True)
    birthday = models.DateField()
    telephone = models.BigIntegerField()
    addr = models.CharField(max_length=64)

    def __str__(self):
        return self.telephone


class Publish(models.Model):
    nid = models.AutoField(primary_key=True)
    name = models.CharField(max_length=32)
    city = models.CharField(max_length=32)
    email = models.EmailField()

    def __str__(self):
        return self.name


class Book(models.Model):
    nid = models.AutoField(primary_key=True)
    title = models.CharField(max_length=32)
    publishDate = models.DateField()
    price = models.DecimalField(max_digits=5, decimal_places=2)

    # 與Publish創建一對多的關係,外鍵字段創建在多的一方
    publish = models.ForeignKey(to="Publish", to_field="nid", on_delete=models.CASCADE)
    # 與Author表創建多對多的關係,ManyToManyField能夠建在兩個模型中的任意一個,自動建立第三張表
    authors = models.ManyToManyField(to='Author', )

    def __str__(self):
        return self.title
app01/models.py

 

  同時將app01/admin.py和app01/stark.py中的內容清空從新進行構建。jquery

(5)刪除數據從新進行數據庫遷移

  1)刪除app01/migrations/下的文件git

  2)刪除db.sqlite3web

  3)數據遷移sql

manage.py@stark_demo > makemigrations
manage.py@stark_demo > migrate

(6)在stark中註冊表:

app01/stark.py:數據庫

from stark.service.stark import site, ModelStark
from django.utils.safestring import mark_safe
from django.urls import reverse
from .models import *

site.register(Book)
site.register(Publish)
site.register(Author)
site.register(AuthorDetail)

  到此頁面已經能夠正常訪問:django

  

二、自定製配置modelform來構建添加頁面

class ModelStark(object):
    def add_view(self, request):
        from django.forms import ModelForm
        from django.forms import widgets as wid

        class ModelFormDemo(ModelForm):
            class Meta:
                model = self.model
                fields = "__all__"
                # 不能使用這種方法,由於每一個表的字段是不一樣的
                # widgets = {
                #     "title": wid.TextInput(attrs={"class": "form-control"})
                # }
        form = ModelFormDemo()  # 實例化
        return render(request, "add_view.html", locals())

三、構建add_view.html模板

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <link rel="stylesheet" href="/static/bootstrap/css/bootstrap.css">
    <script src="/static/js/jquery-1.12.4.min.js"></script>
    <style>
        input,select {
            display: block;
            width: 100%;
            height: 34px;
            padding: 6px 12px;
            font-size: 14px;
            line-height: 1.42857143;
            color: #555;
            background-color: #fff;
            background-image: none;
            border: 1px solid #ccc;
            border-radius: 4px;
            -webkit-box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
            box-shadow: inset 0 1px 1px rgba(0, 0, 0, .075);
            -webkit-transition: border-color ease-in-out .15s, -webkit-box-shadow ease-in-out .15s;
            -o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
            transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
        }
    </style>
</head>
<body>
<h3>添加頁面</h3>
<div class="container">
    <div class="row">
        <div class="col-md-6 col-md-offset-3">
            <form action="" method="post">
                {% for field in form %}
                    <div>
                        <label for="">{{ field.label }}</label>
                        {{ field }}
                    </div>
                {% endfor %}
                <button type="submit" class="btn btn-default">提交</button>
            </form>
        </div>
    </div>
</div>
</body>
</html>
View Code

  因爲每一個表字段不一樣,所以不能使用wigets來給全部標籤添加form-control樣式,直接在頁面用css給input\select構建form-control的樣式。bootstrap

  顯示效果以下所示:

  

四、給全部字段更換爲中文

class ModelStark(object):
    """默認類,定製配置類"""
    list_display = ["__str__",]
    list_display_links = []
    modelform_class = []

    '''代碼省略'''

    def get_modelform_class(self):
        """用來獲取modelform類"""
        if not self.modelform_class:
            # 若是沒有值
            from django.forms import ModelForm
            from django.forms import widgets as wid

            class ModelFormDemo(ModelForm):
                class Meta:
                    model = self.model
                    fields = "__all__"

            return ModelFormDemo
        else:
            # 若是有值說明在用戶已經本身定製過了,直接取值
            return self.modelform_class

    def add_view(self, request):
        ModelFormDemo = self.get_modelform_class()
        form = ModelFormDemo()  # 實例化
        return render(request, "add_view.html", locals())

(1)定義get_modelform_class方法來獲取modelform類。若是在app01/stark.py中自定義配置類沒有modelform_class,則默認爲空,經過這個方法來獲取modelform。

(2)自定義配置Book類,並將字段顯示中文 

from stark.service.stark import site, ModelStark
from .models import *
from django.forms import ModelForm

class BookModelForm(ModelForm):
    class Meta:
        model = Book
        fields = "__all__"

        labels = {
            "title": "書籍名稱",
            "publishDate": "出版日期",
            "price": "價格",
            "publish": "出版社",
            "authors": "做者"
        }

class BookConfig(ModelStark):
    list_display = ["title", "price", "publishDate"]
    modelform_class = BookModelForm

site.register(Book, BookConfig)

(3)顯示效果:

  

五、添加信息提交

(1)add_view視圖函數中處理post請求:

class ModelStark(object):
    def add_view(self, request):
        ModelFormDemo = self.get_modelform_class()
        if request.method == "POST":
            form = ModelFormDemo(request.POST)
            if form.is_valid():  # 校驗字段所有合格
                form.save()
                return redirect(self.get_list_url())  # 跳轉到當前訪問表的查看頁面

            # (精髓)校驗有錯誤返回頁面,且包含了錯誤信息
            return render(request, "add_view.html", locals())

        form = ModelFormDemo()  # 實例化
        return render(request, "add_view.html", locals())

  注意校驗經過跳轉到當前訪問表的查看頁面;校驗不經過返回添加頁面,且包含錯誤信息。

(2)add_view.html在提交報錯時顯示錯誤信息

<style>
    input,select {
        /*代碼省略*/
    }
    .error {
        color: red;
    }
</style>

<body>
<h3>添加頁面</h3>
<div class="container">
    <div class="row">
        <div class="col-md-6 col-md-offset-3">
            <form action="" method="post" novalidate>
                {% csrf_token %}
                {% for field in form %}
                    <div>
                        <label for="">{{ field.label }}</label>
                        {{ field }} <span class="error pull-right">{{ field.errors.0 }}</span>
                    </div>
                {% endfor %}
                <button type="submit" class="btn btn-default pull-right">提交</button>
            </form>
        </div>
    </div>
</div>
</body>

(3)提交顯示效果以下所示:

  

  

2、製做編輯頁面

  編輯頁面視圖和模板都與添加頁面很是類似。

一、change_view視圖編寫

class ModelStark(object):

    def change_view(self, request, id):
        """編輯視圖"""
        ModelFormDemo = self.get_modelform_class()
        # 編輯對象
        edit_obj = self.model.objects.filter(pk=id).first()

        if request.method == "POST":
            form = ModelFormDemo(request.POST, instance=edit_obj)  # instance就是給這個記錄更改成最新的數據
            if form.is_valid():  # 校驗字段所有合格
                form.save()
                return redirect(self.get_list_url())  # 跳轉到當前訪問表的查看頁面

            # (精髓)校驗有錯誤返回頁面,且包含了錯誤信息
            return render(request, "add_view.html", locals())

        form = ModelFormDemo(instance=edit_obj)   # 用instance放入編輯對象就有了編輯數據

        return render(request, "change_view.html", locals())

  這裏最大的區別就是獲取了當前的編輯對象,使用instance放入編輯對象獲取編輯數據;同時在post請求中將記錄更新爲最新的數據。

  這裏是直接把add_view.html複製了一份作成了change_view.py,修改效果以下所示:

  

二、{% include 'form.html' %}優化代碼重複

建立一個form.html:

<div class="container">
    <div class="row">
        <div class="col-md-6 col-md-offset-3">
            <form action="" method="post" novalidate>
                {% csrf_token %}
                {% for field in form %}
                    <div>
                        <label for="">{{ field.label }}</label>
                        {{ field }} <span class="error pull-right">{{ field.errors.0 }}</span>
                    </div>
                {% endfor %}
                <button type="submit" class="btn btn-default pull-right">提交</button>
            </form>
        </div>
    </div>
</div>

add_view.html和change_view.html的body部分修改以下:

<body>
<h3>編輯頁面</h3>
{% include 'form.html' %}
</body>

3、製做刪除頁面

  刪除時不要直接刪除,須要提示確認。

class ModelStark(object):

    def delete_view(self, request, id):
        url = self.get_list_url()
        if request.method == "POST":
            self.model.objects.filter(pk=id).delete()
            return redirect(url)

        # self.model.objects.filter(pk=id).delete()
        return render(request, "delete_view.html", locals())

  一個form表單裏面只能有一個請求按鈕,所以確認刪除是按鈕,取消是一個a標籤跳轉到查看頁面。

  delete_view.html:

<body>
<h3>刪除頁面</h3>

<form action="" method="post">
    {% csrf_token %}
    <button>確認刪除?</button>
    <a href="{{ url }}">取消</a>
</form>
</body>

  執行效果:

  

  確認後顯示效果以下:

  

相關文章
相關標籤/搜索