码迷,mamicode.com
首页 > 编程语言 > 详细

利用python同步windows和linux文件

时间:2018-08-07 00:24:37      阅读:173      评论:0      收藏:0      [点我收藏+]

标签:服务   断开连接   name   with   success   失败   md5   代码   direct   

写python脚本的初衷,每次在windows编辑完文件后,想同步到linux上去,只能够登录服务器,然后再利用网络copy,重复性很大,就想着能不能写一个小脚本帮我同步

逻辑:比对本地和服务器文件的md5,如果md5不一致,则备份服务器上的文件,将本地的给上传上去

代码分为windows端和服务器端,有些东西,都让python一个做了,写着有点累,就想着,能否服务端提供一个端口,windows去调用这个接口,来完成一部分工作

python代码如下:

需要额外安装的包为是paramiko,安装方法:pip install paramiko即可,代码如下,利用paramikoSSHClient来调用服务器自己编写的API(嘿嘿,姑且叫做API)吧,Transport来实现sftp文件的上传,

#!/usr/bin/env python

import os
import hashlib
import paramiko
import time
import sys

def getmd5(filename):
    filehash = hashlib.md5()
    f = open(filename,rb)
    while True:
        b=f.read(8096)
        if not b:
            break
        filehash.update(b)
    f.close()
    return filehash.hexdigest()

def send_files(sftp,ssh,filename,abspathfile,server_dir):
    try:
        print ("删除文件",end=" ")
        print (filename)
        
        ssh.exec_command(bash /root/put_api.sh %s move % filename)
        
        print ("删除文件成功")
        print ("开始上传文件")
        server_file=server_dir + filename

        sftp.put(abspathfile,server_file)
        print ("文件上传成功")

    except:
            print ("文件上传失败")
    
def search_file(dir,path,ssh,server_dir):
    #定义排除以md结尾的字符串
    suffix=md
    #定义循环

    print ("开启sftp")
    t = paramiko.Transport((myhostname,22))
    t.connect(username=root,password=mypassword)
    sftp = paramiko.SFTPClient.from_transport(t)
    
    for filename in os.listdir(path):

        print (time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()))
        print ("开始处理 %s" %(filename))
        
        #如果以md结尾,就continue
        if filename.endswith(suffix):
            print ("不处理以md结尾")
            continue
        
        #定义绝对路径
        abspathfile=dir + \\ + filename

        #获取文件的md5
        localfilemd5=getmd5(abspathfile)+\n

        byte_localfilemd5=localfilemd5.encode(encoding="gb2312")
        print ("%s md5值 %s" %(filename,byte_localfilemd5))
        
        serverfilemd5=get_server_md5(ssh,filename)

        print ("%s 服务器md5值 %s" %(filename,serverfilemd5))
        
        if byte_localfilemd5 == serverfilemd5 :
            print ("md5值一致,不需要上传")
        else:
            print ("md5值不一致,上传文件")

#        send_files(sftp,ssh,filename,abspathfile,server_dir)
            try:
#                send_files(ssh,filename,abspathfile,server_dir)
                send_files(sftp,ssh,filename,abspathfile,server_dir)
            except:
                print ("上传失败...")

    print ("关闭sftp")
    t.close()



def get_server_md5(ssh,filename):
    stdin,stdout,stderr = ssh.exec_command(bash /root/put_api.sh %s % filename)
    result = stdout.read()
    
    return result

def main():
    starttime=time.time()
    
    print ("脚本开始同步")
    print (time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()))
    try:
        ssh = paramiko.SSHClient()
        ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
        ssh.connect(hostname=myhostname,port=22,username=root,password=mypassword)
    except:
        print ("服务器连接失败,异常退出")
        sys.exit(-1)
        
    #定义路径
    local_dir = E:\\TEMP\\note_html
    server_dir= /root/nginx_02/

    #利用函数排除文件
    search_file(local_dir,local_dir,ssh,server_dir)

#    print (get_server_md5(ssh,‘d0180727_install_rabbitmt_png_06.png‘))
    
    ssh.close()
    endtime=time.time()
    print (time.strftime("%Y-%m-%d %H:%M:%S", time.localtime()))
    print ("服务器断开连接,本次文件更新成功")
    print ("本次更新时间为:%.2f s" %(endtime - starttime))
    print ("更精确的时间:",end=" ")
    usedtime = endtime - starttime
    print (usedtime,end=" ")
    print ("s")
    
    
if __name__ == "__main__" :
    main()

Linux 自己编写的API:

#!/bin/bash 

#判断参数的个数是否大于等于1
if [ $# -ge 1 ];then
    
    #定义文件夹
    root_dir="/root/nginx_02/"
    backdir="/root/.backup/"
    abs_filename=$root_dir$1

    #判断是否有这个文件
    if [ -f $abs_filename ];then

        #利用md5sum工具获取文件的md5值
        getfilemd5=`md5sum $abs_filename | awk {print $1}`
        echo "$getfilemd5"

        #判断第二个参数是否是move
        if [ move == $2 ];then
            #判断是否存在备份目录,没有则存在,有则挪至备份目录
            if [ -d $backdir ];then
                nowtime=`date +"%F_%H:%M:%S"`
                
                mv $abs_filename $backdir$1_$nowtime
                
                if [ 0 -eq $? ];then
                    echo "move successful"
                else
                    echo "move failed"
                fi
                
            else
                mkdir -p $backdir
            fi
        fi        

    else
        #报错,没有这个文件
        echo "$1 No such file or directory"
    fi

else
    #报错,参数错误
    echo "Parameter error"
fi
    

 

最终实现的功能如下:

技术分享图片

利用python同步windows和linux文件

标签:服务   断开连接   name   with   success   失败   md5   代码   direct   

原文地址:https://www.cnblogs.com/wang-li/p/9434210.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!