how do I test methods using boto3 with moto
Question: I am writing test cases for a quick class to find / fetch keys from s3, using
boto3. I have used moto in the past to test boto (not 3) code but am trying to
move to boto3 with this project, and running into an issue:

    
    
    class TestS3Actor(unittest.TestCase):
        @mock_s3
        def setUp(self):
            self.bucket_name = 'test_bucket_01'
            self.key_name = 'stats_com/fake_fake/test.json'
            self.key_contents = 'This is test data.'
            s3 = boto3.session.Session().resource('s3')
            s3.create_bucket(Bucket=self.bucket_name)
            s3.Object(self.bucket_name, self.key_name).put(Body=self.key_contents)
    

error:

    
    
    ...
    File "/Library/Python/2.7/site-packages/botocore/vendored/requests/packages/urllib3/connectionpool.py", line 344, in _make_request
    self._raise_timeout(err=e, url=url, timeout_value=conn.timeout)
    File "/Library/Python/2.7/site-packages/botocore/vendored/requests/packages/urllib3/connectionpool.py", line 314, in _raise_timeout
    if 'timed out' in str(err) or 'did not complete (read)' in str(err):  # Python 2.6
    TypeError: __str__ returned non-string (type WantWriteError)
    botocore.hooks: DEBUG: Event needs-retry.s3.CreateBucket: calling handler <botocore.retryhandler.RetryHandler object at 0x10ce75310>
    

It looks like moto is not mocking out the boto3 call correctly - how do I make
that work?


Answer: What worked for me is setting up the environment with `boto` before running my
mocked tests with `boto3`.

Here's a working snippet:

    
    
    import unittest
    import boto
    from boto.s3.key import Key
    from moto import mock_s3
    import boto3
    
    
    class TestS3Actor(unittest.TestCase):
        mock_s3 = mock_s3()
    
        def setUp(self):
            self.mock_s3.start()
            self.location = "eu-west-1"
            self.bucket_name = 'test_bucket_01'
            self.key_name = 'stats_com/fake_fake/test.json'
            self.key_contents = 'This is test data.'
            s3 = boto.connect_s3()
            bucket = s3.create_bucket(self.bucket_name, location=self.location)
            k = Key(bucket)
            k.key = self.key_name
            k.set_contents_from_string(self.key_contents)
    
        def tearDown(self):
            self.mock_s3.stop()
    
        def test_s3_boto3(self):
            s3 = boto3.resource('s3', region_name=self.location)
            bucket = s3.Bucket(self.bucket_name)
            assert bucket.name == self.bucket_name
            # retrieve already setup keys
            keys = list(bucket.objects.filter(Prefix=self.key_name))
            assert len(keys) == 1
            assert keys[0].key == self.key_name
            # update key
            s3.Object(self.bucket_name, self.key_name).put(Body='new')
            key = s3.Object(self.bucket_name, self.key_name).get()
            assert 'new' == key['Body'].read()
    

When run with `py.test test.py` you get the following output:

    
    
    collected 1 items 
    
    test.py .
    
    ========================================================================================= 1 passed in 2.22 seconds =========================================================================================
    

