# 简易云笔记
**Repository Path**: xmlgrg/simple-cloud-notes
## Basic Information
- **Project Name**: 简易云笔记
- **Description**: Django搭建简易的一个云笔记小项目
settings.py DATABASES处修改自己的数据库配置
终端进入项目目录运行 python3 manage.py makemigrations和`python3 manage.py migrate` 完成数据库的迁移
终端进入项目目录运行 python3 manage.py runserver启动服务
http://127.0.0.1:8000/
- **Primary Language**: Python
- **License**: Not specified
- **Default Branch**: master
- **Homepage**: None
- **GVP Project**: No
## Statistics
- **Stars**: 0
- **Forks**: 3
- **Created**: 2022-09-13
- **Last Updated**: 2022-09-13
## Categories & Tags
**Categories**: Uncategorized
**Tags**: None
## README
# 云笔记练习
### 1. 创建项目cloud_note,新建应用user和note
```
tarena@tedu:~/2112$ django-admin startproject cloud_note
tarena@tedu:~/2112$ cd cloud_note/
tarena@tedu:~/2112/cloud_note$ python3 manage.py startapp user
tarena@tedu:~/2112/cloud_note$ python3 manage.py startapp note
```
### 2. 在settings.py中注册应用,为每个应用配置路由文件urls.py
```python
settings.py
INSTALLED_APPS = [
......
'user',
'note',
]
```
```python
user/urls.py
from django.urls import path
from . import views
urlpatterns = [
]
note/urls.py
from django.urls import path
from . import views
urlpatterns = [
]
```
### 3. 当用户访问/user/开头的路由时将功能转到user应用下处理,当用户访问/note/开头的路由时将功能转到note应用下处理
```python
cloud_note/urls.py
from django.urls import path, include
urlpatterns = [
path('admin/', admin.site.urls),
path('user/', include('user.urls')),
path('note/', include('note.urls')),
]
```
### 4. 分别在user应用的models.py中和note应用的models.py中创建模型User和Note(笔记中有)
```python
user/models.py
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 f"用户{self.username}"
note/models.py
from user.models import User
class Note(models.Model):
title = models.CharField('标题', max_length=100)
content = models.TextField('内容')
created_time = models.DateTimeField('创建时间', auto_now_add=True)
updated_time = models.DateTimeField('更新时间', auto_now=True)
user = models.ForeignKey(User, on_delete=models.CASCADE)
```
### 5. 在MySQL中新建数据库cloud_note 设置编码utf8
```mysql
mysql> create database cloud_note default charset utf8;
```
### 6. 修改settings.py中和数据库相关的配置文件链接到数据库cloud_note 完成迁移操作
```python
settings.py 76行
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'cloud_note',
'HOST': '127.0.0.1',
'PORT': '3306',
'USER': 'root',
'PASSWORD': '123456',
}
}
```
```
tarena@tedu:~/2112/cloud_note$ python3 manage.py makemigrations
tarena@tedu:~/2112/cloud_note$ python3 manage.py migrate
```
## 用户相关的功能
### 注册
#### 1. 当用户访问/user/reg时 创建视图函数reg_view 通过视图函数响应模板templates/user/register.html
```python
user/urls.py
path('reg/', views.reg_view),
user/views.py
def reg_view(request):
if request.method == 'GET':
return render(request, 'user/register.html')
elif request.method == 'POST':
pass
```
#### 2. 在项目目录中创建文件夹templates 修改settings.py中和templates 有关的配置DIRS
```python
settings.py
'DIRS': [os.path.join(BASE_DIR,'templates')],
```
#### 3. 在templates目录中创建user目录 在user目录中新建register.html
#### 4. 在register.html中编写一个form表单 接收用户输入的用户名和两次密码 提供一个注册按钮 访问http://127.0.0.1:8000/user/reg
```html
templates/user/register.html
注册页
```
#### 5. 当用户在页面中输入用户名和两次密码 点击提交按钮时,在user应用中的reg_view视图函数中处理注册功能
- 获取用户提交的数据 username password password2
- 校验数据是否可用:是否为空 用户名是否存在 两次密码是否一致
- 根据用户的数据创建user对象 成功后返回响应注册成功
```python
user/views.py
from django.http import HttpResponse
from django.shortcuts import render
from user.models import User
def reg_view(request):
if request.method == 'GET':
return render(request, 'user/register.html')
elif request.method == 'POST':
username = request.POST.get('username')
password = request.POST.get('password')
password2 = request.POST.get('password2')
if not username or not password:
return HttpResponse('用户名或密码不能为空')
user = User.objects.filter(username=username)
if user:
return HttpResponse('用户名太受欢迎了,换一个试试')
if password != password2:
return HttpResponse('两次密码不一致')
User.objects.create(username=username, password=password)
return HttpResponse('注册成功')
```
### 登录功能
#### 1. 当用户访问/user/login/时 定义视图函数login_view 响应模板templates/user/login.html
```python
user/urls.py
path('login/', views.login_view),
user/views.py
def login_view(request):
if request.method == 'GET':
return render(request, 'user/login.html')
elif request.method == 'POST':
pass
```
#### 2. 在templates目录中user目录下新建login.html
#### 3. 在模板login.html中 提供form表单,可以向/user/login/发送post请求,在表单中接收用户输入的用户名和密码,提供一个登录按钮
http://127.0.0.1:8000/user/login
```html
templates/user/login.html
登录页
```
#### 4. 如果用户在登录页输入用户名和密码提交数据时 17:00
- 获取用户post提交的数据 username password
- 校验数据是否可用 是否为空 用户名是否存在 密码是否正确
- 如果数据没有问题 将uname:用户名和uid:用户id保存到session中 完成登录操作
```python
user/views.py
def login_view(request):
if request.method == 'GET':
return render(request, 'user/login.html')
elif request.method == 'POST':
username = request.POST.get('username')
password = request.POST.get('password')
if not username or not password:
return HttpResponse('用户名或密码不能为空')
try:
user = User.objects.get(username=username)
except:
return HttpResponse('用户名或密码有误')
if user.password != password:
return HttpResponse('用户名或密码有误')
request.session['uname'] = user.username
request.session['uid'] = user.id
return HttpResponse('登录成功')
```
## 笔记相关功能
### 笔记列表——展示所有和用户先关的笔记
#### 1. 当用户访问/note/时 定义视图函数list_view,显示模板templates/note/list_note.html
```python
note/urls.py
path('', views.list_view),
note/views.py
def list_view(request):
return render(request, 'note/list_note.html')
```
#### 2. 在list_note.html中显示
- xxx的笔记
- 添加笔记的超链接
- 返回首页的超链接
- 展示所有笔记的表格
```html
templates/note/list_note.html
```
#### 3. 获取session中保存的用户名和用户id,根据用户id查找所有对应的笔记,将数据传递给模板
```python
note/views.py
from .models import Note
def list_view(request):
uname = request.session.get('uname')
uid = request.session.get('uid')
# 根基用户id查询笔记
notes = Note.objects.filter(user_id=uid)
return render(request, 'note/list_note.html', locals())
```
#### 4. 修改模板标签展示数据
```html
list_note.html
ID |
标题 |
创建时间 |
修改时间 |
修改 |
删除 |
{% for note in notes %}
{{ note.id }} |
{{ note.title }} |
{{ note.created_time }} |
{{ note.updated_time }} |
修改
|
删除
|
{% empty %}
用户很懒,什么也没写 |
{% endfor %}
```
### 为所有的笔记功能添加登录验证的装饰器
```python
note/views.py
from django.shortcuts import render, redirect
from .models import Note
# 定义一个装饰器进行登录认证
# 如果用户没有登录直接跳转到登录页面
def login_check(fn):
def wrap(request, *args, **kwargs):
# 在调用fn之前可以做一些事情
if 'uname' not in request.session and 'uid' not in request.session:
return redirect('/user/login/')
return fn(request, *args, **kwargs)
# 在调用fn之后可以做一些事情
return wrap
@login_check
def list_view(request):
uname = request.session.get('uname')
uid = request.session.get('uid')
# 根基用户id查询笔记
notes = Note.objects.filter(user_id=uid)
return render(request, 'note/list_note.html', locals())
@login_check
def add_view(request):
pass
@login_check
def mod_view(request):
pass
@login_check
def del_view(request):
pass
```
### 添加笔记功能
#### 1. 当用户访问/note/add/时 定义视图函数add_view 响应模板templates/note/add_note.html
```python
note/urls.py
path('add/', views.add_view),
note/views.py
@login_check
def add_view(request):
if request.method == 'GET':
return render(request, 'note/add_note.html')
elif request.method == 'POST':
pass
```
#### 2. 在模板add_note.html中 提供一个form表单 可以向/note/add/发送post请求 在表单中添加
- 可以接受用户输入的笔记标题(input)
- 接收用户输入的笔记内容(textarea)
- 提供保存按钮
- 返回列表页的超链接
```html
```
#### 3. 如果用户在页面中点击保存按钮,完成添加笔记操作
- 获取页面中post提交的表单数据
- 校验数据
- 根据用户提交的数据创建笔记对象
- 重定向到列表页
```python
@login_check
def add_view(request):
if request.method == 'GET':
return render(request, 'note/add_note.html')
elif request.method == 'POST':
title = request.POST.get('title')
content = request.POST.get('content')
if not title:
return HttpResponse('笔记必须有一个标题')
# 对用户输入的内容进行转义后保存 确保内容在浏览器解析时不会被当做标签或js代码运行
# from html import escape
content = escape(content)
# 获取用户的id
uid = request.session.get('uid')
Note.objects.create(title=title,content=content, user_id=uid)
return redirect('/note/')
```
### 修改笔记功能
#### 1. 当用户访问/note/mod//时 定义视图函数 mod_view
- 接收路由传递的参数 笔记的id
- 根据id查找笔记对象
- 响应模板note/mod_note.html,将笔记对象传递给模板
```python
urls.py
path('mod//', views.mod_view),
views.py
@login_check
def mod_view(request, id):
if request.method == 'GET':
note = Note.objects.get(id=id)
return render(request, 'note/mod_note.html', locals())
```
#### 2. 在mod_note.html中 定义一个可以向/note/mod//发送post请求的表单,在表单中提供
- 输入框,将当前笔记的主题作为输入框的值显示
- 保存按钮
- 返回列表页的链接
- 文本域,将当前笔记的内容放在文本域中显示
```html
```
#### 3. 当用户在页面中修改内容然后保存时
- 获取用户提交的数据 title content
- 检验数据是否可用
- 将当前笔记中的数据改为用户提交的数据
- 重定向到列表页
```python
@login_check
def mod_view(request, id):
note = Note.objects.get(id=id)
if request.method == 'GET':
return render(request, 'note/mod_note.html', locals())
elif request.method == 'POST':
title = request.POST.get('title')
content = request.POST.get('content')
if not title:
return HttpResponse('笔记必须有一个主题')
note.title = title
note.content = content
note.save()
return redirect('/note/')
```