零基础入门学django框架,超详细基础知识(五)

django基础知识(五)

缓存

定义:

缓存是一类可以更快的读取数据的介质统称,也指其它可以加快数据读取的存储方式。一般用来存储临时数据,常用介质的是读取速度很快的内存

意义:

视图渲染有一定成本,数据库的频繁查询过高;

所以对于低频变动的页面可以考虑使用缓存技术,减少实际渲染次数;

用户拿到响应的时间成本会更低

缓存场景特点:

缓存的地方,数据变动频率较少

Django中设置缓存
  • 数据库缓存

    • 将缓存的数据存储在数据库中

    • 说明:尽管存储介质没有更换,但是当把一次负责查询的结果直接存储到表里,比如多个条件的过滤查询结果,可避免重复进行复杂查询,提升效率;

    • 配置:

      CACHES = {
      	'default': {
      		'BACKEND': 'django.core.cache.backends.db.DatabaseCache',
      		'LOCATION': 'my_cache_table', #初始化表:python manage.py createcachetable
      		'TIMEOUT': 300,#缓存保存时间单位秒,默认值为300,
      		'OPTIONS':{
      				'MAX_ENTRIES': 300,#缓存最大数据条数
      				'CULL_FREQUENCY':2,#缓存条数达到最大值时删除1/x的缓存数据
      			}
      	}
      }
      
  • 本地存储缓存

    • 数据缓存到服务器内存中

    • 配置样例:

      CACHES = {
      	'default': {
      		'BACKEND': 'django. core.cache.backends . locmem. LocMemcache ' ,
      		'LOCATION': 'unique-snowflake' #雪花算法
      	}
      }
      
  • 文件系统缓存

    • 将缓存的数据存储到本地文件中

    • 配置样例:

      CACHES = {
          	'default': {
          	'BACKEND':'django.core.cache.backends.filebased.FileBasedcache ',
          	'LOCATION': '/var/tmp/django_cache ',#这个是文件夹的路径
      	# 'LocATION': 'c : \ test\cache ' ,#windows下示例
      	}
      }
      
Django缓存策略:
  • 整体缓存策略:

    • 视图函数中:

      from django.views.decorators.cache import cache_page
      @cache_page(30) ->单位s #当前缓存存储时间
      def my_view(request):
      	...
      
    • 路由中:

      from django.views.decorators.cache import cache_page
      ur1patterns = [
      			path( 'foo/', cache_page(60)(my_view) ),
      ]
      
  • 局部缓存策略:

    • 缓存api的使用

      ​ 先引入cache对象

      方式1∶使用caches[ 'CACHE配置key]导入具体对象
      	from django.core.cache import caches
      	cache1- caches ['myalias']
      	cache2 = caches ['myalias_2']
      方式2∶
      	from django.core.cache import cache
      	相当于直接引入 CACHES配置项中的'default'项
      
    • cache.set(key, value, timeout)-存储缓存

      • key:缓存的key,字符串类型
      • value:Python对象
      • timeout:缓存存储时间(s),默认为CACHES中的TIMEOUT值
      • 返回值:None
    • cache.get(key)- 获取缓存

      • key:缓存的key
      • 返回值:为key的具体值,如果没有数据,则返回None
    • cache.add(key,value)-存储缓存,只在key不存在时生效

      • 返回值: True[存储成功] or False[存储失败]
    • cache.get_or_set(key, value, timeout)- 如果未获取到数据则执行set操作

      • 返回值: value
    • cache.set_many(dict,timeout)-批量存储缓存

      • dict: key和value的字典
      • timeout:存储时间(s)
      • 返回值:插入不成功的key的数组
    • cache.get_many(key_list)-批量获取缓存数据

      • key_list:包含key的数组
      • 返回值:取到的key和value的字典
    • cache.delete(key) -删除key的缓存数据

      • 返回值: None
    • cache.delete_many(key_list)-批量删除

      • 返回值: None
  • 浏览器缓存策略

    • 强缓存

      不会向服务器发送请求,直接从缓存中读取资源

      • 响应头- Expires
        • 定义:缓存过期时间,用来指定资源到期的时间,是服务器端的具体的时间点
        • 样例: Expires:Thu, 02 Apr 2030 05:14:08 GMT
      • 响应头- Cache-Control
        • 在HTTP/1.1中,Cache-Control主要用于控制网页缓存。
        • 比如当Cache-Control:max-age=120‘代表请求创建时间后的120秒,缓存失效
        • 说明:目前服务器都会带着这两个头同时响应给浏览器,浏览器优先使用Cache-Control
    • 协商缓存

      强缓存的数据过期后,还需要跟服务器进行通信,从而获取最新数据;

      如果强缓存的数据是一些静态文件,大图片等这类比较费带宽且不易变化的数据,强缓存时间到期后,浏览器会去跟服务器协商,当前缓存是否可用,如果可用:服务器不必返回数据,浏览器继续使用原来缓存的数据;如果不可用:则返回最新数据

      • Last-Modified响应头和If-Modified-Since请求头说明:
        (1) Last-Modified为文件的最近修改时间,浏览器第一次请求静态文件时,
        服务器如果返回Last-Modified响应头,则代表该资源为需协商的缓存
        (2) 当缓存到期后,浏览器将之前获取到的Last-Modified值做为请求头

      • lf-Modified-Since的值,与服务器发请求协商,服务端返回304响应码[响应体为空],代表缓存继续使用,200响应码代表缓存不可用[响应体为最新资源]

      • ETag响应头和If-None-Match请求头
        (1) Etag是服务器响应请求时,返回当前资源文件的一个唯一标识(由服务器生成),只要资源有变化, Etag就会重新生成;
        (2) 缓存到期后,浏览器将ETag响应头的值做为lf-None-Match请求头的值,给服务器发请求协商;服务器接到请求头后,比对文件标识,不一致则认为资源不可用,返回200响应码[响应体为最新资源];可用则返回304响应码

        **对比:**Last-Modified VS Etag
        精度不一样 – Etag准确率更高
        性能上 - Last-Modified高,Etag需要计算文件标识
        优先级 – Etag 高;两个头同时出现,浏览器优先取Etag

中间件

定义:
	- 中间件是 Django请求/响应处理的钩子框架。它是一个轻量级的、低级的“插件"系统,用于
		全局改变 Django的输入或输出。
	- 中间件以类的形式体现
	- 每个中间件组件负责做一些特定的功能。例如,Django包含一个中间件组件AuthenticationMiddleware,
		它使用会话将用户与请求关联起来。
编写中间件:
	- 中间件类须继承自django,utils.deprecation.MiddlewareMixin类
  • 中间件类须实现下列五个方法中的一个或多个:
    - process_request(self,request)
    执行路由之前被调用,在每个请求上调用,返回None或HttpResponse对象
    - process_view(self, request, callback, callback_args,callback_kwargs)
    调用视图之前被调用,在每个请求上调用,返回None或HttpResponse对象
    - process_response(self, request, response)
    所有响应返回浏览器被调用,在每个请求上调用,返回HttpResponse对象
    - process_exception(self, request, exception)
    当处理过程中抛出异常时调用,返回一个HttpResponse对象
    - process_template_response(self,request, response)
    在视图函数执行完毕且试图返回的对象中包含render方法时被调用;该方法需要返回实现了render方法的响应对象
    注: 中间件中的大多数方法在返回None时表示忽略当前操作进入下一项事件,当返回HttpResponese对象时表示此请求结束,直接返回给客户端
注册中间件
settings.py中需要注册一下自定义的中间件
	MIDDLEWARE = [
		...
		'middleware.mymiddleware.MyMW2',
	]

**注意:**配置为数组,中间件被调用时以‘先上到下’,进入视图后再‘由下到上’的顺序调用

练习1:

用中间件实现强制某个IP地址只能向/test开头的地址发送5次请求提示:

class VisitLimit(MiddlewareMixin):
	visit_times = {}
	def process_request(self,request):
		ip_address = request.META['REMOTE_ADDR'] #远程客户端的IP地址
		path_url = request.path_info #客户端访问的请求路由信息
		if not re.match('^/test',path_url):
			return
		times = self.visit_times.get(ip_address,0)
		print('ip',ip_address,'已经访问',times)
		self.visit_times[ip_address] = times + 1
		if times < 5:
			return
		return HttpResponse('您已经访问过' + str(times) + '次,访问被禁止')
中间件执行总流程
  • CSRF攻击 - 跨站伪造请求攻击

    • 定义:某些恶意网站上包含链接、表单按钮或者JavaScript,它们会利用登录过的用户在浏览器中的
    • 认证信息试图在你的网站上完成某些操作,这就是跨站请求伪造(CSRF,即Cross-Site Request Forgey)。
  • CSRF防范:

    • django采用’比对暗号’机制防范攻击

    • Cookies中存储暗号1,模板中表单里藏着暗号2,用户只有在本网站下提交数据,暗号2才会随表单提交给服务器, django对比两个暗号,对比成功,则认为是合法请求,否则是违法请求-403响应码

    • 配置步骤:

      1. settings.py中确认MIDDLEWARE django.middleware.csrf.CsrfViewMiddleware是否打开
      2. 模板中, form标签中添加如下标签:{% csrf_token %}
      
    • 特殊说明:

      • 如果某个视图不需要django进行csrf保护,可以用装饰器关闭对此视图的检查

      • 样例:

        from django.views.decorators.csrf import csrf_exempt
        @csrf_exempt
        def my_view(request):
        	return HttpResponse('He1lo wor1d')
        

分页

定义:

分页是指在web页面有大量数据需要显示,为了阅读方便在每个页页中只显示部分数据。

优点:
  • 方便阅读
  • 减少数据提取量,减轻服务器压力。
django中分页的实现:

Django提供了Paginator类可以方便的实现分页功能

Paginator类位于django.core.paginator模块中。

Paginator对象
  • 定义:负责分页数据整体的管理

  • 对象的构造方法

    paginator = Paginator(object_list, per_page)

    ​ 参数

    • object_list需要分类数据的对象列表
    • per_page每页数据个数

    ​ 返回值:

    • Paginator的对象
  • Paginator属性:

    • count:需要分页数据的对象总数
    • num_pages:分页后的页面总数
    • page_range:从1开始的range对象,用于记录当前面码数
    • per_page每页数据的个数
  • Paginator方法:paginator对象.page(number)

    • 参数number为页码信息(从1开始)
    • 返回当前number页对应的页信息
    • 如果提供的页码不存在,抛出lnvalidPage异常
      • lnvalidPage:总的异常基类,包含以下两个异常子类:
        • PageNotAnInteger:当向page()传入一个不是整数的值时抛出
        • EmptyPage:当向page()提供一个有效值,但是那个页面上没有任何对象时抛出
Page对象
  • 定义:负责具体某一页的数据的管理
  • 创建对象:
    • Paginator对象的page()方法返回
      Page对象page = paginator.page(页码)
  • Page对象属性:
    • object_list:当前页上所有数据对象的列表
    • number:当前页的序号,从1开始
    • paginator:当前page对象相关的Paginator对象
  • Page对象方法:
    • has_next():如果有下一页返回True
    • has_previous():如果有上一页返回True
    • has_other_pages():如果有上一页或下一页返回True
    • next_page_number():返回下一页的页码,如果下一页不存在,抛出lnvalidPage异常
    • previous_page_number():返回上一页的页码,如果上一页不存在,抛出InvalidPage异常

生成csv文件

csv文件定义:

逗号分隔值(Comma-Separated Values,CSv,有时也称为字符分隔值,因为分隔字符也可以不是逗号),其文件以纯文本形式存储表格数据(数字和文本)

说明:

可被常见制表工具,如excel等直接进行读取

python中生成csv文件:
  • Python提供了内建库– csv; 可直接通过该库操作csv文件

  • 案例如下:

    import csv
    with open('eggs.csv', 'w', newline=") as csvfile:
    	writer = csv.writer(csvfile)
    	writer.writerow(['a', 'b','c'])
    
  • csv文件下载:

    ​ 在网站中,实现下载CSv,注意如下:

    • 响应Content-Type类型需修改为text/csv。这告诉浏览器该文档是CSV文件,而不时HTML文件

    • 响应会获得一个额外的Content-Disposition标头,其中包含CSv文件的名称。它将被浏览器用于开启“另存为…"对话框

      import csv
      from django.http import HttpResponse
      from .mode1s import Book
      				
      def make_csv_view(request):
      	response = HttpResponse(content_type='text/csv')
      	response['Content-Disposition'] = 'attachment;filename="mybook.csv"'
      	a11_book = Book.objects.a11()
      	writer = csv.writer(response)
      	writer.writerow(['id','title'])
      	for b in a11_book :
      		writer.writerow( [b.id,b.title])
      						
      	return response
      
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值