// check what to do
if ( oldAttribute != null && newAttribute == null )
{
// attribute only exists in the old entry: delete all values
LdifModSpec modSpec;
if ( isReplaceForced )
{
// replace (empty value list)
modSpec = LdifModSpec.createReplace( attributeDescription );
}
else
// addDelForced or default
{
// delete all
modSpec = LdifModSpec.createDelete( attributeDescription );
}
modSpec.finish( LdifModSpecSepLine.create() );
record.addModSpec( modSpec );
}
else if ( oldAttribute == null && newAttribute != null )
{
// attribute only exists in the new entry: add all values
LdifModSpec modSpec;
if ( isReplaceForced )
{
// replace (all values)
modSpec = LdifModSpec.createReplace( attributeDescription );
}
else
// addDelForced or default
{
// add (all new values)
modSpec = LdifModSpec.createAdd( attributeDescription );
}
for ( IValue value : newAttribute.getValues() )
{
modSpec.addAttrVal( computeDiffCreateAttrValLine( value ) );
}
modSpec.finish( LdifModSpecSepLine.create() );
record.addModSpec( modSpec );
}
else if ( oldAttribute != null && newAttribute != null && !oldValues.equals( newValues ) )
{
// attribute exists in both entries, check modifications
if ( isReplaceForced )
{
// replace (all new values)
LdifModSpec modSpec = LdifModSpec.createReplace( attributeDescription );
for ( IValue value : newAttribute.getValues() )
{
modSpec.addAttrVal( computeDiffCreateAttrValLine( value ) );
}
modSpec.finish( LdifModSpecSepLine.create() );
record.addModSpec( modSpec );
}
else
{
// compute diff
List<LdifAttrValLine> toDel = new ArrayList<LdifAttrValLine>();
List<LdifAttrValLine> toAdd = new ArrayList<LdifAttrValLine>();
for ( Map.Entry<String, LdifAttrValLine> entry : oldAttrValLines.entrySet() )
{
if ( !newValues.contains( entry.getKey() ) )
{
toDel.add( entry.getValue() );
}
}
for ( Map.Entry<String, LdifAttrValLine> entry : newAttrValLines.entrySet() )
{
if ( !oldValues.contains( entry.getKey() ) )
{
toAdd.add( entry.getValue() );
}
}
/*
* we use add/del in the following cases:
* - add/del is forced in the connection configuration
* - only values to add
* - only values to delete
* - the sum of adds and deletes is smaller or equal than the number of replaces
*
* we use replace in the following cases:
* - the number of replaces is smaller to the sum of adds and deletes
* - for attributes with X-ORDERED 'VALUES'
*/
if ( isAddDelForced || ( toAdd.size() + toDel.size() <= newAttrValLines.size() && !isOrderedValue )
|| ( !toDel.isEmpty() && toAdd.isEmpty() ) || ( !toAdd.isEmpty() && toDel.isEmpty() ) )
{
// add/del del/add
LdifModSpec addModSpec = LdifModSpec.createAdd( attributeDescription );
for ( LdifAttrValLine attrValLine : toAdd )
{
addModSpec.addAttrVal( attrValLine );
}
addModSpec.finish( LdifModSpecSepLine.create() );
LdifModSpec delModSpec = LdifModSpec.createDelete( attributeDescription );
for ( LdifAttrValLine attrValLine : toDel )
{
delModSpec.addAttrVal( attrValLine );
}
delModSpec.finish( LdifModSpecSepLine.create() );
if ( modifyAddDeleteOrder == ModifyOrder.DELETE_FIRST )
{
if ( delModSpec.getAttrVals().length > 0 )
{
record.addModSpec( delModSpec );
}
if ( addModSpec.getAttrVals().length > 0 )
{
record.addModSpec( addModSpec );
}
}
else
{
if ( addModSpec.getAttrVals().length > 0 )
{
record.addModSpec( addModSpec );
}
if ( delModSpec.getAttrVals().length > 0 )
{
record.addModSpec( delModSpec );
}
}
}
else
{
// replace (all new values)
LdifModSpec modSpec = LdifModSpec.createReplace( attributeDescription );
for ( LdifAttrValLine attrValLine : newAttrValLines.values() )
{
modSpec.addAttrVal( attrValLine );
}
modSpec.finish( LdifModSpecSepLine.create() );
record.addModSpec( modSpec );
}
}
}