【问题标题】:How to mock a boto3 client object/call如何模拟 boto3 客户端对象/调用
【发布时间】:2016-08-06 06:24:59
【问题描述】:

我正在尝试模拟一个特定的 boto3 函数。我的模块 Cleanup 导入 boto3。 Cleanup 还有一个类,“cleaner”。在初始化期间,cleaner 创建一个 ec2 客户端:

self.ec2_client = boto3.client('ec2')

我要模拟ec2客户端方法:desribe_tags(),python说的是:

<bound method EC2.describe_tags of <botocore.client.EC2 object at 0x7fd98660add0>>

我得到的最远的结果是在我的测试文件中导入 botocore 并尝试:

mock.patch(Cleaner.botocore.client.EC2.describe_tags)

失败:

AttributeError: 'module' object has no attribute 'EC2'

如何模拟这个方法?

清理看起来像:

import boto3
class cleaner(object):
    def __init__(self):
        self.ec2_client = boto3.client('ec2')

ec2_client 对象是具有 desribe_tags() 方法的对象。它是一个 botocore.client.EC2 对象,但我从不直接导入 botocore。

【问题讨论】:

  • 在您的清理模块中。您究竟是如何导入 EC2 来使用它的?从外观上看,您正在做类似import boto3 的事情。正确的?所以,我怀疑你的补丁应该类似于Cleanup.boto3.EC2。如果您将模块命名为Cleanup。更多信息肯定会有所帮助。
  • 添加的模块示例
  • @JeffTang 你找到解决方案了吗?我正在寻找类似的东西!

标签: python unit-testing mocking


【解决方案1】:

trying to mock a different method for the S3 client时我找到了解决方案

import botocore
from mock import patch
import boto3

orig = botocore.client.BaseClient._make_api_call

def mock_make_api_call(self, operation_name, kwarg):
    if operation_name == 'DescribeTags':
        # Your Operation here!
        print(kwarg)
    return orig(self, operation_name, kwarg)

with patch('botocore.client.BaseClient._make_api_call', new=mock_make_api_call):
    client = boto3.client('ec2')
    # Calling describe tags will perform your mocked operation e.g. print args
    e = client.describe_tags()

希望对你有帮助:)

【讨论】:

    【解决方案2】:

    应该嘲笑你在哪里测试。因此,如果您正在测试您的 cleaner 类(我建议您在此处使用 PEP8 标准,并使其成为 Cleaner),那么您想要模拟您正在测试的位置。所以,你的补丁实际上应该是 something 沿线:

    class SomeTest(Unittest.TestCase):
        @mock.patch('path.to.Cleaner.boto3.client', return_value=Mock())
        def setUp(self, boto_client_mock):
            self.cleaner_client = boto_client_mock.return_value
    
        def your_test(self):
            # call the method you are looking to test here
    
            # simple test to check that the method you are looking to mock was called
            self.cleaner_client.desribe_tags.assert_called_with()
    

    我建议通读mocking documentation,其中有很多例子可以做你想做的事

    【讨论】:

    • 我不是要模拟 boto3.client。我正在尝试模拟对象botocore.client.EC2 的方法describe_tags,该对象由boto3.client 返回
    • 那么,您仍在实例化 EC2 的工作客户端,但想从您创建的对象中模拟一个方法?通常,当您进行单元测试和模拟修补时,您希望模拟外部,例如那个 EC2 客户端。您仍然可以通过 boto_client_mock 的 return_value 验证要测试的方法。
    • @JeffTang 我提供了一个更详细的示例(未经测试,只是想提供总体思路),说明您可能想要做什么。
    猜你喜欢
    • 2020-10-06
    • 1970-01-01
    • 2016-09-05
    • 1970-01-01
    • 2010-11-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多