}
try {
this.wm.startOperation();
ObjectTypeConf typeConf = this.typeConfReg.getObjectTypeConf( this.entryPoint,
object );
if ( logical && !typeConf.isTMSEnabled()) {
enableTMS(object, typeConf);
}
InternalFactHandle handle = null;
if ( this.wm.isSequential() ) {
handle = createHandle( object,
typeConf );
insert( handle,
object,
rule,
activation,
typeConf );
return handle;
}
final PropagationContext propagationContext = new PropagationContextImpl( this.wm.getNextPropagationIdCounter(),
PropagationContext.INSERTION,
rule,
(activation == null) ? null : activation.getTuple(),
handle,
this.wm.agenda.getActiveActivations(),
this.wm.agenda.getDormantActivations(),
entryPoint );
try {
this.lock.lock();
this.ruleBase.readLock();
// check if the object already exists in the WM
handle = this.objectStore.getHandleForObject( object );
if ( typeConf.isTMSEnabled() ) {
TruthMaintenanceSystem tms = getTruthMaintenanceSystem();
if ( handle != null ) {
insertWhenHandleExists( object, tmsValue, logical, rule, activation, typeConf, handle, tms, propagationContext );
return handle;
}
// get the key for other "equal" objects, returns null if none exist
EqualityKey key = tms.get( object );
if ( logical ) {
if ( key != null && key.getStatus() == EqualityKey.STATED ) {
// You cannot logically insert a previously stated equality equal object, so return null
return null;
}
if ( key == null ) {
handle = createHandle( object,
typeConf ); // we know the handle is null
key = new EqualityKey( handle );
handle.setEqualityKey( key );
tms.put( key );
key.setStatus( EqualityKey.JUSTIFIED ); // new Key, so we know it's JUSTIFIED
} else {
handle = key.getFactHandle();
}
// Any logical propagations are handled via the TMS.addLogicalDependency
tms.addLogicalDependency( handle,
object,
tmsValue,
activation,
activation.getPropagationContext(),
rule,
typeConf );
return key.getFactHandle();
} else { // !logical
if ( key == null ) {
handle = createHandle( object,
typeConf ); // we know the handle is null
key = new EqualityKey( handle );
handle.setEqualityKey( key );
tms.put( key );
} else if ( key.getStatus() == EqualityKey.JUSTIFIED ) {
// Its previous justified, so switch to stated
key.setStatus( EqualityKey.STATED ); // must be done before the justifiedHandle retract
// remove logical dependencies
final InternalFactHandle justifiedHandle = key.getFactHandle();
((PropagationContextImpl)propagationContext).setFactHandle( justifiedHandle ); // necessary to stop recursive retractions
TruthMaintenanceSystemHelper.clearLogicalDependencies( justifiedHandle, propagationContext );
// now update existing handle to new value
return update( justifiedHandle, true, object, Long.MAX_VALUE, activation );
} else { // STATED
handle = createHandle( object,
typeConf ); // we know the handle is null
handle.setEqualityKey( key );
key.addFactHandle( handle );
}
key.setStatus( EqualityKey.STATED ); // KEY is always stated
}
} else {
// TMS not enabled for this object type
if ( handle != null ) {
return handle;
}
handle = createHandle( object,
typeConf );
}
// if the dynamic parameter is true or if the user declared the fact type with the meta tag:
// @propertyChangeSupport
if ( dynamic || typeConf.isDynamic() ) {
addPropertyChangeListener( handle, dynamic );
}
insert( handle,
object,