Search in sources :

Example 1 with ElementContainerHandler

use of org.datanucleus.store.types.containers.ElementContainerHandler in project datanucleus-rdbms by datanucleus.

the class PersistableMapping method postInsert.

/**
 * Method executed just after the insert of the owning object, allowing any necessary action
 * to this field and the object stored in it.
 * @param sm StateManager for the owner
 */
public void postInsert(DNStateManager sm) {
    Object pc = sm.provideField(mmd.getAbsoluteFieldNumber());
    TypeManager typeManager = sm.getExecutionContext().getTypeManager();
    pc = mmd.isSingleCollection() ? singleCollectionValue(typeManager, pc) : pc;
    if (pc == null) {
        // Has been set to null so nothing to do
        return;
    }
    ClassLoaderResolver clr = sm.getExecutionContext().getClassLoaderResolver();
    AbstractMemberMetaData[] relatedMmds = mmd.getRelatedMemberMetaData(clr);
    RelationType relationType = mmd.getRelationType(clr);
    if (relationType == RelationType.ONE_TO_ONE_BI) {
        DNStateManager otherSM = sm.getExecutionContext().findStateManager(pc);
        if (otherSM == null) {
            return;
        }
        AbstractMemberMetaData relatedMmd = mmd.getRelatedMemberMetaDataForObject(clr, sm.getObject(), pc);
        if (relatedMmd == null) {
            // Fsck knows why
            throw new NucleusUserException("You have a field " + mmd.getFullFieldName() + " that is 1-1 bidir yet cannot find the equivalent field at the other side. Why is that?");
        }
        Object relatedValue = otherSM.provideField(relatedMmd.getAbsoluteFieldNumber());
        relatedValue = relatedMmd.isSingleCollection() ? singleCollectionValue(typeManager, relatedValue) : relatedValue;
        if (relatedValue == null) {
            // Managed Relations : Other side not set so update it in memory
            if (NucleusLogger.PERSISTENCE.isDebugEnabled()) {
                NucleusLogger.PERSISTENCE.debug(Localiser.msg("041018", sm.getObjectAsPrintable(), mmd.getFullFieldName(), StringUtils.toJVMIDString(pc), relatedMmd.getFullFieldName()));
            }
            Object replaceValue = sm.getObject();
            if (relatedMmd.isSingleCollection()) {
                ElementContainerHandler containerHandler = typeManager.getContainerHandler(relatedMmd.getType());
                replaceValue = containerHandler.newContainer(relatedMmd, sm.getObject());
            }
            otherSM.replaceField(relatedMmd.getAbsoluteFieldNumber(), replaceValue);
        } else if (relatedValue != sm.getObject()) {
            // Managed Relations : Other side is inconsistent so throw exception
            throw new NucleusUserException(Localiser.msg("041020", sm.getObjectAsPrintable(), mmd.getFullFieldName(), StringUtils.toJVMIDString(pc), StringUtils.toJVMIDString(relatedValue)));
        }
    } else if (relationType == RelationType.MANY_TO_ONE_BI && relatedMmds[0].hasCollection()) {
        // TODO Make sure we have this PC in the collection at the other side
        DNStateManager otherSM = sm.getExecutionContext().findStateManager(pc);
        if (otherSM != null) {
            // Managed Relations : add to the collection on the other side
            Collection relatedColl = (Collection) otherSM.provideField(relatedMmds[0].getAbsoluteFieldNumber());
            if (relatedColl != null && !(relatedColl instanceof SCOCollection)) {
                // TODO Make sure the collection is a wrapper
                boolean contained = relatedColl.contains(sm.getObject());
                if (!contained) {
                    NucleusLogger.PERSISTENCE.info(Localiser.msg("041022", sm.getObjectAsPrintable(), mmd.getFullFieldName(), StringUtils.toJVMIDString(pc), relatedMmds[0].getFullFieldName()));
                // TODO Enable this. Currently causes issues with PMImplTest, InheritanceStrategyTest, TCK "inheritance1.conf"
                /*relatedColl.add(op.getObject());*/
                }
            }
        }
    } else if (relationType == RelationType.MANY_TO_ONE_UNI) {
        DNStateManager otherSM = sm.getExecutionContext().findStateManager(pc);
        if (otherSM == null) {
            // Related object is not yet persisted so persist it
            Object other = sm.getExecutionContext().persistObjectInternal(pc, null, -1, PersistableObjectType.PC);
            otherSM = sm.getExecutionContext().findStateManager(other);
        }
        // Add join table entry
        PersistableRelationStore store = (PersistableRelationStore) storeMgr.getBackingStoreForField(clr, mmd, mmd.getType());
        store.add(sm, otherSM);
    }
}
Also used : NucleusUserException(org.datanucleus.exceptions.NucleusUserException) RelationType(org.datanucleus.metadata.RelationType) ClassLoaderResolver(org.datanucleus.ClassLoaderResolver) TypeManager(org.datanucleus.store.types.TypeManager) Collection(java.util.Collection) SCOCollection(org.datanucleus.store.types.SCOCollection) SCOCollection(org.datanucleus.store.types.SCOCollection) DNStateManager(org.datanucleus.state.DNStateManager) AbstractMemberMetaData(org.datanucleus.metadata.AbstractMemberMetaData) ElementContainerHandler(org.datanucleus.store.types.containers.ElementContainerHandler) PersistableRelationStore(org.datanucleus.store.types.scostore.PersistableRelationStore)

Example 2 with ElementContainerHandler

use of org.datanucleus.store.types.containers.ElementContainerHandler in project datanucleus-rdbms by datanucleus.

the class SingleCollectionMapping method setObject.

@Override
public void setObject(ExecutionContext ec, PreparedStatement ps, int[] pos, Object container) {
    Object value = null;
    if (container != null) {
        ElementContainerHandler containerHandler = ec.getTypeManager().getContainerHandler(mmd.getType());
        ContainerAdapter containerAdapter = containerHandler.getAdapter(container);
        Iterator iterator = containerAdapter.iterator();
        value = iterator.hasNext() ? iterator.next() : null;
    }
    wrappedMapping.setObject(ec, ps, pos, value);
}
Also used : Iterator(java.util.Iterator) ContainerAdapter(org.datanucleus.store.types.containers.ContainerAdapter) ElementContainerHandler(org.datanucleus.store.types.containers.ElementContainerHandler)

Example 3 with ElementContainerHandler

use of org.datanucleus.store.types.containers.ElementContainerHandler in project datanucleus-rdbms by datanucleus.

the class SingleCollectionMapping method getObject.

@Override
public Object getObject(ExecutionContext ec, ResultSet rs, int[] exprIndex) {
    Object object = wrappedMapping.getObject(ec, rs, exprIndex);
    ElementContainerHandler containerHandler = ec.getTypeManager().getContainerHandler(mmd.getType());
    return containerHandler.newContainer(mmd, object);
}
Also used : ElementContainerHandler(org.datanucleus.store.types.containers.ElementContainerHandler)

Example 4 with ElementContainerHandler

use of org.datanucleus.store.types.containers.ElementContainerHandler in project datanucleus-rdbms by datanucleus.

the class ResultSetGetter method fetchObjectField.

public Object fetchObjectField(int fieldNumber) {
    StatementMappingIndex mapIdx = resultMappings.getMappingForMemberPosition(fieldNumber);
    JavaTypeMapping mapping = mapIdx.getMapping();
    AbstractMemberMetaData mmd = cmd.getMetaDataForManagedMemberAtAbsolutePosition(fieldNumber);
    RelationType relationType = mmd.getRelationType(ec.getClassLoaderResolver());
    Object value;
    if (mapping instanceof EmbeddedPCMapping || mapping instanceof SerialisedPCMapping || mapping instanceof SerialisedReferenceMapping) {
        value = mapping.getObject(ec, rs, mapIdx.getColumnPositions(), sm, fieldNumber);
    } else {
        if (mmd.isSingleCollection()) {
            StatementClassMapping relationMappings = resultMappings.getMappingDefinitionForMemberPosition(fieldNumber);
            if (relationMappings != null) {
                Class type = ec.getClassLoaderResolver().classForName(mmd.getCollection().getElementType());
                value = processSubObjectFields(mapping, type, relationMappings);
                ElementContainerHandler containerHandler = ec.getTypeManager().getContainerHandler(mmd.getType());
                value = containerHandler.newContainer(mmd, value);
            } else {
                value = mapping.getObject(ec, rs, mapIdx.getColumnPositions());
            }
        } else if (RelationType.isRelationSingleValued(relationType)) {
            // Process fields of sub-object if available in this result set
            StatementClassMapping relationMappings = resultMappings.getMappingDefinitionForMemberPosition(fieldNumber);
            if (relationMappings != null) {
                value = processSubObjectFields(mapping, mmd.getType(), relationMappings);
            } else {
                value = mapping.getObject(ec, rs, mapIdx.getColumnPositions());
            }
        } else {
            value = mapping.getObject(ec, rs, mapIdx.getColumnPositions());
        }
    }
    if (sm != null) {
        if (relationType == RelationType.ONE_TO_ONE_BI && value != null) {
            // Store the value at the other side of the 1-1 BI for use later if required
            DNStateManager otherSM = ec.findStateManager(value);
            if (otherSM != null) {
                AbstractMemberMetaData[] relMmds = mmd.getRelatedMemberMetaData(ec.getClassLoaderResolver());
                if (!otherSM.isFieldLoaded(relMmds[0].getAbsoluteFieldNumber()) && relMmds[0].getType().isAssignableFrom(sm.getObject().getClass())) {
                    otherSM.storeFieldValue(relMmds[0].getAbsoluteFieldNumber(), sm.getExternalObjectId());
                }
            }
        }
        if (cmd.getSCOMutableMemberFlags()[fieldNumber]) {
            // Wrap any SCO mutable fields
            return SCOUtils.wrapSCOField(sm, fieldNumber, value, false);
        } else if (RelationType.isRelationSingleValued(relationType) && (mmd.getEmbeddedMetaData() != null && mmd.getEmbeddedMetaData().getOwnerMember() != null)) {
            // Embedded PC, so make sure the field is wrapped where appropriate TODO This should be part of ManagedRelationships
            sm.updateOwnerFieldInEmbeddedField(fieldNumber, value);
            return value;
        }
    }
    return value;
}
Also used : JavaTypeMapping(org.datanucleus.store.rdbms.mapping.java.JavaTypeMapping) SerialisedReferenceMapping(org.datanucleus.store.rdbms.mapping.java.SerialisedReferenceMapping) EmbeddedPCMapping(org.datanucleus.store.rdbms.mapping.java.EmbeddedPCMapping) StatementMappingIndex(org.datanucleus.store.rdbms.query.StatementMappingIndex) StatementClassMapping(org.datanucleus.store.rdbms.query.StatementClassMapping) RelationType(org.datanucleus.metadata.RelationType) SerialisedPCMapping(org.datanucleus.store.rdbms.mapping.java.SerialisedPCMapping) DNStateManager(org.datanucleus.state.DNStateManager) AbstractMemberMetaData(org.datanucleus.metadata.AbstractMemberMetaData) ElementContainerHandler(org.datanucleus.store.types.containers.ElementContainerHandler)

Aggregations

ElementContainerHandler (org.datanucleus.store.types.containers.ElementContainerHandler)4 AbstractMemberMetaData (org.datanucleus.metadata.AbstractMemberMetaData)2 RelationType (org.datanucleus.metadata.RelationType)2 DNStateManager (org.datanucleus.state.DNStateManager)2 Collection (java.util.Collection)1 Iterator (java.util.Iterator)1 ClassLoaderResolver (org.datanucleus.ClassLoaderResolver)1 NucleusUserException (org.datanucleus.exceptions.NucleusUserException)1 EmbeddedPCMapping (org.datanucleus.store.rdbms.mapping.java.EmbeddedPCMapping)1 JavaTypeMapping (org.datanucleus.store.rdbms.mapping.java.JavaTypeMapping)1 SerialisedPCMapping (org.datanucleus.store.rdbms.mapping.java.SerialisedPCMapping)1 SerialisedReferenceMapping (org.datanucleus.store.rdbms.mapping.java.SerialisedReferenceMapping)1 StatementClassMapping (org.datanucleus.store.rdbms.query.StatementClassMapping)1 StatementMappingIndex (org.datanucleus.store.rdbms.query.StatementMappingIndex)1 SCOCollection (org.datanucleus.store.types.SCOCollection)1 TypeManager (org.datanucleus.store.types.TypeManager)1 ContainerAdapter (org.datanucleus.store.types.containers.ContainerAdapter)1 PersistableRelationStore (org.datanucleus.store.types.scostore.PersistableRelationStore)1