package gov.va.med.esr.common.builder.entity;

import gov.va.med.esr.common.builder.entity.metaData.AddressMetaDataFromPID;
import gov.va.med.esr.common.model.lookup.AddressType;
import gov.va.med.esr.common.model.lookup.PhoneType;
import gov.va.med.esr.common.model.lookup.Relationship;
import gov.va.med.esr.common.model.party.Address;
import gov.va.med.esr.common.model.party.Phone;
import gov.va.med.esr.common.model.person.Employment;
import gov.va.med.esr.common.model.person.Spouse;
import gov.va.med.fw.util.builder.Builder;
import gov.va.med.fw.util.builder.BuilderException;

/**
 * Builds a Spouse object from a message(SpouseMetaData)
 * 
 * @author Rajiv Patnaik Created on Jul 14, 2005
 * @version 1.0
 * 
 * Copyright © 2005 VHA. All rights reserved
 */
public class SpouseBuilder extends RelationBuilder
{
    /**
     * An instance of serialVersionUID
     */
    private static final long serialVersionUID = 7763815323833215233L;

    private Builder employmentBuilder;
    
    private Builder addressBuilder;

    private Builder addressTypeBuilder;

    private Builder phoneBuilder;

    private Builder phoneTypeBuilder;

    public SpouseBuilder()
    {
        super();
    }

    public Builder getAddressBuilder() {
        return addressBuilder;
    }

    public void setAddressBuilder(Builder addressBuilder) {
        this.addressBuilder = addressBuilder;
    }

    public Builder getAddressTypeBuilder() {
        return addressTypeBuilder;
    }

    public void setAddressTypeBuilder(Builder addressTypeBuilder) {
        this.addressTypeBuilder = addressTypeBuilder;
    }

    public Builder getPhoneBuilder() {
        return phoneBuilder;
    }

    public void setPhoneBuilder(Builder phoneBuilder) {
        this.phoneBuilder = phoneBuilder;
    }

    public Builder getPhoneTypeBuilder() {
        return phoneTypeBuilder;
    }

    public void setPhoneTypeBuilder(Builder phoneTypeBuilder) {
        this.phoneTypeBuilder = phoneTypeBuilder;
    }

    public Builder getEmploymentBuilder() {
        return employmentBuilder;
    }

    public void setEmploymentBuilder(Builder employmentBuilder) {
        this.employmentBuilder = employmentBuilder;
    }

    public Spouse build(SpouseMetaData metaData) throws BuilderException
    {
        Spouse input = metaData.getEntity();
        Spouse output = (input == null) ? new Spouse() : input;

        this.transfer(output, metaData);

        return this.shouldKeep(output) ? output : null;
    }

    protected boolean shouldKeep(Spouse spouse)
    {
        return (super.shouldKeep(spouse));
    }

    protected void transfer(Spouse spouse, SpouseMetaData metaData)
            throws BuilderException
    {
        super.transfer(spouse, metaData);

         spouse.setMaidenName(super.build(spouse.getMaidenName(), metaData
                .getMaidenName()));

         spouse.setRelationship(super.buildRelationship(
                spouse.getRelationship(), Relationship.CODE_SPOUSE.getName()));
        
         spouse.setEmployment(this.buildEmployment(spouse.getEmployment(), metaData.getEmployment()));
         
         spouse.setAddress(this.buildAddress(spouse.getAddress(), metaData.getAddress()));
 
         spouse.setHomePhone(this.buildHomePhone(spouse.getHomePhone(), metaData.getPhone()));
    }
    
    private Employment buildEmployment(Employment input,
            EmploymentMetaData metaData) throws BuilderException {

        if (metaData == null) {
            return null;
        }
        metaData.setEntity(input);

        return (Employment) this.employmentBuilder.build(metaData);
    }

    private Address buildAddress(Address input, AddressMetaData metaData)
            throws BuilderException {

        if (metaData == null)
        {
            return null;
        }
        metaData.setEntity(input);

        Address address = (Address) this.addressBuilder.build(metaData);
        
        //Set address type explicitly because it was not present in the ZDP segment
        AddressType addressType = (AddressType) addressTypeBuilder
        .build(AddressType.CODE_PERMANENT_ADDRESS.getCode());

        address.setType(addressType);
       
        return  address;
    }

    private Phone buildHomePhone(Phone input, PhoneMetaData metaData)
            throws BuilderException {

        if (metaData == null) {
            return null;
        }
        metaData.setEntity(input);

        Phone phone = (Phone) this.phoneBuilder.build(metaData);

        // Set phone type explicitly because it was not present in the ZDP
        // segment
        PhoneType phoneType = (PhoneType) phoneTypeBuilder
                .build(PhoneType.CODE_HOME.getCode());

        phone.setType(phoneType);

        return phone;
    }

 
}