3

Trying to test out the community self-registration with the registration page type of "configurable self-reg page", but I upon clicking register with my phone number I am returned a "Can't verify phone number. For help, contact your community manager." error.

The login page type is set to default page.

I am including the Last Name, First Name, and Mobile fields.

I am using the automated "create a configurable self-reg handler" function to create my apex handler class, and I have viewed the class and everything is as expected.

I have set the "execute registration as" user as myself which is a system admin profile.

Verification method is set to "Text Message".

For the "assign users to a profile and account" page, I have selected the customer community user profile.

If I manually type this phone number into the user object via setup, it takes it. Ex: 3131234567.

Configurable Handler Registration Class (Auto-created):

global class AutocreatedConfigSelfReg1542644056573 implements Auth.ConfigurableSelfRegHandler {

  private final Long CURRENT_TIME = Datetime.now().getTime();
  private final String[] UPPERCASE_CHARS = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'.split('');
  private final String[] LOWERCASE_CHARS = 'abcdefghijklmnopqrstuvwxyz'.split('');
  private final String[] NUMBER_CHARS = '1234567890'.split('');
  private final String[] SPECIAL_CHARS = '!#$%-_=+<>'.split('');

  // This method is called once after verification (if any was configured)
  // This method should create a user and insert it
  // Password can be null
  // Return null or throw an exception to fail creation
  global Id createUser(Id accountId, Id profileId, Map<SObjectField, String> registrationAttributes, String password) {
    User u = new User();
    u.ProfileId = profileId;
    for (SObjectField field : registrationAttributes.keySet()) {
      String value = registrationAttributes.get(field);
      u.put(field, value);
    }

    u = handleUnsetRequiredFields(u);
    generateContact(u, accountId);
    if (String.isBlank(password)) {
      password = generateRandomPassword();
    }
    Site.validatePassword(u, password, password);
    if (u.contactId == null) {
      return Site.createExternalUser(u, accountId, password);
    }
    u.languagelocalekey = UserInfo.getLocale();
    u.localesidkey = UserInfo.getLocale();
    u.emailEncodingKey = 'UTF-8';
    u.timeZoneSidKey = UserInfo.getTimezone().getID();
    insert u;
    System.setPassword(u.Id, password);
    return u.id;
  }

  // Method to autogenerate a password if one was not passed in
  // By setting a password for a user, we won't send a welcome email to set the password
  private String generateRandomPassword() {
    String[] characters = new List<String>(UPPERCASE_CHARS);
    characters.addAll(LOWERCASE_CHARS);
    characters.addAll(NUMBER_CHARS);
    characters.addAll(SPECIAL_CHARS);
    String newPassword = '';
    Boolean needsUpper = true, needsLower = true, needsNumber = true, needsSpecial = true;
    while (newPassword.length() < 50) {
      Integer randomInt = generateRandomInt(characters.size());
      String c = characters[randomInt];
      if (needsUpper && c.isAllUpperCase()) {
        needsUpper = false;
      } else if (needsLower && c.isAllLowerCase()) {
        needsLower = false;
      } else if (needsNumber && c.isNumeric()) {
        needsNumber = false;
      } else if (needsSpecial && !c.isAlphanumeric()) {
        needsSpecial = false;
      }
      newPassword += c; 
    }
    newPassword = addMissingPasswordRequirements(newPassword, needsLower, needsUpper, needsNumber, needsSpecial);
    return newPassword;
  }

  private String addMissingPasswordRequirements(String password, Boolean addLowerCase, Boolean addUpperCase, Boolean addNumber, Boolean addSpecial) {
    if (addLowerCase) {
      password += LOWERCASE_CHARS[generateRandomInt(LOWERCASE_CHARS.size())];
    }
    if (addUpperCase) {
      password += UPPERCASE_CHARS[generateRandomInt(UPPERCASE_CHARS.size())];
    }
    if (addNumber) {
      password += NUMBER_CHARS[generateRandomInt(NUMBER_CHARS.size())];
    }
    if (addSpecial) {
      password += SPECIAL_CHARS[generateRandomInt(SPECIAL_CHARS.size())];
    }
    return password;
  }

  // Generates a random number from 0 up to, but not including, max.
  private Integer generateRandomInt(Integer max) {
    return Math.mod(Math.abs(Crypto.getRandomInteger()), max);
  }

  // Loops over required fields that were not passed in to set to some default value
  private User handleUnsetRequiredFields(User u) {
    if (String.isBlank(u.LastName)){
      u.LastName = generateLastName();
    }
    if (String.isBlank(u.Username)) {
      u.Username = generateUsername();
    }
    if (String.isBlank(u.Email)) {
      u.Email = generateEmail();
    }
    if (String.isBlank(u.Alias)) {
      u.Alias = generateAlias();
    }
    if (String.isBlank(u.CommunityNickname)) {
      u.CommunityNickname = generateCommunityNickname();
    }
    return u;
  }

  // Method to construct a contact for a user
  private void generateContact(User u, Id accountId) {
    // Add logic here if you want to build your own contact for the user
  }

  // Default implementation to try to provide uniqueness
  private String generateAlias() {
    String timeString = String.valueOf(CURRENT_TIME);
    return timeString.substring(timeString.length() - 8);
  }

  // Default implementation to try to provide uniqueness
  private String generateLastName() {
    return 'ExternalUser' + CURRENT_TIME;
  }

  // Default implementation to try to provide uniqueness
  private String generateUsername() {
    return 'externaluser' + CURRENT_TIME + '@company.com';
  }

  // Default implementation to try to provide uniqueness
  private String generateEmail() {
    return 'externaluser' + CURRENT_TIME + '@company.com';
  }

  // Default implementation to try to provide uniqueness
  private String generateCommunityNickname() {
    return 'ExternalUser' + CURRENT_TIME;
  }
}

Any idea on what would could cause the phone number verification to fail?

  • Is the exception coming on this line? Site.createExternalUser(u, accountId, password); – Pranay Jaiswal Nov 19 '18 at 20:33
  • @PranayJaiswal I can't tell... since this appears to be a page not available as a visualforce page I'm not sure how to debug this. The URL is: myorg.na29.force.com/secur/CommunitiesSelfRegUi – S.B. Nov 19 '18 at 20:37
  • 1
    Can you try looking at debug logs? salesforce.stackexchange.com/a/216529/19118 – Pranay Jaiswal Nov 19 '18 at 20:39
  • Thanks, I attempted this, but I am not getting any logs generated. When I go into Builder for the community in settings the Guest User Profile is set to "Test Profile" and this the same profile I am attempt to sign the new users up to, I have tried other profiles as well, but I am getting the result. The profile is included in the members section of the community page as well. – S.B. Nov 19 '18 at 21:56
2

Unfortunately you'll need to purchase an add-on item called Identity Verification Credits in order to use SMS verification. See the Winter '19 release notes:

To verify identities via text message, you purchase a license for Identity Verification Credits, which allows your org a predetermined number of SMS messages for identity verification. For exact limits, contact your Salesforce account rep.

This will appear in the Usage-based Entitlements section of the Company Information page.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.