day02

静态文件及相关配置

1.先编写一个登录功能
	1. 创建Django项目并创建一个APP
	2. 在urls.py添加一组对应关系
    3. 在app的views.py中编写登录核心逻辑
    4. 使用入门三件套与前端做交互
2.我们在访问Django框架资源的使用之所以可以拿到数据,是因为提前在urls.py中开设了相应的资源接口
3.静态文件
	HTML页面上使用的不经常改变的资源
    	1.第三方框架文件
        2.css文件
        3.js文件
        4.图片文件
	针对静态文件资源,一般都会放在static文件夹内
    	当static目录下出现很多不同类型的静态文件资源,可以继续分类管理
        	others文件夹	 第三方框架文件
            css文件夹 	所有的文件
            js文件夹 所有的js文件
            img文件夹 所有的img文件
4.针对静态文件资源的访问,也需要提前开设相应的接口
在settings.py文件最后一行,添加"""静态文件资源配置"""
    STATICFILES_DIRS = [
        os.path.join(BASE_DIR, 'static') #这里static是静态文件存放的目录
    ] # 列表的形式,因为会有很多的静态文件夹
5.接口前缀
	STATIC_URL = '/static/'# 必须以这个前缀为开头才能找到静态文件资源.
	例如STATIC_URL = '/xxx/',静态文件是static下的jquery.js文件,想要访问该jquery.js文件
    '路径需要填写成  /xxx/jquery.js' # 非常重要
    
6.动态解析
    {% load static %}
    <link rel="stylesheet" href="{% static 'bootstrap-3.4.1-dist/css/bootstrap.min.css' %}">
    
案例:
	1.pycharm创建Django项目 项目名:django_02 app名:app01
    2.检查settings.py中 INSTALLED_APPS是否注册app01;修改TEMPLATES中的'DIRS': [os.path.join(BASE_DIR, 'templates')],
    3.urls.py中添加login
        from app01 import views
    urlpatterns = [
        path('admin/', admin.site.urls),
        path('login/', views.login),
    ]
    4.app01目录下views.py中添加login函数
    def login(request):
    return render(request, 'login.html')# 1.返回给前端浏览器一个登录页面
	5.templates中创建login.html
    	在head中添加
        <script src="../static/jquery.js"></script>
    	<link rel="stylesheet" href="../static/bootstrap-3.4.1-dist/css/bootstrap.min.css">
    	<script src="../static/bootstrap-3.4.1-dist/js/bootstrap.min.js"></script>		
    	在body中添加
            <div class="container">
        <div class="row">
            <h1 class="text-center">登录页面</h1>
            <div class="col-md-8 col-md-offset-2">
                <form action="">
                    <p>username:<input type="text" name="username" class="form-control"></p>
                    <p>password:<input type="text" name="password" class="form-control"></p>
                    <input type="submit" value="登录" class="btn btn-success">
                </form>
            </div>
        </div>
    </div>
    6.pycharm启动Django项目,访问 http://127.0.0.1:8000/login,但是样式没有访问到
    7.设置接口前缀,及静态文件资源配置
    	在settings.py中,文件末尾设置
        STATIC_URL = '/static/'
    STATICFILES_DIRS = [
        os.path.join(BASE_DIR, 'static')
    ]
    8.浏览器再次访问,就可以访问到样式了
    9.若修改接口前缀,用到静态文件夹的所有配置都需要跟着修改,此时需要设置动态解析
    	在login.html的head中重新修改
         {% load static %}
    	<script src="{% static 'jquery.js' %}"></script>
    	<link rel="stylesheet" href="{% static 'bootstrap-3.4.1-dist/css/bootstrap.min.css' %}">
    	<script src="{%  static 'bootstrap-3.4.1-dist/js/bootstrap.min.js' %}"></script>
	10.此时修改接口前缀,浏览器访问也能找到静态资源

请求方法

1.GET请求
	朝别人索要数据
    	也可以携带额外的数据,比如访问拉钩网,搜索python岗位,选择工作地点等,虽然是get请求,但是可以携带条件
     		https://url?aaa=bbb&ccc=ddd
            '''?后面的数据,不参与路由匹配'''
        上述携带数据的方式有2个限制
        	1.数据只能是非敏感数据,不能放密码等
            2.数据大小有限制,2KB-4KB左右
		GET请求没有请求头(HTTP数据格式)
2.POST请求
	朝别人提交数据
    	也可以携带额外的数据
        	数据都是放在请求体中,可以携带敏感数据,并且数据大小没有限制
3.form表单默认的数据提交方式是get
	改成post请求方式
		method="post"
	action 控制数据的提交地址
    	方式1:不写,朝当前页面所在的地址提交
        方式2:写后缀/index/ 自动补全IP和端口
        方式3:切全称,比如https://www.baidu.com/
4.提交post请求,需要去配置文件中注释一行代码
	注释掉settings.py中MIDDLEWARE下的'django.middleware.csrf.CsrfViewMiddleware',  

request对象方法

request.method # 获取请求方式,结果是纯大写的字符串
request.POST  # 获取POST请求发生的普通数据(不包括文件)
    request.POST.get()# 默认只获取列表中最后一个数据值
    request.POST.getlist() # 获取键对应的整个列表
request.GET """不是GET请求,是获取url后面携带的非敏感数据""" 
    request.GET.get()# 默认只获取列表中最后一个数据值
    request.GET.getlist() # 获取键对应的整个列表
    
案例:
    1.将login.html中复制一行
    	<p>username:<input type="text" name="username" class="form-control"></p>
	2.view.py中修改login函数
        def login(request):
        if request.method == 'GET':
            return render(request, 'login.html')
        elif request.method == 'POST':
            print(request.POST)#<QueryDict: {'username': ['jason', 'kevin'], 'password': ['123']}>
            print(request.POST.get('username'))#kevin
            print(request.POST.getlist('username'))#['jason', 'kevin']

            print(request.GET)#<QueryDict: {'username': ['jason', 'kevin'], 'password': ['123']}>
            print(request.GET.get('username'))#kevin
            print(request.GET.getlist('username'))#['jason', 'kevin']
            
            return HttpResponse('收到了')
	3.浏览器输入 http://127.0.0.1:8000/login/?username=jason&username=kevin&password=123
    4.pycharm查看结果,
"""补充"""
print(request.path)
print(request.path_info) # 前两个用法相同,都是拿到当前的请求路由 /app01/index/
print(request.get_full_path()) # 拿到当前请求的路由和参数  /app01/index/?name=zhang

优化login函数

def login(request):
    if request.method == 'POST':
        print(request.POST)
        return HttpResponse("处理好了")
    return render(request, 'login.html')

# 将login这样修改,减少if分支

pycharm连接MySQL

先启动数据库,这里不再多说
创建库和表
CREATE DATABASE day55;
USE day55;
CREATE TABLE userinfo (
	id INT PRIMARY KEY auto_increment,
	name VARCHAR ( 32 ),
age INT 
);
INSERT INTO userinfo ( NAME, age ) VALUES ( 'jason', 18 ),( 'kevin', 25 );


1.查找pycharm提供的database按钮
2.点击左上角+号,选择MySQL
3.第一次连接,点击下面的驱动程序文件
4.配置ip,port,password,连接
5.修改数据内容之后,需要点击绿色箭头提交,才会修改成功

Django连接MySQL

Django默认使用的是sqlite3,一般用于本地测试,功能较少
1.在settings.py中配置数据库信息
    DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.mysql',  # 指定数据库软件名
            'NAME': 'day55',  # 指定库名
            'USER': 'root',
            'PASSWORD': '123456',
            'HOST': '127.0.0.1',
            'PORT': 3306,
            'CHARSET': 'utf8'
        }
    }
2.指定连接MySQL的模块
	Django1.11版本 需要在项目或者应用目录下的__init__.py中添加
    	improt pymysql
        pymysql.install_as_MySQLdb()
	Django2.2以上 需要使用mysqlclient模块
    	pip install mysqlclient

Django orm

ORM:对象关系映射
    面向对象中的类	映射成	表
    对象	映射成	记录
    对象.属性	映射成	字段对应的值
"""
ORM的存在可以让不会使用MySQL的python程序员,使用python的语法简单快捷的操作MySQL
"""
1.先去应用目录下的models.py编写模型类
    class User(models.Model):  # 类似于定义了表名
        # id int primary key auto_increment
        id = models.AutoField(primary_key=True)  # 类似于定义了主键
        # name varchar(32)
        name = models.CharField(max_length=32)  # 类似定义了普通字段
        # pwd int
        pwd = models.IntegerField()  # 类似于定义了普通字段
2.数据库迁移/同步命令
	1.将models中有关数据库的操作记录下来(migrations文件夹)
		python3 manage.py makemigrations
	2.将操作真正影响到数据库中
    	python3 manage.py migrate
	'''当修改了models.py中与数据库相关的代码,都必须执行上述2条命令'''
    # 点击pycharm工具,运行manage.py任务,之后 python3 manage.py就不需要敲了,只需要敲下面,
    	makemigrations
	# 默认是同步是所有的应用,也可以单独指定某个应用
        migrate app01
	3.数据库中会创建app01.user以及Django相关的表;Django项目下的app01会生成migrations目录,和0001_initial.py文件,里面记录了第1步定义的表结构
3.表的主键在orm中 可以不写,orm会自动帮你添加一个id的主键
	如果你不想让主键的名称为id,只能自己写主键
4.只要修改models.py的class User中的内容,然后再执行数据库同步命令,就可以实现对字段的修改.
5.在pycharm里先手动加2条数据
	在app01.User中添加 jason,123 和 kevin,321
6.修改view.py文件
from app01 import models # 先导入models
def login(request):
    if request.method == 'POST':
        username = request.POST.get('username')
        password = request.POST.get('password')
        # 查询表数据
        # select * from user where name='' and pwd=''
        # print(models.User.objects.filter())
        """可以用索引取,或者用first取"""
        # user_obj = models.User.objects.filter(name=username, pwd=password)[0]
        user_obj = models.User.objects.filter(name=username, pwd=password).first()
        print(user_obj) # User object (1)
        if user_obj:
            print(user_obj.id) # 1
            print(user_obj.name) # jason
            print(user_obj.pwd) # 123
            return HttpResponse('登录成功')
        return HttpResponse("用户名或密码错误")
	return render(request, 'login.html')
7.浏览器输入 http://127.0.0.1:8000/login 输入jason和123
8.查看pycharm的返回的结果

orm语法

1.查
	models.User.objects.filter() # 结果可以看成是一个列表套数据对象
    models.User.objects.filter().first() # 如何获取对象,可以使用fitrst()方法,如果没有值,会返回None;使用if判断即可
     models.User.objects.filter(name=username, pwd=password).query # 查看执行的sql语句
2.增
	models.User.objects.create()
    案例:
        views.py中修改
        def login(request):
            if request.method == 'POST':
                username = request.POST.get('username')
                password = request.POST.get('password')

                # 新增表数据
                models.User.objects.create(name=username, pwd=password)
                return HttpResponse('注册成功')
            return render(request, 'login.html')
3.改
	models.User.objects.filter(id=1).update(name='jasonNB') # 不添加filter就是修改所有
        案例:
            views.py中修改
        def login(request):
            if request.method == 'POST':
                username = request.POST.get('username')
                password = request.POST.get('password')

                # 修改表数据
                models.User.objects.filter(id=1).update(name='jasonNB')
                return HttpResponse('修改成功')
            return render(request, 'login.html')
4.删
	models.User.objects.filter(id=4).delete() # 不添加filter就是删除所有
        案例:
            views.py中修改
        def login(request):
            if request.method == 'POST':
                username = request.POST.get('username')
                password = request.POST.get('password')

                # 删除表数据
                models.User.objects.filter(id=4).delete()
                return HttpResponse('删除成功')
            return render(request, 'login.html')
        
"""补充"""
# 增
res=models.类名(username=username,password=password)
res.save()
# 改
res=models.表名.objects.filter().first()
res.username=username
res.password=password
res.save()

orm外键关联

1.MySQL中判断表关系 
	一对多,外键字段建在多的一方;models.ForeignKey(to='被关联的表名',to_field='被关联的表名中得字段')
    # 被关联的表中是主键字段,to_field字段可以不写,默认就是主键
    多对多,外键字段建在第三张关系表;models.OneToOneField(to='被关联的表名')
    一对一,外键字段建在查询频率较高的表中;models.ManyToManyField(to='被关联的表名')
2.ORM
	一对多,外键字段建在多的一方
    	publish = models.ForeignKey(to='Publish', on_delete=models.CASCADE)
        """Django2.2需要加on_delete=models.CASCADE"""
        """Django1.1不需要添加on_delete=models.CASCADE"""
	多对多,外键字段可以直接写在某张表中,orm会自动创建第三张表
    	authors = models.ManyToManyField(to='Authors')
	一对一,外键字段建在查询频率较高的表中
    	detail = models.OneToOneField(to='AuthorDetail', on_delete=models.CASCADE)
"""创建表关系,先将基表创建出来,然后再添加外键字段,且不用考虑先创建被关联表。"""
案例:
    # 创建4个表, 分别是 书,出版社,作者,作者详情
    	书和出版社,是一对多关系
		书和作者,是多对多关系
		作者和作者详情,是一多一关系
	1.在models.py中添加
        # 图书表
        class Book(models.Model):
            title = models.CharField(max_length=64)
            """
                max_digits=None,  总位数
                decimal_places=None 小数后面的位数
            """
            # price decimal(8,2)
            price = models.DecimalField(max_digits=8, decimal_places=2)
            # 如何创建一对多的关系
            # publish_id = models.ForeignKey(to='Publish', to_field='id')
            publish = models.ForeignKey(to='Publish', on_delete=models.CASCADE)  # 默认是与Publish表的主键建立关系
            '''如果是外键字段的话,会自动帮你拼接_id,如果你自己写了,它也会给你拼上'''
            # 如何创建多对多的关系
            authors = models.ManyToManyField(to='Author')
            '''
                authors字段是一个虚拟字段,意思是不会在book表中创建出来authors字段,它就是用来告诉django给我创建出来第三张表
            '''
        # 出版社表
        class Publish(models.Model):
            title = models.CharField(max_length=64)
            addr = models.CharField(max_length=255)
        # 作者表
        class Author(models.Model):
            name = models.CharField(max_length=64)
            # author_detail_id = models.OneToOneField(to='AuthorDetail', to_field='id')
            # author_detail_id = models.OneToOneField(to='AuthorDetail')
            '''如果是外键字段的话,会自动帮你拼接_id,如果你自己写了,它也会给你拼上'''
            author_detail = models.OneToOneField(to='AuthorDetail', on_delete=models.CASCADE)
            '''因为to='AuthorDetail' 加了引号,所以关联外键的时候,创建表的时候顺序不重要.要是去掉了引号,就要小心了,必须先创建被关联表'''
        # 作者详情表
        class AuthorDetail(models.Model):
            phone = models.CharField(max_length=64)
            qq = models.CharField(max_length=64)
            wechat = models.CharField(max_length=64)

	2.执行迁移命令
    	pycharm打开终端
        	python3 manage.py makemigrations
            python3 manage.py migrate
	3.查看数据库
    	除了上述4张表,还自动创建了app01_book_authors这张多对多的第三张表
"""关联外键时,Django 1.11版本不需要加,Django2.2需要加 on_delete"""
    例如 author_detail = models.OneToOneField(to='AuthorDetail', on_delete=models.CASCADE)
    on_delete
    当删除关联表中的数据时,当前表与其关联的行的行为。

    models.CASCADE
    删除关联数据,与之关联也删除

    models.DO_NOTHING
    删除关联数据,引发错误IntegrityError

    models.PROTECT
    删除关联数据,引发错误ProtectedError

    models.SET_NULL
    删除关联数据,与之关联的值设置为null(前提FK字段需要设置为可空)

    models.SET_DEFAULT
    删除关联数据,与之关联的值设置为默认值(前提FK字段需要设置默认值)

    models.SET
    删除关联数据,
    a. 与之关联的值设置为指定值,设置:models.SET(值)
    b. 与之关联的值设置为可执行对象的返回值,设置:models.SET(可执行对象)
posted @ 2023-05-09 09:08  也曾滿眼愛意丶  阅读(48)  评论(0)    收藏  举报