抓取携程某个城市所有起飞到达航班并保存

  • 代码
  • 需求
  • 思路
  • 教训
  • 关键点
  • ToDo
  • 代码

代码

https://download.csdn.net/download/liujiayou/11589246

需求

需要大规模接送机的时候,要掌握某个城市所有出入港航班信息。之前用Excel VBS编写了一个,这回试着写第一个暴力猴脚本。

思路

在https://flights.ctrip.com/schedule/可以输入想要查询的城市,以”兴义“为例,最终得到所有兴义出入港航班列表。
https://flights.ctrip.com/schedule/acx-inmap.html(入港)
https://flights.ctrip.com/schedule/acx-outmap.html(出港)
0、在原来菜单右边增加下载,如下图。

1、点击下载先抓取第一页表格数据。

2、查看第一页表格底部下一页 元素。如果有后续页面,那个这个元素的名称为"schedule_down",如果没有那个这个元素的名称为"schedule_down_disable"。

3、打开一个新窗口,把下一页 元素的链接作为窗口的地址,打开第二页数据。利用window.onload和window.onunload的回调函数抓取第二页数据。

4、查看第二页表格底部下一页 元素,并且不断在此新窗口打开下一页 元素的链接并抓取数据,直到下一页 的名称为"schedule_down_disable"。

5、保存结果到一个CSV文件中,如下图。

教训

JS是单线程,代码的执行不是顺序的。习惯了按常规顺序执行语句的方法去写,程序很容易进入死循环或者根本不按设想的去执行。

关键点

按常规的写法,新窗口的onload回调函数,在第一次加载完后是正常运行的。如果再给出新地址,刷新窗口后onload就不执行,造成后续页面无法自动刷新和抓取。

关键在于要把window.onload和window.onunload回调函数在onunload(onunload是在刷新网址前发生的)的时候再绑定一下。如下:

        //add handlenewWindow.onload= winLoaded;newWindow.onunload = winUnloaded;

ToDo

本来想点击下载后,隐藏此按钮。下载完成后,再显示。但还是由于单线程的原因,如果伪代码如下:

隐藏代码
保存代码
显示代码

则由于保存代码需要一段时间执行,因此,后面的显示代码直接执行了,没有达到先隐藏再显示的效果。
试过用promise, async wait等方法,没得到想要的结果。

代码

可以直接在暴力猴中增加新脚本,粘贴下面代码过去。

// ==UserScript==
// @icon http://pic.c-ctrip.com/common/c_logo2013.png
// @name            Ctrip Flight
// @author          初一他大爷
// @description     Download Ctrip Flight
// @include         http*://flights.ctrip.com/schedule/*-*map.html
// @require         http://cdn.bootcss.com/jquery/1.8.3/jquery.min.js
// @version         0.0.1
// @grant           none
// ==/UserScript==var finalData;//Write data
function writeData(toSave){//Create <a>var eleLink = document.createElement('a');eleLink.download = "flight.csv";eleLink.style.display = 'none';var strData =  "\ufeff" + "航线名,起飞,到达,起飞机场,到达机场,航空公司,航班号,\r" + toSave;var objFile = new Blob([strData],{type: 'text/csv,charset=UTF-8'});eleLink.href = (window.URL || window.webkitURL).createObjectURL(objFile);//Append <a>document.body.appendChild(eleLink);//Click <a>eleLink.click();//Remove <a>document.body.removeChild(eleLink);
}Append button to main page
function appendButton(savecontent) {//Prepare buttonvar a = document.createElement("a");var li = document.createElement("li");var ul = document.getElementsByClassName("nav-bar-set")[0];a.textContent = "下载";a.setAttribute('id', "downloadFlight");a.setAttribute('href', "javascript:void(0)");li.setAttribute('class', "set-list");li.appendChild(a);ul.appendChild(li);
}//Download flights
function downloadFlight(){var newWindow;var nextPage;var newURL;//Collect 1st page datafinalData = GetData(this.document);//Collect data of rest page(s)nextPage =  document.getElementsByClassName("schedule_down")[0];if(nextPage){//original nextPage.href is http, main page is https.newURL = nextPage.href.replace(/http/, "https");//New windownewWindow = window.open(newURL, "FilghtWindow", "directories=no,resizable=no, width=400, height=400");newWindow.focus();var winLoaded = function(){//Collect restfinalData = finalData + GetData(newWindow.document);//NextnextPage =  newWindow.document.getElementsByClassName("schedule_down")[0];if (nextPage){newURL = nextPage.href.replace(/http/, "https");newWindow.location.replace(newURL);}else{//Finishconsole.log(finalData);writeData(finalData);newWindow.close();}}var winUnloaded = function(){setTimeout(function(){newWindow.onload= winLoaded;newWindow.onunload = winUnloaded;},0);}//add handlenewWindow.onload= winLoaded;newWindow.onunload = winUnloaded;}
}//Get data from page
function GetData(docData){//Get tablevar tblRows = $(".fltlist_table > tbody > tr",docData);var lngRowLength;if (!tblRows && typeof(tblRows)!="undefined" && tblRows!=0){ alert("Cannot find table: fltlist_table");return;}  lngRowLength = tblRows.length;//console.log(lngRowLength);//Traversevar aryData = [lngRowLength];var strTmp = "";var strData = "";for(var i=0; i<lngRowLength; i++){aryData[i] = new Array(7)aryData[i][0] = tblRows[i].cells[0].innerText;strTmp = tblRows[i].cells[1].innerText;aryData[i][1] = strTmp.slice(0,strTmp.indexOf("\n"));aryData[i][2] = strTmp.slice(strTmp.indexOf("\n")+1);strTmp = tblRows[i].cells[2].innerText;aryData[i][3] = strTmp.slice(0,strTmp.indexOf("\n"));aryData[i][4] = strTmp.slice(strTmp.indexOf("\n")+1);strTmp = tblRows[i].cells[6].innerText;aryData[i][5] = strTmp.slice(0,strTmp.indexOf("\n"));aryData[i][6] = strTmp.slice(strTmp.indexOf("\n")+1);//mergefor(var j=0; j<7; j++){strData = strData + aryData[i][j] + ",";}strData = strData + "\r"       } return strData;
}//Wait till main page is loaded
window.addEventListener('DOMContentLoaded', (event) => {//Append button and its click functionappendButton("");document.getElementById("downloadFlight").onclick = function () {downloadFlight();};
});//Impoartnt:select a element from aother window
//$("a.schedule_down",newWindow.document)[0].click();
//Impoartnt:select a element from aother window

第一个暴力猴脚本- 抓取携程某个城市所有起飞、到达航班并保存相关推荐

  1. python爬取携程酒店信息_不写代码玩转爬虫实例(3) - 抓取携程酒店信息

    背景需求 有不少朋友问永恒君携程网站的酒店信息怎么抓取,今天这篇文章来分享一下使用web scraper来快速实现抓取携程酒店信息. 例如,在携程官网搜索北京 密云水库的酒店信息, 可以搜索到非常多的 ...

  2. pyhton爬虫(12)——抓取携程酒店评论数据

    本文主要目标是抓取携程酒店基本信息和用户评论数据.具体来说,酒店基本信息包括:酒店名.酒店星级.酒店最低房价.用户推荐比.酒店总评分等:用户评论数据包括:用户评论时间,用户评分,评论内容等. 实现代码 ...

  3. python爬携程_用python selenium抓取携程信息

    最近在学习selenium,遇到一个很奇怪的问题,debug了半天还是没弄明白,我是在测试抓取携程网站的机票信息 我的代码: # -*- coding: utf-8 -*- from selenium ...

  4. python爬取携程网游记_网页爬虫 - 用python selenium抓取携程信息

    问 题 最近在学习selenium,遇到一个很奇怪的问题,debug了半天还是没弄明白,我是在测试抓取携程网站的机票信息 我的代码: # -*- coding: utf-8 -*- from sele ...

  5. Python脚本抓取大乐透开奖结果核对定投号码邮件通知

    最近学习了一下Python的基础,想写个东西练练手.正好每次跟号的大乐透还需要手动兑奖或者去彩票站兑奖,自己写一个脚本自动抓取开奖结果,核对开奖金额后邮件通知. 整体思路: 找可抓取开奖结果网站 找可 ...

  6. 编写你的第一个油猴脚本

    油猴简介 Tampermonkey(油猴)是一款免费的浏览器扩展和最为流行的用户脚本管理器,它适用于 Chrome, Microsoft Edge, Safari, Opera Next, 和 Fir ...

  7. Python爬虫案例:爬取携程评论

    前言 之前爬取美团,马蜂窝等网站的数据都挺顺利,大众点评(这个反爬机制有点麻烦)在磕磕绊绊中也算成功(重点是网页页数的变化和关键字的隐藏替换)但携程居然遇到了瓶颈. 主要是查看源代码时发现关键商户信息 ...

  8. 携程ajax,Python爬虫实战之爬取携程评论

    一.分析数据源 这里的数据源是指html网页?还是Aajx异步.对于爬虫初学者来说,可能不知道怎么判断,这里辰哥也手把手过一遍. 提示:以下操作均不需要登录(当然登录也可以) 咱们先在浏览器里面搜索携 ...

  9. python爬取携程网游记_Python爬虫案例:爬取携程评论

    前言 之前爬取美团,马蜂窝等网站的数据都挺顺利,大众点评(这个反爬机制有点麻烦)在磕磕绊绊中也算成功(重点是网页页数的变化和关键字的隐藏替换)但携程居然遇到了瓶颈. 主要是查看源代码时发现关键商户信息 ...

  10. python爬取携程景区用户评论

    python爬取携程景区用户评论(爬虫时遇到翻页但url不变问题时的解决办法) python爬取携程景区用户评论 Ajax页面加载的页面和普通页面的不同 解决办法 效果 python爬取携程景区用户评 ...

最新文章

  1. 求一个整数的阶乘结果中后缀0的个数
  2. Easyui的DateBox日期格式化
  3. intel 指令集_苹果首款ARM Mac来了,浅谈ARM和Intel处理器
  4. 三维点云学习(2)下-Octree
  5. Atitit usrQBM1603短信验证码规范
  6. 做APP,从头到尾产品经理需要做什么?- 项目启动前
  7. 中国广电即将放号,感受到压力的中国移动率先推出19元5G套餐
  8. 小米2A com.android.phone,104.android 简单的检查小米手机系统和华为手机系统是否打开通话自动录音功能,跳转通话录音页面...
  9. 【微机原理作业】8086存储器读写实验
  10. python基础知识整理13-正则re
  11. Netperf性能测试工具
  12. matlab设计倒频系统,OFDM技术仿真(MATLAB代码)
  13. WPF 实现Logo动画
  14. Samba服务+Samba实验
  15. Redis源码笔记四: skiplist
  16. loss损失不下降的原因
  17. 关于PyCharm基本使用 - 【图文讲解】
  18. 【自动驾驶】车道线拟合算法---最小二乘法拟合直线
  19. 显卡ai性能测试软件,超频性能测试:TDP限制严重
  20. python中的逻辑运算符优先级比较——串连特性

热门文章

  1. wps怎么免费导出简历_WPS表格办公—一键添加简历模板
  2. 串口485接法图_rs485接口接线怎样操作?
  3. workstation服务启动报错。错误1075:依存服务不存在, 或已标记为删除的解决方法
  4. 电脑上如何进行录屏?
  5. 一键式文件共享软件Jirafeau
  6. usb声卡驱动_哑巴电脑拯救者——它可能是你见过使用最简单的外接声卡!
  7. SplitContainer控件设置固定比例
  8. Unity3D 制作按钮开关,旋钮开关,摇杆手柄 插件
  9. C++ 后台开发面试时一般考察什么?
  10. Hybird接口的理解