django 学习笔记3 精通django
p1 = Publisher(...)
p1.save()
上面这两步加起来相当与是
p1 = Publisher.objects.create(...)
Publisher.objects.all() Publisher.objects.filter(country="U.S.A.",state_province="CA") Publisher.objects.filter(name__contains="press") # 两个下划线 books = Book.objects.filter(title__icontains=q) # 包含q,且不区分大小写,不建议在大型生产数据库中使用 icontains 查询,因为速度可能很慢
检索单个对象:get不返回对象或返回多个对象会导致异常 Publisher.objects.get(name="Apress") Publisher.objects.order_by("state_province", "address") Publisher.objects.order_by("-name") Publisher.objects.filter(country="U.S.A.").order_by("-name") Publisher.objects.order_by('name')[0:2] # 查询固定数量的行 Publisher.objects.all().update(country='USA') # 更新多条记录 Publisher.objects.filter(country='USA').delete() >>> p = Publisher.objects.get(name="O'Reilly") >>> p.delete() Publisher.objects.all().delete() # 删除所有数据
class Publisher(models.Model): name = models.CharField(max_length=30) address = models.CharField(max_length=50) city = models.CharField(max_length=60) state_province = models.CharField(max_length=30) country = models.CharField(max_length=50) website = models.URLField() def __str__(self): return self.name class Meta: ordering = ['name'] # 指定查询时的默认排序
# 内嵌在 Publisher 类定义体中的 class Meta(即要缩进,放在 class Publisher 内部)
save 和 update 的区别:save 会导致更新所有字段,update 会只更新需要更新的字段。而且update可以用来更新多条记录
管理员页面路径:/admin/
把模型添加到管理后台 : admin.site.register(Book)
定义模型时,允许字段为空:email = models.EmailField(blank=True)
如果想让日期字段(如 DateField、TimeField、DateTimeField)或数值字段(如
IntegerField、DecimalField、FloatField)接受空值,要同时添加 null=True 和 blank=True
email = models.EmailField(blank=True, verbose_name='e-mail') # verbose_name是管理后台界面上显示的字段标注
下面是管理后台相关的知识点:
自定义 ModelAdmin : class AuthorAdmin(admin.ModelAdmin): list_display = ('first_name', 'last_name', 'email') # 显示的字段
search_fields = ('first_name', 'last_name') # 搜索的字段
list_filter = ('publication_date',) # 过滤字段
ordering = ('-publication_date',) # 排序
fields = ('title', 'authors', 'publisher', 'publication_date') # 指定在编辑页面显示的字段顺序,同时也指定了可以比编辑的字段
filter_horizontal = ('authors',) # 编辑多对多的字段时,方便选择
raw_id_fields = ('publisher',) # 在编辑时,当关联的选项太多,不方便选择时,可以手动输入查找
![](https://img2020.cnblogs.com/blog/1161222/202011/1161222-20201107114422168-1130308995.png)
admin.site.register(Author, AuthorAdmin)
request.META 的值是一个 Python 字典,包含请求的所有 HTTP 首部
常见的几个键有: HTTP_REFERER 、HTTP_USER_AGENT 、REMOTE_ADDR
def ua_display_good2(request): ua = request.META.get('HTTP_USER_AGENT', 'unknown') return HttpResponse("Your browser is %s" % ua)
request.GET 和 request.POST :POST 数据一般由 HTML表单提交,而 GET 数据既可以来自表单,也可以来自页面 URL 中的查询字符串
def search(request): if 'q' in request.GET: message = 'You searched for: %r' % request.GET['q'] else: message = 'You submitted an empty form.' return HttpResponse(message)
过滤器示例:
<p>Found {{ books|length }} book{{ books|pluralize }}.</p>
这里用到了 pluralize 模板过滤器,它会根据找到的图书数量输出正确的单复数
<form action="" method="get"> 上面是HTML中的代码片段,action="" 的意思是,“把表单提交到与当前页面相同的 URL”
url(r'^reviews/([0-9]{4})/$', views.year_archive), 若想捕获 URL 中的值,把值放在括号里
虽然 [0-9]{4} 只匹配字符串中的整数,但是传给 views.year_archive() 视图函数的 year 参数是字符串,而不是整数
url(r'^reviews/(?P<year>[0-9]{4})/$', views.year_archive) # 具名分组
给视图函数传递额外参数: urlpatterns = [ url(r'^reviews/(?P<year>[0-9]{4})/$', views.year_archive, {'foo': 'bar'} # 字典类型 ), ]
urlpatterns = [
url(r'^reviews/', include('inner'), {'reviewid': 3}),
]
Django 在不同的层中提供了执行 URL 反转所需的工具:
在模板中,使用 url 模板标签。
在 Python 代码中,使用 django.core.urlresolvers.reverse() 函数。
在处理 Django 模型实例 URL 相关的高层代码中,使用 get_absolute_url() 方法
在 Python 代码中则要这么做:
为 URL 模式命名时,要确保不与其他应用中的名称冲突。如果你把 URL 模式命名为 comment,而另一个应用也这么做,在模板中使用这个名称时就无法确定该生成哪个 URL
把引入的 URL 配置放入命名空间中有两种方式:
url(r'^reviews/', include('reviews.urls', namespace='author-reviews', app_name='reviews')),
from django.conf.urls import include, url from . import views reviews_patterns = [ url(r'^$', views.IndexView.as_view(), name='index'), url(r'^(?P<pk>\d+)/$', views.DetailView.as_view(), name='detail'),] url(r'^reviews/', include((reviews_patterns, 'reviews', 'author-reviews'))),
转义:This will not be escaped: {{ data|escape}}
禁用 转义:This will not be escaped: {{ data|safe }}
字符串字面量插入模板时不会自动转义
TEMPLATES 中的模板路径应该使用 Unix 风格的正斜线,即便在 Windows 中也是如此
INSTALLED_APPS 中罗列应用的顺序 影响找到的模板是哪个
假如你想自定义 Django 的管理后台,你可以选择覆盖 django.contrib.admin 中的 admin/base_site.html 模
板,把自定义的模板 admin/base_site.html 保存在 myproject.reviews 应用中。
此时,在 INSTALLED_APPS 中必须把 myproject.reviews 放在 django.contrib.admin 前面,否则将先加载 django.contrib.admin,你自定义的模板就被忽略了
自定义的过滤器其实就是普通的 Python 函数,接受一个或多个参数
反向使用外键: >>> p = Publisher.objects.get(name='Apress Publishing') >>> p.book_set.filter(title__icontains='django')
book_set 属性是生成的:把模型名的小写形式与 _set 连在一起
多对多值与外键值的获取方式类似,不过处理的是 QuerySet 值,而非模型实例
>>> b = Book.objects.get(id=50)
b.authors.filter(first_name='Adrian')
模型中自定义的方法为对象添加数据行层的功能。管理器的作用是执行数据表层的操作,
管理器的 raw() 方法用于执行原始的 SQL 查询,其返回结果是模型实例集合
class Person(models.Model):
first_name = models.CharField(...)
last_name = models.CharField(...)
birth_date = models.DateField(...)
>>> for p in Person.objects.raw('SELECT * FROM myapp_person'): ... print(p)
Django 默认把“应用标注”(manage.py startapp 命令指定的名称)与类
名使用下划线联结在一起得到数据库表名。在上述示例中,我们假设 Person 模型在 myapp 应用中,因此对应
的表是 myapp_person
执行的查询还可以包含模型中没有定义的字段
people = Person.objects.raw('SELECT *, age(birth_date) AS age FROM myapp_person')
为 raw() 传递参数 :
>>> lname = 'Doe' >>> Person.objects.raw('SELECT * FROM myapp_person WHERE last_name = %s', [lname])
执行的查询不完全映射到模型上时,执行自定义sql
from django.db import connection def my_custom_sql(self): cursor = connection.cursor() cursor.execute("UPDATE bar SET foo = 1 WHERE baz = %s", [self.baz]) cursor.execute("SELECT foo FROM bar WHERE baz = %s", [self.baz]) row = cursor.fetchone() return row
注意,传入参数时,如果查询中有百分号,应该编写两个百分号
cursor.execute("SELECT foo FROM bar WHERE baz = '30%%' ANDid = %s", [self.id])
当作上下文管理器使用: with connection.cursor() as c: c.execute(...) 等效于: c = connection.cursor() try: c.execute(...) finally: c.close()
士大夫
士大夫