@Transactional(propagation = Propagation.REQUIRED, noRollbackFor = IllegalArgumentException.class)
  public boolean change(Identifier internalId, String changedId) {
    // check if both identifier are of the same type

    if (internalId == null || StringUtils.isEmpty(changedId)) {
      throw new IllegalArgumentException("new or old identifer couldn't be null");
    }
    if (internalId.getValue().equals(changedId)) {
      logger.debug("new identifier is the same no need to change existing identifier");
      return false;
    }

    final Person person =
        this.findPersonByIdentifier(internalId.getType().getName(), internalId.getValue());
    if (person == null)
      throw new IllegalArgumentException(
          format(
              "The person with the provided identifier [%s] does not exist",
              internalId.getValue()));

    final Person person2 = this.findPersonByIdentifier(internalId.getType().getName(), changedId);
    if (person2 != null && person.getId() != person2.getId()) {
      throw new IllegalArgumentException(
          format("The person with the proposed new identifier [%s] already exists.", changedId));
    }
    Map<String, Identifier> primaryIds = person.getPrimaryIdentifiersByType();
    Identifier currId = primaryIds.get(internalId.getType().getName());
    if (currId == null)
      throw new IllegalStateException("Provided Id doesnt exist as primary identifier ");
    if (currId.getValue().equals(changedId)) {
      logger.debug(
          format(
              "The provided new primary identifier [%s] already assigned to the person.",
              changedId));
    } else if (!currId.getValue().equals(internalId.getValue())) {
      throw new IllegalArgumentException(
          format(
              "The provided primary identifier [%s] does not match the current primary identifier",
              internalId.getValue()));
    }
    // check if the provided new identifier is already there, and if so, do the update, otherwise -
    // do the insert.
    Identifier providedId = person.findIdentifierByValue(internalId.getType().getName(), changedId);
    if (providedId == null) {

      providedId = person.addIdentifier(internalId.getType(), changedId);
    }
    providedId.setPrimary(true);
    providedId.setDeleted(false);
    currId.setPrimary(false);
    currId.setDeleted(true);
    return true;
  }
  /**
   * Move All Sor Records from one person to another.
   *
   * @param fromPerson person losing sor records.
   * @param toPerson person receiving sor records.
   * @return Result of move. Validation errors if they occurred or the Person receiving sor records.
   */
  public boolean moveAllSystemOfRecordPerson(Person fromPerson, Person toPerson) {
    // get the list of sor person records that will be moving.
    List<SorPerson> sorPersonList = personRepository.getSoRRecordsForPerson(fromPerson);

    // move each sorRecord
    for (final SorPerson sorPerson : sorPersonList) {
      moveSystemOfRecordPerson(fromPerson, toPerson, sorPerson);
    }

    Set<? extends Identifier> oldIdentifiers = fromPerson.getIdentifiers();
    Set<? extends IdCard> oldIdCards = fromPerson.getIdCards();

    this.personRepository.deletePerson(fromPerson);
    logger.info("moveAllSystemOfRecordPerson: Deleted From Person");
    for (Identifier identifier : oldIdentifiers) {

      if (toPerson.getIdentifiersByType().get(identifier.getType().getName()) == null) {
        Identifier oldIdentifierAttachedTotoPerson =
            toPerson.addIdentifier(identifier.getType(), identifier.getValue());
        /// if type of this identifier don't exist then add this identifier as primary and not
        // deleted

        oldIdentifierAttachedTotoPerson.setDeleted(false);
        oldIdentifierAttachedTotoPerson.setPrimary(true);
      }
      // and if this exist then add this identifier as deleted and no primary
      else {
        Identifier oldIdentifierAttachedTotoPerson =
            toPerson.addIdentifier(identifier.getType(), identifier.getValue());
        /// if type of this identifier don't exist then add this identifier as primary and not
        // deleted

        oldIdentifierAttachedTotoPerson.setDeleted(true);
        oldIdentifierAttachedTotoPerson.setPrimary(false);
        ;
      }
    }
    for (IdCard oldIdCard : oldIdCards) {
      if (toPerson.getPrimaryIdCard() == null) {
        toPerson.addIDCard(oldIdCard);
      } else {
        if (oldIdCard.isPrimary()) oldIdCard.setPrimary(false);
        toPerson.addIDCard(oldIdCard);
      }
    }

    this.personRepository.savePerson(toPerson);

    return true;
  }