从零搭建一个django项目-3-数据存储-mysql

2022-06-13 13:16:52 浏览数 (1)

0

创建mysql数据库

pycharm可以直接配置数据库连接访问数据库(如果没有看看是不是社区版,idea也可以这样),使用sql创建数据库并设置编码集为utf8。

代码语言:javascript复制
CREATE DATABASE`django_wx` DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci;

1

编写模型类

就像java中有mybatis、hibernate这样的orm框架,django也有将数据库操作语句封装的结果集,可以让我们不用写原生sql就可以操作数据。

首先要编写模型类,也就是models.py 文件。

代码语言:javascript复制
from django.utils import timezone
from django.db import models
# Create your models here.
class DB_weatherinfo_base(models.Model):
    city = models.CharField(primary_key=True,verbose_name='地市',null=False ,blank=False,max_length=5)
    province = models.CharField(verbose_name='省份',null=False ,blank=False,max_length=5)
    weather =  models.CharField(verbose_name='天气现象',null=False ,blank=False,max_length=5)
    temperature =  models.CharField(verbose_name='实时气温',null=False ,blank=False,max_length=5)
    winddirection =  models.CharField(verbose_name='风向',null=False ,blank=False,max_length=5)
    windpower =  models.CharField(verbose_name='风力级别',null=False ,blank=False,max_length=5)
    humidity =  models.CharField(verbose_name='空气湿度',null=False ,blank=False,max_length=3)
    reporttime =  models.DateTimeField(verbose_name='数据发布的时间',default=timezone.now)
    # 设置联合主键
    class Meta:
        verbose_name_plural ="当前天气"
    def __str__(self):
        return str(self.city str(self.reporttime) self.weather)
class DB_weatherinfo_all(models.Model):
    city = models.CharField(verbose_name='地市',null=False ,blank=False,max_length=5)
    province = models.CharField(verbose_name='省份',null=False ,blank=False,max_length=5)
    date = models.CharField(verbose_name='日期',null=False ,blank=False,max_length=10)
    week = models.CharField(verbose_name='星期',null=False ,blank=False,max_length=1)
    dayweather =  models.CharField(verbose_name='白天天气',null=False ,blank=False,max_length=5)
    nightweather =  models.CharField(verbose_name='晚上天气',null=False ,blank=False,max_length=5)
    daytemp =  models.CharField(verbose_name='白天气温',null=False ,blank=False,max_length=5)
    nighttemp =  models.CharField(verbose_name='晚上气温',null=False ,blank=False,max_length=5)
    daywind =  models.CharField(verbose_name='白天风向',null=False ,blank=False,max_length=5)
    nightwind =  models.CharField(verbose_name='晚上风向',null=False ,blank=False,max_length=5)
    daypower =  models.CharField(verbose_name='白天风力',null=False ,blank=False,max_length=5)
    nightpower =  models.CharField(verbose_name='晚上风力',null=False ,blank=False,max_length=5)
    reporttime =  models.DateTimeField(verbose_name='数据发布的时间',default=timezone.now)
    # 设置联合主键
    class Meta:
        verbose_name_plural ="未来天气"
        unique_together=('city','date')
    def __str__(self):
        return str(self.city self.date self.dayweather)

因为实时天气和未来天气预报的数据不同所以写了两个模型类,其中verbose_name属性是用来在后台展示用的。null设置数据库字段不能为空,blank设置前端传入不能为空,True则是默认可以为空。

修改数据库源:在setting文件里

代码语言:javascript复制
DATABASES = {
    'default': {
        # 配置使用mysql
        'ENGINE': 'django.db.backends.mysql',  # 数据库产品
        'HOST': "xxxx.xxxx.xxxx.xxxx",  # 数据库ip
        'PORT': 3306,  # 数据库端口
        'USER': "用户名",  # 用户名
        'PASSWORD': "密码",  # 密码
        'NAME': "数据库名",  # 数据库名
        'OPTIONS': {'charset': 'utf8'},
    }
}

引入mysql连接模块:我这里还没安装可以直接鼠标放上去按alt加回车安装。

代码语言:javascript复制
import pymysql
pymysql.install_as_MySQLdb()

执行两句命令让表真正生效:

代码语言:javascript复制
python manage.py makemigrations
python manage.py migrate

重新连接数据库查询:可以看到库里多了一些表,除了django默认的一些表还是我们新加的这两个表。

2

后台管理

为了测试下数据我们可以用下django自带的后台,首先创建一个管理员账号使用命令:python manage.py createsuperuser

登录后台url默认为:http://127.0.0.1:8000/admin/

输入正确密码以后登录成功,可以看到两个默认的表,怎么样能看到我们的两个表呢,需要在admin.py里面配置。以下配置是将myapp里面所有模型类都注册到后台。

代码语言:javascript复制
from django.contrib import admin
# Register your models here.
import inspect,sys
from myapp.models import *
cls_members = inspect.getmembers(sys.modules[__name__],inspect.isclass)
for name,cls in cls_members:
    admin.site.register(cls)

刷新页面可以看到我们的两个表了,后面的s是django默认给我们加的表示多个。

可以将verbose_name 改为 verbose_name_plural 就可以去除末尾的 ‘s’。verbose_name指定在admin管理界面中显示中文;verbose_name表示单数形式的显示,verbose_name_plural表示复数形式的显示;中文的单数和复数一般不作区别。

手动添加一条数据,

保存看看:显示的是我们def __str__(self):方法返回的信息

增加一条当前天气:

查看数据库:

两个表各有一条数据:

3

入库方法

先写一个试验一下:

代码语言:javascript复制
from myapp.models import DB_weatherinfo_base
from myapp.utils.weatherInfo_utils import Gaode_tianqi
import datetime

class get_weatherinfo_base(APIView):
    # authentication_classes = [JwtAuthorizationAuthentication, ]
    def get(self, request, *args, **kwargs):
        city = self.kwargs['city']
        tianqi = Gaode_tianqi(city).get_weatherinfo_base()

        update_or_create_weatherinfo_base(city, tianqi)
        return Response({"datas":tianqi})

def update_or_create_weatherinfo_base(city,tianqi):
    try:
        lives = tianqi['lives'][0]
        city = lives['city']
        province = lives['province']
        weather = lives['weather']
        temperature = lives['temperature']
        winddirection = lives['winddirection']
        windpower = lives['windpower']
        humidity = lives['humidity']
        reporttime = lives['reporttime']
        reporttime = datetime.datetime.strptime(reporttime, '%Y-%m-%d %H:%M:%S')
        obj, created = DB_weatherinfo_base.objects.update_or_create(city=city, defaults={"province": province, "weather": weather,
                                                                                 "temperature": temperature,
                                                                                 "winddirection": winddirection,
                                                                                 "windpower": windpower,
                                                                                 "humidity": humidity,
                                                                                 "reporttime": reporttime})
        return {'status': True}
    except Exception as e:
        print(e.__str__())
        return {'status': False}

通过postman调用时间报错:

查询得知修改:可以更改USE_TZ 设置解释为可以修改时区。

代码语言:javascript复制
USE_TZ = False

重新调用postman可以看到入库了。

重新调用沈阳市:后面的时间更新了,即update_or_create没有时候创建已有的数据更新,city=city表示关键字以这个查询,后面的defaults接收一个元祖里面是要更新的字段。

接下来编写all的天气更新方法:

代码语言:javascript复制
class get_weatherinfo_all(APIView):
    # authentication_classes = [JwtAuthorizationAuthentication, ]
    def get(self, request, *args, **kwargs):
        city = self.kwargs['city']
        tianqi = Gaode_tianqi(city).get_weatherinfo_all()
        update_or_create_weatherinfo_all(city, tianqi)
        return Response({"datas":tianqi})
def update_or_create_weatherinfo_all(city,tianqi):
    forecasts  = tianqi['forecasts'][0]
    casts = forecasts['casts']
    try:
        for cast in casts:
            city = forecasts['city']
            province = forecasts['province']
            date = cast['date']
            week = cast['week']
            dayweather = cast['dayweather']
            nightweather = cast['nightweather']
            daytemp = cast['daytemp']
            nighttemp = cast['nighttemp']
            daywind = cast['daywind']
            nightwind = cast['nightwind']
            daypower = cast['daypower']
            nightpower = cast['nightpower']
            reporttime = forecasts['reporttime']
            reporttime = datetime.datetime.strptime(reporttime, '%Y-%m-%d %H:%M:%S')
            obj, created = DB_weatherinfo_all.objects.update_or_create( defaults={"province": province, "week": week,
                                                                                     "dayweather": dayweather,
                                                                                     "nightweather": nightweather,
                                                                                     "daytemp": daytemp,
                                                                                     "nighttemp": nighttemp,
                                                                                     "daywind": daywind,
                                                                                     "nightwind": nightwind,
                                                                                     "daypower": daypower,
                                                                                     "nightpower": nightpower,
                                                                                     "reporttime": reporttime
                                                                                                       },city=city,date=date)
        return {'status': True}
    except Exception as e:
        print(e.__str__())
        return {'status': False}

使用postman调用看看:

也入库了。表示方法可用。

4

预告:

下几章节加上登录检验功能,

方案1:网页版:注册(md5加密),验证码(涉及图片和邮箱发送),登录(jwt生成token并检验)等知识

方案2:微信小程序版:搭建小程序环境 登录(使用微信小程序提供的登录方法),登录成功获取token(使用jwt)

默认方案1,看看有没有留言选方案2的,希望大家看完点个赞。

0 人点赞