云笔记项目

  • ​​云笔记项目​​
  • ​​项目准备​​
  • ​​shell操作​​
  • ​​settings.py​​
  • ​​用户注册模块​​
  • ​​用户登录模块​​
  • ​​网站首页​​
  • ​​笔记模型模块​​
  • ​​列表页​​
  • ​​注册后台​​
  • ​​项目部署​​

云笔记项目

云笔记项目 - 功能拆解
用户模块:注册、登陆、退出登陆
笔记模块:增删该查

项目准备

shell操作

创建项目文件夹

django-admin startproject tedu_note

创建用户模块

python manage.py startapp user

创建对应的数据库

mysql> create database tedu_note default charset utf8;

测试是否成功

python manage.py runserver

settings.py

禁用csrf中间件(一个防范csrf攻击的组件)

# setting.py
MIDDLEWARE = [
...
# 'django.middleware.csrf.CsrfViewMiddleware',
...
]

配置数据库

DATABASES = {
'default': {
'ENGINE': 'mysql',
'NAME': 'tedu_note',
'USER': 'root',
'PASSWORD': '2226958871',
'HOST': '127.0.0.1',
'PORT': '3306',
}
}

更改时区和地域

# 中文
LANGUAGE_CODE = 'zh-Hans'
# 亚洲/上海
TIME_ZONE = 'Asia/Shanghai'

Django小项目:云笔记项目_mysql

用户注册模块

先写好数据库的表单

# user/models.py
from django.db import models


# Create your models here.
class User(models.Model):
# 用户名属性
username = models.CharField("用户名", max_length=30, unique=True)
# 用户密码属性
password = models.CharField("密码", max_length=32)
# 创建时间属性
created_time = models.DateTimeField("创建时间", auto_now_add=True)
# 更新时间
updated_time = models.DateTimeField("更新时间", auto_now=True)

def __str__(self):
return "username %s" % self.username

生成迁移文件

python manage.py makemigrations
# user/migrations/*.py
# Generated by Django 2.2.12 on 2021-07-14 06:31

from django.db import migrations, models


class Migration(migrations.Migration):

initial = True

dependencies = [
]

operations = [
migrations.CreateModel(
name='User',
fields=[
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('username', models.CharField(max_length=30, unique=True, verbose_name='用户名')),
('password', models.CharField(max_length=32, verbose_name='密码')),
('created_time', models.DateTimeField(auto_now_add=True, verbose_name='创建时间')),
('updated_time', models.DateTimeField(auto_now=True, verbose_name='更新时间')),
],
),
]

数据迁移到数据库

python manage.py migrate
// mysql
show databases;
use tedu_note;
desc user_user;
+--------------+-------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+--------------+-------------+------+-----+---------+----------------+
| id | int | NO | PRI | NULL | auto_increment |
| username | varchar(30) | NO | UNI | NULL | |
| password | varchar(32) | NO | | NULL | |
| created_time | datetime(6) | NO | | NULL | |
| updated_time | datetime(6) | NO | | NULL | |
+--------------+-------------+------+-----+---------+----------------+
5 rows in set (0.01 sec)

现在来开始第一个路由:用户注册。此处采用分布式路由方法

首先打开template的APP许可

# settings.py
TEMPLATES = [
...
'APP_DIRS': True,
...
]

然后先在urls进行配置,并重user文件夹中新建urls.py文件

# urls.py
from django.contrib import admin
from django.urls import path, include

urlpatterns = [
path('admin/', admin.site.urls),
path('user/', include('user.urls'))
]

接下来是在user文件夹进行配置

cd user
mkdir templates
cd ./templates
mkdir user

接下来写东西

# user/views.py
from django.shortcuts import render
from django.http import HttpResponse
from .models import User


# Create your views here.
def reg_view(request):
# 注册
if request.method == 'GET':
# GET 返回页面
return render(request, 'user/register.html')
elif request.method == 'POST':
# POST 处理提交数据
username = request.POST['username']
password_1 = request.POST['password_1']
password_2 = request.POST['password_2']
# 1 两个密码要保持一致
if password_1 != password_2:
return HttpResponse("两次密码输入不一致")
# 2 当前用户名是否可用
old_user = User.objects.filter(username=username)
if old_user:
return HttpResponse("用户名已经被注册")
# 3 插入数据
User.objects.create(username=username, password=password_1)
return HttpResponse("注册成功")

我们可以加固一下密码:用哈希算法

m = hashlib.md5()
m.update(password_1.encode())
password_m = m.hexdigest()

我们可以来看看数据库的内容

mysql> select * from user_user;
+----+----------+----------------------------------+----------------------------+----------------------------+
| id | username | password | created_time | updated_time |
+----+----------+----------------------------------+----------------------------+----------------------------+
| 1 | lh | e10adc3949ba59abbe56e057f20f883e | 2021-07-14 07:32:34.103765 | 2021-07-14 07:32:34.103765 |
+----+----------+----------------------------------+----------------------------+----------------------------+
2 rows in set (0.00 sec)

免登陆一天

# 免登陆一天
request.session['username'] = username
request.session['id'] = user.id
# settings.py
SESSION_COOKIE_AGE = 60 * 10 * 6 * 24# 设置过期时间10分钟,默认为两周
SESSION_SAVE_EVERY_REQUEST = True
SESSION_EXPIRE_AT_BROWSER_CLOSE = True # 设置关闭浏览器时失效

用户登录模块

配置路由

urlpatterns = [
path('login', views.login_view)
]
def login_view(request):
if request.method == 'GET':
# 获取登陆页面
return render(request, "user/login.html")
elif request.method == 'POST':
# 处理数据
username = request.POST['username']
password = request.POST['password']

try:
user = User.objects.get(username=username)
except Exception as e:
print('--login user error %s' % e)
return HttpResponse('登陆失败')

# 比对密码
m = hashlib.md5()
m.update(password.encode())

if m.hexdigest() != user.password:
return HttpResponse('登陆失败')

# 免登陆一天
request.session['username'] = username
request.session['id'] = user.id

return HttpResponse("登陆成功 ")

下面是优化的免登陆的版本

def login_view(request):
if request.method == 'GET':
# 获取登陆页面
if request.session.get('username') and request.session.get('uid'):
return HttpResponse("已经登陆")
# 检查cookies
c_username = request.COOKIES.get('username')
c_uid = request.COOKIES.get('uid')
if c_username and c_uid:
# 回写session
request.session['username'] = c_username
request.session['uid'] = c_uid
return HttpResponse("已经登陆")
return render(request, "user/login.html")
elif request.method == 'POST':
# 处理数据
username = request.POST['username']
password = request.POST['password']

try:
user = User.objects.get(username=username)
except Exception as e:
print('--login user error %s' % e)
return HttpResponse('登陆失败')

# 比对密码
m = hashlib.md5()
m.update(password.encode())

if m.hexdigest() != user.password:
return HttpResponse('登陆失败')

# 免登陆一天
request.session['username'] = username
request.session['id'] = user.id

resp = HttpResponse("登陆成功 ")

if 'remember' in request.POST:
resp.set_cookie('username', username, 3600 * 24 * 3)
resp.set_cookie('uid', user.id, 3600 * 24 * 3)
return resp

网站首页

用分布式方法生成独立应用模块

python manage.py startapp index
# settings.py
INSTALLED_APPS = [
...
'index',
]
# index/index_view
from django.shortcuts import render


# Create your views here.
def index_view(request):
return render(request, 'index/index.html')
<!--index.html-->
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>首页</title>
</head>
<body>

{% if request.session.username %}
<p>
欢迎 {{ request.session.username }}
</p>
<p>
<a href="/user/logout">退出</a>
</p>
<p>
<a href="">进入我的笔记</a>
</p>
{% else %}
{% if request.COOKIES.username %}
<p>
欢迎 {{ request.COOKIES.username }}
</p>
<p>
<a href="/user/logout">退出</a>
</p>
<p>
<a href="">进入我的笔记</a>
</p>
{% else %}
<p>
<a href="/user/login">登陆</a>
</p>
<p>
<a href="/user/reg">注册</a>
</p>
{% endif %}
{% endif %}
</body>
</html>

写一写退出登陆模块

# user/logout
def logout_view(request):
request.session.flush()
response = HttpResponseRedirect('/index')
response.delete_cookie('username')
response.delete_cookie('uid')
return response

笔记模型模块

分布式构建笔记应用

python manage.py startapp note

数据迁移

python manage.py makemigrations
python manage.py migrate

进入数据库里面看看

mysql> desc note_note;
+--------------+--------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+--------------+--------------+------+-----+---------+----------------+
| id | int | NO | PRI | NULL | auto_increment |
| title | varchar(100) | NO | | NULL | |
| content | longtext | NO | | NULL | |
| created_time | datetime(6) | NO | | NULL | |
| updated_time | datetime(6) | NO | | NULL | |
+--------------+--------------+------+-----+---------+----------------+
5 rows in set (0.01 sec)

配置好路由

urlpatterns = [
path('admin/', admin.site.urls),
path('user/', include('user.urls')),
path('index/', include('index.urls')),
path('note/', include('note.urls'))
]

列表页

from django.urls import path
from . import views

urlpatterns = [
path('all', views.list_view),
path('add', views.add_view),
]

定义视图函数

import requests
from django.shortcuts import render
from django.http import HttpResponse, HttpResponseRedirect
from .models import Note


# Create your views here.
def check_login(fn):
def wrap(request, *args, **kwargs):
if 'username' not in request.session or 'uid' not in request.session:
# 检查cookies
c_username = request.COOKIES.get('username')
c_uid = request.COOKIES.get('uid')
if not c_username or not c_uid:
return HttpResponseRedirect('/user/login')
else:
# 回写session
request.session['username'] = c_username
request.session['uid'] = c_uid
return fn(request, *args, **kwargs)
return wrap


def list_view(request):
pass


@check_login
def add_view(request):
if request.method == 'GET':
return render(request, 'note/add_note.html')
elif request.method == 'POST':
# 处理数据
uid = request.session['uid']
title = request.POST['title']
content = request.POST['content']

Note.objects.create(title=title, content=content)
return HttpResponse("添加笔记成功")

注册后台

python manage.py createsuperuser

把数据放入后台

from django.contrib import admin
from .models import 模型类
# Register your models here.
admin.site.register(模型类)

Django小项目:云笔记项目_数据库_02

项目部署

我这个是Windows下的,所以得先把项目放置到服务器上(ssh连接)

?  ~ cd ./Pycharm
? Pycharm ls
db.sqlite3 index manage.py mysql note tedu_note user

安装相关的库

sudo pip3 install uwsgi
sudo apt-get install libmysqlclient-dev
pip install mysqlclient

启动uwsgi

uwsgi --ini uwsgi.ini
[uWSGI] getting INI configuration from uwsgi.ini