前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >day96-day98-media配置&token时效&models字段auto_XX

day96-day98-media配置&token时效&models字段auto_XX

原创
作者头像
少年包青菜
修改2020-03-24 10:07:33
5590
修改2020-03-24 10:07:33
举报
文章被收录于专栏:Python 学习

1.涉及到图片上传的 media 设置,项目中一般仅配置一次

1.1models里面的类表有图片上传的字段

1.2settings里面的配置

代码语言:javascript
复制
# media配置
MEDIA_URL = "media/"
MEDIA_ROOT = os.path.join(BASE_DIR, "media")

1.3项目urls.py里面的配置

代码语言:javascript
复制
from django.conf.urls import url, include
from django.contrib import admin
# 复制
from LuffyProject import settings
from django.views.static import serve

urlpatterns = [
    url(r'^admin/', admin.site.urls),
    url(r'^api/course/', include('course.urls')),
    url(r'^', include('login.urls')),
    url(r'^', include('pay.urls')),
    # 复制
    url(r'media/(?P<path>.*)$', serve, {'document_root': settings.MEDIA_ROOT})
]

1.4项目启动后,会在项目目录下生成一个 media 的文件夹,里面存放的是上传的图片

1.5序列化器里面返回图片字段给前端

2.注册与登录

2.1序列化器

代码语言:javascript
复制
from rest_framework import serializers
from course import models
import hashlib


# 注册&登录序列化器
class AccountSerializer(serializers.ModelSerializer):
    class Meta:
        model = models.Account
        fields = ['username', 'pwd']

    def create(self, validated_data):
        username = validated_data['username']
        pwd = validated_data['pwd']

        user_obj = models.Account.objects.create(
            username=username,
            # 这是模拟前端传递密文密码
            pwd=hashlib.md5(pwd.encode()).hexdigest()
        )

        return user_obj

2.2注册与登录视图

代码语言:javascript
复制
# Create your views here.
import uuid

from rest_framework.response import Response
from rest_framework.views import APIView

from course import models
from . import serializers
from utlils import my_response


# 注册视图
class RegisterView(APIView):
    @staticmethod
    def post(request):
        try:
            ser_obj = serializers.AccountSerializer(data=request.data)
            if ser_obj.is_valid():
                ser_obj.save()
                return Response('注册成功!-->{}'.format(ser_obj.data))
        except Exception as error:
            error = error
            return Response('注册异常!')
        return Response('注册失败!')


# 登录视图
class LoginView(APIView):
    @staticmethod
    def post(request):
        login_obj = my_response.LoginResponse()
        username = request.data.get('username', '')
        pwd = request.data.get('pwd', '')
        if not username or not pwd:
            login_obj.code = 1010
            login_obj.error = '用户名或密码不能为空'
        else:
            try:
                user_obj = models.Account.objects.filter(
                    username=username,
                    pwd=pwd
                ).first()
                if not user_obj:
                    login_obj.code = 1020
                    login_obj.error = '用户名或密码错误'
                else:
                    user_obj.token = uuid.uuid4()
                    user_obj.save()
                    login_obj.msg = '登录成功'
                    # 登录之后返回 token
                    login_obj.token = user_obj.token
            except Exception as e:
                e = e
        # 对象调用__dict__,返回对象属性键值对
        return Response(login_obj.__dict__)

2.3my_response.py,作为使用,可以实现返回信息解耦

代码语言:javascript
复制
class LoginResponse:
    def __init__(self):
        self.code = 1000
        self.error = ''
        self.msg = ''

3.关于认证类校验token是否过期

3.1首先 models 里的字段一定存在 models.DateTimeField(auto_now=True)

3.2关于 auth_now 和 auth_now_add 的区别,day67也有讲述

3.2.1 auto_now=True

代码语言:javascript
复制
from django.db import models
class Book(models.Model):
    title = models.Charfield(max_length=32)
    date = models.Datefield(auto_now = True)

那么在更新数据是两种方法对auto_now的影响:

代码语言:javascript
复制
# 1.update方法:
models.Book.objects.filter(title='asd').update(title='ads')
# .update() 方法不会改变date的时间,还是保存着创建时的时间点


# 2.save()方法:
obj = models.Book.objects.filter(title='asd').first()
obj.title='ads'
obj.save()
# .save() 方法是保存了更改时的时间点

3.2.2 auto_now_add=True:

代码语言:javascript
复制
from django.db import models
class Book(models.Model):
    title = models.Charfield(max_length=32)
    date = models.Datefield(auto_now_add = True)

此时,update方法和.save()方法对时间都是无效的。

那么我们如何手动的更改时间呢?

方法如下:

代码语言:javascript
复制
models.Book.objects.filter(title='asd').update(date=datetime.datetime.now())

3.3认证类代码如下

1.1 token = request.META.get('HTTP_AUTHENTICATE','')

1.2 now() 函数返回当前时区的时间

代码语言:javascript
复制
from rest_framework.authentication import BaseAuthentication
from rest_framework.exceptions import AuthenticationFailed
from course import models
from django.utils.timezone import now


# 认证类
class MyAuthentication(BaseAuthentication):
    def authenticate(self, request):
        """从消息头获得 token"""
        token = request.META.get('HTTP_AUTHENTICATE', '')
        print(request.META)
        if not token:
            raise AuthenticationFailed('token不能为空')
        user_obj = models.Account.objects.filter(token=token).first()
        if not user_obj:
            raise AuthenticationFailed('token不合法')
        
        """获取上一次登录的时间"""
        old_time = user_obj.create_token_time
        """now()将返回本地时区的时间"""
        now_time = now()
        """判断 token 是否过期"""
        if (now_time - old_time).seconds > 20:
            raise AuthenticationFailed('token已经过期,请重新登录')

        return user_obj, token

3.4关于从消息头获取 token

3.5token过期时间的判断,时、分、秒,注意 from django.utils.timezone import now

代码语言:javascript
复制
from rest_framework.authentication import BaseAuthentication
from rest_framework.exceptions import AuthenticationFailed
from course import models
from django.utils.timezone import now


# 认证类
class MyAuthentication(BaseAuthentication):
    def authenticate(self, request):
        if request.method == 'OPTIONS':
            return None
        """从消息头获得 token"""
        token = request.META.get('HTTP_AUTHENTICATE', '')

        # print('request.META-->', request.META)

        if not token:
            raise AuthenticationFailed('token不能为空')
        user_obj = models.Account.objects.filter(token=token).first()
        if not user_obj:
            raise AuthenticationFailed('token不合法')

        """获取上一次登录的时间"""
        old_time = user_obj.create_token_time
        """now()将返回本地时区的时间"""
        now_time = now()
        """判断 token 是否过期"""
        if (now_time - old_time).seconds > 100000:
            raise AuthenticationFailed('token已经过期,请重新登录')

        return user_obj, token

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 1.涉及到图片上传的 media 设置,项目中一般仅配置一次
    • 1.1models里面的类表有图片上传的字段
      • 1.2settings里面的配置
        • 1.3项目urls.py里面的配置
          • 1.4项目启动后,会在项目目录下生成一个 media 的文件夹,里面存放的是上传的图片
            • 1.5序列化器里面返回图片字段给前端
            • 2.注册与登录
              • 2.1序列化器
                • 2.2注册与登录视图
                  • 2.3my_response.py,作为使用,可以实现返回信息解耦
                  • 3.关于认证类校验token是否过期
                    • 3.1首先 models 里的字段一定存在 models.DateTimeField(auto_now=True)
                      • 3.2关于 auth_now 和 auth_now_add 的区别,day67也有讲述
                        • 3.2.1 auto_now=True
                        • 3.2.2 auto_now_add=True:
                      • 3.3认证类代码如下
                        • 3.4关于从消息头获取 token
                          • 3.5token过期时间的判断,时、分、秒,注意 from django.utils.timezone import now
                          相关产品与服务
                          文件存储
                          文件存储(Cloud File Storage,CFS)为您提供安全可靠、可扩展的共享文件存储服务。文件存储可与腾讯云服务器、容器服务、批量计算等服务搭配使用,为多个计算节点提供容量和性能可弹性扩展的高性能共享存储。腾讯云文件存储的管理界面简单、易使用,可实现对现有应用的无缝集成;按实际用量付费,为您节约成本,简化 IT 运维工作。
                          领券
                          问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档