All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.eclipse.persistence.queries.ObjectLevelModifyQuery Maven / Gradle / Ivy

There is a newer version: 5.0.0-B03
Show newest version
/*
 * Copyright (c) 1998, 2021 Oracle and/or its affiliates. All rights reserved.
 *
 * This program and the accompanying materials are made available under the
 * terms of the Eclipse Public License v. 2.0 which is available at
 * http://www.eclipse.org/legal/epl-2.0,
 * or the Eclipse Distribution License v. 1.0 which is available at
 * http://www.eclipse.org/org/documents/edl-v10.php.
 *
 * SPDX-License-Identifier: EPL-2.0 OR BSD-3-Clause
 */

// Contributors:
//     Oracle - initial API and implementation from Oracle TopLink
package org.eclipse.persistence.queries;

import org.eclipse.persistence.internal.helper.*;
import org.eclipse.persistence.internal.sessions.*;
import org.eclipse.persistence.exceptions.*;
import org.eclipse.persistence.descriptors.ClassDescriptor;

/**
 * 

Purpose: * Abstract class for all object modify queries. * *

Responsibilities: *

    *
  • Stores {@literal &} retrieves the object to modify. *
  • Stores {@literal &} retrieves the primary key of the objects. *
* * @author Yvon Lavoie * @since TOPLink/Java 1.0 */ public abstract class ObjectLevelModifyQuery extends ModifyQuery { /* Primary key of the object to be modified. */ protected Object primaryKey; /* The object being modified. */ protected Object object; /* A changeSet representing the object being modified */ protected ObjectChangeSet objectChangeSet; /* The clone of the object being modified from unit of work. */ protected Object backupClone; /** * PUBLIC: * Initialize the state of the query. */ protected ObjectLevelModifyQuery() { this.cascadePolicy = CascadePrivateParts; } /** * INTERNAL: * Ensure that the descriptor has been set. */ @Override public void checkDescriptor(AbstractSession session) throws QueryException { if (this.descriptor == null) { if (getObject() == null) { throw QueryException.objectToModifyNotSpecified(this); } //Bug#3947714 Pass the object instead of class in case object is proxy ClassDescriptor referenceDescriptor = session.getDescriptor(getObject()); if (referenceDescriptor == null) { throw QueryException.descriptorIsMissing(getObject().getClass(), this); } setDescriptor(referenceDescriptor); } } /** * INTERNAL: * All have done is move code from UnitOfWork.internalExecuteQuery */ @Override public Object executeInUnitOfWork(UnitOfWorkImpl unitOfWork, AbstractRecord translationRow) throws DatabaseException { if (unitOfWork.isAfterWriteChangesButBeforeCommit()) { throw ValidationException.illegalOperationForUnitOfWorkLifecycle(unitOfWork.getLifecycle(), "executeQuery(ObjectLevelModifyQuery)"); } return executeInUnitOfWorkObjectLevelModifyQuery(unitOfWork, translationRow); } /** * INTERNAL: * This code was moved from UnitOfWork.internalExecuteQuery. */ protected Object executeInUnitOfWorkObjectLevelModifyQuery(UnitOfWorkImpl unitOfWork, AbstractRecord translationRow) throws DatabaseException, OptimisticLockException { if (!unitOfWork.getCommitManager().isActive()) { throw QueryException.invalidQuery(this); } if ((this.object != null) && (unitOfWork.isClassReadOnly(this.object.getClass(), this.descriptor))) { return this.object; } // CR#3216 - Apply check to ObjectLevelModifyQuery not just WriteObjectQuery if (unitOfWork.shouldPerformNoValidation() && unitOfWork.isUnregisteredExistingObject(this.object)) { //if the object is an unregistered existing object then skip it. This // Will only be in the collection if validation is turned off return null; } return super.executeInUnitOfWork(unitOfWork, translationRow); } /** * INTERNAL: * Return the backup clone of the object from the unit of work. */ public Object getBackupClone() { // PERF: A backup clone is only required for the old commit, // So avoid its creation for normal commit. if ((backupClone == null) && this.session.isUnitOfWork()) { setBackupClone(((UnitOfWorkImpl)this.session).getBackupCloneForCommit(this.object, this.descriptor)); } return backupClone; } /** * PUBLIC: * Return the object required for modification. */ public Object getObject() { return object; } /** * PUBLIC: * Return the ObjectChangeSet representing the object being changed */ public ObjectChangeSet getObjectChangeSet() { return this.objectChangeSet; } /** * INTERNAL: * Get the primary key for the query */ public Object getPrimaryKey() { return primaryKey; } /** * Return the domain class associated with this query. */ @Override public Class getReferenceClass() { if (this.object == null) { if (this.descriptor != null) { return this.descriptor.getJavaClass(); } return null; } return this.object.getClass(); } /** * INTERNAL: * Return the reference class for a query * Note: Although the API is designed to avoid classpath dependencies for the MW, since the object * is specified at runtime, this will not be an issue. */ @Override public String getReferenceClassName() { Class referenceClass = getReferenceClass(); if (referenceClass != null) { return referenceClass.getName(); } else { return null; } } /** * INTERNAL: * Return the name to use for the query in performance monitoring. */ @Override public void resetMonitorName() { this.monitorName = getClass().getSimpleName() + ":" + getReferenceClassName(); } /** * PUBLIC: * Return if this is an object level modify query. */ @Override public boolean isObjectLevelModifyQuery() { return true; } /** * INTERNAL: * Prepare the receiver for execution in a session. * In particular check that the tables on the descriptor are set. */ @Override protected void prepare() throws QueryException { checkDescriptor(this.session); if (this.object != null) {// Prepare can be called without the object set yet. this.object = this.descriptor.getObjectBuilder().unwrapObject(this.object, this.session); } if (this.descriptor.isAggregateDescriptor()) { throw QueryException.aggregateObjectCannotBeDeletedOrWritten(getDescriptor(), this); } super.prepare(); } /** * INTERNAL: * Prepare the receiver for execution in a session. * In particular check that the tables on the descriptor are set. */ @Override public void prepareForExecution() throws QueryException { super.prepareForExecution(); if (this.object == null) { throw QueryException.objectToModifyNotSpecified(this); } this.object = this.descriptor.getObjectBuilder().unwrapObject(this.object, this.session); if (this.primaryKey == null) { if (this.objectChangeSet != null) { this.primaryKey = this.objectChangeSet.getId(); } else { this.primaryKey = this.descriptor.getObjectBuilder().extractPrimaryKeyFromObject(this.object, this.session); } } } /** * INTERNAL: * Set the backup clone of the object from the unit of work. */ public void setBackupClone(Object backupClone) { this.backupClone = backupClone; } /** * PUBLIC: (REQUIRED) * Set the object required for modification. */ public void setObject(Object object) { this.object = object; } /** * INTERNAL: * Set the ObjectChangeSet representing the object to be written */ public void setObjectChangeSet(ObjectChangeSet changeSet) { this.objectChangeSet = changeSet; } /** * INTERNAL: * Set the primary key for the query. */ public void setPrimaryKey(Object primaryKey) { this.primaryKey = primaryKey; } @Override public String toString() { return Helper.getShortClassName(getClass()) + "(" + getObject() + ")"; } }




© 2015 - 2024 Weber Informatics LLC | Privacy Policy