【问题标题】:Correct way to test a function测试功能的正确方法
【发布时间】:2019-01-02 13:09:56
【问题描述】:

可以在测试中调用build_admins_message 来构建将用于模拟断言的预期结果吗?

实施:

@slack_messages.on_pattern('(?i)^admins$')
def handle_admins_message(event, body, match):
    team_id = event['team_id']
    user_id = body['user']

    message = build_admins_message(team_id, user_id)
    Slack(team_id).send_message(user_id, **message)

测试:

class TestAdminsMessageHandler(TestCase):
    def setUp(self):
        team = SlackTeam.objects.create(team_id='TEAMID')
        SlackUser.objects.create(team=team, user_id='USERID')

    def tearDown(self):
        SlackUser.objects.all().delete()
        SlackTeam.objects.all().delete()

    @mock.patch('slango.slack.Slack.send_message')
    def test_correct_text(self, send_message_mock):
        event = {
            'team_id': 'TEAMID',
            'event': {
                'text': 'admins',
                'user': 'USERID'
            }
        }

        handle_admins_message(event, event['event'])

        expected_message = build_admins_message('TEAMID', 'USERID')

        send_message_mock.assert_called_with('USERID', **expected_message)

build_admins_message的实现:

def build_admins_message(team_id, user_id):
    user = SlackUser.retrieve(team_id, user_id)
    admins = SlackUser.objects.filter(
        is_bot_admin=True, team__team_id=team_id).order_by(
            'real_name', 'display_name')

    attachments = []
    if user.is_bot_admin:
        attachments.append(build_admin_picker())

    for admin in admins:
        attachments.append(build_admin_item(user, admin))

    attachments.append(build_admin_more())

    return {
        'text': "Here is users with admin rights:",
        'attachments': attachments
    }

【问题讨论】:

    标签: python unit-testing testing mocking integration-testing


    【解决方案1】:

    这取决于build_admins_message 在您的程序中的角色。

    由于程序的不同部分都需要以相同的方式构建消息,这可能没问题。考虑您是否可以更明确地说明 build_admins_message 是这样使用的,例如使用依赖注入。确保您的辅助方法有自己的测试。 (我通常认为使用patch 是一种设计气味,但请记住,这并不意味着有问题!)

    如果 build_admins_message 仅作为 handle_admins_message 的辅助函数存在,那么在您的测试中使用它会违反封装并将您的测试与实现联系太多。在这种情况下,我只需在测试中手动写出预期的消息。

    【讨论】:

    • 我在整个程序中多次使用build_admins_message 函数,我也希望手动写出预期的消息,但build_admins_message 返回的字典很大。
    • 如何使build_admins_message 成为更明确的依赖关系?
    • 我在问题中添加了实现
    • @DmitryChernyshov 再看一遍,我可能不会打扰。也许也修补了build_admins_message 并断言这就是所谓的。也许如果我更了解你的程序和 Slack 库,我会有更好的主意。
    猜你喜欢
    • 2015-06-13
    • 2014-12-31
    • 1970-01-01
    • 2020-01-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-03-05
    • 2017-06-06
    相关资源
    最近更新 更多