1. 程式人生 > >利用python同步windows和linux文件

利用python同步windows和linux文件

linux then image byte exec 編輯 return col ash

寫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文件