Python Forum
Pickle a file over a socket in 1024 segments
Thread Rating:
  • 1 Vote(s) - 2 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Pickle a file over a socket in 1024 segments
#7
Here a minimal implementation. I have done it to wake up.
Later i realized that my variable name for received was wrong..

server.py
import socket
import os
import struct
import hashlib


def handle(client, addr):
    buffsize = 1024
    file = '/home/deadeye/foster_the_people_20110408_128.mp3'
    print('File size:', os.path.getsize(file))
    fsize = struct.pack('!I', os.path.getsize(file))
    print('Len of file size struct:', len(fsize))
    client.send(fsize)
    with open(file, 'rb') as fd:
        while True:
            chunk = fd.read(buffsize)
            if not chunk:
                break
            client.send(chunk)
        fd.seek(0)
        hash = hashlib.sha512()
        while True:
            chunk = fd.read(buffsize)
            if not chunk:
                break
            hash.update(chunk)
        client.send(hash.digest())
    client.close()

addr = ('', 8080)
sock = socket.socket()
sock.bind(addr)
sock.listen(5)

# while True loop normally
# to handle incomming connections 
client, addr = sock.accept()
print('Got connection from:', addr)
handle(client, addr)
sock.close()
client.py
mport socket
import os
import struct
import hashlib

addr = ('localhost', 8080)
sock = socket.socket()
sock.connect(addr)
print('Connected to', addr)

received = 0
chunks = []
while received< 4:
    data = sock.recv(4 - received)
    received += len(data)
    chunks.append(data)
print('Received len of file size struct', len(b''.join(chunks)))
fsize = struct.unpack('!I', b''.join(chunks))[0]
print('Filesize:', fsize)

buffer = 1024
received = 0
chunks = []
while received < fsize:
    data = sock.recv(min(fsize - received, buffer))
    received += len(data)
    chunks.append(data)
file = b''.join(chunks)
print('Received file')
print('Expected size:', fsize)
print('Received size:', len(file))

received = 0
chunks = []
while received < 64:
    data = sock.recv(64 - received)
    received += len(data)
    chunks.append(data)
sha512 = b''.join(chunks)
print('Received Hash', len(sha512), sha512)
sock.close()

hash_ok = hashlib.sha512(file).digest() == sha512
print('Hash is ok') if hash_ok else print('Hash is not ok')
The problem with sockets are, that the call recv(size) does not guarantee that you really receiving this given data size. So you have to send the file size you want to send. With struct.pack and struct.unpack you can send the given file size. Afterwards I'm sending a hash, to check if the transfer was really right.

I did not any optimization. On client side you can write the data to disk instead of appending the chunks into a list. The check afterwards can be done with the same procedure as shown on server side. But this is optional to check the data integrity.

If you want to have the song, write a PN :-D
Almost dead, but too lazy to die: https://sourceserver.info
All humans together. We don't need politicians!
Reply


Messages In This Thread
RE: Pickle a file over a socket in 1024 segments - by DeaD_EyE - Aug-08-2017, 06:09 AM

Possibly Related Threads…
Thread Author Replies Views Last Post
  how to send an image from server to client using PICKLE module dafdaf 1 3,162 Jun-02-2020, 01:08 PM
Last Post: nuffink
  File transfer with xmodem CRC (1024) checksum Jhonbovi 3 8,390 Nov-08-2018, 09:01 AM
Last Post: Larz60+

Forum Jump:

User Panel Messages

Announcements
Announcement #1 8/1/2020
Announcement #2 8/2/2020
Announcement #3 8/6/2020