тдд - я должен издеваться здесь или использовать реальную реализацию - PullRequest
2 голосов
/ 27 июня 2011

Я пишу синтаксический анализатор аргументов программы, просто для улучшения TDD, и я столкнулся со следующей проблемой.Скажем, мой парсер определен следующим образом:

class ArgumentsParser {
    public ArgumentsParser(ArgumentsConfiguration configuration) {
        this.configuration = configuration;
    }

    public void parse(String[] programArguments) {
        // all the stuff for parsing
    }
}

, и я предполагаю, что реализация ArgumentsConfiguration выглядит следующим образом:

class ArgumentsConfiguration {
    private Map<String, Class> map = new HashMap<String, Class>();

    public void addArgument(String argName, Class valueClass) {
        map.add(argName, valueClass);
    }

    // get configured arguments methods etc.
}

Это мой текущий этап.На данный момент в тесте я использую:

@Test
public void shouldResultWithOneAvailableArgument() {
    ArgumentsConfiguration config = prepareSampleConfiguration(); 
    config.addArgument("mode", Integer.class);
    ArgumentsParser parser = new ArgumentsParser(configuration);
    parser.parse();
    // ....
}

Мой вопрос, если такой способ является правильным?Я имею в виду, нормально ли использовать реальную ArgumentsConfiguration в тестах?Или я должен издеваться над этим?Реализация по умолчанию (текущая) довольно проста (только завернутая в Map), но я представляю, что она может быть более сложной, как выборка конфигурации из источника данных.Тогда было бы естественно издеваться над таким «дорогим» поведением.Но какой здесь предпочтительный способ?

РЕДАКТИРОВАТЬ: Может быть, более ясно: я должен насмехаться над ArgumentsConfiguration даже без написания какой-либо реализации (просто определить ее публичные методы), использовать mock для тестирования и позже разобраться с реальной реализацией (-ями),или я должен использовать самый простой в тестах, и пусть они косвенно освещают эту реализацию.Но если да, то как насчет тестирования другой реализации Конфигурации, представленной позже?

Ответы [ 3 ]

5 голосов
/ 28 июня 2011

Правильный ответ заключается в том, что вам следует высмеивать все, что вы не пытаетесь тестировать напрямую (например, любые зависимости, которые есть у тестируемого объекта, которые не относятся непосредственно к конкретному тестовому кейсу).

5 голосов
/ 27 июня 2011

Тогда было бы естественно издеваться над таким "дорогим" поведением.

Дело не в этом.Вы не издеваетесь над сложными классами.

Вы издеваетесь над тем, чтобы полностью изолировать классы.

Полная изоляция гарантирует, что тесты демонстрируют, что классы следуют своему интерфейсу и не имеют скрытых особенностей реализации.

Кроме того, полная изоляция значительно упрощает отладку неудачного теста.Это либо тест, либо тестируемый класс, либо поддельные объекты.В идеале тест и макеты настолько просты, что не требуют никакой отладки, оставляя только тестируемый класс.

0 голосов
/ 29 июня 2011

В этом случае, поскольку ваша ArgumentsConfiguration очень проста, я бы рекомендовал использовать реальную реализацию, пока ваши требования не потребуют чего-то более сложного. Кажется, в вашем классе ArgumentsConfiguration нет никакой логики, поэтому использовать реальный объект безопасно. Если наступит время, когда конфигурация будет более сложной, то, вероятно, следует использовать не создание конфигурации, которая взаимодействует с каким-либо источником данных, а создание объекта ArgumentsConfiguration из этого источника данных. Тогда у вас может быть тест, который убедится, что он правильно генерирует конфигурацию из источника данных, и вам не нужны лишние абстракции.

...