0

I have a very simple TCP server in Python 3.6, and I would like to use it to send arbitrary objects.

I am able to send a simple list with this code:

myList = [99, 88]
current_connection.send(bytes(myList))

However, this code fails with exception 'dict' object cannot be interpreted as an integer.

myList = [99,88,{'a': 3},77]
current_connection.send(bytes(myList))

How can I send this list, which contains a tuple?

I would also like to send a custom object like this:

myObject = customObject()
current_connection.send(bytes(myObject))

However, that code throws exception cannot convert 'customObject' object to bytes. What is the proper way to send the custom object?

Is there a method I should be using other than socket.send()?

Here is the complete code:

import socket

def listen():
    connection = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    connection.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
    connection.bind(('localhost', 5555))
    connection.listen(10)
    while True:
        current_connection, address = connection.accept()
        while True:
            data = current_connection.recv(2048)
            try:
                #myList = [99,88,{'a': 3},77]
                myList = [99, 88]
                current_connection.send(bytes(myList))
            except Exception as e:
                print(e)
            print(data)

if __name__ == "__main__":
    try:
        listen()
    except KeyboardInterrupt:
        pass
    print('done')

If send() cannot do what I have described, is there a more effective way to send data?

martineau
  • 119,623
  • 25
  • 170
  • 301
Jacob Quisenberry
  • 1,131
  • 3
  • 20
  • 48
  • To send an arbitrary object over a socket, you need to *serialize* it to a stream of bytes. The `pickle`, `json`, and `struct` modules are different approaches to this. – jasonharper Jun 07 '18 at 23:19
  • Here's an [answer](https://stackoverflow.com/questions/18478287/making-object-json-serializable-with-regular-encoder/18561055#18561055) that shows how to convert them to JSON format which uses the `pickle` and `json` modules. – martineau Jun 08 '18 at 00:44

1 Answers1

1

Why don't you convert your list to json first and transmit across socket like:

myList = [99,88,{'a': 3},77]
current_connection.send(json.dumps(myList).encode())

At receiver

myList = json.loads(received_bytes.decode())

I would also like to send a custom object like this:

Two solution exists

  1. easiest is pickle.dumps(your_obj).
  2. Write json serializer for your object.
Avezan
  • 673
  • 4
  • 9
  • 1
    Both the JSON and the pickle solution worked in my case. To serialize an object to JSON, I used this: `json.dumps(c, default=lambda o: o.__dict__)`. – Jacob Quisenberry Jun 08 '18 at 03:59