1. 程式人生 > 程式設計 >python實現檔案分片上傳的介面自動化

python實現檔案分片上傳的介面自動化

背景和目的:

利用python request 編寫指令碼測試公司系統的檔案上傳介面。前端讀取檔案的大小然後檔案分片傳給後端,後端將每一片資料重新組合成檔案。大概的過程是:前端將整個檔案的md5、size(大小)、name(檔名)、ext(檔案字尾)、totalchunk(分片總數)與分片檔案的md5、chunk(分片資料),chunkindex(當前分片檔案的下標)等傳給後臺,後臺取得這些資料後,通過chunkindex將每一片資料重組,重組完後,進行md5校驗,判斷檔案上傳是否成功。我只需要去呼叫後臺的介面,然後判斷檔案是否上傳成功,並且上傳沒有錯誤,其他的檔案校驗就不用去深究。

開發前端使用的是vue,後臺使用的是php,要利用python實現對這一介面的呼叫,那麼就先要將前端資料給模擬出來,然後迴圈去呼叫介面,將檔案分片上傳,我的思路大概如下:

1.獲取整個檔案的大小、名字、字尾、分片總數,定義每片檔案的大小:

def __init__(self,data):
  dat = json.loads(data)
  self.path = dat['path'] # 獲取檔案路徑
  self.CHUNK_SIZE = 1024*1024*2 # 定義每片檔案的大小
  self.size = os.path.getsize(dat['path']) # 獲取檔案的大小
  self.totalchunk = math.ceil(self.size / self.CHUNK_SIZE) # 獲取檔案的分片總數
  self.ext = os.path.basename(dat['path']).split('.').pop() # 獲取檔案的字尾
  self.name = os.path.basename(dat['path']) # 獲取檔案的名字

2.獲取檔案的md5,查看了開發那邊的md5演算法,利用python實現過程如下:

# 使用hashlib庫的md5方法獲取指定檔案的md5
def getmd5(self,path):
m = hashlib.md5()
with open(path,'rb') as f:
 for line in f:
  m.update(line)
  md5code = m.hexdigest()
  return md5code

 # 開發那邊對md5的演算法進行了優化,當檔案的大小小於1M時,直接通過getmd5方法去獲取檔案的md5值;
 # 當檔案大於1M時,通過擷取整個檔案中的某幾個片段,然後拼接成一個檔案,再去獲取其md5值,最後刪除這個檔案
 def md5(self,path):
  if self.size < 1024 * 1024:
   return self.getmd5(path)
  f = open(path,'rb')
  f.seek(0,0)
  data = f.read(2012)
  f.seek(int(self.size / 2) - 1999,0)
  data += f.read(1999)
  f.seek(-2010,2)
  data += f.read(2010)
  f.close()
  path = 'D:/copy_' + str(os.path.basename(path))
  f = open(path,'wb')
  f.write(data)
  f.close()
  val = self.getmd5(path)
  os.remove(path)
  return val

3.呼叫檔案上傳的介面

def uploading(self,chunkIndex):
  MD5 = self.md5(self.path) # 整個檔案的md5
  start = (chunkIndex - 1) * self.CHUNK_SIZE # 擷取檔案的起始位置
  end = min(self.size,start + self.CHUNK_SIZE)# 擷取檔案的結束位置
  f = open(self.path,'rb')
  f.seek(start)
  data = f.read(end) # 待分片上傳的資料
  f.close()
  path1 = 'D:/copy_' + str(os.path.basename(self.path)) # 將該資料儲存在本地
  f = open(path1,'wb')
  f.write(data)
  f.close()
  chunk_md5 = self.md5(path1) # 讀取分片上傳資料的md5
  # 將所有的資料儲存在files字典當中,利用requests的files傳輸資料
  # 使用requests files型別時,要像下面一樣構建引數,不然會有錯誤
  files={
   'chunk':('blob',data,'application/octet-stream'),'name':(None,self.name),'ext':(None,self.ext),'index':(None,chunkIndex),'total': (None,self.totalchunk),'size': (None,self.size),'chunk_md5': (None,chunk_md5),'md5': (None,MD5),}
  # 使用requests傳送介面請求
  res = self.request.send('post','https://10.104.17.222/bank/elements/uploading',verify=False,files=files)
  os.remove(path1) # 刪除存在本地的分片檔案
  return res.json()

4.迴圈呼叫檔案上傳的介面

chunkIndex = 1
 while chunkIndex <= totalchunk:
 res2 = upload.uploading(chunkIndex)
 chunkIndex += 1

5.從伺服器上去讀取通過介面上傳的檔案的md5值,判斷是否正確

以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支援我們。