学习django整整10天辣!!虽然都是用碎片时间在学习,但是感觉还是学到了很多,这几天做了一个待办事项的demo,麻雀虽小五脏俱全,虽然前端真的很寒酸,但我的确没有那么多精力去美化前端了嘤嘤嘤。就用这篇博客记录整个源代码吧,然后再提取一些核心知识点方便以后查阅。
目录
最终效果
1.项目目录
虽然是小demo,但是目录结构都是严格按照做大项目做的,所以创建了一个todolist的文件夹,实现todolist这个app的全部代码都在这里面。app外没有什么逻辑实现的代码,但是相关配置还是有的,所以就已截图的方式圈出我的改动,app里面的代码全部粘贴了。
2.setting.py
3.urls
4.todolist_static
base.css
body{
background-color: #f7f9ff;
}
#topnav{
font-size:1.35em;
padding-left:5em;
padding-right:5em;
}
nav input{
width:70%!important
}
edit.css
#form-edit{
margin-left:10em;
margin-right:10em;
}
home.css
.no-underline>tr>td>a:hover{
text-decoration:none;
}
#line-through{
text-decoration:line-through;
}
5.about.html
{% extends "todolist/base.html"%}
{% block title%}
关于我们
{% endblock title%}
{% block 关于高亮%}
active
{% endblock 关于高亮%}
{% block main_content%}
<h4>一款小巧、简洁的待办清单工具,帮你规划日常事务</h4>
{% endblock main_content%}
6.base.html
<!doctype html>
{%load static%}
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<meta name="description" content="">
<meta name="author" content="">
<link rel="icon" href="../../../../favicon.ico">
<title>{% block title%}未命名{% endblock title%}</title>
<!--lable icon-->
<link href="{% static 'todolist/icons/icon_list.png' %}" rel="shortcut icon" />
<!-- Bootstrap core CSS -->
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/css/bootstrap.min.css" integrity="sha384-MCw98/SFnGE8fJT3GXwEOngsV7Zt27NXFoaoApmYm81iuXoPkFOJwJ8ERdknLPMO" crossorigin="anonymous">
<!-- custom style for this template-->
<link rel="stylesheet" href="{% static 'todolist/css/base.css' %}">
<link rel="stylesheet" href="{% block css%}{% endblock css%}">
</head>
<body>
<nav class="navbar navbar-expand-md navbar-dark bg-dark mb-4" id="topnav">
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarCollapse" aria-controls="navbarCollapse" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="navbarCollapse">
<ul class="navbar-nav mr-auto">
<li class="nav-item {% block 主页高亮%}{% endblock 主页高亮%}">
<a class="nav-link" href="{% url 'todolist:主页'%}">待办清单</a>
</li>
<li class="nav-item {% block 关于高亮%}{% endblock 关于高亮%}">
<a class="nav-link" href="{% url 'todolist:关于'%}">关于本站</a>
</li>
</ul>
<!--action 表单的信息发送到哪里去-->
<!--{% csrf_token %}防止跨站攻击-->
{% block add%}
{% endblock add%}
</div>
</nav>
<main role="main" class="container">
<br>
{% block main_content%}
{% endblock main_content%}
</main>
<!-- Bootstrap core JavaScript
================================================== -->
<!-- Placed at the end of the document so the pages load faster -->
<script src="https://code.jquery.com/jquery-3.3.1.slim.min.js" integrity="sha384-q8i/X+965DzO0rT7abK41JStQIAqVgRVzpbzo5smXKp4YfRvH+8abtTE1Pi6jizo" crossorigin="anonymous"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.3/umd/popper.min.js" integrity="sha384-ZMP7rVo3mIykV+2+9J3UJ46jBk0WLaUAdn689aCwoqbBJiSnjAK/l8WvCWPIPm49" crossorigin="anonymous"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/js/bootstrap.min.js" integrity="sha384-ChfqqxuZUCnJSK3+MXmPNIyE6ZbWh2IMqE241rYiqJxyMiZ6OW/JmZQ5stwEULTy" crossorigin="anonymous"></script>
</body>
</html>
7.home.htm
{% extends "todolist/base.html"%}
{%load static%}
{% block css%}{% static 'todolist/css/home.css' %}{% endblock css%}
{% block title%}你的个人待办清单{% endblock title%}
{% block 主页高亮%}active{% endblock 主页高亮%}
{% block add%}
<form class="form-inline mt-2 mt-md-0" method="POST" action="">
{% csrf_token %}
<input class="form-control mr-sm-2" type="text" placeholder="待办事项" aria-label="Search" name="待办事项">
<button class="btn btn-outline-success my-2 my-sm-0" type="submit">添加</button>
</form>
{% endblock add%}
{% block main_content%}
{% if 警告%}
<div class="alert alert-warning alert-dismissible fade show" role="alert">
<strong>{{ 警告 }}</strong>
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
{% endif %}
{% if 信息%}
<div class="alert alert-warning alert-dismissible fade show" role="alert">
<strong>{{ 信息 }}</strong>
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
{% endif %}
<br>
<table class="table table-hover">
<thead>
<tr>
<th scope="col">序号</th>
<th scope="col">待办事项</th>
<th scope="col">编辑</th>
<th scope="col">划掉</th>
<th scope="col">删除</th>
</tr>
</thead>
<tbody class="no-underline">
{% for 每一件事 in 全部清单 %}
{% if 每一件事.done%}
<tr class="table-dark">
<th scope="row" class="text-dark">{{forloop.counter}}</th>
<td class="text-dark" id="line-through">{{每一件事.thing}}</td>
<td><a class="text-secondary" href="#">不可编辑</a></td>
<td>
<form method="POST" action="{% url 'todolist:划掉' 每一件事.id %}">
{% csrf_token %}
<input name="完成状态" type="hidden" value="未完成" >
<button type="submit" class="btn btn-outline-success my-2 my-sm-0" >撤销</button>
</form>
</td>
<td>
<!-- Button trigger modal -->
<button data-toggle="modal" data-target="#exampleModal" type="button" class="btn btn-outline-success my-2 my-sm-0" >删除</button>
<!-- Modal -->
<div class="modal fade" id="exampleModal" tabindex="-1" role="dialog" aria-labelledby="exampleModalLabel" aria-hidden="true">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="exampleModalLabel">请确认</h5>
<button type="button" class="close" data-dismiss="modal" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
<div class="modal-body">
确定要删除该未办事项吗?{{每一件事.thing}}
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-dismiss="modal">取消</button>
<form method="POST" action="{% url 'todolist:删除' 每一件事.id %}">
{% csrf_token %}
<button type="submit" class="btn btn-primary">确认</button>
</form>
</div>
</div>
</div>
</div>
</td>
</tr>
{% else %}
<tr>
<th scope="row">{{forloop.counter}}</th>
<td>{{每一件事.thing}}</td>
<td><a class="text-info" href="{% url 'todolist:新编辑' 每一件事.id %}">
<button type="submit" class="btn btn-outline-success my-2 my-sm-0">编辑</button>
</a></td>
<td>
<form method="POST" action="{% url 'todolist:划掉' 每一件事.id %}">
{% csrf_token %}
<input name="完成状态" type="hidden" value="已完成" >
<button type="submit" class="btn btn-outline-success my-2 my-sm-0">划掉</button>
</form>
</td>
<td>
<!-- Button trigger modal -->
<button data-toggle="modal" data-target="#exampleModal{{forloop.counter}}" type="button" class="btn btn-outline-success my-2 my-sm-0" >删除</button>
<!-- Modal -->
<div class="modal fade" id="exampleModal{{forloop.counter}}" tabindex="-1" role="dialog" aria-labelledby="exampleModal{{forloop.counter}}Label" aria-hidden="true">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="exampleModal{{forloop.counter}}Label">请确认</h5>
<button type="button" class="close" data-dismiss="modal" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
<div class="modal-body">
确定要删除该未办事项吗?{{每一件事.thing}}
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-dismiss="modal">取消</button>
<form method="POST" action="{% url 'todolist:删除' 每一件事.id %}">
{% csrf_token %}
<button type="submit" class="btn btn-primary">确认</button>
</form>
</div>
</div>
</div>
</div>
</td>
</tr>
</tr>
{% endif %}
{% endfor %}
</tbody>
</table>
{% endblock main_content%}
8.newedit.html
{% extends "todolist/base.html"%}
{%load static%}
{% block css%}{% static 'todolist/css/edit.css'%}{% endblock css%}
{% block title%}
编辑页面
{% endblock title%}
{% block main_content%}
<form id="form-edit" method="POST" action="">
{% csrf_token %}
<div class="form-group">
<label for="editTodo"></label>
<input name="已修改事项" class="form-control form-control-lg" id="editTodo" type="text" value="{{待修改事项}}">
<small id="help" class="form-text text-muted">在这里编辑待办事项</small>
</div>
{{警告}}
<button type="submit" class="btn btn-primary btn-lg btn-block">提交</button>
</form>
{% endblock main_content%}
9.apps.py
from django.apps import AppConfig
class TodolistConfig(AppConfig):
name = 'todolist'
10.models.py
from django.db import models
#创建Model
#制作迁移文件
#真正迁移
# Create your models here.
class Todo(models.Model):
thing = models.CharField(max_length=50)
done = models.BooleanField(default=False)
def __str__(self):
return self.thing
11.urls.py
from django.urls import path
from . import views
app_name='todolist' # 与app同名,为了避免命名冲突
urlpatterns = [
path('home/',views.home, name='主页'),
path('about/',views.about, name='关于'),
path('edit/', views.edit, name='编辑'),
path('delete/<每一件事_id>', views.delete, name='删除'),
path('cross/<每一件事_id>', views.cross, name='划掉'),
path('newedit/<每一件事_id>', views.newedit, name='新编辑'),
]
# !!!!delete传过来的地址后面加了数字,用<forloop_counter>代替,forloop_counter会传递到函数delete里面
# /delete/1
12.views.py
from django.shortcuts import render,redirect
from .models import Todo
# Create your views here.
# lst = [
# {'待办事项': '遛狗', '已完成': False},
# {'待办事项': '逛街', '已完成': False},
# {'待办事项': '泡脚', '已完成': True},
# ]
def home(request):
if request.method == 'POST':
if request.POST['待办事项'] == '':
content = {'全部清单':Todo.objects.all(), '警告':'请输入内容!'}
return render(request, "todolist/home.html", content)
else:
a_row = Todo(thing=request.POST['待办事项'])
a_row.save()
content = {'全部清单':Todo.objects.all(), '信息':'添加成功!'}
return render(request,"todolist/home.html", content)
elif request.method == 'GET':
content = {'全部清单': Todo.objects.all()}
return render(request, "todolist/home.html" ,content) # 渲染出一个逻辑,返回给用户
def about(request):
return render(request,'todolist/about.html') # 渲染出一个逻辑,返回给用户
def edit(request):
return render(request,'todolist/edit.html') # 渲染出一个逻辑,返回给用户
def newedit(request,每一件事_id):
if request.method == 'POST':
if request.POST['已修改事项'] =='':
return render(request, 'todolist/newedit.html', {'警告':'请输入内容!'})
else:
a = Todo.objects.get(id=每一件事_id)
a.thing = request.POST['已修改事项']
a.save()
return redirect("todolist:主页")
elif request.method == 'GET':
content1 = {'待修改事项': Todo.objects.get(id=每一件事_id).thing }
return render(request,'todolist/newedit.html',content1) # 渲染出一个逻辑,返回给用户
def delete(request, 每一件事_id): # 完成删除的逻辑处理,然后再把网页跳转到主页
# 先要知道用户点的那个条记录,然后再删
# 利用forloot_counter,从1开始计数的
a = Todo.objects.get(id=每一件事_id)
a.delete()
return redirect("todolist:主页")
# def cross(request, thing_id): # 完成划掉的逻辑处理,然后再把网页跳转到主页
# if request.POST['完成状态'] == '已完成':
# lst[int(forloop_counter)-1]['已完成']=True
# return redirect("todolist:主页")
# else:
# lst[int(forloop_counter) - 1]['已完成'] = False
# return redirect("todolist:主页")
def cross(request, 每一件事_id): # 完成划掉的逻辑处理,然后再把网页跳转到主页
if request.POST['完成状态'] == '已完成':
a= Todo.objects.get(id=每一件事_id)
a.done = True
a.save()
return redirect("todolist:主页")
else:
a = Todo.objects.get(id=每一件事_id)
a.done = False
a.save()
return redirect("todolist:主页")
总结
- 数据之间的传递用到了sqlite3数据库,是django自带的,很轻很好用,但可能不适合大型网站
- 数据库的表是通过model管理的,需要建立迁移文件,然后再迁移,如果model改变了,一定要记得再建一次迁移文件然后迁移
- 数据库的后台数据可以进入admin页面去查看,但在这之前要在cmd里面创建一个超级用户,admin后台管理也是django自带的,简直太强大了!
- 操作数据库中的数据,增加和修改都要调用一下save方法,这点非常容易忘记
- 用户的每一次点击,都需要给反馈,return或者redirect,这点也不要忘了
- 关于页面间数据传递,业务逻辑处理的的具体实现都在代码里面了,需要用的时候再来看吧
- django这一块,到这里就阶段性收摊了...