Beispiel #1
0
  @Override
  public void updateCredentialDirectly(UserCredentialValueModel credModel) {
    CredentialEntity credentialEntity = getCredentialEntity(user, credModel.getType());

    if (credentialEntity == null) {
      credentialEntity = new CredentialEntity();
      credentialEntity.setId(KeycloakModelUtils.generateId());
      credentialEntity.setType(credModel.getType());
      credentialEntity.setCreatedDate(credModel.getCreatedDate());
      credentialEntity.setUser(user);
      em.persist(credentialEntity);
      user.getCredentials().add(credentialEntity);
    }

    credentialEntity.setValue(credModel.getValue());
    credentialEntity.setSalt(credModel.getSalt());
    credentialEntity.setDevice(credModel.getDevice());
    credentialEntity.setHashIterations(credModel.getHashIterations());
    credentialEntity.setCounter(credModel.getCounter());
    credentialEntity.setAlgorithm(credModel.getAlgorithm());
    credentialEntity.setDigits(credModel.getDigits());
    credentialEntity.setPeriod(credModel.getPeriod());

    em.flush();
  }
Beispiel #2
0
  @Override
  public void updateCredential(UserCredentialModel cred) {
    CredentialEntity credentialEntity = getCredentialEntity(user, cred.getType());

    if (credentialEntity == null) {
      credentialEntity = new CredentialEntity();
      credentialEntity.setId(KeycloakModelUtils.generateId());
      credentialEntity.setType(cred.getType());
      credentialEntity.setDevice(cred.getDevice());
      credentialEntity.setUser(user);
      em.persist(credentialEntity);
      user.getCredentials().add(credentialEntity);
    }
    if (cred.getType().equals(UserCredentialModel.PASSWORD)) {
      byte[] salt = getSalt();
      int hashIterations = 1;
      PasswordPolicy policy = realm.getPasswordPolicy();
      if (policy != null) {
        hashIterations = policy.getHashIterations();
        if (hashIterations == -1) hashIterations = 1;
      }
      credentialEntity.setValue(
          new Pbkdf2PasswordEncoder(salt).encode(cred.getValue(), hashIterations));
      credentialEntity.setSalt(salt);
      credentialEntity.setHashIterations(hashIterations);
    } else {
      credentialEntity.setValue(cred.getValue());
    }
    credentialEntity.setDevice(cred.getDevice());
    em.flush();
  }
Beispiel #3
0
 protected AccessToken initToken(
     RealmModel realm,
     ClientModel client,
     UserModel user,
     UserSessionModel session,
     ClientSessionModel clientSession) {
   AccessToken token = new AccessToken();
   if (clientSession != null) token.clientSession(clientSession.getId());
   token.id(KeycloakModelUtils.generateId());
   token.subject(user.getId());
   token.audience(client.getClientId());
   token.issuedNow();
   token.issuedFor(client.getClientId());
   token.issuer(clientSession.getNote(OIDCLoginProtocol.ISSUER));
   if (session != null) {
     token.setSessionState(session.getId());
   }
   if (realm.getAccessTokenLifespan() > 0) {
     token.expiration(Time.currentTime() + realm.getAccessTokenLifespan());
   }
   Set<String> allowedOrigins = client.getWebOrigins();
   if (allowedOrigins != null) {
     token.setAllowedOrigins(allowedOrigins);
   }
   return token;
 }
 @Override
 public void preprocessFederatedIdentity(
     KeycloakSession session,
     RealmModel realm,
     IdentityProviderMapperModel mapperModel,
     BrokeredIdentityContext context) {
   String template = mapperModel.getConfig().get(TEMPLATE);
   Matcher m = substitution.matcher(template);
   StringBuffer sb = new StringBuffer();
   while (m.find()) {
     String variable = m.group(1);
     if (variable.equals("ALIAS")) {
       m.appendReplacement(sb, context.getIdpConfig().getAlias());
     } else if (variable.equals("UUID")) {
       m.appendReplacement(sb, KeycloakModelUtils.generateId());
     } else if (variable.startsWith("CLAIM.")) {
       String name = variable.substring("CLAIM.".length());
       Object value = AbstractClaimMapper.getClaimValue(context, name);
       if (value == null) value = "";
       m.appendReplacement(sb, value.toString());
     } else {
       m.appendReplacement(sb, m.group(1));
     }
   }
   m.appendTail(sb);
   String username = sb.toString();
   context.setModelUsername(username);
 }
Beispiel #5
0
  @Override
  public void insertEntity(MongoIdentifiableEntity entity, MongoStoreInvocationContext context) {
    Class<? extends MongoEntity> clazz = entity.getClass();

    // Find annotations for ID, for all the properties and for the name of the collection.
    EntityInfo entityInfo = getEntityInfo(clazz);

    // Create instance of BasicDBObject and add all declared properties to it (properties with null
    // value probably should be skipped)
    BasicDBObject dbObject =
        mapperRegistry.convertApplicationObjectToDBObject(entity, BasicDBObject.class);

    DBCollection dbCollection = database.getCollection(entityInfo.getDbCollectionName());

    String currentId = entity.getId();

    // Generate random ID if not set already
    if (currentId == null) {
      currentId = KeycloakModelUtils.generateId();
      entity.setId(currentId);
    }

    // Adding "_id"
    dbObject.put("_id", currentId);

    try {
      dbCollection.insert(dbObject);
    } catch (MongoException e) {
      throw convertException(e);
    }

    // Treat object as created in this transaction (It is already submited to transaction)
    context.addCreatedEntity(entity);
  }
Beispiel #6
0
 private CredentialEntity setCredentials(UserEntity user, UserCredentialModel cred) {
   CredentialEntity credentialEntity = new CredentialEntity();
   credentialEntity.setId(KeycloakModelUtils.generateId());
   credentialEntity.setType(cred.getType());
   credentialEntity.setDevice(cred.getDevice());
   credentialEntity.setUser(user);
   return credentialEntity;
 }
Beispiel #7
0
 private void persistAttributeValue(String name, String value) {
   UserAttributeEntity attr = new UserAttributeEntity();
   attr.setId(KeycloakModelUtils.generateId());
   attr.setName(name);
   attr.setValue(value);
   attr.setUser(user);
   em.persist(attr);
   user.getAttributes().add(attr);
 }
 private String insertApplicationRole(DBCollection roles, String roleName, String applicationId) {
   BasicDBObject role = new BasicDBObject();
   String roleId = KeycloakModelUtils.generateId();
   role.append("_id", roleId);
   role.append("name", roleName);
   role.append("applicationId", applicationId);
   role.append("nameIndex", applicationId + "//" + roleName);
   roles.insert(role);
   return roleId;
 }
Beispiel #9
0
 public AccessTokenResponseBuilder generateRefreshToken() {
   if (accessToken == null) {
     throw new IllegalStateException("accessToken not set");
   }
   refreshToken = new RefreshToken(accessToken);
   refreshToken.id(KeycloakModelUtils.generateId());
   refreshToken.issuedNow();
   refreshToken.expiration(Time.currentTime() + realm.getSsoSessionIdleTimeout());
   return this;
 }
Beispiel #10
0
  @Override
  public Scope create(final String name, final ResourceServer resourceServer) {
    ScopeEntity entity = new ScopeEntity();

    entity.setId(KeycloakModelUtils.generateId());
    entity.setName(name);
    entity.setResourceServerId(resourceServer.getId());

    getMongoStore().insertEntity(entity, getInvocationContext());

    return new ScopeAdapter(entity, getInvocationContext(), this.authorizationProvider);
  }
Beispiel #11
0
  @Override
  public Policy create(String name, String type, ResourceServer resourceServer) {
    PolicyEntity entity = new PolicyEntity();

    entity.setId(KeycloakModelUtils.generateId());
    entity.setName(name);
    entity.setType(type);
    entity.setResourceServerId(resourceServer.getId());

    getMongoStore().insertEntity(entity, getInvocationContext());

    return new PolicyAdapter(entity, getInvocationContext(), this.authorizationProvider);
  }
Beispiel #12
0
  @Override
  public void addConsent(UserConsentModel consent) {
    String clientId = consent.getClient().getId();

    UserConsentEntity consentEntity = getGrantedConsentEntity(clientId);
    if (consentEntity != null) {
      throw new ModelDuplicateException(
          "Consent already exists for client [" + clientId + "] and user [" + user.getId() + "]");
    }

    consentEntity = new UserConsentEntity();
    consentEntity.setId(KeycloakModelUtils.generateId());
    consentEntity.setUser(user);
    consentEntity.setClientId(clientId);
    em.persist(consentEntity);
    em.flush();

    updateGrantedConsentEntity(consentEntity, consent);
  }
Beispiel #13
0
 public AccessTokenResponseBuilder generateIDToken() {
   if (accessToken == null) {
     throw new IllegalStateException("accessToken not set");
   }
   idToken = new IDToken();
   idToken.id(KeycloakModelUtils.generateId());
   idToken.subject(accessToken.getSubject());
   idToken.audience(client.getClientId());
   idToken.issuedNow();
   idToken.issuedFor(accessToken.getIssuedFor());
   idToken.issuer(accessToken.getIssuer());
   idToken.setSessionState(accessToken.getSessionState());
   if (realm.getAccessTokenLifespan() > 0) {
     idToken.expiration(Time.currentTime() + realm.getAccessTokenLifespan());
   }
   transformIDToken(
       session, idToken, realm, client, userSession.getUser(), userSession, clientSession);
   return this;
 }
  private void addDefaultMappers(KeycloakSession session, DBCollection clients) {
    DBCursor clientsCursor = clients.find();
    try {
      while (clientsCursor.hasNext()) {
        BasicDBObject currentClient = (BasicDBObject) clientsCursor.next();

        BasicDBList dbProtocolMappers = new BasicDBList();
        currentClient.put("protocolMappers", dbProtocolMappers);

        Object claimMask = currentClient.get("allowedClaimsMask");
        MigrationProvider migrationProvider = session.getProvider(MigrationProvider.class);
        List<ProtocolMapperRepresentation> protocolMappers =
            migrationProvider.getMappersForClaimMask((Long) claimMask);

        for (ProtocolMapperRepresentation protocolMapper : protocolMappers) {
          BasicDBObject dbMapper = new BasicDBObject();
          dbMapper.put("id", KeycloakModelUtils.generateId());
          dbMapper.put("protocol", protocolMapper.getProtocol());
          dbMapper.put("name", protocolMapper.getName());
          dbMapper.put("consentRequired", protocolMapper.isConsentRequired());
          dbMapper.put("consentText", protocolMapper.getConsentText());
          dbMapper.put("protocolMapper", protocolMapper.getProtocolMapper());

          Map<String, String> config = protocolMapper.getConfig();
          BasicDBObject dbConfig = MapMapper.convertMap(config);
          dbMapper.put("config", dbConfig);

          dbProtocolMappers.add(dbMapper);
        }

        // Remove obsolete keys from client
        currentClient.remove("allowedClaimsMask");

        log.debugv("Added default mappers to application {1}", currentClient.get("name"));
        clients.save(currentClient);
      }
    } finally {
      clientsCursor.close();
    }
  }
  private void addAdminRole(
      String roleName, String realmId, String applicationId, String realmAdminAppRoleId) {
    String roleTableName = database.correctObjectName("KEYCLOAK_ROLE", Table.class);
    String compositeRoleTableName = database.correctObjectName("COMPOSITE_ROLE", Table.class);
    String newRoleId = KeycloakModelUtils.generateId();

    InsertStatement insertRole =
        new InsertStatement(null, null, roleTableName)
            .addColumnValue("ID", newRoleId)
            .addColumnValue("APP_REALM_CONSTRAINT", applicationId)
            .addColumnValue("APPLICATION_ROLE", true)
            .addColumnValue("NAME", roleName)
            .addColumnValue("REALM_ID", realmId)
            .addColumnValue("APPLICATION", applicationId);

    // Add newly created role to the composite roles of 'realm-admin' role
    InsertStatement insertCompRole =
        new InsertStatement(null, null, compositeRoleTableName)
            .addColumnValue("COMPOSITE", realmAdminAppRoleId)
            .addColumnValue("CHILD_ROLE", newRoleId);

    statements.add(insertRole);
    statements.add(insertCompRole);
  }
Beispiel #16
0
 public void setEmail(String email) {
   this.email = email;
   this.emailConstraint = email != null ? email : KeycloakModelUtils.generateId();
 }
  protected void addDefaultProtocolMappers() throws SQLException, DatabaseException {
    String protocolMapperTableName = database.correctObjectName("PROTOCOL_MAPPER", Table.class);
    String protocolMapperCfgTableName =
        database.correctObjectName("PROTOCOL_MAPPER_CONFIG", Table.class);

    PreparedStatement statement =
        jdbcConnection.prepareStatement("select ID, NAME, ALLOWED_CLAIMS_MASK from CLIENT");

    try {
      ResultSet resultSet = statement.executeQuery();
      try {
        boolean first = true;
        while (resultSet.next()) {
          if (first) {
            confirmationMessage.append("Migrating claimsMask to protocol mappers for clients: ");
            first = false;
          }

          Object acmObj = resultSet.getObject("ALLOWED_CLAIMS_MASK");
          long mask = (acmObj != null) ? ((Number) acmObj).longValue() : ClaimMask.ALL;

          MigrationProvider migrationProvider = this.kcSession.getProvider(MigrationProvider.class);
          List<ProtocolMapperRepresentation> protocolMappers =
              migrationProvider.getMappersForClaimMask(mask);

          for (ProtocolMapperRepresentation protocolMapper : protocolMappers) {
            String mapperId = KeycloakModelUtils.generateId();

            InsertStatement insert =
                new InsertStatement(null, null, protocolMapperTableName)
                    .addColumnValue("ID", mapperId)
                    .addColumnValue("PROTOCOL", protocolMapper.getProtocol())
                    .addColumnValue("NAME", protocolMapper.getName())
                    .addColumnValue("CONSENT_REQUIRED", protocolMapper.isConsentRequired())
                    .addColumnValue("CONSENT_TEXT", protocolMapper.getConsentText())
                    .addColumnValue("PROTOCOL_MAPPER_NAME", protocolMapper.getProtocolMapper())
                    .addColumnValue("CLIENT_ID", resultSet.getString("ID"));
            statements.add(insert);

            for (Map.Entry<String, String> cfgEntry : protocolMapper.getConfig().entrySet()) {
              InsertStatement cfgInsert =
                  new InsertStatement(null, null, protocolMapperCfgTableName)
                      .addColumnValue("PROTOCOL_MAPPER_ID", mapperId)
                      .addColumnValue("NAME", cfgEntry.getKey())
                      .addColumnValue("VALUE", cfgEntry.getValue());
              statements.add(cfgInsert);
            }
          }

          confirmationMessage.append(resultSet.getString("NAME") + ", ");
        }

        // It means that some provider where processed
        if (!first) {
          confirmationMessage.append(". ");
        }
      } finally {
        resultSet.close();
      }
    } finally {
      statement.close();
    }
  }
  protected void convertSocialToIdFedRealms() throws SQLException, DatabaseException {
    String identityProviderTableName = database.correctObjectName("IDENTITY_PROVIDER", Table.class);
    String idpConfigTableName = database.correctObjectName("IDENTITY_PROVIDER_CONFIG", Table.class);

    PreparedStatement statement =
        jdbcConnection.prepareStatement(
            "select RSC.NAME, VALUE, REALM_ID, UPDATE_PROFILE_ON_SOC_LOGIN from REALM_SOCIAL_CONFIG RSC,REALM where RSC.REALM_ID = REALM.ID ORDER BY RSC.REALM_ID, RSC.NAME");
    try {
      ResultSet resultSet = statement.executeQuery();
      try {
        boolean providerInProgress = false;
        String socialProviderId = null;
        String clientId = null;
        String clientSecret;
        String realmId = null;
        boolean updateProfileOnSocialLogin = false;
        boolean first = true;

        while (resultSet.next()) {
          if (first) {
            confirmationMessage.append("Migrating social to identity providers: ");
            first = false;
          }

          if (!providerInProgress) {
            String key = resultSet.getString("NAME");
            int keyIndex = key.indexOf(".key");
            if (keyIndex == -1) {
              throw new IllegalStateException("Can't parse the provider from column: " + key);
            }

            socialProviderId = key.substring(0, keyIndex);
            clientId = resultSet.getString("VALUE");
            realmId = resultSet.getString("REALM_ID");
            updateProfileOnSocialLogin = resultSet.getBoolean("UPDATE_PROFILE_ON_SOC_LOGIN");
            providerInProgress = true;
          } else {
            clientSecret = resultSet.getString("VALUE");

            String internalId = KeycloakModelUtils.generateId();
            InsertStatement idpInsert =
                new InsertStatement(null, null, identityProviderTableName)
                    .addColumnValue("INTERNAL_ID", internalId)
                    .addColumnValue("ENABLED", true)
                    .addColumnValue("PROVIDER_ALIAS", socialProviderId)
                    .addColumnValue("PROVIDER_ID", socialProviderId)
                    .addColumnValue("UPDATE_PROFILE_FIRST_LOGIN", updateProfileOnSocialLogin)
                    .addColumnValue("STORE_TOKEN", false)
                    .addColumnValue("AUTHENTICATE_BY_DEFAULT", false)
                    .addColumnValue("REALM_ID", realmId);
            InsertStatement clientIdInsert =
                new InsertStatement(null, null, idpConfigTableName)
                    .addColumnValue("IDENTITY_PROVIDER_ID", internalId)
                    .addColumnValue("NAME", "clientId")
                    .addColumnValue("VALUE", clientId);
            InsertStatement clientSecretInsert =
                new InsertStatement(null, null, idpConfigTableName)
                    .addColumnValue("IDENTITY_PROVIDER_ID", internalId)
                    .addColumnValue("NAME", "clientSecret")
                    .addColumnValue("VALUE", clientSecret);

            statements.add(idpInsert);
            statements.add(clientIdInsert);
            statements.add(clientSecretInsert);
            confirmationMessage.append(socialProviderId + " in realm " + realmId + ", ");

            providerInProgress = false;
          }
        }

        // It means that some provider where processed
        if (!first) {
          confirmationMessage.append(". ");
        }
      } finally {
        resultSet.close();
      }
    } finally {
      statement.close();
    }
  }
Beispiel #19
0
/**
 * @author <a href="mailto:[email protected]">Bill Burke</a>
 * @version $Revision: 1 $
 */
@NamedQueries({
  @NamedQuery(
      name = "getAllUsersByRealm",
      query = "select u from UserEntity u where u.realmId = :realmId order by u.username"),
  @NamedQuery(
      name = "getAllUsersByRealmExcludeServiceAccount",
      query =
          "select u from UserEntity u where u.realmId = :realmId and (u.serviceAccountClientLink is null) order by u.username"),
  @NamedQuery(
      name = "searchForUser",
      query =
          "select u from UserEntity u where u.realmId = :realmId and (u.serviceAccountClientLink is null) and "
              + "( lower(u.username) like :search or lower(concat(u.firstName, ' ', u.lastName)) like :search or u.email like :search ) order by u.username"),
  @NamedQuery(
      name = "getRealmUserById",
      query = "select u from UserEntity u where u.id = :id and u.realmId = :realmId"),
  @NamedQuery(
      name = "getRealmUserByUsername",
      query = "select u from UserEntity u where u.username = :username and u.realmId = :realmId"),
  @NamedQuery(
      name = "getRealmUserByEmail",
      query = "select u from UserEntity u where u.email = :email and u.realmId = :realmId"),
  @NamedQuery(
      name = "getRealmUserByLastName",
      query = "select u from UserEntity u where u.lastName = :lastName and u.realmId = :realmId"),
  @NamedQuery(
      name = "getRealmUserByFirstLastName",
      query =
          "select u from UserEntity u where u.firstName = :first and u.lastName = :last and u.realmId = :realmId"),
  @NamedQuery(
      name = "getRealmUserByServiceAccount",
      query =
          "select u from UserEntity u where u.serviceAccountClientLink = :clientInternalId and u.realmId = :realmId"),
  @NamedQuery(
      name = "getRealmUserCount",
      query = "select count(u) from UserEntity u where u.realmId = :realmId"),
  @NamedQuery(
      name = "deleteUsersByRealm",
      query = "delete from UserEntity u where u.realmId = :realmId"),
  @NamedQuery(
      name = "deleteUsersByRealmAndLink",
      query = "delete from UserEntity u where u.realmId = :realmId and u.federationLink=:link")
})
@Entity
@Table(
    name = "USER_ENTITY",
    uniqueConstraints = {
      @UniqueConstraint(columnNames = {"REALM_ID", "USERNAME"}),
      @UniqueConstraint(columnNames = {"REALM_ID", "EMAIL_CONSTRAINT"})
    })
public class UserEntity {
  @Id
  @Column(name = "ID", length = 36)
  @Access(
      AccessType
          .PROPERTY) // we do this because relationships often fetch id, but not entity.  This
                     // avoids an extra SQL
  protected String id;

  @Column(name = "USERNAME")
  protected String username;

  @Column(name = "FIRST_NAME")
  protected String firstName;

  @Column(name = "CREATED_TIMESTAMP")
  protected Long createdTimestamp;

  @Column(name = "LAST_NAME")
  protected String lastName;

  @Column(name = "EMAIL")
  protected String email;

  @Column(name = "ENABLED")
  protected boolean enabled;

  @Column(name = "EMAIL_VERIFIED")
  protected boolean emailVerified;

  // Hack just to workaround the fact that on MS-SQL you can't have unique constraint with multiple
  // NULL values TODO: Find better solution (like unique index with 'where' but that's proprietary)
  @Column(name = "EMAIL_CONSTRAINT")
  protected String emailConstraint = KeycloakModelUtils.generateId();

  @Column(name = "REALM_ID")
  protected String realmId;

  @OneToMany(cascade = CascadeType.REMOVE, orphanRemoval = true, mappedBy = "user")
  protected Collection<UserAttributeEntity> attributes = new ArrayList<UserAttributeEntity>();

  @OneToMany(cascade = CascadeType.REMOVE, orphanRemoval = true, mappedBy = "user")
  protected Collection<UserRequiredActionEntity> requiredActions =
      new ArrayList<UserRequiredActionEntity>();

  @OneToMany(cascade = CascadeType.REMOVE, orphanRemoval = true, mappedBy = "user")
  protected Collection<CredentialEntity> credentials = new ArrayList<CredentialEntity>();

  @Column(name = "FEDERATION_LINK")
  protected String federationLink;

  @Column(name = "SERVICE_ACCOUNT_CLIENT_LINK")
  protected String serviceAccountClientLink;

  public String getId() {
    return id;
  }

  public void setId(String id) {
    this.id = id;
  }

  public String getUsername() {
    return username;
  }

  public void setUsername(String username) {
    this.username = username;
  }

  public Long getCreatedTimestamp() {
    return createdTimestamp;
  }

  public void setCreatedTimestamp(Long timestamp) {
    createdTimestamp = timestamp;
  }

  public String getFirstName() {
    return firstName;
  }

  public void setFirstName(String firstName) {
    this.firstName = firstName;
  }

  public String getLastName() {
    return lastName;
  }

  public void setLastName(String lastName) {
    this.lastName = lastName;
  }

  public String getEmail() {
    return email;
  }

  public void setEmail(String email) {
    this.email = email;
    this.emailConstraint = email != null ? email : KeycloakModelUtils.generateId();
  }

  public boolean isEnabled() {
    return enabled;
  }

  public void setEnabled(boolean enabled) {
    this.enabled = enabled;
  }

  public String getEmailConstraint() {
    return emailConstraint;
  }

  public void setEmailConstraint(String emailConstraint) {
    this.emailConstraint = emailConstraint;
  }

  public boolean isEmailVerified() {
    return emailVerified;
  }

  public void setEmailVerified(boolean emailVerified) {
    this.emailVerified = emailVerified;
  }

  public Collection<UserAttributeEntity> getAttributes() {
    return attributes;
  }

  public void setAttributes(Collection<UserAttributeEntity> attributes) {
    this.attributes = attributes;
  }

  public Collection<UserRequiredActionEntity> getRequiredActions() {
    return requiredActions;
  }

  public void setRequiredActions(Collection<UserRequiredActionEntity> requiredActions) {
    this.requiredActions = requiredActions;
  }

  public String getRealmId() {
    return realmId;
  }

  public void setRealmId(String realmId) {
    this.realmId = realmId;
  }

  public Collection<CredentialEntity> getCredentials() {
    return credentials;
  }

  public void setCredentials(Collection<CredentialEntity> credentials) {
    this.credentials = credentials;
  }

  public String getFederationLink() {
    return federationLink;
  }

  public void setFederationLink(String federationLink) {
    this.federationLink = federationLink;
  }

  public String getServiceAccountClientLink() {
    return serviceAccountClientLink;
  }

  public void setServiceAccountClientLink(String serviceAccountClientLink) {
    this.serviceAccountClientLink = serviceAccountClientLink;
  }

  @Override
  public boolean equals(Object o) {
    if (this == o) return true;
    if (o == null) return false;
    if (!(o instanceof UserEntity)) return false;

    UserEntity that = (UserEntity) o;

    if (!id.equals(that.id)) return false;

    return true;
  }

  @Override
  public int hashCode() {
    return id.hashCode();
  }
}
  private void convertSocialToIdFedRealms() {
    DBCollection realms = db.getCollection("realms");
    DBCursor realmsCursor = realms.find();

    try {
      while (realmsCursor.hasNext()) {
        BasicDBObject realm = (BasicDBObject) realmsCursor.next();
        boolean updateProfileOnInitialSocialLogin =
            realm.getBoolean("updateProfileOnInitialSocialLogin");
        BasicDBObject socialConfig = (BasicDBObject) realm.get("socialConfig");

        BasicDBList identityProviders = (BasicDBList) realm.get("identityProviders");
        if (identityProviders == null) {
          identityProviders = new BasicDBList();
          realm.put("identityProviders", identityProviders);
        }

        if (socialConfig != null) {
          for (Map.Entry<String, Object> entry : socialConfig.entrySet()) {
            if (entry.getKey().endsWith("###key")) {
              String socialProviderId = entry.getKey().substring(0, entry.getKey().indexOf("###"));
              String clientId = (String) entry.getValue();
              String clientSecret = socialConfig.getString(socialProviderId + "###secret");

              DBObject identityProviderConfig =
                  new BasicDBObjectBuilder()
                      .add("clientId", clientId)
                      .add("clientSecret", clientSecret)
                      .get();

              DBObject identityProvider =
                  new BasicDBObjectBuilder()
                      .add("internalId", KeycloakModelUtils.generateId())
                      .add("providerId", socialProviderId)
                      .add("alias", socialProviderId)
                      .add("updateProfileFirstLogin", updateProfileOnInitialSocialLogin)
                      .add("enabled", true)
                      .add("storeToken", false)
                      .add("authenticateByDefault", false)
                      .add("config", identityProviderConfig)
                      .get();

              identityProviders.add(identityProvider);
              log.debugv("Converted social provider {0} to identity provider", socialProviderId);
            }
          }
        }

        // Remove obsolete keys from realm
        realm.remove("social");
        realm.remove("updateProfileOnInitialSocialLogin");
        realm.remove("socialConfig");

        // Update realm in DB now
        realms.save(realm);

        log.debugv(
            "Social providers of realm {0} converted to identity providers", realm.get("_id"));
      }
    } finally {
      realmsCursor.close();
    }
  }