예제 #1
0
  /**
   * Creates a snapshot of the entity.
   *
   * @since 2.0.0
   */
  private void snapshot() {
    ManagedInstance.LOG.trace("Snapshot generated for instance {0}", this);

    if (this.snapshot.size() == 0) {
      for (final AbstractMapping<?, ?, ?> mapping : this.type.getMappingsSingular()) {
        this.snapshot.put(mapping, mapping.get(this.instance));
      }
    }
  }
예제 #2
0
  /**
   * Sets the status.
   *
   * @param status the status to set
   * @since 2.0.0
   */
  public void setStatus(Status status) {
    this.oldStatus = this.status;

    if (status != this.status) {
      ManagedInstance.LOG.debug(
          "Instance status changing for {0}: {1} -> {2}", this, this.status, status);

      this.status = status;
    }
  }
예제 #3
0
  /**
   * Resets the change status of the instance.
   *
   * @since 2.0.0
   */
  public void reset() {
    ManagedInstance.LOG.trace("Reset instance {0}", this);

    this.collectionsChanged.clear();

    this.changed = false;

    this.snapshot.clear();
    this.snapshot();
  }
예제 #4
0
  /**
   * Handles the entities that have been orphaned.
   *
   * @param entityManager the entity manager
   * @since 2.0.0
   */
  public void handleOrphans(EntityManagerImpl entityManager) {
    ManagedInstance.LOG.debug("Inspecting orphans for instance {0}", this);

    for (int i = 0; i < this.collectionsChanged.size(); i++) {
      final PluralMappingEx<?, ?, ?> collection = this.collectionsChanged.get(i);
      if (collection.isAssociation()) {
        ((PluralAssociationMappingImpl<?, ?, ?>) collection).removeOrphans(entityManager, this);
      }
    }
  }
예제 #5
0
  /**
   * Flushes the associations.
   *
   * @param connection the connection
   * @param removals true if the removals should be flushed and false for the additions
   * @param force true to force, effective only for insertions and for new entities.
   * @throws SQLException thrown if there is an underlying SQL Exception
   * @since 2.0.0
   */
  public void flushAssociations(Connection connection, boolean removals, boolean force)
      throws SQLException {
    if (!removals || (this.status != Status.NEW)) {
      ManagedInstance.LOG.debug("Flushing associations for instance {0}", this);

      for (final JoinedMapping<?, ?, ?> collection : this.type.getMappingsJoined()) {
        collection.flush(connection, this, removals, force);
      }
    }
  }
예제 #6
0
  /**
   * Handles the entities that have been added.
   *
   * @param entityManager the entity manager
   * @since 2.0.0
   */
  public void handleAdditions(EntityManagerImpl entityManager) {
    ManagedInstance.LOG.debug("Inspecting additions for instance {0}", this);

    for (int i = 0; i < this.collectionsChanged.size(); i++) {
      final PluralMappingEx<?, ?, ?> collection = this.collectionsChanged.get(i);

      if (collection instanceof PluralAssociationMappingImpl) {
        ((PluralAssociationMappingImpl<?, ?, ?>) collection).persistAdditions(entityManager, this);
      }
    }
  }
예제 #7
0
  /**
   * Refreshes the instance from the database.
   *
   * @param entityManager the entity manager
   * @param connection the connection
   * @param lockMode the lock mode
   * @param processed the set of processed instances
   * @since 2.0.0
   */
  public void refresh(
      EntityManagerImpl entityManager,
      Connection connection,
      LockModeType lockMode,
      Set<Object> processed) {
    ManagedInstance.LOG.debug("Refeshing instance {0}", this);

    this.type.performRefresh(connection, this, lockMode, processed);

    for (final AssociationMappingImpl<?, ?, ?> association : this.type.getAssociations()) {
      association.refresh(this, processed);
    }
  }
예제 #8
0
  /**
   * Cascades the remove operation
   *
   * @param entityManager the entity manager
   * @param processed registry of processed entities
   * @param instances the managed instances
   * @since 2.0.0
   */
  public void cascadeRemove(
      EntityManagerImpl entityManager,
      ArrayList<Object> processed,
      LinkedList<ManagedInstance<?>> instances) {
    ManagedInstance.LOG.debug("Cascading remove on {0}", this);

    for (final AssociationMappingImpl<?, ?, ?> association : this.type.getAssociationsRemovable()) {

      // if the association a collection attribute then we will cascade to each element
      if (association instanceof PluralAssociationMappingImpl) {
        final PluralAssociationMappingImpl<?, ?, ?> mapping =
            (PluralAssociationMappingImpl<?, ?, ?>) association;

        // extract the collection
        final Collection<?> collection;
        if (mapping.getAttribute().getCollectionType() == CollectionType.MAP) {
          collection = ((Map<?, ?>) mapping.get(this.instance)).values();
        } else {
          collection = (Collection<?>) mapping.get(this.instance);
        }

        // cascade to each element in the collection
        if (collection instanceof List) {
          final List<?> list = (List<?>) collection;
          for (int i = 0; i < list.size(); i++) {
            entityManager.removeImpl(list.get(i), processed, instances);
          }
        } else {
          for (final Object element : collection) {
            entityManager.removeImpl(element, processed, instances);
          }
        }
      } else {
        final SingularAssociationMappingImpl<?, ?> mapping =
            (SingularAssociationMappingImpl<?, ?>) association;
        final Object associate = mapping.get(this.instance);

        if (associate != null) {
          entityManager.removeImpl(associate, processed, instances);
        }
      }
    }
  }
예제 #9
0
  /**
   * Cascades the detach operation.
   *
   * @param entityManager the entity manager
   * @since 2.0.0
   */
  public void cascadeDetach(EntityManagerImpl entityManager) {
    this.status = Status.DETACHED;

    ManagedInstance.LOG.debug("Cascading detach on {0}", this);

    for (final AssociationMappingImpl<?, ?, ?> association :
        this.type.getAssociationsDetachable()) {

      // if the association a collection attribute then we will cascade to each element
      if (association instanceof PluralAssociationMappingImpl) {
        final PluralAssociationMappingImpl<?, ?, ?> mapping =
            (PluralAssociationMappingImpl<?, ?, ?>) association;

        final Collection<?> collection;
        if (mapping.getAttribute().getCollectionType() == CollectionType.MAP) {
          collection = ((Map<?, ?>) mapping.get(this.instance)).values();
        } else {
          // extract the collection
          collection = (Collection<?>) mapping.get(this.instance);
        }

        // cascade to each element in the collection
        if (collection instanceof List) {
          final List<?> list = (List<?>) collection;
          for (int i = 0; i < list.size(); i++) {
            entityManager.detach(list.get(i));
          }
        } else {
          for (final Object element : collection) {
            entityManager.detach(element);
          }
        }
      } else {
        final SingularAssociationMappingImpl<?, ?> mapping =
            (SingularAssociationMappingImpl<?, ?>) association;
        final Object associate = mapping.get(this.instance);

        entityManager.detach(associate);
      }
    }
  }
예제 #10
0
  /**
   * Processes the associations.
   *
   * @since 2.0.0
   */
  public void processJoinedMappings() {
    ManagedInstance.LOG.debug("Post processing associations for instance {0}", this);

    final HashSet<String> _joinsLoaded = this.joinsLoaded;

    for (final PluralMappingEx<?, ?, ?> mapping : this.type.getMappingsPlural()) {
      final HashSet<String> joinsLoaded2 = _joinsLoaded;
      if (!joinsLoaded2.contains(mapping.getPath())) {
        if (mapping.isEager()) {
          mapping.load(this);
        } else {
          mapping.setLazy(this);
        }
      }
    }

    final X _instance = this.instance;
    final EntityManagerImpl entityManager = this.session.getEntityManager();

    for (final SingularAssociationMappingImpl<?, ?> mapping : this.type.getAssociationsSingular()) {
      if (mapping.isEager()) {
        if (!_joinsLoaded.contains(mapping.getPath())) {
          mapping.initialize(this);
        } else {
          final Object associate = mapping.get(_instance);
          if (associate instanceof EnhancedInstance) {
            final EnhancedInstance enhancedInstance = (EnhancedInstance) associate;
            if (!enhancedInstance.__enhanced__$$__isInitialized()) {
              final ManagedInstance<?> associateManagedInstance =
                  enhancedInstance.__enhanced__$$__getManagedInstance();
              entityManager.find(
                  associateManagedInstance.getType().getJavaType(),
                  associateManagedInstance.getId().getId());
            }
          }
        }
      }
    }
  }
예제 #11
0
  /**
   * Increments the version of the instance.
   *
   * @param connection the connection
   * @param commit true if version update should be committed immediately
   * @throws SQLException thrown in case of an underlying SQL error
   * @since 2.0.0
   */
  public void incrementVersion(Connection connection, boolean commit) throws SQLException {
    if (!this.type.getRootType().hasVersionAttribute()) {
      return;
    }

    final EntityTypeImpl<? super X> rootType = this.type.getRootType();

    final BasicAttribute<? super X, ?> version = rootType.getVersionAttribute();

    if (this.oldVersion == null) {
      switch (this.type.getVersionType()) {
        case SHORT:
          final short shortValue = (((Number) version.get(this.instance)).shortValue());
          this.oldVersion = shortValue;
          version.set(this.instance, shortValue + 1);

          ManagedInstance.LOG.debug("Version upgraded instance: {0} - {1}", this, shortValue);

          break;
        case SHORT_OBJECT:
          final Short shortObjValue =
              version.get(this.instance) == null
                  ? 0
                  : //
                  Short.valueOf((((Number) version.get(this.instance)).shortValue()));
          this.oldVersion = shortObjValue;

          version.set(this.instance, shortObjValue + 1);

          ManagedInstance.LOG.debug("Version upgraded instance: {0} - {1}", this, shortObjValue);

          break;

        case INT:
          final int intValue = (((Number) version.get(this.instance)).intValue());
          this.oldVersion = intValue;

          version.set(this.instance, intValue + 1);

          ManagedInstance.LOG.debug("Version upgraded instance: {0} - {1}", this, intValue);

          break;
        case INT_OBJECT:
          final Integer intObjValue =
              version.get(this.instance) == null
                  ? 0
                  : //
                  Integer.valueOf(((Number) version.get(this.instance)).intValue());
          this.oldVersion = intObjValue;

          version.set(this.instance, intObjValue + 1);

          ManagedInstance.LOG.debug("Version upgraded instance: {0} - {1}", this, intObjValue);

          break;
        case LONG:
          final long longValue = (((Number) version.get(this.instance)).longValue());
          this.oldVersion = longValue;

          version.set(this.instance, longValue + 1);

          ManagedInstance.LOG.debug("Version upgraded instance: {0} - {1}", this, longValue);

          break;
        case LONG_OBJECT:
          final Long longObjValue =
              version.get(this.instance) == null
                  ? 0l
                  : //
                  Long.valueOf((((Number) version.get(this.instance)).longValue()));
          this.oldVersion = longObjValue;

          version.set(this.instance, longObjValue + 1);

          ManagedInstance.LOG.debug("Version upgraded instance: {0} - {1}", this, longObjValue);

          break;

        case TIMESTAMP:
          final Timestamp value = new Timestamp(System.currentTimeMillis());
          this.oldVersion = version.get(this.instance);

          version.set(this.instance, value);

          ManagedInstance.LOG.debug("Version upgraded instance: {0} - {1}", this, value);
      }
    }

    if (commit) {
      final Object newVersion = version.get(this.instance);
      rootType.performVersionUpdate(connection, this, this.oldVersion, newVersion);

      ManagedInstance.LOG.debug(
          "Version committed instance: {0} - {1} -> {2}", this, this.oldVersion, newVersion);

      this.oldVersion = null;
    } else {
      this.changed();
    }
  }
예제 #12
0
  /**
   * Fills the sequence / table generated values. The operation returns false if at least one entity
   * needs to obtain identity from the database.
   *
   * @return false if all OK, true if if at least one entity needs to obtain identity from the
   *     database
   * @since 2.0.0
   */
  public boolean fillIdValues() {
    ManagedInstance.LOG.debug("Auto generating id values for {0}", this);

    return this.hasInitialId = this.fillValuesImpl();
  }
예제 #13
0
  /**
   * Cascades the persist operation.
   *
   * @param entityManager the entity manager
   * @param processed registry of processed entities
   * @param instances the managed instances
   * @return true if an implicit flush is required, false otherwise
   * @since 2.0.0
   */
  public boolean cascadePersist(
      EntityManagerImpl entityManager,
      ArrayList<Object> processed,
      LinkedList<ManagedInstance<?>> instances) {
    ManagedInstance.LOG.debug("Cascading persist on {0}", this);

    boolean requiresFlush = false;

    for (final AssociationMappingImpl<?, ?, ?> association :
        this.type.getAssociationsPersistable()) {

      // if the association a collection attribute then we will cascade to each element
      if (association instanceof PluralAssociationMappingImpl) {
        final PluralAssociationMappingImpl<?, ?, ?> mapping =
            (PluralAssociationMappingImpl<?, ?, ?>) association;

        switch (mapping.getAttribute().getCollectionType()) {
          case MAP:
            // extract the map
            final Map<?, ?> map = (Map<?, ?>) mapping.get(this.instance);

            // cascade to each element in the map
            for (final Object element : map.values()) {
              requiresFlush |= entityManager.persistImpl(element, processed, instances);
            }

            break;
          case LIST:
            // extract the list
            final List<?> list = (List<?>) mapping.get(this.instance);

            // cascade to each element in the list
            for (int i = 0; i < list.size(); i++) {
              requiresFlush |= entityManager.persistImpl(list.get(i), processed, instances);
            }

            break;
          default:
            // extract the collection
            final Collection<?> collection = (Collection<?>) mapping.get(this.instance);

            // cascade to each element in the collection
            if (collection instanceof List) {
              final List<?> castedList = (List<?>) collection;
              for (int i = 0; i < castedList.size(); i++) {
                requiresFlush |= entityManager.persistImpl(castedList.get(i), processed, instances);
              }
            } else {
              for (final Object element : collection) {
                requiresFlush |= entityManager.persistImpl(element, processed, instances);
              }
            }

            break;
        }
      } else {
        final SingularAssociationMappingImpl<?, ?> mapping =
            (SingularAssociationMappingImpl<?, ?>) association;
        final Object associate = mapping.get(this.instance);
        if (associate != null) {
          requiresFlush |= entityManager.persistImpl(associate, processed, instances);
        }
      }
    }

    return requiresFlush;
  }