-1

I have a method where I fetch user input, check if certain values exist, and based on that build my own custom input object that I would use to search in a database. The code for the search method is as follows.

public SearchDocumentResult searchData(EmployeeInput employeeInput) {
    EmployeeInput getEmployeeInputForSearch = buildApplicationInputForSearch(employeeInput);
    if (employeeInput != null) {
        return super.searchForExactData(getEmployeeInputForSearch);
    } else {
        return super.searchForCloseMatchData(getTestPersonInput);
    }
}

The methods with multiple if checks on the input are as follows. Both the below methods and the above method exist in the same class.

private Application buildApplicationInputForSearch(Application applicationInput) {
        Application.Builder applicationForSearch = Application.builder();
        String jobIdFromInput = applicationInput.getJobId();
        applicationForSearch.withIsTagged(applicationInput.isTagged());
        if (!StringUtils.isEmpty(jobIdFromInput)) {
            applicationForSearch.withJobId(jobIdFromInput);
        }
        FormSection formSectionInput = applicationInput.getFormSection();
        if (formSectionInput != null) {
            this.buildFormSectionInputForSearch(formSectionInput);
        }
        return applicationForSearch.build();
    }
private FormSection buildFormSectionInputForSearch(FormSection formSectionInput) {
    FormSection.Builder formSectionForSearch = FormSection.builder();
    String formCountry = formSectionInput.getCountry();
    Map<String, String> employeeQuestions = formSectionInput.getEmployeeQuestions();
    Map<String, String> applicationQuestions = formSectionInput.getApplicationQuestions();
    List<String> formNames = formSectionInput.getNames();
    if (!StringUtils.isEmpty(formCountry)) {
        formSectionForSearch.withCountry(formCountry);
    }
    if (formNames.size() > 0) {
        formSectionForSearch.withNames(formNames);
    }
    if (employeeQuestions.size() > 0) {
        formSectionForSearch.withEmployeeQuestions(employeeQuestions);
    }
    if (applicationQuestions.size() > 0) {
        formSectionForSearch.withApplicationQuestions(applicationQuestions);
    }
    return formSectionForSearch.build();
}

The EmployeeInput is a model class that gets generated through a library and therefore I cannot make that use Java Optional for fields that may or may not exist. Using this EmployeeInput object as it is, how can I make this code more readable, with less if conditions? Any help would be much appreciated.

AnOldSoul
  • 173

1 Answers1

0

You can have the first part as follows:

private Application buildApplicationInputForSearch(Application applicationInput) {
        return Application.builder()
                .withJobId(applicationInput.getJobId())
                .withIsTagged(applicationInput.isTagged())
                .withFormSection(applicationInput.getFormSection())
                .build();
    }

then in the Application.Builder you have the following

// the simple case
public Builder withJobId(String jobId) {
  if(isNotEmpty(jobId)) {
    this.jobId = jobId;
  }

return this; }

... // for the complex case create another builder public Builder withFormSection(FormSection formSection) { this.formSectionInput = FormSectionInput.builder() .withWhatever(formSection.getWhatever()) ... ... .build(); }

Move all the if statements that you have around the builder calls, into the builder methods. This also makes your buildFormSection method unnecesary. The "optional" logic will now be in the builder and you will not have to worry about it when creating the query input. If you want to allow empty strings or arrays, you can overload the builder method with another boolean flag.

So in addition to the standard withSomething(String something) you also have:

public Builder withSomething(String something, boolean skipValidation) {
  if(skipValidation || isNotEmpty(something)) {
    this.something = something;
  }

return this; }

Edit: if you want to convey that there is some validation within the builder methods, you can call them withValidSomething, which removes the need for the withSomething(..., boolean skipValidation).

Blaž Mrak
  • 478
  • 3
  • 8