Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Test client doesn't encode/decode the data #1427

Closed
senstar-nross opened this issue Dec 9, 2020 · 3 comments · Fixed by RC-MODULE/rumboot-tools#12
Closed

Test client doesn't encode/decode the data #1427

senstar-nross opened this issue Dec 9, 2020 · 3 comments · Fixed by RC-MODULE/rumboot-tools#12

Comments

@senstar-nross
Copy link

senstar-nross commented Dec 9, 2020

Sending data with emit() and getting the data back with get_received() returns the actual object emitted not one that got encoded to json and back. This can mask at least 2 different types of bugs.

The real socketio client encodes the data in packet.py encode()

    if data is not None:
        if needs_comma:
            encoded_packet += ','
        encoded_packet += self.json.dumps(data, separators=(',', ':'))

but the socketio test client just stores the object for later retrieval.

This caused my test code to miss two errors:

  1. The object I sent was not json encodable and caused an exception.
  2. If you change the object after emit the changes appear when you get the data from get_received(). I had a test that passed because the object that was emitted had wrong data that was emitted but was changed to correct data later. This passed in test but failed in production

Steps to reproduce the behavior:
Case 1:

  1. in a flask app emit an object with an non-json encodable type (like datetime or mongo ObjectId)
  2. test with pytest using socketio.test_client
  3. code will run
  4. test again without using pytest code will throw an exception (TypeError: Object of type ObjectId is not JSON serializable)

Case 2:
#in server
data = {'test': 1}
emit('test', data)
data['test']=2

#in pytest
assert socketio_client.get_received()[0]['args'][0]['test'] == 1 #this assert will fail

Expected behavior
In the first case should throw an exception
in the second case the assertion should pass

@senstar-nross
Copy link
Author

senstar-nross commented Dec 9, 2020

what about just calling pkt.decode(pkt.encode()) in test_client.py?

def __init__(self, app, socketio, namespace=None, query_string=None,
             headers=None, flask_test_client=None):
    def _mock_send_packet(sid, pkt):
        pkt.decode(pkt.encode())  #<<<<<<<<<<<<<<<<<<<<<<
        if pkt.packet_type == packet.EVENT or \
                pkt.packet_type == packet.BINARY_EVENT:
 ...

@senstar-nross
Copy link
Author

well that didn't work :(

@senstar-nross
Copy link
Author

I have no idea if i should submit a PR for this or not. I haven't ever contributed to a project before. so anyway, i think this works. It forces the encoding for non binary events and fixes the two issue that i noted above...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant