有了这个脚本,妈妈再也不用担心我下雨天忘带伞了!

伞.jpeg

我讨厌下雨天,尤其是出门却没带伞的下雨天。每到这个时候,就特羡慕大头儿子,“人家有伞,我有大头”。。。既然没有大头儿子的天赋异禀,就只能老老实实地带伞了。

蛋,总是忘了带肿么破!!!

在多次被北京的大雨拍在路上之后,我痛定思痛,决定要想个法子解决忘带伞这一世纪难题。。。

其实这个问题很好解决嘛,早晨出门前看下天气预报不就行了。对于像我这种每天能够早早起床、舒展一会儿身体、做一顿营养早餐、看一个小时书、在上班路上欣赏北京美景的人来说so easy。

才怪。

每天睡的比猪晚、起的比猪早,早晨急忙爬起来刷个牙洗个脸,连个饭都吃不上就要去挤地铁,这还天天迟到呢!哪还能想起来去看天气预报啊!!!

主动去看天气预报这个方案对我来基本无解。。。

那,就被动好了,让基友在我需要带伞的时候,主动提醒我一下吧。

好,祭出基友之友--Python!!!

我想让python做以下事情:

流程图.png

所以,要实现以下三部分:

  1. 爬取天气数据
  2. 判断是否有雨
  3. 发送提醒

嗯,开搞。

爬天气预报数据

先找个靠谱的天气预报网站,看了一圈,感觉这个中国天气预报挺靠谱的,毕竟敢用“中国”命名呢。下图就是目标数据了:

天气数据.png

打开浏览器控制台,找到数据在html中的位置:

html1.png

可以看到,7天的天气数据位于 id="7d"div标签 -> ul标签 -> li标签 中。

再看看li中的具体结构:

html2.png
  • 日期位于 li标签 -> h1标签 中;
  • 天气位于 li标签 ->** class="wea"**的p标签 中;
  • 最高温度位于 li标签 -> class="tem"p标签 ->span标签 中;
  • 最低温度位于 li标签 -> class="tem"p标签 -> i标签 中。

数据找好了,开始爬数据出来。鉴于爬数据的逻辑简单,直接用urllib2BeautifulSoup来做。

# 爬取7天内的天气数据
from bs4 import BeautifulSoup
import urllib2
def fetch_weather_datas():
    # 请求页面数据
    response = urllib2.urlopen(url='http://www.weather.com.cn/weather/101010100.shtml') 
    body = response.read()

    # 用BeautifulSoup解析,取出7天的天气数据
    soup = BeautifulSoup(body, "lxml")
    tags = soup.select('#7d > ul > li')

    return ['%s\t%s\t%s\t%s' %  # 对七天的数据分别解析,将解析后的每天的数据拼接成“日期+天气+最高气温+最低气温”的字符串,\t分隔
        (
            tag.select('h1')[0].string, # 取时间数据
            tag.select('.wea')[0]['title'],  # 取天气数据
            tag.select('.tem > span')[0].string, # 取最高气温
            tag.select('.tem > i')[0].string # 取最低气温
        ) 
        for tag in tags] # 返回结果为List

今天是否有雨?

拿到天气数据之后,要看下今天的天气如何,是否需要提醒我带伞。

# 传入爬到的天气数据,判断今天是否是雨天
def is_rainy_day(weather_data):
    return '雨' in weather_data

发送提醒

因为我手机上的邮件客户端始终在后台开启,选择用邮件的方式来做提醒比较合适,所以使用了Python自带的邮件发送工具:smtplib
需要有一个发送提醒邮件的邮箱账号,我用的是新浪的邮箱。

# 发送邮件
import smtplib
from email.mime.text import MIMEText
from email.header import Header
def send_mail(receivers, datas):
    mail_host = 'smtp.sina.com'  # 设置服务器,不同的邮箱对应的smtp服务器地址不同
    mail_user = 'username'  # 用户名,发送邮件的邮箱账号的用户名
    mail_pass = 'password'  # 密码,发送邮件的邮箱密码

    # 定义邮件内容
    message = MIMEText('\n'.join(datas), 'plain', 'utf-8') # 邮件内容为爬取到的近7天天气数据
    message['From'] = Header(mail_user) # 邮件的发送方
    message['To'] = Header(','.join(receivers), 'utf-8') # 邮件的接受方,逗号分隔
    message['Subject'] = Header('天气提醒', 'utf-8') # 邮件主题

    try:
        smtpObj = smtplib.SMTP()
        smtpObj.connect(mail_host, 25)  # 连接服务器, 25 为新浪邮箱 SMTP 端口号
        log('连接服务器成功..')
        smtpObj.login(mail_user, mail_pass) # 登录服务器
        log('登录邮箱服务器成功..')
        smtpObj.sendmail(from_addr=mail_user, to_addrs=receivers, msg=message.as_string()) # 发送邮件
        log('邮件发送成功..')
    except smtplib.SMTPException as e:
        log('无法发送邮件...' + e.message)


# 日志打印
import time
def log(msg):
    timestamp = time.strftime('%Y-%m-%d %H:%M:%S', time.localtime(time.time()))
    print '[%s] %s' % (timestamp, msg)

整合

将上边编写完成的方法按下边的方式整合到一起,就是一个能够发送天气提醒的脚本了:

try:
    weather_datas = fetch_weather_datas() # 爬取天气数据
    if is_rainy_day(weather_datas[0]):  # 今天是否是雨天
        send_mail('xxxx@sina.com', weather_datas) # 发送天气数据到目标邮箱
    else:
        log('今天天气良好..')
except:
    log('出错..')

定时执行

写完脚本后,我希望这个脚本能在每天早晨6点30分执行,这样我就能在醒来的第一时间就能看到提醒邮件并带上雨伞了。

首先需要一个能联网的服务器,将脚本放在服务器中。

然后,用crontab来做定时的任务(linux环境)。执行:

crontab -e

此时会进入vim界面,进入编辑模式,输入:

30 6 * * * /usr/bin/python xxxx/weather.py >> run.log

保存,此时定时任务就跑起来了,日志记录在run.log文件中。

具体的cron表达式语法在网上有很多教程,就不细说了。

完成

不必再羡慕大头儿子了!虽然他有大头,但是我有伞啊~


Tip

完整的代码可以看这里

如有问题,欢迎交流~

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,684评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 87,143评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,214评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,788评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,796评论 5 368
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,665评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,027评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,679评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 41,346评论 1 299
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,664评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,766评论 1 331
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,412评论 4 321
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,015评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,974评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,203评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,073评论 2 350
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,501评论 2 343

推荐阅读更多精彩内容

  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,596评论 18 139
  • 一 在外漂泊时间久了,就会发现,回家不过是过年的例行公事,不回家却是自由舒服的常态。 中秋节,你回不回家?有人如是...
    是喵儿啊阅读 615评论 3 0
  • 目标明确了,计划也制定好了,该去实践了,可是仅仅依靠“实践”并不能保证成功,那么如何去实践呢,这是第7章解决的问题...
    kelinda阅读 206评论 0 1
  • 感觉早早田的每个人都在努力让自己向上做好,但有时候太走进内在了,学的东西感觉一直是理论层面的,当我们从理论探索出实...
    凤飞飞1阅读 188评论 0 0
  • -1- 没错,那时候车马很慢,邮件很慢,时光很慢,慢到这辈子只够爱一个人。 爸爸妈妈自小认识但不熟悉,结婚二十多年...
    超级带感的狗狗草阅读 551评论 2 2