Source: app/util/form/parseGMapsAddressComponents.js

import marketConfig from 'common/src/app/config/market/market.configdefinitions';
import { addressFields } from '../../data/enum/FieldNames/AccountFieldNames';
import { countryCodeValue } from '../../data/enum/Countries';
import * as AddressFormats from '../../data/AddressFormats';

/** @module */

/**
 * Converts the `address_components` array returned by the Google Maps API into an
 * object with values for the `AddressInput` component.
 *
 * @function parseGMapsAddressComponents
 * @param addressComponents
 * @returns {object} An object with values to attach to an address form
 * @category forms
 */
export default function parseGMapsAddressComponents(addressComponents, country) {
  const gMapsValue = {
    administrative_area_level_1: 'short_name',
  };

  const nameByType = addressComponents.reduce((types, component) => {
    component.types.forEach(
      type =>
        // eslint-disable-next-line no-param-reassign
        (types[type] = component[gMapsValue[type] ? gMapsValue[type] : 'long_name']),
    );

    return types;
  }, {});

  const address = {
    [addressFields.ADDRESS_LINE_1]: '',
    [addressFields.ADDRESS_LINE_2]: '',
    [addressFields.ADDRESS_LINE_3]: '',
    [addressFields.CITY_OR_TOWN]: nameByType.postal_town || nameByType.locality || '',
    [addressFields.STATE]: nameByType.administrative_area_level_1 || '',
    [addressFields.ZIP_OR_POSTAL]: nameByType.postal_code || '',
    [addressFields.COUNTRY]: nameByType.country || '',
    [addressFields.COUNTY]: nameByType.administrative_area_level_2 || '',
  };

  const AddressFormat = AddressFormats[countryCodeValue[country || marketConfig.defaultCountry]];
  // temporary fix for country from API not matching the country list
  if (Object.keys(AddressFormat).includes(addressFields.COUNTRY)) {
    address[addressFields.COUNTRY] = 'GB';
  } else {
    delete address[addressFields.COUNTRY];
  }

  if (nameByType.route) {
    if (nameByType.street_number) {
      address[addressFields.ADDRESS_LINE_1] = `${nameByType.street_number} ${nameByType.route}`;
    } else if (Object.keys(AddressFormat).includes(addressFields.ADDRESS_LINE_2)) {
      address[addressFields.ADDRESS_LINE_1] =
        nameByType.premise || nameByType.point_of_interest || nameByType.establishment;
      address[addressFields.ADDRESS_LINE_2] = nameByType.route;
    } else {
      address[addressFields.ADDRESS_LINE_1] = nameByType.route;
    }
  }

  return address;
}