2013-05-07 3 views
11

Я работаю над классом, который отправляет RequestDTO на веб-службу. Мне нужно проверить запрос до его отправки.Как уменьшить цикломатическую сложность?

Запрос может быть отправлен из 3-х разных мест, и для каждого «requesttype» существуют различные правила валидации. request1 должен иметь имя и номер телефона, request2 должен иметь адрес и т. д.)

У меня есть DTO, который содержит длинный список полей (имя, адрес, город, номер телефона и т. д.), и это тот же самый DTO отправленный независимо от того, какой тип запроса он есть.

Я создал 3 различных метода проверки и на основе типа, вызываемого соответствующим методом.

В каждом из этих методов у меня есть длинный список if-else для проверки полей, необходимых для каждого типа запроса.

private void validateRequest1(Request request) { 
    StringBuilder sb = new StringBuilder(); 
    if (null == request) { 
     throw new IllegalArgumentException("Request is null"); 
    } 
    if (isFieldEmpty(request.getName())) { *see below 
     sb.append("name,")); 
    } 
    if (isFieldEmpty(request.getStreet())) { 
     sb.append("street,")); 
    } 
    ... 

isFieldEmpty() проверяет строку на нуль и isEmpty() и возвращает логическое

Это дает мне цикломатическую сложности 28 в одном из этих методов, так что мой вопрос .. можно ли уменьшить эту сложность? - если да, то как мне это сделать?

В конечном итоге мне нужно проверить много полей, и я не могу понять, как это может быть сделано без большого количества проверок:/

+1

Моей идеей было бы: Использовать какой-то объект FieldChecker, который инкапсулирует проверку пустоты (или какой-либо другой) и действие, которое необходимо предпринять ('sb.append()') и т. Д., И перебирать список таких объектов. Это делает код более четким, поскольку вы должны явно определять выходы и входы этой проверки. – millimoose

ответ

22

Простой способ заключается в содействии проверки в отдельный метод:

private String getAppendString(String value, String appendString) { 
    if (value == null || value.isEmpty()) { 
     return ""; 
    } 
    return appendString; 
} 

И тогда вы можете использовать этот метод вместо тех if блоков:

sb.append(getAppendString(request.getStreet(), "street,"); 

Это позволит снизить сложность от 28 до 3. Всегда помните: высокая сложность COUN ts являются признаком того, что метод пытается сделать слишком много. Сложность может быть решена путем деления проблемы на более мелкие части, как мы это делали здесь.

1

Другим подходом было бы обеспечить выполнение этого контракта в самом объекте Request. Если поле требуется или не может быть нулевым, скажем так, когда создается запрос.

Создайте запрос таким образом, чтобы он был на 100% действителен и готов к работе, когда существует конструктор.

Я бы также создал эту версию String в методе Request toString(). Он должен знать, как сделать себя.

Смежные вопросы