python实现的一个火车票转让信息采集器


Posted in Python onJuly 09, 2014

好吧,我承认我是对晚上看到一张合适的票转让但打过电话去说已经被搞走了这件事情感到蛋疼。直接上文件吧。

#coding: utf-8
'''
春运查询火车票转让信息
Author: piglei2007@gmail.com
Date: 2011.01.25
'''
import re
import os
import time
import urlparse
import datetime
import traceback
import urllib2
import socket
socket.setdefaulttimeout(20)

BLANK_RE = re.compile(r"\s+")

opener = urllib2.build_opener(urllib2.HTTPCookieProcessor())
opener.addheaders = [
  ("User-agent", "Mozilla/5.0 (X11; U; FreeBSD i386; en-US; rv:1.9.1) Gecko/20090704 Firefox/3.5"),
  ("Accept", "*/*"),
]
urllib2.install_opener(opener)

from BeautifulSoup import BeautifulSoup

SOURCE = {
  "58": "http://bj.58.com/huochepiao/?Num=%(train)s&StartTime=%(date)s00",
  "ganji": "http://bj.ganji.com/piao/cc_%(train)s/%(date)s/",
}
RECORD_FILE = "/tmp/ticket_records.txt"

def parse_record():
  try:
    return set([x.strip() for x in open(RECORD_FILE, "r").readlines()])
  except IOError:
    open(RECORD_FILE, "w")
    return set()

def flush_record(records):
  open(RECORD_FILE, "w").write("\n".join(records))

def main(config):
  """
  开始抓取
  """
  existed = parse_record()
  to_email = []

  for train in config["trains"]:
    for date in config["dates"]:
      for type, _url in SOURCE.items():
        url = _url % dict(train=train, date=date)
        content = urllib2.urlopen(url).read()
        soup = BeautifulSoup(content)
        result = parse_content(type, soup, train)
        for url, text in result:
          url = urlparse.urljoin(_url, url)
          # 只要卧铺!
          if url not in existed and u"卧" in text:
            to_email.append([text, url])
          existed.add(url)
  if to_email:
    content = "".join(
      [x for x in [" | ".join(y) for y in to_email]]
    ).encode("utf-8")
    simple_mail(config["people"], content)
  flush_record(existed)

def parse_content(type, soup, train):
  """
  获得车次信息
  """
  result = []
  if type == "58":
    info_table = soup.find("table", id="infolist")
    if info_table:
      for x in info_table.findAll("tr", text=re.compile(ur"%s(?!时刻表)" % train, re.I)):
        a = x.parent
        _text = BLANK_RE.sub("", a.text)
        result.append([a["href"], _text])
  if type == "ganji":
    for x in soup.findAll("dl", {"class": "list_piao"}):
      a = x.dt.a
      result.append([a["href"], a.text])
  return result

EMAIL_HOST = 'smtp.sohu.com'
EMAIL_HOST_USER = 'yourname@sohu.com'
EMAIL_HOST_PASSWORD = 'yourpassword'
EMAIL_PORT = 25

def simple_mail(to, content):
  """
  发送邮件
  """
  import smtplib
  from email.mime.text import MIMEText

  msgRoot = MIMEText(content, 'html', 'UTF-8')
  msgRoot['Subject'] = "[%s]有票来啦!!!!" % datetime.datetime.today().isoformat(" ")
  msgRoot['From'] = EMAIL_HOST_USER
  msgRoot['To'] = ", ".join(to)

  s = smtplib.SMTP(EMAIL_HOST, EMAIL_PORT)
  s.login(EMAIL_HOST_USER, EMAIL_HOST_PASSWORD)
  s.sendmail(EMAIL_HOST_USER, to, msgRoot.as_string())
  s.close()

def switch_time_zone():
  """
  切换时区
  """
  os.environ["TZ"] = "Asia/Shanghai"
  time.tzset()

switch_time_zone()

if __name__ == '__main__':
  config = {
    "trains": ("k471",),
    "dates": ("20110129",),
    "people": (
      "youremail@sohu.com",
    )
  }
  try:
    main(config)
    print "%s: ok" % datetime.datetime.today()
  except Exception, e:
    print traceback.format_exc()

然后放入cron,你懂的。

Python 相关文章推荐
Python实现的Google IP 可用性检测脚本
Apr 23 Python
python 爬取微信文章
Jan 30 Python
python实现class对象转换成json/字典的方法
Mar 11 Python
python爬虫之xpath的基本使用详解
Apr 18 Python
Python基于datetime或time模块分别获取当前时间戳的方法实例
Feb 19 Python
解决pyinstaller打包发布后的exe文件打开控制台闪退的问题
Jun 21 Python
解决python文件双击运行秒退的问题
Jun 24 Python
python实现银行管理系统
Oct 25 Python
如何完美的建立一个python项目
Oct 09 Python
如何利用Python matplotlib绘制雷达图
Dec 21 Python
将不规则的Python多维数组拉平到一维的方法实现
Jan 11 Python
python对文档中元素删除,替换操作
Apr 02 Python
python的描述符(descriptor)、装饰器(property)造成的一个无限递归问题分享
Jul 09 #Python
Python中__init__和__new__的区别详解
Jul 09 #Python
Python中使用logging模块代替print(logging简明指南)
Jul 09 #Python
Python中的魔法方法深入理解
Jul 09 #Python
gearman的安装启动及python API使用实例
Jul 08 #Python
python实现跨文件全局变量的方法
Jul 07 #Python
Python中的并发编程实例
Jul 07 #Python
You might like
生成静态页面的PHP类
2006/11/25 PHP
PHP文章按日期(月日)SQL归档语句
2012/11/29 PHP
PHP生成条形图的方法
2014/12/10 PHP
thinkPHP微信分享接口JSSDK用法实例
2017/07/07 PHP
event对象的方法 兼容多浏览器
2009/06/27 Javascript
Javascript 类与静态类的实现(续)
2010/04/02 Javascript
js创建子窗口并且回传值示例代码
2013/07/02 Javascript
js替代copy(示例代码)
2013/11/27 Javascript
5种处理js跨域问题方法汇总
2014/12/04 Javascript
jQuery中removeAttr()方法用法实例
2015/01/05 Javascript
javascript等号运算符使用详解
2015/04/16 Javascript
JavaScript+CSS实现仿天猫侧边网页菜单效果
2015/08/25 Javascript
基于BootStrap Metronic开发框架经验小结【四】Bootstrap图标的提取和利用
2016/05/12 Javascript
jquery层级选择器的实现(匹配后代元素div)
2016/09/05 Javascript
在网页中插入百度地图的步骤详解
2016/12/02 Javascript
原生JS实现圣旨卷轴展开效果
2017/03/06 Javascript
详解在React中跨组件分发状态的三种方法
2018/08/09 Javascript
示例vue 的keep-alive缓存功能的实现
2018/12/13 Javascript
python进阶教程之模块(module)介绍
2014/08/30 Python
python批量修改文件名的实现代码
2014/09/01 Python
Django的session中对于用户验证的支持
2015/07/23 Python
PyQt4编程之让状态栏显示信息的方法
2019/06/18 Python
PYTHON如何读取和写入EXCEL里面的数据
2019/10/28 Python
canvas离屏技术与放大镜实现代码示例
2018/08/31 HTML / CSS
俄罗斯天然和有机产品、健康生活网上商店:Fitomarket.ru
2020/10/09 全球购物
一道输出判断型Java面试题
2014/10/01 面试题
Java面试笔试题大全
2016/11/23 面试题
小学三八妇女节活动方案
2014/03/16 职场文书
经营管理策划方案
2014/05/22 职场文书
酒店端午节活动方案
2014/08/26 职场文书
西安兵马俑导游词
2015/02/02 职场文书
银行催款通知书
2015/04/17 职场文书
舞蹈社团活动总结
2015/05/07 职场文书
教学工作总结范文5篇
2019/08/19 职场文书
Nginx解决403 forbidden的完整步骤
2021/04/01 Servers
pandas中DataFrame重置索引的几种方法
2021/05/24 Python