ETL应用场景中,若对端接口文件未能提供,任务会处于循环等待,直到对端提供为止,该方法极大的消耗了系统资源。为此想到了一种方法,一次获取一个平台的文件,实现思路如下:

1、第一次获取对端平台提供目录下给定日期的所有接口文件,并保存文件列表;

2、后续每隔n分钟重启获取任务,每次先获取文件列表,和上次列表进行对比,当发生如下情况时,会重新获取:

A、有新文件产生;

B、有文件大小变化

实现方法如下:

[ftp.properties]

ipaddress = 10.25.xxx.xxx
username = xxxxx
password = xxxxx #\u5F53 encryption \u6709\u503C\u65F6\uFF0C\u5C06\u8FDB\u884C\u5BC6\u7801\u89E3\u6790
encryption = #\u5F53resolve \u4E3A False\u65F6\uFF0C\u9700\u8981\u66FF\u6362\u8FDC\u7A0B\u76EE\u5F55\u548C\u5F53\u524D\u76EE\u5F55\u7684\u53C2\u6570
resolve = 1
remoteDir = /bosscdr/tobak/jf_bass
localDir = /interface/cyg/[SDT_YYYYMMDD] #\u4E0A\u6B21\u4FDD\u5B58\u7684\u6587\u4EF6\u83B7\u53D6\u5217\u8868
lastFileList = /interface/cyg/lastfilelist.txt
# -*-  coding:utf-8 -*-
'''
函数说明 :获取远程文件
编写时间: 2015-5-5
编 写 人 : chenyangang
----------------------------------------
实现方法:
1、获取配置文件中制定的ftp服务器信息,用户名采用加密方式
2、获取远程目录下的文件列表,若存在保存的文件列表,进行比对,提取差异文件
3、根据差异文件进行文件获取
'''
import datetime
import ConfigParser
import os
import ftplib
import cPickle class GetDataBaseDiff(object): def __init__(self, config, interfaceID = None, interfaceDate = None, delay = 0):
self.config = config
self.interfaceID = interfaceID #默认为当天日期
if interfaceDate == None:
self.interfaceDate = datetime.date.strftime(datetime.date.today() - \
datetime.timedelta(delay),"%Y%m%d") def getConfig(self, interfaceDate): readConfig = ConfigParser.ConfigParser()
with open(self.config,'r') as configFile: readConfig.readfp(configFile)
hostaddr = readConfig.get('ftp.properties','ipaddress')
username = readConfig.get('ftp.properties','username') #是否解析参数和加密
resolve = readConfig.get('ftp.properties','resolve')
encryption = readConfig.get('ftp.properties','encryption') #目录信息
remoteDir = readConfig.get('ftp.properties','remoteDir')
localDir = readConfig.get('ftp.properties','localDir') #存储上次获取文件列表
lastFileList = readConfig.get('ftp.properties','lastFileList') if encryption == '' :
password = readConfig.get('ftp.properties','password')
else:
command = encryption + ' ' + readConfig.get('ftp.properties','password')
password = os.popen(command) if resolve == '' :
month = interfaceDate[0:6]
remoteDir = remoteDir.replace(r"[SDT_YYYYMMDD]", interfaceDate)
remoteDir = remoteDir.replace(r"[SDT_YYYYMM]",month) localDir = localDir.replace(r"[SDT_YYYYMMDD]", interfaceDate)
localDir = localDir.replace(r"[SDT_YYYYMM]",month) return hostaddr, username, password, remoteDir, localDir, lastFileList def connect(self, hostaddr, username, password): try:
connftp = ftplib.FTP(hostaddr)
except ftplib.error_perm:
print "The ipaddress (ipaddress) refused!" %{'ipaddress':hostaddr} try:
connftp.login(username, password)
except ftplib.error_perm:
print "This username (username) refuse connect, please check your\
username or password!" %{'username':username} return connftp def getFileList(self, connftp, remoteDir): #获取文件详细信息,包括权限、文件大小、属主等信息,其中第5项为文件大小
connftp.cwd(remoteDir)
filesDetail = connftp.nlst('-l') #保存文件名称和大小
fileList = {} for fileDetail in filesDetail:
filelistFromDetail = fileDetail.strip().split()
fileList[filelistFromDetail[-1]] = filelistFromDetail[4] return fileList def comparisonFileList(self, lastFileList, newFileList): #装载上一次文件获取信息 if len(open(lastFileList, "rb").readlines()) > 0 :
with open(lastFileList, "rb") as fp:
try:
lastfileList = cPickle.load(fp)
except EOFError:
print "Load (filename) was failed"%{'filename':lastFileList}
else:
lastfileList={} lastfileset = set(lastfileList.keys())
newfileSet = set(newFileList.keys()) #提取新增文件列表
diffFileList = list(newfileSet - lastfileset)
sameFileName = list(newfileSet & lastfileset) #提取前后文件大小不一致的文件列表
for samefilename in sameFileName:
if newFileList[samefilename] != lastfileList[samefilename]:
diffFileList.append(samefilename) del lastfileList
#保存最新文件获取列表
fp = open(lastFileList, "wb") lastfileList = cPickle.dump(newFileList, fp)
fp.close() return diffFileList def machedFileList(self, diffFileList, interfaceID, interfaceDate):
return [flist for flist in diffFileList if interfaceID in flist \
and interfaceDate in flist] def download(self, connftp, localDir, getFileList): #进入本地目录
if not os.path.isdir(localDir) :
os.makedirs(localDir) try:
os.chdir(localDir)
except :
print 'Dose\'t enter the directory , mybe you have not authority!' #获取最新文件
for remotefile in getFileList:
try:
connftp.retrbinary("RETR %s"%remotefile, open(remotefile,"wb").write)
except ftplib.error_perm:
print 'ERROR: cannot read file "%s"' % remotefile connftp.quit() if __name__ == '__main__' :
interfaceDate = ''
interfaceID = None
getDataBaseDiff = GetDataBaseDiff('./config.properties', interfaceDate, 0)
hostaddr, username, password, remoteDir, localDir, lastFileList = getDataBaseDiff.getConfig(interfaceDate) connectionFtp = getDataBaseDiff.connect(hostaddr, username, password) fileList = getDataBaseDiff.getFileList(connectionFtp, remoteDir)
diffFileList = getDataBaseDiff.comparisonFileList(lastFileList, fileList) if interfaceID is not None and len(diffFileList) >0:
getFileList = getDataBaseDiff.machedFileList(diffFileList, interfaceID, interfaceDate)
getDataBaseDiff.download(connectionFtp, localDir, getFileList)
else:
getDataBaseDiff.download(connectionFtp, localDir, diffFileList)

如上,是学习python后,尝试编写的代码。可修改为配置文件中配置多个平台,获取多平台接口数据。

ETL应用:一种一次获取一个平台接口文件的方法的更多相关文章

  1. JS中对获取一个标签的class的方法封一个库

    在JS中我们经常会会用到,获取一个标签的id var aId=document.getElementById("id") 现在虽然有getElementsByClassName这个 ...

  2. 使用fuser命令kill一个终端(特殊文件)的方法

    /*********************************************************************  * Author  : Samson  * Date   ...

  3. 用js如何获取一个上传文件的扩展名

    function suffix(file_name){     var result =/\.[^\.]+/.exec(file_name);     return result; }

  4. 记录一种下载https网址中的mp4文件的方法

    需要下载一个网页中的视频, 页面中的视频播放器为 JW player, 通过搜索发现可以下载对应的视频. 1. 使用chrome浏览器分析 网页中的视频地址: F12或者右键-->检查, 在打开 ...

  5. 通过ES6 封装了一个上传文件的方法 XMLHttpRequest() 通用

    ### 上传进度回显,上传速度回显 ### 源码如下,新建index.js装起来 export class UploadServers { constructor (options) { this.x ...

  6. ASP.NET之MVC 微信公众号授权给第三方平台的技术实现流程(获取第三方平台access_token)

    “出于安全考虑,在第三方平台创建审核通过后,微信服务器每隔10分钟会向第三方的消息接收地址推送一次component_verify_ticket,用于获取第三方平台接口调用凭据”.这是文档中的原话,也 ...

  7. Entity Framework 6 Recipes 2nd Edition(13-2)译 -> 用实体键获取一个单独的实体

    问题 不管你用DBFirst,ModelFirst或是CodeFirst的方式,你想用实体键获取一个单独的实体.在本例中,我们用CodeFirst的方式. 解决方案 假设你有一个模型表示一个Paint ...

  8. java中的反射机制,以及如何通过反射获取一个类的构造方法 ,成员变量,方法,详细。。

    首先先说一下类的加载,流程.只有明确了类这个对象的存在才可以更好的理解反射的原因,以及反射的机制. 一.  类的加载 当程序要使用某个类时,如果该类还未被加载到内存中,则系统会通过加载,连接,初始化三 ...

  9. 获取一个 app 的 URL Scheme 的方法:

    获取一个 app 的 URL Scheme 的方法: 上这个网站 URL Schemes 查一下相应的 app 的 URL Scheme 是否有被收录 第一种方法没找到的话,把相应的 app 的 ip ...

随机推荐

  1. Python的实例方法,类方法,静态方法之间的区别及调用关系

    如果只看这个图,很多人可能会看的一头雾水,特别是学过完全面向对象语言的同学, Python 是双面向的,既可以面向函数编程,也可以面向对象编程,所谓面向函数就是单独一个. py 文件,里面没有类,全是 ...

  2. fzu 2250 不可能弹幕结界 分析+模拟,考察思维严谨。

    Problem 2250 不可能弹幕结界 Accept: 5    Submit: 13Time Limit: 1000 mSec    Memory Limit : 65536 KB Problem ...

  3. cookie做订单

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/ ...

  4. 003android初级篇之【转】Android开发中颜色的定义方法

    正好用到颜色的定义,但脑子里没有记住具体,转载一篇加强印象 1.使用Color类的常量,如: int color = Color.BLUE; // 创建一个蓝色 是使用Android提供的颜色 int ...

  5. Win7机器上安装Ubuntu 14.0.4

    折腾了两天,分享一下经历. 我须要在已经安装了win7的机器上安装Ubuntu 14.0.4 (两者共存),研究下来有例如以下几种方案, 都折腾了一遍.分享一下经验: 方式1: wubi.exe, 把 ...

  6. Linux shell (ssh批量配置免秘)读取配置文件,进行远程操作

    需要目标机器安装有 expect 命令 分成五个文件config.ini(配置文件).id_ras.pub(公钥).read.sh(一个函数,用于读取配置文件).test.sh(执行文件).run.s ...

  7. jquery call 函数改变this作用域

    call的用法在许多地方都看到过介绍.可以用来改变函数的作用域. 在页面中我们在一个input中添加click事件 <input id="Button1" type=&quo ...

  8. MathType可以编辑省略号吗

    说到省略号大家可能会想到写文章的时候会用到,其实在数学中也会常常的使用到.当数学过程是重复有规律性的过程时,就会用到它.MathType是一款数学公式编辑器,那么,在数学公式中,MathType编辑时 ...

  9. HDU1087 Super Jumping! Jumping! Jumping! 最大连续递增子段

    Super Jumping! Jumping! Jumping! Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 ...

  10. 【Cocos游戏实战】功夫小子第八课之游戏打包和相关问题说明

    至此,功夫小子系列的Cocos2d-x的实战文章就结束了. 源代码地址: https://github.com/SuooL/KungfuBoy 如须要资源请邮件我 1020935219@qq.com ...