Advertisement
Guest User

Untitled

a guest
Dec 19th, 2016
113
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 5.99 KB | None | 0 0
  1. import os
  2. import smtplib
  3. import zipfile
  4. from email.header import Header
  5. from email.mime.multipart import MIMEMultipart
  6. from email.mime.text import MIMEText
  7.  
  8. import math
  9. import paramiko
  10. import datetime
  11. import re
  12.  
  13.  
  14. def send_email(_from, from_name, from_password, recipient, recipient_name, message):
  15. mail = MIMEMultipart()
  16. mail['From'] = Header(from_name + '\n' + _from, 'utf-8').encode()
  17. mail['To'] = Header(recipient_name + '\n' + recipient, 'utf-8').encode()
  18. mail['Subject'] = Header('{} Log迁移报告'.format(datetime.date.today()), 'utf-8').encode()
  19.  
  20. mail.attach(MIMEText(message, 'html', 'utf-8'))
  21. server = smtplib.SMTP('smtp.ym.163.com', 25) # smtp默认端口25
  22. server.set_debuglevel(5)
  23. server.login(from_name, from_password)
  24. server.sendmail(recipient_name, [recipient, ], mail.as_string())
  25. server.quit()
  26.  
  27.  
  28. def get_dir_size(dir):
  29. size = 0
  30. for root, dirs, files in os.walk(dir):
  31. size += sum([os.path.getsize(os.path.join(root, name)) for name in files])
  32. # 单位kb
  33. size = math.ceil(size / 1024)
  34. return size
  35.  
  36.  
  37. class Disk(object):
  38. __path = '/'
  39. __disk = ''
  40. ssh = None
  41. __sftp = None
  42.  
  43. server_info = {}
  44.  
  45. def __init__(self, *args, **kwargs):
  46. if args:
  47. self.__path = args[0]
  48. self.__disk = os.statvfs(self.__path)
  49.  
  50. def capacity(self):
  51. # 磁盘容量
  52. return self.__disk.f_blocks * self.__disk.f_bsize
  53.  
  54. def remaining_capacity(self):
  55. # 磁盘剩余容量
  56. return self.__disk.f_bavail * self.__disk.f_bsize
  57.  
  58. def remaining_capacity_ratio(self):
  59. # 磁盘剩余容量比例
  60. return self.remaining_capacity() / self.capacity()
  61.  
  62. def get_server_info(self):
  63. # df 命令单位kb
  64. stdin, stdout, stderr = disk.ssh.exec_command('df ' + REMOTELY_PATH)
  65. info = stdout.readlines()[1]
  66. info = info.split(' ')
  67. for _ in info:
  68. info.remove('')
  69. self.server_info['used'] = int(info[1])
  70. self.server_info['available'] = int(info[2])
  71. self.server_info['percentage'] = float(info[4][0:-1:1]) / 100
  72. return self.server_info
  73.  
  74. def gets_the_servers_remaining_capacity(self):
  75. self.get_server_info()
  76. return self.server_info['available']
  77.  
  78. def get_file_size(self, path, file):
  79. return os.path.getsize(path + file)
  80.  
  81. def zip_file(self, path, file):
  82. zip_file = zipfile.ZipFile(path + file + '.zip', 'w')
  83. zip_file.write(path + file, file)
  84. zip_file.close()
  85. os.remove(path + file)
  86.  
  87. def connect_to_the_server(self, host, port, username, password):
  88. ssh = paramiko.SSHClient()
  89. ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
  90. ssh.connect(host, port, username, password)
  91.  
  92. self.ssh = ssh
  93. self.__sftp = paramiko.SFTPClient.from_transport(ssh.get_transport())
  94. return True
  95.  
  96. def close_connect(self):
  97.  
  98. if self.__sftp is not None:
  99. self.__sftp.close()
  100. self.__sftp = None
  101.  
  102. if self.ssh is not None:
  103. self.ssh.close()
  104. self.ssh = None
  105.  
  106. def upload_file(self, path, file, **kwargs):
  107. try:
  108. remotely_path = kwargs['remotely_path']
  109. except KeyError:
  110. remotely_path = '/'
  111. try:
  112. remotely_name = kwargs['remotely_name']
  113. except KeyError:
  114. remotely_name = file
  115.  
  116. if os.path.isfile(path + file):
  117. if self.__sftp is None:
  118. print('请先调用 connect_to_the_server 方法')
  119. return False
  120. else:
  121. # print('upload {} to {}'.format(path + file, remotely_path + remotely_name))
  122. # self.__sftp.put(path + file, remotely_path + remotely_name)
  123. return True
  124. else:
  125. print('请检查路径 -> \'{}\''.format(path + file))
  126. return False
  127.  
  128. def get_file_list(self, path):
  129. result = []
  130. list = os.listdir(path)
  131. for i in list:
  132. print('filename : {}, match : {}'.format(i, MATCH.match(i)))
  133. if i[0] == '.' or MATCH.match(i):
  134. pass
  135. else:
  136. result.append(i)
  137. return result
  138.  
  139. def upload_the_file_within_the_path(self, path, remotely_path, file):
  140. if not os.path.isdir(path + file):
  141. self.zip_file(path, file)
  142. file = file + '.zip'
  143. self.upload_file(path, file, remotely_path=remotely_path)
  144. os.remove(path + file)
  145. return None
  146. else:
  147. path = path + file + '/'
  148. remotely_path = remotely_path + file + '/'
  149. file_list = self.get_file_list(path)
  150. for file in file_list:
  151. stdin, stdout, stderr = self.ssh.exec_command('mkdir ' + remotely_path)
  152. if stdout.readlines() == []:
  153. self.upload_the_file_within_the_path(path, remotely_path, file)
  154.  
  155.  
  156. if __name__ == '__main__':
  157. # ---------------------------目标服务器账号---------------------------
  158. HOST = '120.26.100.13'
  159. PORT = 1105
  160. USER = 'buhao'
  161. PASSWORD = 'buhao@123!'
  162. # ---------------------------目标服务器账号---------------------------
  163.  
  164. THRESHOLD = 0 # 剩余磁盘空间小于这个值时会进行传递文件操作
  165.  
  166. PATH = '/Users/xuzhaoning/Documents/' # 本地目录
  167. FILE = 'test'
  168. REMOTELY_PATH = '/home/buhao/xzn_test/' # 上传服务器目录(要有这个目录)
  169.  
  170. # 正则匹配规则 今日log不同步
  171. # MATCH = re.compile('[^\d]*' + str(datetime.date.today()) + '[^\d]*')
  172. MATCH = re.compile('.*' + str(datetime.date.today()) + '.*')
  173.  
  174. disk = Disk()
  175.  
  176. if disk.remaining_capacity_ratio() < 1.0:
  177. disk.connect_to_the_server(HOST, PORT, USER, PASSWORD)
  178.  
  179. if get_dir_size(PATH + FILE) < disk.gets_the_servers_remaining_capacity() and disk.get_server_info()[
  180. 'percentage'] > 0.1:
  181. disk.upload_the_file_within_the_path(PATH, REMOTELY_PATH, FILE)
  182. else:
  183. # TODO 其他通知处理
  184. pass
  185. disk.close_connect()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement