/* * Copyright (c) 2015 EMC Corporation * All Rights Reserved */ package com.emc.storageos.volumecontroller.impl.block.taskcompleter; import java.net.URI; import java.util.ArrayList; import java.util.Collection; import java.util.List; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.emc.storageos.db.client.DbClient; import com.emc.storageos.db.client.model.BlockConsistencyGroup; import com.emc.storageos.db.client.model.Operation; import com.emc.storageos.db.client.model.StringSet; import com.emc.storageos.db.client.model.Volume; import com.emc.storageos.db.client.model.VolumeGroup; import com.emc.storageos.db.client.util.NullColumnValueGetter; import com.emc.storageos.exceptions.DeviceControllerException; import com.emc.storageos.svcs.errorhandling.model.ServiceCoded; import com.emc.storageos.volumecontroller.TaskCompleter; /** * Task completer for update application volumes * */ public class ApplicationTaskCompleter extends TaskCompleter{ private static final long serialVersionUID = -9188670003331949130L; private static final Logger log = LoggerFactory.getLogger(ApplicationTaskCompleter.class); protected Collection<URI> addVolumes; protected Collection<URI> removeVolumes; protected Collection<URI> consistencyGroups; public ApplicationTaskCompleter(URI volumeGroupId, Collection<URI> addVolumes, Collection<URI>removeVols, Collection<URI> consistencyGroups, String opId) { super(VolumeGroup.class, volumeGroupId, opId); this.addVolumes = addVolumes; this.removeVolumes = removeVols; this.consistencyGroups = consistencyGroups; } @Override protected void complete(DbClient dbClient, Operation.Status status, ServiceCoded coded) throws DeviceControllerException { log.info("START ApplicationCompleter complete"); super.setStatus(dbClient, status, coded); updateWorkflowStatus(status, coded); if (addVolumes != null) { for (URI voluri : addVolumes) { switch (status) { case error: setErrorOnDataObject(dbClient, Volume.class, voluri, coded); break; default: setReadyOnDataObject(dbClient, Volume.class, voluri); addApplicationToVolume(voluri, dbClient); } } } if (removeVolumes != null) { for (URI voluri : removeVolumes) { switch (status) { case error: setErrorOnDataObject(dbClient, Volume.class, voluri, coded); break; default: setReadyOnDataObject(dbClient, Volume.class, voluri); removeApplicationFromVolume(voluri, dbClient); } } } if (consistencyGroups != null && !consistencyGroups.isEmpty()) { for (URI cguri : consistencyGroups) { switch (status) { case error: setErrorOnDataObject(dbClient, BlockConsistencyGroup.class, cguri, coded); break; default: updateConsistencyGroup(cguri, dbClient); setReadyOnDataObject(dbClient, BlockConsistencyGroup.class, cguri); } } } log.info("END ApplicationCompleter complete"); } /** * Remove application from the volume applicationIds attribute * @param voluri The volumes that will be updated * @param dbClient */ protected void removeApplicationFromVolume(URI voluri, DbClient dbClient) { Volume volume = dbClient.queryObject(Volume.class, voluri); String appId = getId().toString(); StringSet appIds = volume.getVolumeGroupIds(); if(appIds != null) { appIds.remove(appId); } dbClient.updateObject(volume); } /** * Add the application to the volume applicationIds attribute * @param voluri The volume that will be updated * @param dbClient */ protected void addApplicationToVolume(URI voluri, DbClient dbClient) { Volume volume = dbClient.queryObject(Volume.class, voluri); StringSet applications = volume.getVolumeGroupIds(); if (applications == null) { applications = new StringSet(); } applications.add(getId().toString()); volume.setVolumeGroupIds(applications); dbClient.updateObject(volume); // handle clones StringSet fullCopies = volume.getFullCopies(); List<Volume> fullCopiesToUpdate = new ArrayList<Volume>(); if (fullCopies != null && !fullCopies.isEmpty()) { for (String fullCopyId : fullCopies) { Volume fullCopy = dbClient.queryObject(Volume.class, URI.create(fullCopyId)); if (fullCopy != null && NullColumnValueGetter.isNullValue(fullCopy.getFullCopySetName())) { fullCopy.setFullCopySetName(fullCopy.getReplicationGroupInstance()); fullCopiesToUpdate.add(fullCopy); } } } if (!fullCopiesToUpdate.isEmpty()) { dbClient.updateObject(fullCopiesToUpdate); } } /** * Update arrayConsistency attribute * @param cguri The consistency group that will be updated * @param dbClient */ protected void updateConsistencyGroup(URI cguri, DbClient dbClient) { BlockConsistencyGroup cg = dbClient.queryObject(BlockConsistencyGroup.class, cguri); if (cg != null && !cg.getInactive()) { if (cg.getArrayConsistency()) { log.info("Updated consistency group arrayConsistency"); cg.setArrayConsistency(false); dbClient.updateObject(cg); } } } }