From d32db3bb2bb02acc0e71fce3fac58e79d103e06a Mon Sep 17 00:00:00 2001 From: Grayson Koonce Date: Fri, 7 Aug 2015 16:19:28 -0700 Subject: [PATCH] Raise ValueError when anything but map[string]string is used for Thrift headers --- CHANGES.rst | 3 ++- tchannel/schemes/thrift.py | 11 ++++++++-- tests/schemes/test_thrift.py | 41 ++++++++++++++++++++++++++++++++++++ 3 files changed, 52 insertions(+), 3 deletions(-) diff --git a/CHANGES.rst b/CHANGES.rst index b8065743..797c1e91 100644 --- a/CHANGES.rst +++ b/CHANGES.rst @@ -5,7 +5,8 @@ Changelog 0.15.2 (unreleased) ------------------- -- Nothing changed yet. +- Raise informative and obvious ``ValueError`` when anything + but a map[string]string is passed as headers to the ``TChannel.thrift`` method. 0.15.1 (2015-08-07) diff --git a/tchannel/schemes/thrift.py b/tchannel/schemes/thrift.py index b10b01f7..874d693c 100644 --- a/tchannel/schemes/thrift.py +++ b/tchannel/schemes/thrift.py @@ -21,11 +21,18 @@ def __init__(self, tchannel): def __call__(self, request=None, headers=None, timeout=None, retry_on=None, retry_limit=None): - if headers is None: + if not headers: headers = {} # serialize - headers = serializer.serialize_headers(headers=headers) + try: + headers = serializer.serialize_headers(headers=headers) + except (AttributeError, TypeError): + raise ValueError( + 'headers must be a map[string]string (a shallow dict' + ' where keys and values are strings)' + ) + body = serializer.serialize_body(call_args=request.call_args) response = yield self._tchannel.call( diff --git a/tests/schemes/test_thrift.py b/tests/schemes/test_thrift.py index caba9fbf..7b84c1ce 100644 --- a/tests/schemes/test_thrift.py +++ b/tests/schemes/test_thrift.py @@ -1141,3 +1141,44 @@ def testString(request, response, proxy): yield tchannel.thrift( service.testString('no return!?') ) + + +@pytest.mark.gen_test +@pytest.mark.callz +def test_headers_should_be_a_map_of_strings(): + + tchannel = TChannel('client') + + with pytest.raises(ValueError): + yield tchannel.thrift( + request=True, + headers={'key': 1}, + ) + + with pytest.raises(ValueError): + yield tchannel.thrift( + request=True, + headers={1: 'value'}, + ) + + with pytest.raises(ValueError): + yield tchannel.thrift( + request=True, + headers=100, + ) + + with pytest.raises(ValueError): + yield tchannel.thrift( + request=True, + headers={ + 'key': { + 'key': 'value', + }, + }, + ) + + with pytest.raises(ValueError): + yield tchannel.thrift( + request=True, + headers=Exception() + )