mardi 1 septembre 2020

Delegation of object creation logic based on the Builder pattern

Here is my implementation of object population loosely based on the Builder pattern.

I am using methods for constructing objects. I cannot use constructors. The idea is to break the object construction into smaller parts and delegate this responsibility to a separate class instead of having all the object creation/population code inside the concerned Business class.

Create the object (by new keyword) once and send its reference to different setter methods to populate a set of fields and make the methods return the updated reference back.

I want to know your opinion about this implementation. Is it good or bad ? I think it is a nice way of constructing complex objects by taking some inspiration from the Builder pattern but it may have its own downsides as well (one could be - increased number of lines of code).

Let me know what you think.

Example (the actual use case involves a fairly complex object, I have translated the concept in simple terms for better understandability)

I have a Person class like so:

@Getter
@Setter
public class Person {

    String firstName;
    String lastName;

    AddressInfo addressInfo;
    SocialInfo socialInfo;

}

AddressInfo class:

@Getter
@Setter
public class AddressInfo {

    String addressLine1;
    String addressLine2;
    String stateCode;
    String city;
    String zipCode;

}

SocialInfo class:

@Getter
@Setter
public class SocialInfo {

    String ssn;
    String taxId;
}

I have a Builder class marked as a Spring singleton bean for populating different parts of the Person object:

@Component
public class PersonBuilder {

    public Person preparePerson(String firstName, String lastName) {
        Person p = new Person();
        p.setFirstName(firstName);
        p.setLastName(lastName);
        return p;
    }
    
    public Person populateAddressInfo(AddressInfo addressInfo, Person p) {
    
        boolean addressIsValid = // make an API call to validate the address
        
        if(addressIsValid)
            p.setAddressInfo(addressInfo);
            
        return p;
    }
    
    public Person populateSocialInfo(SocialInfo socialInfo, Person p) {
    
        isSsnValid = // make an API call to validate the SSN
        
        if(isSsnValid)
            p.setSocialInfo(socialInfo);
            
        return p;
    }
}

and finally the class which contains the business logic:

class SomeBusinessLogic {

    @Autowired
    PersonBuilder personBuilder;

    Person p = personBuilder.preparePerson("John", "Doe");
    AddressInfo addressInfo = new AddressInfo;
    // set addressInfo fields
    p = personBuilder.populateAddressInfo(addressInfo);
    
    SocialInfo socialInfo = new SocialInfo();
    // set socialInfo fields
    p = personBuilder.populateSocialInfo(socialInfo);

    // Person object "p" is now ready to be used
    
}

Aucun commentaire:

Enregistrer un commentaire