url配置系统
1.无名分组
urlpatterns = [ url(r'admin/', admin.site.urls), url(r'^blog/article/(d+)/$', blog_views.article_year), url(r'^blog/article/(d+)/(d+)$', blog_views.article_yearMonth), ]
def article_year(request, year): return HttpResponse(str(year)) def article_yearMonth(request, year, month): return HttpResponse('OK'+year+month)
2.有名分组
url(r'^blog/article/(?P<year_id>d+)/(?P<month_id>d+)$', blog_views.article_yearMonth),
def article_yearMonth(request, year_id, month_id): return HttpResponse('OK'+year_id+month_id)
3.路由分发
根据app进行url分发,目的是解耦
from django.conf.urls import url,include urlpatterns = [ url(r'^admin/', admin.site.urls), url(r'^blog/', include('blog.urls')), ]
#blogurls.py from blog import views as blog_views urlpatterns = [ url(r'article/(d+)$, blog_views.article_year'), url(r'^article/(d+)/(d+)$', blog_views.article_yearMonth), ]
4.url反向解析
urlpatterns = [ url(r'^blog/', include('blog.urls')), url(r'^login.html/', app01_views.login, name='LOGIN') ]
#app01views.py def login(request): if request.method == 'POST': user=request.POST.get('user') pwd=request.POST.get('pwd') return HttpResponse('登陆成功') return render(request, 'login.html')
#login.html <form action='{% url 'LOGIN' %}' method='post'> <p>姓名 <input type='text' name='user'/></p> <p>密码 <input type='password' name='pwd'/></p> <input type='submit'> </form>
视图函数
1.请求对象
request(请求对象):
request.GET ---- get请求数据
request.POST ---- post请求数据
request.method ---- 请求方式
request.path ---- 请求路径
request.get_full_path() ---- 请求全路径
request.getlist() ---- 请求数据(涉及到select等多选的属性时用到,select中需要写上multiple)
2.响应对象
HttpResponse()
render(request,template_name,context)
template:模板
context:上下文
redirect(跳转,重定向)
redirect('/路径/')
模拟点击submit请求:
请求url:http://127.0.0.1:8000/login/
(1)请求url:/login/ POST
(2)url(r'^login', app01_views.login, name='LOGIN'),
(3)llogin(request): 验证, if 成功: redirect('/index/')
重定向请求:
请求路径:http://127.0.0.1:8000/index/
(1)/index/ GET
(2)url(r'index/', app01_views, name='index')
(3)index(request): 从数据库取出数据,渲染到index.html页面
用户看到的是:渲染好的index.html页面
模板语法
功能:为了更有逻辑的将数据库中的数据渲染到模板中
1.渲染变量
变量:{{ }}
深度查询: 句点符.
标签:{% %}
{% for i in obj %}{% endfor %}
{% if n > 20 %}{% else %}{% endif %}
{% for i in obj %}{% empty %}<p>没有</p>{% endfor %}
2.变量过滤器
{{ var|filter_name:参数 }}
{{ age|add:10 }}:值在原来的基础上加10
{{ date|date:"Y-m-d" }}:输出的时间格式改变
{{ value|default:'值为空' }}:从数据库无法取到数据时,这样显示更友好
{{ value|length }}:显示长度
{{ value|slice:"2:-1" }}:截取
{{ value|truncatechars:"20" }}:按照字符截断
{{ value|truncatewords:"4" }}:按照单词截断
{{ value|safe }}:对HTML和JS标签不进行自动转义
3.自定义过滤器和标签
a.在settings中的INSTALLED_APPS配置当前app,
b.在app中创建templatetags模块
c.在templatetags模块中创建任意.py文件,如:my_tag.py
from django import template from django.utils.safestring import mark_safe register=template.Library() @register.filter def filter_multi(v1, v2): return v1*v2 @register.simple_tag def simple_tag_multi(v1, v2): return v1*v2 @register.simple_tag def my_input(id, arg): result="<input type='text' id='%s' class='%s'>" % (id, arg,) return mark_safe(result)
d.在使用自定义simple_tag和filter的html文件中导入创建的my_tag.py
{% load my_tag %}
e.使用simple_tag和filter
{{ num|filter_multi:12 }}
{% multi_tag n 5 2 %}
{% if num|multi:10 > 100 %}{% else %}{% endif %}
区别:
a.自定义的filter只能接受两个参数
b.自定义的simple_tag不能与if使用
4.继承
{% extends "base.html" %} ---> 继承母版
{% block content %}My amazing blog{% endblock %} ---> 编写扩展内容
{{ block.super }} --> 继续引用父类的内容
ORM系统
映射关系
表名 <----> 类名
字段 <----> 属性
表记录 <----> 类实例对象
#models.py class Book(models.Model): id=models.AutoField(primary_key=True) title=models.CharField(max_length=32) pubDate=models.DateField() price=models.DecimalField(max_digits=6,decimal_places=2) publish=models.CharField(max_length=32)
python manage.py makemigrations
python manage.py migrate
数据库引擎更改:
MYsqlDB--->pymysql
在应用的__init__文件中加入:
import pymysql
pymysql.install_as_MySQLdb()
单表操作:
插入数据方式1:create有返回值---插入的记录对象
book_obj=models.Book.objects.create(title=title,pubDate=pubdate,price=price,publisher_id=publish_id)
print(book_obj.title)
print(book_obj.price)
插入数据方式2:
book_obj=models.Book.objects.create(title=title,pubDate=pubdate,publish=publish)
book_obj.price=price
book_obj.save()
ORM表关系:
一对多:
一对多添加
关联字段放在多的一方
# 添加数据方式1
publish_obj=models.Publish.objects.get(name='renmin')
book_obj=models.Book.objects.create(title='python',price=122,pubDate='2012-12-12',publisher=publish_obj)
# 添加数据方式2
book_obj=models.Book.objects.create(title='python',price=122,pubDate='2012-12-12',publisher_id=publish_obj.id)
book_obj=models.Book.objects.create(title='python',price=122,pubDate='2012-12-12',publisher_id=2)
# 添加数据方式3
obj=models.Book(title='python',price=122,pubDate='2012-12-12',publisher=publish_obj)
obj.save()
一对多查询
book_python=models.Book.objects.filter(title="python").first()
print(book_python.title)
print(book_python.price)
print(book_python.publisher) # Publish object :返回的是与这本书关联的出版社对象
print(book_python.publisher.name)
多对多:
创建第三张表
一对一:
关联字段可以放在两张表的任意一张,关联字段必须唯一约束
ORM查询API:
a. models.Book.objects.all() --> 查询全部,返回queryset
b. booklist=models.Book.objects.filter(price=134,title='数学书') --> 过滤,返回queryset # [obj1,]
c. book_obj=models.Book.objects.get(title='数学书') ---> 返回model对象,也就是类对象。没有必要通过索引取值,print(book_obj.title),
而且get()括号中取出的值必须唯一,返回结果有且只能有一个,多了就会报错,所以get后面用一般用id来做,保证唯一性,models.Book.objects.get(id=11)
d. 如果返回的是queryset,就可以调用first(),last()
book_obj1=models.Book.objects.all().first().first()
print(obj.title)
book_obj2=models.Book.objects.filter(price=134).last()
e. book_obj=models.Book.objects.exclude(price=134) 与filter()相反,过滤出不符合条件的QuerySet [obj1,obj2,]
for book in book_obj:
print(book.title)
f. count:返回对象的个数
count=models.Book.objects.exclude(price=134).count()
print(count)
g. order_by()
book_list=models.Book.objects.all().order_by("price")
for i in book_list:
print(i.title, i.price)
从大到小排列
book_list=models.Book.objects.all().order_by("-price")
h. reverse()反转
book_list=models.Book.objects.all().order_by("-price").reverse()
i. values(),存的是字典
rel=models.Book.objects.all().values(“title”) 返回QuerySet,里面是一个个的字典 [{},{},]
print(rel) # <QuerySet [{'title':'语文书'},{'title':'数学书'},{'title':'英语书'},{'title':'物理书'}]>
j. values_list(),存的是元组
rel=models.Book.objects.all().values_list(“title”)
print(rel) # <QuertSet [('语文书',),('数学书',),('英语书',)]>
k. exist(),判断是否有值,有值后再做其他操作
ret=models.Book.objects.all().exist()
if ret:
print('OK')
else:
print('NO')
单表查询之双下划线:
首先在settings里面加入如下配置:
LOGGING = { 'version': 1, 'disable_existing_loggers': False, 'handlers': { 'console':{ 'level':'DEBUG', 'class':'logging.StreamHandler', }, }, 'loggers': { 'django.db.backends': { 'handlers': ['console'], 'propagate': True, 'level':'DEBUG', }, } }
以后只要执行ORM操作,sql语句就会打印出来
模糊查询:
book_list=models.Book.objects.filter(id__get=8) # id>8的输出出来,返回的是QuerySet
print(book_list.count())
book_list2=models.Book.objects.filter(title__startswith='语')
print(book_list[0].title)
book_list3=models.Book.objects.filter(title__icontains='py')
print(book_list[0].title)
models.Tb1.objects.filter(id__lt=10, id__gt=1) # 获取id>1且id<10的值
models.Tb1.objects.filter(id__in=[11, 22, 33]) #获取id等于11,22,33的数据
models.Tb1.objects.filter(id__range=[1, 2]) # 范围 between and