Python实现FTP文件传输的实例


Posted in Python onJuly 07, 2019

FTP一般流程

FTP对应PASV和PORT两种访问方式,分别为被动和主动,是针对FTP服务器端进行区分的,正常传输过程中21号端口用于指令传输,数据传输端口使用其他端口。

PASV:由客户端发起数据传输请求,服务器端返回并携带数据端口,并且服务器端开始监听此端口等待数据,为被动模式;

PORT:客户端监听端口并向服务器端发起请求,服务器端主动连接此端口进行数据传输,为主动模式。

Python实现FTP文件传输的实例

其中TYPE分两种模式,I对应二进制模式、A对应ASCII模式;

PASV为客户端发送请求,之后227为服务器端返回操作码表示成功,并且后面带有服务器端监听的端口:143x256(左移8位)+48

之后通过STOR命令进行数据下载,下载完成后返回226表示数据传输完成。

2. Python代码实现:

中文路径问题:由于FTP支持ASCII编码,Python ftplib中编码方式使用latin-1,而window默认编码方式为gbk,所以使用Python处理时需先将中文路径编码为gbk之后译码为latin-1字符;

上传下载使用storline和retrline,对应二进制使用storbinary和retrbinary。对于stor类函数后面的参数fp表示接收一个文件对象,支持read方法,一般为打开需要上传的源文件,而retr类函数后面的参数表示对于返回数据的处理方法。

从一个FTP服务器到另一个FTP服务器的数据传输:

利用本地电脑作为数据缓存,但并不将数据保存到硬盘,只在内存中存储进行数据传输;其中一端作为下载一端为数据上传。

首先登陆两个FTP服务器,transfercmd函数用于发送命令并返回已建立好连接的本地Socket,此时分别在两个本地Socket进行数据的收发即可。

在测试中发现,在发送完一个文件之后只有及时的关闭socket,21端口才会返回226,数据完成指示,这样才可以循环下一个文件,在完成之后要退出FTP。

#coding=utf-8

import ftplib,os.path,os
import socket

f1=ftplib.FTP('172.16.2.76')
f2=ftplib.FTP('172.16.25.153')


class myFTP:
    path='file/download/bbb/'
    # ftplib中编码使用latin-1
    title='版本'.encode(encoding='gbk').decode(encoding='latin-1')
    path1=path+title  
    localDir='E:\\ver\\fp\\'
    
    path2='abc/edf/'
    

    def __init__(self):
           
      try:
        f1.login('username','password')
      except ftplib.error_perm:
        print('f1 cannot loggin!')
        return

      try:
        f2.login()
      except ftplib.error_perm:
        print('f2 cannot loggin!')
        return
        
    def ftpD(self):
             
      filelist=[]
      fileLIST=[]
      filels=f1.retrlines('LIST %s'%(self.path1),callback=filelist.append)
      f1.cwd(self.path1)
      for file in filelist:
        fileAttr=file.split(' ')
        fileName=fileAttr[-1]
        fileType=fileAttr[0][0]
        if fileType=='-':
          fileLIST.append(fileName)
    
      for file in fileLIST:
        path=self.localDir+file
        f1.retrbinary('RETR %s'%(file),open(path,'wb').write)
        print('%s download.....'%(file))    
      f1.quit()
    
    def ftpU(self,fun=1):
    
      os.chdir(self.localDir)
      fileList=os.listdir()
      
      # upload file
      if fun==1:
          for file in fileList:
            path=self.path2
            f2.storbinary('STOR %s'%(path+file),open(file,'rb'))
            print('%s uploading......'%(file))
      
      #delete file
      if fun==0:
          try:
              for file in fileList:
                path=self.path2
                f2.delete(path+file)
                print('%s delete......'%(file))
          except ftplib.error_perm:
              print('no file to delete!!')
              return
      
      f2.quit()
    
    def test(self):
      
      f1.cwd(self.path1)
      f2.cwd(self.path2)
      fileList=f1.nlst()
      print(fileList)
      
      for file in fileList:
        print('transfer %s......'%(file))
        f1.voidcmd('TYPE I')
        f2.voidcmd('TYPE I')
        sock1=f1.transfercmd('RETR %s'%(file))
        sock2=f2.transfercmd('STOR %s'%(file))
    
        while 1:
      
            data=sock1.recv(1024)
            sock2.sendall(data)
            
            if len(data)==0:
              break
        # 数据发送完成后需关闭socket,服务器21端口才会有返回    
        sock1.close()
        sock2.close()
            
                          
        res1=f1.getresp()
        #print('f1 >> %s'%(res1))
        res2=f2.getresp()
        #print('f2 >> %s'%(res2))    
                   
      f1.quit()
      f2.quit()

    
if __name__=='__main__':
  ftptest=myFTP() 
  ftptest.ftpU(0)
  #ftptest.test()
  #ftptest.ftpD()
Python 相关文章推荐
python 实现插入排序算法
Jun 05 Python
在Linux上安装Python的Flask框架和创建第一个app实例的教程
Mar 30 Python
python使用pil生成图片验证码的方法
May 08 Python
Python模拟三级菜单效果
Sep 11 Python
Python实现文件信息进行合并实例代码
Jan 17 Python
python使用Matplotlib绘制分段函数
Sep 25 Python
python 多线程中子线程和主线程相互通信方法
Nov 09 Python
Python实现 PS 图像调整中的亮度调整
Jun 28 Python
python程序 创建多线程过程详解
Sep 23 Python
python GUI库图形界面开发之PyQt5 MDI(多文档窗口)QMidArea详细使用方法与实例
Mar 05 Python
使用matlab 判断两个矩阵是否相等的实例
May 11 Python
Django --Xadmin 判断登录者身份实例
Jul 03 Python
Python爬虫动态ip代理防止被封的方法
Jul 07 #Python
Python异常处理例题整理
Jul 07 #Python
解决pycharm下os.system执行命令返回有中文乱码的问题
Jul 07 #Python
在python中实现调用可执行文件.exe的3种方法
Jul 07 #Python
Python求两点之间的直线距离(2种实现方法)
Jul 07 #Python
对Python中画图时候的线类型详解
Jul 07 #Python
Python 3 实现定义跨模块的全局变量和使用教程
Jul 07 #Python
You might like
第一个无线电台是由谁发明的
2021/03/01 无线电
手把手教你使用DedeCms的采集的图文教程
2007/03/11 PHP
据说是雅虎的一份PHP面试题附答案
2009/01/07 PHP
php注册和登录界面的实现案例(推荐)
2016/10/24 PHP
php 静态属性和静态方法区别详解
2017/04/09 PHP
jQuery的一些特性和用法整理小结
2010/01/13 Javascript
jquery中ajax学习笔记4
2011/10/16 Javascript
RequireJS使用注意细节
2016/05/15 Javascript
JavaScript中的splice方法用法详解
2016/07/20 Javascript
Js得到radiobuttonlist选中值的两种方法(推荐)
2016/08/25 Javascript
NodeJS学习笔记之Module的简介
2017/03/24 NodeJs
解决微信小程序中的滚动穿透问题
2019/09/16 Javascript
[09:34]2018DOTA2国际邀请赛寻真——永不放弃的iG
2018/08/14 DOTA
关于Python中空格字符串处理的技巧总结
2017/08/10 Python
python读取excel表格生成erlang数据
2017/08/26 Python
Python2随机数列生成器简单实例
2017/09/04 Python
速记Python布尔值
2017/11/09 Python
Python3实现的字典遍历操作详解
2018/04/18 Python
python从zip中删除指定后缀文件(推荐)
2019/12/05 Python
已安装tensorflow-gpu,但keras无法使用GPU加速的解决
2020/02/07 Python
Html5如何唤起百度地图App的方法
2019/01/27 HTML / CSS
世界上最大的售后摩托车零配件超市:J&P Cycles
2017/12/08 全球购物
法国设计制造的扫帚和刷子:Andrée Jardin
2018/12/06 全球购物
新加坡第一大健康与美容零售商:屈臣氏新加坡(Watsons Singapore)
2020/12/11 全球购物
JPA的优势都有哪些
2013/07/04 面试题
生产总经理岗位职责
2013/12/19 职场文书
婚礼司仪主持词
2014/03/14 职场文书
法定代表人授权委托书
2014/04/04 职场文书
防沙治沙典型材料
2014/05/07 职场文书
文明城市创建标语
2014/06/16 职场文书
2015年控辍保学工作总结
2015/05/18 职场文书
2016十一国庆节感言
2015/12/09 职场文书
详解JavaScript中的执行上下文及调用堆栈
2021/04/29 Javascript
Mysql中调试存储过程最简单的方法
2021/06/30 MySQL
Java并发编程必备之Future机制
2021/06/30 Java/Android
SQL Server表分区删除详情
2021/10/16 SQL Server