Class BasicUserInfo

java.lang.Object
com.iizix.user.UserInfoBase
com.iizix.server.db.BasicUserInfo
All Implemented Interfaces:
IBasicUserInfoDetailNames

public class BasicUserInfo extends UserInfoBase implements IBasicUserInfoDetailNames
User information in the database. Depending on call, various members are not always populated.
Author:
Christopher Mindus
  • Field Details

    • refreshTime

      public final long refreshTime
      The time in milliseconds since the epoch when this instance was created and refreshed.
  • Method Details

    • getUserIDs

      public static long[] getUserIDs(Connection conn) throws SQLException
      Gets all the defined user ID's. With the user ID's, you can then retrieve the users using:
        long id=...;
        UserAuthentication userAuth=UserAuthentication.getInstance();
        AuthenticatedUser user=userAuth.getUser(id);
        BasicUserInfo info=user.getBasicUserInfo();
      
      Parameters:
      conn - The JDBC connection.
      Returns:
      The array of User ID's.
      Throws:
      SQLException - For SQL errors.
    • createNewUser

      public static BasicUserInfo createNewUser(String userName, String hashPW, boolean changePW, String email, String langCode, boolean hasLoggedIn, Map<String,String> details, String... groupNames) throws SQLException, NotFoundException
      Creates a new user and writes the information to the database.

      Note: The length of a details value should be maximum 3000 characters. If the it exceeds, it will be truncated.

      Parameters:
      userName - The user name: unique, not empty, maximum length 254.
      hashPW - The hashed password. It is based on PBKDF2 with Keyed-Hash Message Authentication Code (HMAC) with a SHA-256 hash. It can start with "EXT:" if the user has signed in using an external Sign In Provider, e.g. LinkedIn or Facebook, the remaining part of the string identifies the provider and the users identifier for that provider.
      changePW - Require user to change password upon next login (set to false for EXTERNAL password hash).
      email - Email address, null for none: maximum length 254. A non-blank address is written as the details IZS-Email and IZS-EmailVerify (to verify) as well, when the details carry no IZS-Email, so that its verification link and "resend" work (AC-D-6).
      langCode - The selected language code, null for none.
      hasLoggedIn - Flag for user is or has logged in (will update last_login time).
      details - Details map: keys maximum length 40, values maximum length 3000. Set details to null for none.
      groupNames - The groups the user should belong to.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If a group name is not found.
      NullPointerException - If hashPW is null.
      IllegalArgumentException - If hashPW is an empty string.
    • createNewUser

      public static BasicUserInfo createNewUser(Connection conn, String userName, String hashPW, boolean changePW, String email, String langCode, boolean hasLoggedIn, Map<String,String> details, GroupInfo... groups) throws SQLException, NotFoundException
      Creates a new user and writes the information to the database.

      Note: The length of a details value should be maximum 3000 characters. If the it exceeds, it will be truncated.

      Parameters:
      userName - The user name: unique, not empty, maximum length 254.
      hashPW - The hashed password. It is based on PBKDF2 with Keyed-Hash Message Authentication Code (HMAC) with a SHA-256 hash. It can start with "EXTERNAL:" if the user has signed in using an external Sign In Provider, e.g. LinkedIn or Facebook, the remaining part of the string identifies the provider and the users identifier for that provider.
      changePW - Require user to change password upon next login (set to false for EXTERNAL password hash).
      email - Email address, null for none: maximum length 254. A non-blank address is written as the details IZS-Email and IZS-EmailVerify (to verify) as well, when the details carry no IZS-Email, so that its verification link and "resend" work (AC-D-6).
      langCode - The selected language code, null for none.
      hasLoggedIn - Flag for user is or has logged in (will update last_login time).
      details - Details map: keys maximum length 40, values maximum length 3000. Set details to null for none.
      groups - The groups the user should belong to.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If a group name is not found.
      NullPointerException - If hashPW is null.
      IllegalArgumentException - If hashPW is an empty string.
    • newBasicUserInfo

      public static BasicUserInfo newBasicUserInfo(Connection conn, String userName, boolean lockForUpdate) throws SQLException, NotFoundException
      Constructs the UserInfo by loading the information from the database.
      Parameters:
      conn - The connection.
      userName - The user name.
      lockForUpdate - Flag indicating the user should be locked for update.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If user is not found.
    • newBasicUserInfo

      public static BasicUserInfo newBasicUserInfo(Connection conn, long id) throws SQLException, NotFoundException
      Constructs the UserInfo by loading the information from the database.
      Parameters:
      conn - The connection.
      id - The unique ID.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If user is not found.
    • countUsersFromEmail

      public static int countUsersFromEmail(Connection conn, String emailAddress) throws SQLException
      Counts the users that hold an e-mail address as their registered address, for the sign-in by address (SignIn flow D-3, CC-LOGIN-L10A1-SERVER-GAPS): the address is matched exactly as stored, like newBasicUserInfoFromEmail(Connection, String).
      Parameters:
      conn - The connection.
      emailAddress - The email address, as registered.
      Returns:
      The count of users holding the address, 0 for none.
      Throws:
      SQLException - For SQL errors.
    • newBasicUserInfoFromEmail

      public static BasicUserInfo newBasicUserInfoFromEmail(Connection conn, String emailAddress) throws SQLException, NotFoundException
      Constructs the UserInfo by loading the information from the database: the FIRST account that holds the address, for the callers of before shared addresses were allowed (EM-D-1, CC-FIX-SIGNIN-ACCOUNT-MAIL). Every account holding the address: newBasicUserInfosFromEmail(Connection, String).
      Parameters:
      conn - The connection.
      emailAddress - The email address to look-up.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If user is not found.
    • newBasicUserInfosFromEmail

      public static List<BasicUserInfo> newBasicUserInfosFromEmail(Connection conn, String emailAddress) throws SQLException
      Constructs the UserInfos of every account that holds an e-mail address as its registered address, matched exactly as stored (EM-D-1, CC-FIX-SIGNIN-ACCOUNT-MAIL: several accounts may carry one address - a personal account and an administrator account behind a support mailbox; a password reset mails one link per account, a sign-in by the address asks for the user name).
      Parameters:
      conn - The connection.
      emailAddress - The email address, as registered.
      Returns:
      The users holding the address, in the order of the database; empty for none.
      Throws:
      SQLException - For SQL errors.
    • toString

      public String toString()
      String representation of the class.
      Overrides:
      toString in class Object
      Returns:
      A string with user and distance.
    • getPasswordHash

      public String getPasswordHash()
      Gets the 'hash_pw', never null (max 120 chars). It is based on PBKDF2 with Keyed-Hash Message Authentication Code (HMAC) with a SHA-256 hash. It can start with "EXT:" if the user has signed in using an external Sign In Provider, e.g. LinkedIn or Facebook, the remaining part of the string identifies the provider and the users identifier for that provider.
      Returns:
      A string with a hashed password, or "EXTERNAL" if the user has signed in using an external Sign In Provider, e.g. LinkedIn or Facebook.
    • mustChangePassword

      public boolean mustChangePassword()
      Returns if the password must be changed upon next login.
      Specified by:
      mustChangePassword in class UserInfoBase
      Returns:
      Flag 'change_pw' to change the password.
    • canChangePassword

      public UserLocaleString canChangePassword()
      Checks if the user is allowed to change his password. Note that this does not check if the user id disabled: please do so using getDisabledReason().
      Specified by:
      canChangePassword in class UserInfoBase
      Returns:
      null if allowed and user can change his password, otherwise a UserLocaleString instance for the reason of the password being fixed and that it can never be changed.
    • getLastLogin

      public long getLastLogin()
      Gets the 'last_login' time in milliseconds since the epoch, 0 for never.
      Specified by:
      getLastLogin in class UserInfoBase
    • getLastFail

      public long getLastFail()
      Gets the 'last_fail' time in milliseconds since the epoch, 0 for never.
      Specified by:
      getLastFail in class UserInfoBase
    • getFailCount

      public int getFailCount()
      Gets the 'fail_count' value, zero for never.
      Specified by:
      getFailCount in class UserInfoBase
    • getDisabledReason

      public UserLocaleString getDisabledReason()
      Gets the 'disabled' reason, null for user not disabled.
      Specified by:
      getDisabledReason in class UserInfoBase
      Returns:
      The user 'disabled' reason, or null for user not disabled.
    • getDisabledReasonText

      public String getDisabledReasonText()
      Gets the 'disabled' reason text as stored in the database, null for user not disabled. Unlike getDisabledReason() it is not mapped to a UserLocaleString, so a free-text reason (e.g. the sign-in path's "Too many invalid logins") is returned as written and nothing is logged.
      Returns:
      The stored 'disabled' reason, or null for user not disabled.
    • getUUID

      public String getUUID()
      Returns the UUID for this user.
      Returns:
      The UUID of this user based of the ID, user name and email.
    • needsNewHashedPassword

      public boolean needsNewHashedPassword()
      Checks if a new password needs to be provided to the database during current successful login. As the password is available, it makes it possible to save a new hash with perhaps new algorithms. This makes it very hard to crack.
      Returns:
      true if 'failCount' is larger than 3 or 'disabledReason' is present. true is also returned if 'lastLogin' is longer than a week from current time. false is otherwise returned.
    • updateSuccessfulLogin

      public void updateSuccessfulLogin(Connection conn, String newHashedPassword) throws SQLException
      Updates the information to the database for a successful login.

      The connection must be in auto-commit "off" and have the user selected for update.

      If it is required, the password hash is updated. This is done every week or after a failure. This method will also reset the disabled status.

      Parameters:
      conn - The connection.
      newHashedPassword - A new hashed password to update the entry with, null for no change.
      Throws:
      SQLException - For SQL errors.
    • updateSuccessfulLogin

      public void updateSuccessfulLogin(Connection conn, String newHashedPassword, boolean resetChangePassword) throws SQLException
      Updates the information to the database for a successful login.

      The connection must be in auto-commit "off" and have the user selected for update.

      If it is required, the password hash is updated. This is done every week or after a failure. This method will also reset the disabled status.

      Parameters:
      conn - The connection.
      newHashedPassword - A new hashed password to update the entry with, null for no change.
      resetChangePassword - Flag to also reset the changePW (only used when newHashedPassword is specified).
      Throws:
      SQLException - For SQL errors.
    • updateFailedLogin

      public void updateFailedLogin(Connection conn, String disabledReason) throws SQLException, NotFoundException
      Updates the information to the database for failed login.

      The connection must be in auto-commit "off" and have the user selected for update.

      Parameters:
      conn - The connection.
      disabledReason - The reason to disable the user, null for no change.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted since login.
    • setDisabledReason

      public void setDisabledReason(Connection conn, String disabledReason) throws SQLException, NotFoundException
      Sets or clears the 'disabled' reason of the user: an administrator's disable or enable, which counts no failed login - compare updateFailedLogin(Connection,String), the sign-in's call, which counts one and can only set a reason. Enabling (a null reason) also clears the failure count and the last failure time, so that the enabled account is not held back by the failures that disabled it (CC-FIX-SERVERADMIN SA-3).

      The connection must be in auto-commit "off"; the caller commits.

      Parameters:
      conn - The connection.
      disabledReason - The reason to disable the user, null to enable the user.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted since login.
    • changePassword

      public UserLocaleString changePassword(String oldPassword, String password) throws SQLException, NotFoundException
      Changes the password for the user without checking if the password entropy is met.
      Parameters:
      oldPassword - The old password.
      password - The new password.
      Returns:
      null for success, otherwise the error enum value.
      Throws:
      NullPointerException - If the one of the passwords is null.
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted since login.
    • changePassword

      public UserLocaleString changePassword(String oldPassword, String password, int historyLength) throws SQLException, NotFoundException
      Changes the password for the user, keeping the history of passwords the policy asks for: the new password may be neither the current one nor any of the historyLength most recently replaced ones, and the replaced hash is recorded in IZS.USER_PASSWORDS, which holds at most that many rows for the user afterwards (CC-LOGIN-SERVER-CORE; the table existed since the schema was written and was read by no code, IIZI-AUTH-001). The password entropy is not checked here: the caller checks the policy first.
      Parameters:
      oldPassword - The old password.
      password - The new password.
      historyLength - The password history length of the policy, zero for no history: then exactly changePassword(String,String).
      Returns:
      null for success, otherwise the reason: the user is disabled, the password is fixed, the old password does not match (UserLocaleString.HashedPasswordMismatch), or the new password was used recently (UserLocaleString.PasswordReused).
      Throws:
      NullPointerException - If the one of the passwords is null.
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted since login.
    • resetPasswordTo

      public UserLocaleString resetPasswordTo(String password, int historyLength) throws SQLException, NotFoundException
      Replaces the password from a verified password reset link (CC-LOGIN-SERVER-CORE): the checks of changePassword(String,String,int) except the old password, which the holder of the link does not know. The change flag is cleared and the failed sign-ins are forgotten, as the user has proved to hold the registered mailbox; the disabled state is not touched (a disabled account is refused here). The password entropy is not checked here.
      Parameters:
      password - The new password.
      historyLength - The password history length of the policy, zero for no history.
      Returns:
      null for success, otherwise the reason: the user is disabled, the password is fixed, the account is an external Sign In Provider's, or the new password was used recently (UserLocaleString.PasswordReused).
      Throws:
      NullPointerException - If the password is null.
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted.
    • writePasswordSetByAdministrator

      public UserLocaleString writePasswordSetByAdministrator(Connection conn, String password, boolean mustChange, int historyLength) throws SQLException, NotFoundException
      Writes a password an administrator set for the user on the caller's connection, no commit (CC-ACCOUNT-EMAIL-PASSWORD, AE-1; AdminAccountChanges.setPassword): the checks of resetPasswordTo(String,int) but the disabled state and the fixed password - the administrator's authority - with the history the policy keeps, then the change flag as the administrator asked. The failed sign-ins are forgotten and every device token of the user is deleted, as every change of a password does. The caller checked the policy and commits; this instance holds the new hash and flag once the write succeeded, so the caller rolls back on a refusal only. The password entropy is not checked here.
      Parameters:
      conn - The connection, auto-commit "off".
      password - The new password; never logged.
      mustChange - true when the user must change it at the next sign-in.
      historyLength - The password history length of the policy, zero for no history.
      Returns:
      null for success, otherwise the reason: the account is an external Sign In Provider's (UserLocaleString.FixedPassword), or the new password was used recently (UserLocaleString.PasswordReused); nothing was written then.
      Throws:
      NullPointerException - If the password is null.
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted.
    • isPasswordInHistory

      public boolean isPasswordInHistory(String password, int historyLength) throws SQLException
      Checks if a password is the user's current one or one of the most recently replaced ones (CC-LOGIN-SERVER-CORE). A connection is taken from the pool for the history.
      Parameters:
      password - The password to check, in clear.
      historyLength - How many replaced passwords count, zero for the current one only.
      Returns:
      true when the password was used recently.
      Throws:
      SQLException - For SQL errors.
    • isPasswordInHistory

      public boolean isPasswordInHistory(Connection conn, String password, int historyLength) throws SQLException
      Checks if a password is the user's current one or one of the most recently replaced ones (CC-LOGIN-SERVER-CORE): each candidate hash is checked as a sign-in checks it, so the cost is one PBKDF2 per candidate.
      Parameters:
      conn - The connection.
      password - The password to check, in clear.
      historyLength - How many replaced passwords count, zero for the current one only.
      Returns:
      true when the password was used recently.
      Throws:
      SQLException - For SQL errors.
    • resetPassword

      public UserLocaleString resetPassword(StringBuilder randomPassword) throws SQLException, NotFoundException
      Resets the password for the user, returning a random password set for the user, and that the user must change password upon next sign in.
      Parameters:
      randomPassword - The StringBuilder instance that is filled in with the generated random password meeting the highest password entropy configurable.
      Returns:
      null for success, otherwise the error reason.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted since login.
    • resetPassword

      public UserLocaleString resetPassword(Connection conn, StringBuilder randomPassword) throws SQLException, NotFoundException
      Resets the password on the caller's connection WITHOUT committing, for a caller that completes the reset together with other work in one transaction - ServerAdmin's reset, which mails the new password and rolls the reset back when the mail cannot be sent (CC-FIX-SERVERADMIN SA-4). Otherwise as resetPassword(StringBuilder).

      The connection must be in auto-commit "off". This instance is NOT updated by this method: the caller commits and then calls refreshFromDB(Connection), so that the cached user shows the new hash and the change flag, or rolls back, after which the instance is right as it is. Until the commit a sign-in, which reads the row, sees the old password.

      Parameters:
      conn - The connection.
      randomPassword - The StringBuilder instance that is filled in with the generated random password meeting the highest password entropy configurable.
      Returns:
      null for success, otherwise the error reason.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted since login.
    • writeGeneratedPassword

      public String writeGeneratedPassword(Connection conn, String password) throws SQLException, NotFoundException
      Writes a password the caller generated and the change flag to the row on the connection, no commit, no change to this instance: the generated initial password of a built server's administrator (CC-ADMIN-FIRST-PASSWORD, AP-1 and AP-5), for which the account may be disabled - a disabled administrator must not come back with the public password either. Every device token of the user is deleted with it, on the same connection, as for every change of the password (CC-LOGIN-L5-DEVICE-TOKEN). The caller commits.
      Parameters:
      conn - The connection, auto-commit "off".
      password - The generated password; never logged.
      Returns:
      The hash written.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted.
    • refreshFromDB

      public void refreshFromDB(Connection conn) throws SQLException, NotFoundException
      Re-reads the sign-in bookkeeping of this user from its row: the password hash, the change flag, the last login, the last failure, the failure count and the disabled reason - what a commit of resetPassword(Connection,StringBuilder) has changed. The name, e-mail, languages, creation time, groups and details are not re-read.
      Parameters:
      conn - The connection, in auto-commit "off"; the caller owns its transaction.
      Throws:
      SQLException - For SQL errors.
      NotFoundException - If the user has been deleted.
    • getGroups

      public GroupInfo[] getGroups(boolean reload) throws NotFoundException, SQLException
      Gets the groups of this user.
      Parameters:
      reload - Forces reload of the groups.
      Returns:
      The array of group informations.
      Throws:
      NotFoundException - If a group is not found.
      SQLException - For SQL errors.
    • addGroups

      public int addGroups(Connection conn, GroupInfo... groups) throws SQLException
      Adds the groups to the user.
      Parameters:
      conn - The connection.
      groups - The groups to add.
      Returns:
      Count of added groups (if already added before).
      Throws:
      SQLException - For SQL errors.
    • removeGroups

      public int removeGroups(Connection conn, GroupInfo... groups) throws SQLException
      Removes the groups from the user.
      Parameters:
      conn - The connection.
      groups - The groups to add.
      Returns:
      Count of removed groups (if not present before).
      Throws:
      SQLException - For SQL errors.
    • getDetails

      public Map<String,String> getDetails()
      Gets the cached and current user details. Details are e.g. fax number, profile picture.
      Specified by:
      getDetails in class UserInfoBase
      Returns:
      A new read-only copy of the details with name as key and the value for it.
    • getDetails

      public Map<String,String> getDetails(boolean reload) throws SQLException
      Gets the (cached and current) user details. Details are e.g. fax number, profile picture.

      Note: If you have a JDBC connection, use getDetails(Connection, boolean) instead for efficiency.

      Specified by:
      getDetails in class UserInfoBase
      Parameters:
      reload - Reload flag from database.
      Returns:
      If reload is false, a cached read-only map with the details name as key and the value for it, otherwise a fresh copy of the details from the database.
      Throws:
      SQLException - For SQL errors.
    • getDetails

      public Map<String,String> getDetails(Connection conn, boolean reload) throws SQLException
      Gets the user details. Details are e.g. fax number, profile picture. If not previously loaded, the "reload" flag is ignored and the details are loaded.
      Specified by:
      getDetails in class UserInfoBase
      Parameters:
      conn - The connection, null for cached values only.
      reload - Reload flag, i.e. instructs a full reload of all details from the database.
      Returns:
      A cached read-only map with the details name as key and the value for it.
      Throws:
      SQLException - For SQL errors.
    • updateUserDetails

      public void updateUserDetails(Map<String,String> detailsMap) throws SQLException
      Updates user details and stores it in the database. A detail value can be added and removed. It is added if the entry is not present previously, updated if the entry did exist and the value is non-null, removed if the value is null.

      The cached details map are maintained for the user in a map, but outside updates to the database will not reflect changes to this.

      The exceptions thrown in this method may occur during the processing of changes. The database will be rolled back, however, the cached copy might be partially updated.

      Parameters:
      detailsMap - The map with details to change, keys are the detail names and the values are the new respective detail value. If the detail value is null, the detail is deleted.

      The detail following names are ignored:

      These names are used in conjunction with the License System.

      Throws:
      SQLException - For SQL errors.
      NullPointerException - If detail is null.
    • setUserDetail

      public String setUserDetail(Connection conn, String detail, String value) throws SQLException
      Sets a detail and stores it in the database. A detail value can be added and removed.

      Details are maintained for the user in a map, but outside updates to the database will not reflect changes to this.

      Note: The length of the detail value should be maximum 3000 characters. If the it exceeds, it will be truncated.

      Parameters:
      conn - The connection.
      detail - The detail name.
      value - The value, null to delete the detail.
      Returns:
      The previous value (if all details are previously loaded), null otherwise. If the detail name should not be stored in the details (see detail) parameter, null is returned and nothing is performed.
      Throws:
      SQLException - For SQL errors.
      NullPointerException - If detail is null.
    • setEmailVerified

      public int setEmailVerified(String email)
      Marks an email to be verified. The details like DETAIL_VerifyEmail[-nn] are checked and the appropriate one is removed.
      Parameters:
      email - The mail verified.
      Returns:
      1 for successful removal of verification, 0 if already verified, -1 if email is not registered with the user, or -2 for database SQL errors (already logged).
      Throws:
      NullPointerException - If email is null.
    • setEmailVerified

      public int setEmailVerified(Connection conn, String email) throws SQLException
      Marks an email to be verified. The details like DETAIL_VerifyEmail[-nn] are checked and the appropriate one is removed.
      Parameters:
      conn - The connection.
      email - The mail verified.
      Returns:
      1 for successful removal of verification, 0 if already verified, or -1 if email is not registered with the user.
      Throws:
      SQLException - For SQL errors.
      NullPointerException - If email is null.
    • getMailsToVerify

      public List<String> getMailsToVerify()
      Gets all the mails that needs verification. The current details are used, so if you need a fresh copy, update them using @{link getDetails(boolean) or preferable getDetails(Connection, boolean) if you have a database connection.
      Returns:
      The list of alphabetically sorted mails to verify.
    • sendMailsToUnverifiedMailAddresses

      public int sendMailsToUnverifiedMailAddresses(List<String> verifyMails, MailSender mailSender, String subject, String fromEmail, String bccEmails, String message, String externalWebServerBaseURL) throws NotFoundException, IOException, IllegalStateException, MessagingException
      Helper method to send a mail to all unverified mails for this user. The mail will be sent as plain text UTF-8 encoded mail.

      The message parameter is a formatted message that should contain two tags:

      • ${url} required tag that will contain the URL that the user must open in order to verify the mail.
      • ${email} optional tag that will be replaced with the email that needs verification.
      Parameters:
      verifyMails - The mails to verify, retrieved from getMailsToVerify().
      mailSender - The mail sender, null to get the default mail sender.
      subject - Subject that can contain the tag ${mail}.
      fromEmail - From email address.
      bccEmails - BCC email(s) [comma separated for multiple], null for none.
      message - The mail message to send.
      externalWebServerBaseURL - The external base URL for the web server, e.g. "https://lic.mindus.co", use null for default. The default address is retrieved using ServerShell.getExternalWebServerBaseURL().
      Returns:
      Count of mails queued for sending.
      Throws:
      NotFoundException - If mailSender cannot not be found (and the parameter mailSender, or if the externalWebServerBaseURL is null and the method ServerShell.getExternalWebServerBaseURL() returns null.
      IOException - If the mail queue directory does not exist.
      MessagingException - For messaging errors.
      IllegalStateException - For illegal state when creating a mail to queue, or if the server is not started.
    • transferEmailDetails

      public int transferEmailDetails(Map<String,Object> otherDetails)
      Transfers all email settings such as primary email, optional additional email(s), verified emails, etc, from the details inside this BasicUserInfo instance and another details map.
      Parameters:
      otherDetails - Other details map to update.
      Returns:
      The count of changed values (new value or removed value).