TCP communication between python and raspberry pi and sending data and files - python

I am currently working on a program of mine to try to send two csv files from my raspberry pi (client) to my laptop (server). In addition, I need to write two different sets of data to the two different csv files. The first one is raw data which will continue to write in data every 30 seconds and another is averaging of the raw data every 15 mins)
My first question is: Is it possible to do the above task? Or do I need to write two different servers and clients codes? (Refer to both codes below). Can I combine both of them? So that it can write two different data (raw and averaging) to two different csv file at the same time.
My second question is: How do I append new sets of data without rewriting the entire file (I tried append before and it duplicates the file data over and over again).
Client.py (This code currently only sends one csv file which is the raw data)
import time
import socket
TCP_IP = '192.168.1.105'
TCP_PORT = 5005
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((TCP_IP, TCP_PORT))
f = open('sensingdata.csv', 'rb')
print 'Sending...'
l = f.read(1024)
while (l):
print 'Sending...'
s.send(l)
l = f.read(1024)
print "Done Sending"
time.sleep(30)
Server.py
import socket
import sys
TCP_IP = ""
TCP_PORT = 5005
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((TCP_IP, TCP_PORT))
s.listen(5)
while True:
conn, addr = s.accept()
f = open('sensing1.csv', 'wb')
print "Got connection from", addr
print "Receiving..."
l = conn.recv(1024)
while (l):
print "Receiving Data..."
f.write(l)
l = conn.recv(1024)
print "Done Receiving"
f.close()
conn.close()
Client2.py (This code is for the appending of averaging data)
import time
import socket
TCP_IP = '192.168.1.105'
TCP_PORT = 5005
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((TCP_IP, TCP_PORT))
g = open('average.csv', 'rb')
print 'Sending Averaging Data...'
l = f.read(1024)
while (l):
print 'Sending...'
s.send(l)
l = g.read(1024)
print "Done Sending"
time.sleep(900)
Server2.py
import socket
import sys
import csv
TCP_IP = ""
TCP_PORT = 5005
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((TCP_IP, TCP_PORT))
s.listen(5)
while True:
conn, addr = s.accept()
g = open('average.csv', 'ab')
print "Got connection from", addr
print "Receiving Averaging Data..."
l = conn.recv(1024)
for rows in g:
while (l):
if row not in rows:
print "Receiving Averaging Data..."
g.write(l)
l = conn.recv(1024)
print "Done Receiving"
g.close()
conn.close()

Related

How to send python socket bytes and strings?

I want to send images and text for the server from the client file. But since I'm new to the socket, I don't know how to do it. Please help me.
codes:
#server.py
import socket
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind(("localhost", 1236))
s.listen(5)
c, addr = s.accept()
image_datas, d1, d2 = c.recv(1024)
f = open("C:\\Users\\SD\\Desktop\\image.jpg", "wb")
while image_datas:
f.write(image_datas)
image_datas = c.recv(1024)
print(d1,d2)
f.close()
c.close()
s.close()
#client.py
import socket
c = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
c.connect(("tcp.ngrok.io", ))
f = open("image.jpg", "rb")
img_data = f.read()
data1 = "hello"
data2 = "server"
c.send(img_data,data2,data3)
f.close()
c.close()

Reading data from a python socket received from multiple clients

I am writing a python program (master.py) to read the data received from 2 separate clients. This is the code example:
master.py:
data_agg = ''
HOST = '172.31.31.207'
PORT = 50008
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((HOST, PORT))
s.listen(2)
conn, addr = s.accept()
print 'Connected by', addr
while 1:
data = conn.recv(65535)
data_agg += data
if not data: break
data_arr = json.loads(data_agg.decode('utf-8'))
data_arr = sorted(data_arr)
print "Sorted attay: \n"
print data_arr
Two clients have the following code:
HOST = '172.31.31.207'
PORT = 50008
s0 = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s0.connect((HOST, PORT))
s0.send(sorted_data_string)
s0.close()
However i only receive data from a single client. What would be a proper way to read the data from a socket arriving from multiple receivers?
If you want your server th handle multiple clients, you can put accept() in a loop and add new clients to a list of connected clients. Then you can read - write to each of those clients.
HOST = '172.31.31.207'
PORT = 50008
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((HOST, PORT))
s.listen(2)
clients = []
while True:
conn, addr = s.accept()
clients += [{'conn':conn, 'addr':addr}]
print 'Connected by', addr
data_agg = ''
while True:
data = conn.recv(65535)
if not data:
break
data_agg += data
data_arr = sorted(json.loads(data_agg.decode('utf-8')))
print "Sorted attay: \n"
print data_arr
conn.close()
s.close()
You could improve the above code by using thread, so that you can handle multiple clients at the same time. You can do this by defining a handle_client function, and run it on a new thread.
while True:
conn, addr = s.accept()
print 'Connected by', addr
start_new_thread(handle_client, (conn,))

audio over python tcp error

I am writing a simple python tcp code to send over a wav file however I seem to be getting stuck. can someone explain why my code is not working correctly?
Server Code
import socket, time
import scipy.io.wavfile
import numpy as np
def Main():
host = ''
port = 3333
MAX = 65535
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((host,port))
s.listen(1)
print "Listening on port..." + str(port)
c, addr = s.accept()
print "Connection from: " + str(addr)
wavFile = np.array([],dtype='int16')
i = 0
while True:
data = c.recvfrom(MAX)
if not data:
break
# print ++i
# wavfile = np.append(wavfile,data)
print data
timestr = time.strftime("%y%m%d-%h%m%s")
print timestr
# wavF = open(timestr + ".wav", "rw+")
scipy.io.wavfile.write(timestr + ".wav",44100, data)
c.close()
if __name__ == '__main__':
Main()
Client Code
host, port = "", 3333
import sys , socket
import scipy.io.wavfile
# create a tcp/ip socket
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
# connect the socket to the port where the server is listening
server_address = (host, port)
print >>sys.stderr, 'connecting to %s port %s' % server_address
input_data = scipy.io.wavfile.read('Voice 005.wav',)
audio = input_data[1]
sock.connect(server_address)
print 'have connected'
try:
# send data
sock.sendall(audio)
print "sent" + str(audio)
sock.close()
except:
print('something failed sending data')
finally:
print >>sys.stderr, 'closing socket'
print "done sending"
sock.close()
Please help someone, I want to send an audio file to my embedded device with tcp since it crucial data to be processed on the embedded device.
Not sure why you go to the trouble of using scipy and numpy for this, since you can just use the array module to create binary arrays that will hold the wave file. Can you adapt and use the simple client/server example below?
(Note: I've copy/pasted a small Windows sound file called 'tada.wav' to the same folder to use with the test scripts.)
Code for the server script:
import socket
HOST = '' # Symbolic name meaning all available interfaces
PORT = 50007 # Arbitrary non-privileged port
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((HOST, PORT))
s.listen(1)
print('Listening...')
conn, addr = s.accept()
print('Connected by', addr)
outfile = open("newfile.wav", 'ab')
while True:
data = conn.recv(1024)
if not data: break
outfile.write(data)
conn.close()
outfile.close()
print ("Completed.")
Code for the client:
from array import array
from os import stat
import socket
arr = array('B') # create binary array to hold the wave file
result = stat("tada.wav") # sample file is in the same folder
f = open("tada.wav", 'rb')
arr.fromfile(f, result.st_size) # using file size as the array length
print("Length of data: " + str(len(arr)))
HOST = 'localhost'
PORT = 50007
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((HOST, PORT))
s.send(arr)
print('Finished sending...')
s.close()
print('done.')
This works for me (though only tested by running both on localhost) and I end up with a second wave file that's an exact copy of the one sent by the client through the socket.

Socket programing - constantly send and recive data (python)

I'm programing a very simple screen sharing program.
I have the code for sending and reciving the screen picture. I want the server to be able to recive data at any time, and I want the Client to send the data every 3 seconds. this is the code:
Server:
import socket
import zlib
def conv(code):
with open('Image2.pgm', 'wb') as f:
f.write(code)
TCP_IP = '127.0.0.1'
TCP_PORT = 5005
BUFFER_SIZE = 100000
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((TCP_IP, TCP_PORT))
s.listen(1)
conn, addr = s.accept()
print 'Connection address:', addr
while 1:
data = conn.recv(BUFFER_SIZE)
if not data: break
str = zlib.decompress(data)
conv(str)
print "All OK"
conn.send(data) # echo
conn.close()
Client:
import socket
import pyscreenshot as ImageGrab
import zlib
def PrtSc():
ImageGrab.grab_to_file("Image.pgm")
f = open("Image.pgm", "rb")
Image = f.read()
Image = zlib.compress(Image)
return Image
TCP_IP = '127.0.0.1'
TCP_PORT = 5005
BUFFER_SIZE = 100000
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((TCP_IP, TCP_PORT))
s.send(PrtSc())
data = s.recv(BUFFER_SIZE)
s.close()
print "received data:", data
Thanks :)

python search string from socket

I have the following text file:
ADDRESS1 192.168.124.1
ADDRESS2 192.168.124.2
ADDRESS3 192.168.124.3
And I wrote the following string server in python (strsrv.py) :
#!/usr/bin/env python
import socket
import sys
host = ''
port = 50000
backlog = 5
size = 1024
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
s.bind((host,port))
s.listen(backlog)
while 1:
global f
client, address = s.accept()
data = client.recv(size)
with open('list.txt', 'r') as my_file:
for f in my_file.readlines():
if(f.find('%s' % data)>-1):
data = f
if f:
client.send(data)
client.send(f)
client.close()
I'm trying to connect to this server sending a string. This string must match one of lines described on text file. Ex: sending 'ADDRESS1' should return 'ADDRESS1 192.168.124.1' from the server, but it doesn't works. Any string sent returns only the last line of the text file. Please could someone point me to the right direction? Thanks :)
How are you testing this? Assuming you open a socket and connect to the host you should see that you are in fact receiving the correct line as well as the last one. Why? Because in the for loop you keep changing the value of f, the last value of f will be the last line in the file, and you send it back after sending data (which at that point is the correct value).
Here's a suggestion for how you might modify your code (assuming you want the full line back and you dont want wildcarding):
#!/usr/bin/env python
import socket
import sys
host = ''
port = 50000
backlog = 5
size = 1024
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
s.bind((host,port))
s.listen(backlog)
# build dict of addresses first, no need to do this for each message
with open('list.txt', 'r') as my_file:
address_map = dict(line.split() for line in my_file)
while True:
client, address = s.accept()
req_address = client.recv(size)
ip = address_map.get(req_address, 'Not found')
client.send(req_address + ' ' + ip)
client.close()
You can simply test this by doing this while the above is running:
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(('', 50000))
s.send('ADDRESS2')
s.recv(1024)

Categories