Skip to content

Commit

Permalink
MID-2413 delete async on debug pages
Browse files Browse the repository at this point in the history
  • Loading branch information
1azyman committed Jun 25, 2015
1 parent 449b33e commit 8257789
Show file tree
Hide file tree
Showing 4 changed files with 109 additions and 144 deletions.
Expand Up @@ -71,6 +71,7 @@ pageTasks.category.ImportFromFile=Import from file
pageTasks.category.ImportingAccounts=Importing accounts
pageTasks.category.LiveSynchronization=Live synchronization
pageTasks.category.Reconciliation=Reconciliation
pageTasks.category.Utility=Utility
#legacy
pageTasks.category.UserRecomputation=User recomputation
pageTasks.category.Recomputation=Recomputation
Expand Down
Expand Up @@ -20,19 +20,15 @@
import com.evolveum.midpoint.prism.PrismObject;
import com.evolveum.midpoint.prism.PrismProperty;
import com.evolveum.midpoint.prism.PrismPropertyDefinition;
import com.evolveum.midpoint.prism.delta.ObjectDelta;
import com.evolveum.midpoint.prism.match.PolyStringNormMatchingRule;
import com.evolveum.midpoint.prism.path.ItemPath;
import com.evolveum.midpoint.prism.polystring.PolyStringNormalizer;
import com.evolveum.midpoint.prism.query.*;
import com.evolveum.midpoint.schema.GetOperationOptions;
import com.evolveum.midpoint.schema.ResultHandler;
import com.evolveum.midpoint.schema.SelectorOptions;
import com.evolveum.midpoint.schema.constants.ObjectTypes;
import com.evolveum.midpoint.schema.constants.SchemaConstants;
import com.evolveum.midpoint.schema.result.OperationResult;
import com.evolveum.midpoint.schema.util.ObjectQueryUtil;
import com.evolveum.midpoint.schema.util.ObjectTypeUtil;
import com.evolveum.midpoint.security.api.AuthorizationConstants;
import com.evolveum.midpoint.task.api.Task;
import com.evolveum.midpoint.task.api.TaskManager;
Expand Down Expand Up @@ -71,11 +67,9 @@
import com.evolveum.midpoint.web.util.WebMiscUtil;
import com.evolveum.midpoint.web.util.WebModelUtils;
import com.evolveum.midpoint.xml.ns._public.common.common_3.*;

import com.evolveum.prism.xml.ns._public.query_3.QueryType;
import org.apache.commons.lang.StringUtils;
import org.apache.wicket.ajax.AjaxRequestTarget;
import org.apache.wicket.ajax.form.AjaxFormChoiceComponentUpdatingBehavior;
import org.apache.wicket.ajax.form.AjaxFormComponentUpdatingBehavior;
import org.apache.wicket.ajax.form.OnChangeAjaxBehavior;
import org.apache.wicket.ajax.markup.html.form.AjaxCheckBox;
Expand All @@ -92,7 +86,6 @@
import org.apache.wicket.markup.repeater.Item;
import org.apache.wicket.model.*;
import org.apache.wicket.request.mapper.parameter.PageParameters;
import org.springframework.beans.factory.annotation.Autowired;

import javax.xml.namespace.QName;
import java.util.*;
Expand Down Expand Up @@ -136,9 +129,7 @@ public class PageDebugList extends PageAdminConfiguration {
private IModel<DebugConfDialogDto> confDialogModel;
private IModel<List<ObjectViewDto>> resourcesModel;

private int objectsDeleted = 0;

public PageDebugList(){
public PageDebugList() {
this(true);
}

Expand All @@ -160,7 +151,7 @@ protected DebugConfDialogDto load() {
}
};

resourcesModel= new LoadableModel<List<ObjectViewDto>>() {
resourcesModel = new LoadableModel<List<ObjectViewDto>>() {

@Override
protected List<ObjectViewDto> load() {
Expand Down Expand Up @@ -201,7 +192,7 @@ public int compare(ObjectViewDto o1, ObjectViewDto o2) {

private void initLayout() {
DeleteAllDialog deleteAllDialog = new DeleteAllDialog(ID_DELETE_ALL_DIALOG,
createStringResource("pageDebugList.dialog.title.deleteAll")){
createStringResource("pageDebugList.dialog.title.deleteAll")) {

@Override
public void yesPerformed(AjaxRequestTarget target) {
Expand Down Expand Up @@ -234,7 +225,7 @@ public void yesPerformed(AjaxRequestTarget target) {
}

@Override
public boolean getLabelEscapeModelStrings(){
public boolean getLabelEscapeModelStrings() {
return false;
}
};
Expand All @@ -250,7 +241,7 @@ public boolean getLabelEscapeModelStrings(){

DebugSearchDto dto = searchModel.getObject();
Class type = dto.getType().getClassDefinition();
addOrReplaceTable(new RepositoryObjectDataProvider(this, type){
addOrReplaceTable(new RepositoryObjectDataProvider(this, type) {

@Override
protected void saveProviderPaging(ObjectQuery query, ObjectPaging paging) {
Expand Down Expand Up @@ -402,26 +393,26 @@ public void onSubmit(AjaxRequestTarget target, Form<?> form) {
}
}));

// headerMenuItems.add(new InlineMenuItem(createStringResource("pageDebugList.menu.deleteAllType"), true,
// new HeaderMenuAction(this) {
//
// @Override
// public void onSubmit(AjaxRequestTarget target, Form<?> form) {
// deleteAllType(target);
// }
// }));
headerMenuItems.add(new InlineMenuItem(createStringResource("pageDebugList.menu.deleteAllType"), true,
new HeaderMenuAction(this) {

@Override
public void onSubmit(AjaxRequestTarget target, Form<?> form) {
deleteAllType(target);
}
}));

headerMenuItems.add(new InlineMenuItem(createStringResource("pageDebugList.menu.deleteShadowsOnResource"),
new Model(true),
new AbstractReadOnlyModel<Boolean>() {

@Override
public Boolean getObject() {
DebugSearchDto dto = searchModel.getObject();
return ObjectTypes.SHADOW.equals(dto.getType());
}
@Override
public Boolean getObject() {
DebugSearchDto dto = searchModel.getObject();
return ObjectTypes.SHADOW.equals(dto.getType());
}

}, false, new HeaderMenuAction(this) {
}, false, new HeaderMenuAction(this) {

@Override
public void onClick(AjaxRequestTarget target) {
Expand Down Expand Up @@ -584,7 +575,7 @@ private void listObjectsPerformed(AjaxRequestTarget target) {
target.add(table);
}

private ObjectQuery createQuery(){
private ObjectQuery createQuery() {
DebugSearchDto dto = searchModel.getObject();

List<ObjectFilter> filters = new ArrayList<>();
Expand Down Expand Up @@ -663,130 +654,58 @@ public String getObject() {
};
}

private void deleteAllIdentitiesConfirmed(AjaxRequestTarget target,DeleteAllDto dto) {
private void deleteAllIdentitiesConfirmed(AjaxRequestTarget target, DeleteAllDto dto) {
Collection<SelectorOptions<GetOperationOptions>> options = new ArrayList<>();
GetOperationOptions opt = GetOperationOptions.createRaw();
options.add(SelectorOptions.create(ItemPath.EMPTY_PATH, opt));

Task task = createSimpleTask(OPERATION_LAXATIVE_DELETE);
OperationResult result = new OperationResult(OPERATION_LAXATIVE_DELETE);

objectsDeleted = 0;

if(dto.getDeleteUsers()){
deleteAllUsers(task, result, options);
}
if(dto.getDeleteOrgs()){
deleteAllOrgUnits(task, result, options);
}
if(dto.getDeleteAccountShadow()){
deleteAllAccountShadows(task, result, options, true);
}
if(dto.getDeleteNonAccountShadow()){
deleteAllAccountShadows(task, result, options, false);
try {
if (dto.getDeleteUsers()) {
ObjectQuery query = createDeleteAllUsersQuery();
deleteObjectsAsync(UserType.COMPLEX_TYPE, query, true, result);
}
if (dto.getDeleteOrgs()) {
deleteObjectsAsync(OrgType.COMPLEX_TYPE, null, true, result);
}
if (dto.getDeleteAccountShadow()) {
deleteAllShadowsConfirmed(result, true);
}
if (dto.getDeleteNonAccountShadow()) {
deleteAllShadowsConfirmed(result, false);
}
} catch (Exception ex) {
result.computeStatus(getString("pageDebugList.message.laxativeProblem"));
LoggingUtils.logException(LOGGER, getString("pageDebugList.message.laxativeProblem"), ex);
}

LOGGER.info("Deleted {} out of {} objects.", objectsDeleted, getObjectsToDelete());

target.add(getListTable());
target.add(getFeedbackPanel());

result.recomputeStatus();
showResult(result);
}

private void deleteAllUsers(Task task, final OperationResult result, Collection<SelectorOptions<GetOperationOptions>> options){
ResultHandler<UserType> userHandler = new ResultHandler<UserType>() {

@Override
public boolean handle(PrismObject object, OperationResult parentResult) {
if (!SystemObjectsType.USER_ADMINISTRATOR.value().equals(object.asObjectable().getOid())) {
ObjectDelta delta = ObjectDelta.createDeleteDelta(UserType.class, object.asObjectable().getOid(), getPrismContext());
Task task = createSimpleTask(OPERATION_LAXATIVE_DELETE);
OperationResult r = result.createMinorSubresult(OPERATION_LAXATIVE_DELETE);

try {
getModelService().executeChanges(WebMiscUtil.createDeltaCollection(delta), ModelExecuteOptions.createRaw(), task, r);
objectsDeleted++;

if (objectsDeleted % DELETE_LOG_INTERVAL == 0)
LOGGER.info("Deleted {} out of {} objects.", objectsDeleted, getObjectsToDelete());

r.recordSuccess();
} catch (Exception ex) {
r.computeStatus(getString("pageDebugList.message.singleUserDeleteProblem"));
LoggingUtils.logException(LOGGER, getString("pageDebugList.message.singleUserDeleteProblem"), ex);
}
parentResult.addSubresult(r);
}
return true;
}
};

try {
getModelService().searchObjectsIterative(UserType.class, null, userHandler, options, task, result);
} catch (Exception ex) {
result.computeStatus(getString("pageDebugList.message.laxativeProblem"));
LoggingUtils.logException(LOGGER, getString("pageDebugList.message.laxativeProblem"), ex);
}
}
private ObjectQuery createDeleteAllUsersQuery() {
InOidFilter inOid = InOidFilter.createInOid(SystemObjectsType.USER_ADMINISTRATOR.value());
NotFilter not = new NotFilter(inOid);

private void deleteAllOrgUnits(Task task, final OperationResult result, Collection<SelectorOptions<GetOperationOptions>> options){
try {
deleteObjectsAsync(OrgType.COMPLEX_TYPE, null, result);
} catch (Exception ex) {
result.computeStatus(getString("pageDebugList.message.laxativeProblem"));
LoggingUtils.logException(LOGGER, getString("pageDebugList.message.laxativeProblem"), ex);
}
return ObjectQuery.createObjectQuery(not);
}

private void deleteAllAccountShadows(Task task, final OperationResult result, Collection<SelectorOptions<GetOperationOptions>> options,
boolean deleteAccountShadows){
ResultHandler<ShadowType> shadowHandler = new ResultHandler<ShadowType>() {
private void deleteAllShadowsConfirmed(OperationResult result, boolean deleteAccountShadows)
throws ObjectAlreadyExistsException, ObjectNotFoundException, SchemaException {

@Override
public boolean handle(PrismObject object, OperationResult parentResult) {
ObjectDelta delta = ObjectDelta.createDeleteDelta(ShadowType.class, object.asObjectable().getOid(), getPrismContext());
Task task = createSimpleTask(OPERATION_LAXATIVE_DELETE);
OperationResult r = result.createMinorSubresult(OPERATION_LAXATIVE_DELETE);

try {
getModelService().executeChanges(WebMiscUtil.createDeltaCollection(delta), ModelExecuteOptions.createRaw(), task, r);
objectsDeleted++;

if (objectsDeleted % DELETE_LOG_INTERVAL == 0)
LOGGER.info("Deleted {} out of {} objects.", objectsDeleted, getObjectsToDelete());

r.recordSuccess();
} catch (Exception ex) {
r.computeStatus(getString("pageDebugList.message.singleShadowDeleteProblem"));
LoggingUtils.logException(LOGGER, getString("pageDebugList.message.singleShadowDeleteProblem"), ex);
}
parentResult.addSubresult(r);
return true;
}
};
ObjectFilter kind = EqualFilter.createEqual(ShadowType.F_KIND, ShadowType.class,
getPrismContext(), null, ShadowKindType.ACCOUNT);

try {
if(deleteAccountShadows){
ObjectFilter filter = EqualFilter.createEqual(ShadowType.F_KIND, ShadowType.class, getPrismContext(), null, ShadowKindType.ACCOUNT);
ObjectQuery query = ObjectQuery.createObjectQuery(filter);
getModelService().searchObjectsIterative(ShadowType.class, query, shadowHandler, options, task, result);
} else {
ObjectFilter filter = EqualFilter.createEqual(ShadowType.F_KIND, ShadowType.class, getPrismContext(), null, ShadowKindType.ACCOUNT);
ObjectQuery query = ObjectQuery.createObjectQuery(NotFilter.createNot(filter));
getModelService().searchObjectsIterative(ShadowType.class, query, shadowHandler, options, task, result);
}

} catch (Exception ex) {
result.computeStatus(getString("pageDebugList.message.laxativeProblem"));
LoggingUtils.logException(LOGGER, getString("pageDebugList.message.laxativeProblem"), ex);
ObjectQuery query;
if (deleteAccountShadows) {
query = ObjectQuery.createObjectQuery(kind);
} else {
query = ObjectQuery.createObjectQuery(NotFilter.createNot(kind));
}
}

private int getObjectsToDelete(){
DeleteAllDialog dialog = (DeleteAllDialog)get(ID_DELETE_ALL_DIALOG);
return dialog.getObjectsToDelete();
deleteObjectsAsync(ShadowType.COMPLEX_TYPE, query, true, result);
}

private void exportSelected(AjaxRequestTarget target, DebugObjectItem item) {
Expand Down Expand Up @@ -863,8 +782,30 @@ private void deleteAllIdentities(AjaxRequestTarget target) {
}

private void deleteAllTypeConfirmed(AjaxRequestTarget target) {
//todo implement [lazyman] as background task...
warn("Not implemented yet, will be implemented as background task.");
DebugSearchDto dto = searchModel.getObject();

LOGGER.debug("Deleting all of type {}", dto.getType());

OperationResult result = new OperationResult(OPERATION_DELETE_OBJECTS);
try {
ObjectQuery query = null;
if (ObjectTypes.USER.equals(dto.getType())) {
query = createDeleteAllUsersQuery();
}

QName type = dto.getType().getTypeQName();

deleteObjectsAsync(type, query, true, result);

info(getString("pageDebugList.messsage.deleteAllOfType", dto.getType()));
} catch (Exception ex) {
result.recomputeStatus();
result.recordFatalError("Couldn't delete objects of type " + dto.getType(), ex);

LoggingUtils.logException(LOGGER, "Couldn't delete objects of type " + dto.getType(), ex);
}

showResult(result);
target.add(getFeedbackPanel());
}

Expand All @@ -885,7 +826,7 @@ private void deleteSelectedConfirmed(AjaxRequestTarget target, List<DebugObjectI
target.add(getFeedbackPanel());
}

private void clearSearchPerformed(AjaxRequestTarget target){
private void clearSearchPerformed(AjaxRequestTarget target) {
DebugSearchDto dto = searchModel.getObject();
dto.setText(null);

Expand Down Expand Up @@ -921,12 +862,11 @@ private void deleteAllShadowsOnResourceConfirmed(AjaxRequestTarget target) {
try {
RefFilter ref = RefFilter.createReferenceEqual(ShadowType.F_RESOURCE_REF, ShadowType.class,
getPrismContext(), dto.getResource().getOid());
ObjectQuery objectQuery = new ObjectQuery();
objectQuery.setFilter(ref);
ObjectQuery objectQuery = ObjectQuery.createObjectQuery(ref);

QName type = ShadowType.COMPLEX_TYPE;

deleteObjectsAsync(type, objectQuery, result);
deleteObjectsAsync(type, objectQuery, true, result);

info(getString("pageDebugList.messsage.deleteAllShadowsStarted", dto.getResource().getName()));
} catch (Exception ex) {
Expand All @@ -940,7 +880,7 @@ private void deleteAllShadowsOnResourceConfirmed(AjaxRequestTarget target) {
target.add(getFeedbackPanel());
}

private void deleteObjectsAsync(QName type, ObjectQuery objectQuery, OperationResult result)
private void deleteObjectsAsync(QName type, ObjectQuery objectQuery, boolean raw, OperationResult result)
throws SchemaException, ObjectAlreadyExistsException, ObjectNotFoundException {

Task task = createSimpleTask(result.getOperation());
Expand All @@ -951,7 +891,7 @@ private void deleteObjectsAsync(QName type, ObjectQuery objectQuery, OperationRe
objectQuery = new ObjectQuery();
}

QueryType query = QueryJaxbConvertor.createQueryType(objectQuery, getPrismContext());;
QueryType query = QueryJaxbConvertor.createQueryType(objectQuery, getPrismContext());

PrismPropertyDefinition queryDef = new PrismPropertyDefinition(SchemaConstants.MODEL_EXTENSION_OBJECT_QUERY,
QueryType.COMPLEX_TYPE, getPrismContext());
Expand All @@ -965,6 +905,12 @@ private void deleteObjectsAsync(QName type, ObjectQuery objectQuery, OperationRe
typeProp.setRealValue(type);
task.setExtensionProperty(typeProp);

PrismPropertyDefinition rawDef = new PrismPropertyDefinition(SchemaConstants.MODEL_EXTENSION_OPTION_RAW,
DOMUtil.XSD_BOOLEAN, getPrismContext());
PrismProperty<QName> rawProp = rawDef.instantiate();
rawProp.setRealValue(raw);
task.setExtensionProperty(rawProp);

task.savePendingModifications(result);

TaskManager taskManager = getTaskManager();
Expand Down

0 comments on commit 8257789

Please sign in to comment.