美文网首页
Python3 Flask APScheduler 定时查询天气

Python3 Flask APScheduler 定时查询天气

作者: 南城忆往 | 来源:发表于2021-02-01 08:53 被阅读0次
Python: 3.8
APScheduler:3.6.3
# 不知道说明原因 不引用下面这个库 from flask_apscheduler import APScheduler 会报错。
Flask-APScheduler: 1.11.0 

作为自己的笔记,我就不过多的说明了。这不是我擅长的部分。而且定时任务的很多参数这里面并没有记录,后续待补充(意味着:如果没有特别需求的情况下是不会有补充啦~)。

# 文件名称 weather.py

import requests
from flask import Flask
from flask_apscheduler import APScheduler
import configparser
import os
import sqlite3
import logging.config

"""
这是每隔5分钟去获取一次最新的天气情况。并保存到SQLite3数据库中的一个DEMO。
@auter joker create on 2020-03-21 
"""
env = os.environ
HOST = env.get('HOST', default='0.0.0.0')
PORT = env.get('PORT', default=5000)
TIME_INTERVAL = env.get('TIME_INTERVAL', default=2)
FILE_NAME = env.get('FILE_NAME', default='./conf/cityCode.ini')
WEATHER_API = env.get('WEATHER_API', default='http://t.weather.sojson.com/api/weather/city/')
SQLITE_DATABASE = env.get('SQLITE_DATABASE', default='./conf/weather.db')
CITY_CODE = None
logging.config.fileConfig('./conf/weather.conf')
logger = logging.getLogger()


class APSchedulerJobConfig(object):
    JOBS = [
        # {  # 每隔5S执行一次
        #     'id': 'job',
        #     'func': '__main__:method_test',  # 方法名
        #     'args': (1, 2),  # 入参
        #     'trigger': 'interval',  # interval表示循环任务
        #     'seconds': 5,
        # },
        {  # 每隔5M执行一次
            'id': 'job1',
            'func': '__main__:save_weather',  # 方法名
            'args': None,  # 入参
            'trigger': 'interval',  # interval表示循环任务
            'minutes': int(TIME_INTERVAL),
        }
    ]


app = Flask(__name__)
# 为实例化的flask引入配置
app.config.from_object(APSchedulerJobConfig)


# ************** common *************

class SqliteTool(object):
    def __init__(self):
        self.conn = sqlite3.connect(database=SQLITE_DATABASE, timeout=3.0)
        self.cursor = self.conn.cursor()

    def save(self, temp):
        try:
            # 创建数据库
            # cursor.execute("create table weather( id integer primary key autoincrement,
            # temperature varchar(50), insertDate timestamp not null default (datetime('now','localtime')))")
            sql = 'insert into weather (temperature, city, cityCode, humidity) values (?, ?, ?, ?)'
            self.cursor.execute(sql, temp)
            self.conn.commit()
            self.cursor.close()
            self.conn.close()
        except Exception as e:
            logger.error('数据持久化错误,请联系管理员 %s' % e)


def get_city_code(city):
    """
    获取城市编码
    :param city:
    :return:
    """
    global CITY_CODE
    if CITY_CODE is None:
        con = configparser.ConfigParser()
        con.read(FILE_NAME, encoding='utf-8')
        items = con.items('CityCode')
        CITY_CODE = dict(items)

    return CITY_CODE.get(city)


def get_context(code):
    """
    获取天气数据
    :param code:
    :return:
    """
    try:
        url = WEATHER_API + code
        with requests.get(url, stream=True, timeout=1.0) as r:
            if r.status_code == 200:
                return r.json()
            else:
                return None
    except Exception as e:
        r.close()
        logger.error(e, '请求出错。')
    finally:
        r.close()

# ************** common *************


def save_weather():
    # if city is None:
    #     city = '南京'
    code = get_city_code('南京')
    weather_json = get_context(code)
    if weather_json is not None:
        temp_data = [weather_json.get('data').get('wendu'), weather_json.get('cityInfo').get('city'),
                     weather_json.get('cityInfo').get('citykey'), weather_json.get('data').get('shidu')]
        SqliteTool().save(temp_data)
    else:
        weather_json = ''
    logger.info(weather_json)
    return weather_json


# @app.route('/weather/<city>')
# def get_weather(city):
#     result = save_weather(city)
#     return jsonify(result), 200


@app.route("/hello")
def check():
    return "success", 200


if __name__ == '__main__':
    scheduler = APScheduler()
    scheduler.init_app(app)
    scheduler.start()
    app.run(host=HOST, port=int(PORT), debug=False)

附上打包脚本及相关配置文件:

日志配置

# weather.conf
[loggers]
keys=root

[handlers]
keys=consoleHandler,rotatingFileHandler

[formatters]

keys=simpleFmt

[logger_root]
level=INFO
handlers=consoleHandler,rotatingFileHandler

[handler_consoleHandler]
class=StreamHandler
level=DEBUG
formatter=simpleFmt
args=(sys.stdout,)

[handler_rotatingFileHandler]
class=handlers.RotatingFileHandler
level=DEBUG
formatter=simpleFmt
args=("./logs/weather.log", "a", 20*1024*1024, 10,'utf-8')

[formatter_simpleFmt]
format=%(asctime)s [ %(levelname)s ] %(message)s
datefmt=

城市编码

# citiCode.ini
北京=101010100
上海=101020100
广州=101280101
深圳=101280601
南京=101190101
溧水=101190102
高淳=101190103
江宁=101190104
六合=101190105
江浦=101190106
浦口=101190107
海淀=101010200
朝阳=101010300
顺义=101010400
怀柔=101010500
通州=101010600
昌平=101010700
延庆=101010800
丰台=101010900
石景山=101011000
;还有很多,就不一一列举。

SQLite3建库脚本

# 数据库脚本:
create table weather
(
    id          integer
        primary key autoincrement,
    temperature varchar(50),
    insertDate  timestamp default datetime('now', 'localtime') not null,
    humidity    varchar(50),
    city        varchar(20),
    cityCode    int
);

create index weather_insertDate_index
    on weather (insertDate);

Dockerfile

# Dockerfile 源文件未加密。

#!/bin/bash
FROM python:3.6-alpine

ENV LANG C.UTF-8
ENV TZ Asia/Shanghai

WORKDIR /usr/src/app

RUN pip3 install --upgrade pip
RUN pip3 install requests==2.20.1
RUN pip3 install Flask==1.1.1
RUN pip3 install APScheduler==3.6.3
RUN pip3 install Flask-APScheduler==1.11.0

RUN mkdir conf logs
COPY conf/cityCode.ini ./conf/cityCode.ini
COPY conf/weather.db ./conf/weather.db
COPY weather_app.pyc ./weather_app.pyc

CMD [ "python3", "./weather_app.pyc" ]

容器编排 Docker-compose.yml

# docker-compose.yml
version: "3"

services:
  weather_app:
    build: .
    image: weather_app
    container_name: weather_app
    volumes:
      - /usr/local/weather/conf/:/usr/src/app/conf
      - /usr/local/weather/logs/:/usr/src/app/logs
    environment:
      WEATHER_API: "http://t.weather.sojson.com/api/weather/city/"
      TIME_INTERVAL: 5
    ports:
      - 5001:5000
    restart: always

相关文章

网友评论

      本文标题:Python3 Flask APScheduler 定时查询天气

      本文链接:https://www.haomeiwen.com/subject/jqupyhtx.html