对比如下:
| 特性维度 | FTP | SFTP | SCP | TFTP |
|---|---|---|---|---|
| 安全性 | 明文传输 | 基于SSH加密 | 基于SSH加密 | 无加密 |
| 默认端口 | 21 | 22 | 22 | 69 |
| 协议基础 | TCP | SSH | SSH | UDP |
| 认证方式 | 用户名/密码 | 多种(如公钥) | SSH认证 | 无认证 |
| 交互性 | 交互式命令 | 交互式命令 | 仅命令行 | 非交互式 |
| 目录操作 | 支持 | 支持 | 需-r递归 |
不支持 |
| 适用场景 | 内网、匿名访问 | 安全要求高的环境 | 简单文件复制 | 局域网内小文件、网络设备配置 |
ftp ip地址
输入用户名密码进入以后。
dir查看当前目录
put 可以put本地内容进当前目录
比如 put D:/1.txt 远程文件名
get 远程文件名 本地文件名
delete删除
这是当时已经成功实现功能的代码,具体的嘛,懒得讲了和说了,就是上传文件还有每进度5%给出日志提示
def vm_upload(**kwargs):step_progress_callback = kwargs.get('step_progress_callback')host = kwargs.get("IP")username = kwargs.get("LoginName")pwd = kwargs.get("LoginPwd")# 实例化 FTPftp = FTP()# 设置调试等级, 0 不调试, 1 只打印命令与响应, 2 打印详细信息 ftp.set_debuglevel(0)# 设置 FTP 主动被动模式, False 主动模式, True 被动模式(默认的模式) ftp.set_pasv(True)# 设置编码格式ftp.encoding = 'utf-8'try:# 连接与登录ftp.connect(host, 21)ftp.login(username, pwd)logger.info(f"FTP connection successful: {ftp.getwelcome()}")step_progress_callback(20)# 切换到目标目录ftp.cwd("/oas/images")logger.info("Switched to directory: /oas/images")# 检测是否已有虚拟机文件,有则跳过上传remote_filename = VM_VMXlocal_file_to_upload = 'D:/'+VM_VMXtry:# 尝试获取远程文件大小,如果文件存在则跳过上传remote_file_size = ftp.size(remote_filename)logger.info(f"Remote file already exists, size: {remote_file_size} bytes. Skipping upload.")# 可选:比较文件大小,如果不同则覆盖上传local_file_size = os.path.getsize(local_file_to_upload)if remote_file_size == local_file_size:logger.info("Local and remote file sizes match, skipping upload.")step_progress_callback(100)return True, "File already exists and sizes match, upload skipped"else:logger.info("File sizes differ, proceeding with upload...")# 删除远程文件以便重新上传 ftp.delete(remote_filename)logger.info("Deleted existing remote file for re-upload")except error_perm as e:# 文件不存在,继续上传if "550" in str(e):logger.info("Remote file does not exist, proceeding with upload")else:raise e# 获取文件大小用于进度计算file_size = os.path.getsize(local_file_to_upload)logger.info(f"Starting file upload, size: {file_size} bytes ({file_size / 1024 / 1024:.2f} MB)")# 进度跟踪变量uploaded_size = 0last_logged_progress = 0def progress_callback(data):nonlocal uploaded_size, last_logged_progressuploaded_size += len(data)progress_percent = (uploaded_size / file_size) * 100# 每完成5%记录一次日志,避免过于频繁的日志输出if progress_percent - last_logged_progress >= 5 or uploaded_size == file_size:logger.info(f"Upload progress: {progress_percent:.1f}% ({uploaded_size}/{file_size} bytes)")last_logged_progress = progress_percent - (progress_percent % 5)# 更新步骤进度,从20%到100%step_progress = 20 + (progress_percent * 0.8)step_progress_callback(step_progress)# 上传文件(带进度回调)with open(local_file_to_upload, 'rb') as local_file:ftp.storbinary(f'STOR {remote_filename}', local_file, callback=progress_callback)logger.info("File upload completed")# 退出客户端 ftp.quit()step_progress_callback(100)return True, "upload vm successfully"except Exception as e:logger.error(f"File upload failed: {str(e)}")# 确保在异常情况下也关闭连接try:if ftp:ftp.quit()except:passreturn False, f"upload vm failed: {str(e)}"