You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@geode.apache.org by je...@apache.org on 2018/05/24 20:31:20 UTC
[geode] branch develop updated: GEODE-4858: Convert *DefinedIndex commands to use ResultModel and Sin… (#1983)
This is an automated email from the ASF dual-hosted git repository.
jensdeppe pushed a commit to branch develop
in repository https://gitbox.apache.org/repos/asf/geode.git
The following commit(s) were added to refs/heads/develop by this push:
new 71145b6 GEODE-4858: Convert *DefinedIndex commands to use ResultModel and Sin… (#1983)
71145b6 is described below
commit 71145b6f09efe5dbf8627a0525acef33777b8bed
Author: Jens Deppe <jd...@pivotal.io>
AuthorDate: Thu May 24 13:31:13 2018 -0700
GEODE-4858: Convert *DefinedIndex commands to use ResultModel and Sin… (#1983)
---
.../geode/cache/configuration/RegionConfig.java | 10 +-
.../org/apache/geode/cache/query/IndexType.java | 12 ++
.../cli/commands/ClearDefinedIndexesCommand.java | 11 +-
.../cli/commands/CreateDefinedIndexesCommand.java | 136 +++++-------------
.../internal/cli/commands/DefineIndexCommand.java | 22 +--
.../internal/cli/commands/IndexDefinition.java | 17 ++-
.../management/internal/cli/domain/IndexInfo.java | 115 ---------------
.../functions/CreateDefinedIndexesFunction.java | 106 ++++++--------
.../internal/cli/remote/CommandExecutor.java | 2 +-
.../internal/cli/result/model/ResultModel.java | 3 +
.../sanctioned-geode-core-serializables.txt | 3 +-
.../CreateDefinedIndexesCommandDUnitTest.java | 155 ++++++++++++++++-----
.../commands/CreateDefinedIndexesCommandTest.java | 60 +++-----
.../cli/commands/CreateJndiBindingCommandTest.java | 2 +-
.../commands/DestroyJndiBindingCommandTest.java | 2 +-
.../CreateDefinedIndexesFunctionTest.java | 85 ++++++-----
16 files changed, 326 insertions(+), 415 deletions(-)
diff --git a/geode-core/src/main/java/org/apache/geode/cache/configuration/RegionConfig.java b/geode-core/src/main/java/org/apache/geode/cache/configuration/RegionConfig.java
index 447e88f..8dbb387 100644
--- a/geode-core/src/main/java/org/apache/geode/cache/configuration/RegionConfig.java
+++ b/geode-core/src/main/java/org/apache/geode/cache/configuration/RegionConfig.java
@@ -681,18 +681,24 @@ public class RegionConfig implements CacheElement {
}
/**
- * Sets the value of the type property.
+ * Sets the value of the type property. Also sets the keyIndex property to true if the type
+ * being set is "key".
*
* allowed object is
* {@link String }
*
+ * @deprecated Index should only be a "key" or "range" type which is set using
+ * {@link #setKeyIndex(Boolean)}
*/
public void setType(String value) {
- if ("range".equalsIgnoreCase(value) || "hash".equalsIgnoreCase(value)) {
+ if ("range".equalsIgnoreCase(value) || "hash".equalsIgnoreCase(value)
+ || "key".equalsIgnoreCase(value)) {
this.type = value.toLowerCase();
} else {
throw new IllegalArgumentException("Invalid index type " + value);
}
+
+ setKeyIndex("key".equalsIgnoreCase(value));
}
@Override
diff --git a/geode-core/src/main/java/org/apache/geode/cache/query/IndexType.java b/geode-core/src/main/java/org/apache/geode/cache/query/IndexType.java
index 702eca7..ce90db8 100644
--- a/geode-core/src/main/java/org/apache/geode/cache/query/IndexType.java
+++ b/geode-core/src/main/java/org/apache/geode/cache/query/IndexType.java
@@ -84,4 +84,16 @@ public enum IndexType {
return name;
}
+ public static IndexType valueOfSynonym(String name) {
+ name = name.toUpperCase();
+
+ switch (name) {
+ case "KEY":
+ return valueOf("PRIMARY_KEY");
+ case "RANGE":
+ return valueOf("FUNCTIONAL");
+ }
+
+ return valueOf(name);
+ }
}
diff --git a/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/ClearDefinedIndexesCommand.java b/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/ClearDefinedIndexesCommand.java
index d36bcea..5c27bd3 100644
--- a/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/ClearDefinedIndexesCommand.java
+++ b/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/ClearDefinedIndexesCommand.java
@@ -18,10 +18,8 @@ package org.apache.geode.management.internal.cli.commands;
import org.springframework.shell.core.annotation.CliCommand;
import org.apache.geode.management.cli.CliMetaData;
-import org.apache.geode.management.cli.Result;
import org.apache.geode.management.internal.cli.i18n.CliStrings;
-import org.apache.geode.management.internal.cli.result.InfoResultData;
-import org.apache.geode.management.internal.cli.result.ResultBuilder;
+import org.apache.geode.management.internal.cli.result.model.ResultModel;
import org.apache.geode.management.internal.security.ResourceOperation;
import org.apache.geode.security.ResourcePermission;
@@ -30,11 +28,8 @@ public class ClearDefinedIndexesCommand extends InternalGfshCommand {
@CliMetaData(relatedTopic = {CliStrings.TOPIC_GEODE_REGION, CliStrings.TOPIC_GEODE_DATA})
@ResourceOperation(resource = ResourcePermission.Resource.CLUSTER,
operation = ResourcePermission.Operation.MANAGE, target = ResourcePermission.Target.QUERY)
- // TODO : Add optionContext for indexName
- public Result clearDefinedIndexes() {
+ public ResultModel clearDefinedIndexes() {
IndexDefinition.indexDefinitions.clear();
- InfoResultData infoResult = ResultBuilder.createInfoResultData();
- infoResult.addLine(CliStrings.CLEAR_DEFINED_INDEX__SUCCESS__MSG);
- return ResultBuilder.buildResult(infoResult);
+ return ResultModel.createInfo(CliStrings.CLEAR_DEFINED_INDEX__SUCCESS__MSG);
}
}
diff --git a/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommand.java b/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommand.java
index dd00505..10816bd 100644
--- a/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommand.java
+++ b/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommand.java
@@ -15,33 +15,27 @@
package org.apache.geode.management.internal.cli.commands;
-import java.util.ArrayList;
-import java.util.HashMap;
import java.util.List;
-import java.util.Map;
import java.util.Set;
-import java.util.TreeSet;
import org.springframework.shell.core.annotation.CliCommand;
import org.springframework.shell.core.annotation.CliOption;
-import org.apache.geode.cache.execute.ResultCollector;
+import org.apache.geode.cache.configuration.CacheConfig;
+import org.apache.geode.cache.configuration.RegionConfig;
import org.apache.geode.distributed.DistributedMember;
-import org.apache.geode.distributed.internal.InternalConfigurationPersistenceService;
import org.apache.geode.management.cli.CliMetaData;
import org.apache.geode.management.cli.ConverterHint;
-import org.apache.geode.management.cli.Result;
+import org.apache.geode.management.cli.SingleGfshCommand;
import org.apache.geode.management.internal.cli.functions.CliFunctionResult;
import org.apache.geode.management.internal.cli.functions.CreateDefinedIndexesFunction;
import org.apache.geode.management.internal.cli.i18n.CliStrings;
-import org.apache.geode.management.internal.cli.result.ErrorResultData;
-import org.apache.geode.management.internal.cli.result.InfoResultData;
-import org.apache.geode.management.internal.cli.result.ResultBuilder;
-import org.apache.geode.management.internal.configuration.domain.XmlEntity;
+import org.apache.geode.management.internal.cli.result.model.ResultModel;
import org.apache.geode.management.internal.security.ResourceOperation;
import org.apache.geode.security.ResourcePermission;
-public class CreateDefinedIndexesCommand extends InternalGfshCommand {
+public class CreateDefinedIndexesCommand extends SingleGfshCommand {
+ public static final String CREATE_DEFINED_INDEXES_SECTION = "create-defined-indexes";
private static final CreateDefinedIndexesFunction createDefinedIndexesFunction =
new CreateDefinedIndexesFunction();
@@ -49,8 +43,7 @@ public class CreateDefinedIndexesCommand extends InternalGfshCommand {
@CliMetaData(relatedTopic = {CliStrings.TOPIC_GEODE_REGION, CliStrings.TOPIC_GEODE_DATA})
@ResourceOperation(resource = ResourcePermission.Resource.CLUSTER,
operation = ResourcePermission.Operation.MANAGE, target = ResourcePermission.Target.QUERY)
- // TODO : Add optionContext for indexName
- public Result createDefinedIndexes(
+ public ResultModel createDefinedIndexes(
@CliOption(key = {CliStrings.MEMBER, CliStrings.MEMBERS},
optionContext = ConverterHint.MEMBERIDNAME,
@@ -58,106 +51,41 @@ public class CreateDefinedIndexesCommand extends InternalGfshCommand {
@CliOption(key = {CliStrings.GROUP, CliStrings.GROUPS},
optionContext = ConverterHint.MEMBERGROUP,
- help = CliStrings.CREATE_DEFINED_INDEXES__GROUP__HELP) final String[] group) {
+ help = CliStrings.CREATE_DEFINED_INDEXES__GROUP__HELP) final String[] groups) {
- Result result;
- List<XmlEntity> xmlEntities = new ArrayList<>();
+ ResultModel result = new ResultModel();
if (IndexDefinition.indexDefinitions.isEmpty()) {
- final InfoResultData infoResult = ResultBuilder.createInfoResultData();
- infoResult.addLine(CliStrings.DEFINE_INDEX__FAILURE__MSG);
- return ResultBuilder.buildResult(infoResult);
+ return ResultModel.createInfo(CliStrings.DEFINE_INDEX__FAILURE__MSG);
}
- try {
- final Set<DistributedMember> targetMembers = findMembers(group, memberNameOrID);
+ Set<DistributedMember> targetMembers = findMembers(groups, memberNameOrID);
+ if (targetMembers.isEmpty()) {
+ return ResultModel.createError(CliStrings.NO_MEMBERS_FOUND_MESSAGE);
+ }
- if (targetMembers.isEmpty()) {
- return ResultBuilder.createUserErrorResult(CliStrings.NO_MEMBERS_FOUND_MESSAGE);
- }
+ List<CliFunctionResult> functionResults = executeAndGetFunctionResult(
+ createDefinedIndexesFunction, IndexDefinition.indexDefinitions, targetMembers);
+ result.addTableAndSetStatus(CREATE_DEFINED_INDEXES_SECTION, functionResults, false);
+ result.setConfigObject(IndexDefinition.indexDefinitions);
- final ResultCollector<?, ?> rc = executeFunction(createDefinedIndexesFunction,
- IndexDefinition.indexDefinitions, targetMembers);
-
- final List<Object> funcResults = (List<Object>) rc.getResult();
- final Set<String> successfulMembers = new TreeSet<>();
- final Map<String, Set<String>> indexOpFailMap = new HashMap<>();
-
- for (final Object funcResult : funcResults) {
- if (funcResult instanceof CliFunctionResult) {
- final CliFunctionResult cliFunctionResult = (CliFunctionResult) funcResult;
-
- if (cliFunctionResult.isSuccessful()) {
- successfulMembers.add(cliFunctionResult.getMemberIdOrName());
-
- // Only add the XmlEntity if it wasn't previously added from the result of another
- // successful member.
- XmlEntity resultEntity = cliFunctionResult.getXmlEntity();
- if ((null != resultEntity) && (!xmlEntities.contains(resultEntity))) {
- xmlEntities.add(cliFunctionResult.getXmlEntity());
- }
- } else {
- final String exceptionMessage = cliFunctionResult.getMessage();
- Set<String> failedMembers = indexOpFailMap.get(exceptionMessage);
-
- if (failedMembers == null) {
- failedMembers = new TreeSet<>();
- }
-
- failedMembers.add(cliFunctionResult.getMemberIdOrName());
- indexOpFailMap.put(exceptionMessage, failedMembers);
- }
- }
- }
+ return result;
+ }
- // TODO: GEODE-3916.
- // The index creation might succeed in some members and fail in others, the current logic only
- // reports to the user the members on which the operation was successful, giving no details
- // about the failures. We should report the exact details of what failed/succeeded, and
- // where/why.
- if (!successfulMembers.isEmpty()) {
- final InfoResultData infoResult = ResultBuilder.createInfoResultData();
- infoResult.addLine(CliStrings.CREATE_DEFINED_INDEXES__SUCCESS__MSG);
-
- int num = 0;
-
- for (final String memberId : successfulMembers) {
- ++num;
- infoResult.addLine(CliStrings
- .format(CliStrings.CREATE_DEFINED_INDEXES__NUMBER__AND__MEMBER, num, memberId));
- }
- result = ResultBuilder.buildResult(infoResult);
-
- } else {
- // Group members by the exception thrown.
- final ErrorResultData erd = ResultBuilder.createErrorResultData();
-
- final Set<String> exceptionMessages = indexOpFailMap.keySet();
-
- for (final String exceptionMessage : exceptionMessages) {
- erd.addLine(exceptionMessage);
- erd.addLine(CliStrings.CREATE_INDEX__EXCEPTION__OCCURRED__ON);
- final Set<String> memberIds = indexOpFailMap.get(exceptionMessage);
-
- int num = 0;
- for (final String memberId : memberIds) {
- ++num;
- erd.addLine(CliStrings.format(CliStrings.CREATE_DEFINED_INDEXES__NUMBER__AND__MEMBER,
- num, memberId));
- }
- }
- result = ResultBuilder.buildResult(erd);
- }
- } catch (Exception e) {
- result = ResultBuilder.createGemFireErrorResult(e.getMessage());
+ @Override
+ public void updateClusterConfig(String group, CacheConfig config, Object configObject) {
+ Set<RegionConfig.Index> updatedIndexes = (Set<RegionConfig.Index>) configObject;
+ if (updatedIndexes == null) {
+ return;
}
- for (XmlEntity xmlEntity : xmlEntities) {
- persistClusterConfiguration(result,
- () -> ((InternalConfigurationPersistenceService) getConfigurationPersistenceService())
- .addXmlEntity(xmlEntity, group));
- }
+ for (RegionConfig.Index index : updatedIndexes) {
+ RegionConfig region = config.findRegionConfiguration(index.getFromClause());
+ if (region == null) {
+ throw new IllegalStateException("RegionConfig is null");
+ }
- return result;
+ region.getIndexes().add(index);
+ }
}
}
diff --git a/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/DefineIndexCommand.java b/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/DefineIndexCommand.java
index 9437278..71782f3 100644
--- a/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/DefineIndexCommand.java
+++ b/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/DefineIndexCommand.java
@@ -18,24 +18,22 @@ package org.apache.geode.management.internal.cli.commands;
import org.springframework.shell.core.annotation.CliCommand;
import org.springframework.shell.core.annotation.CliOption;
+import org.apache.geode.cache.configuration.RegionConfig;
import org.apache.geode.cache.query.IndexType;
import org.apache.geode.management.cli.CliMetaData;
import org.apache.geode.management.cli.ConverterHint;
-import org.apache.geode.management.cli.Result;
-import org.apache.geode.management.internal.cli.domain.IndexInfo;
import org.apache.geode.management.internal.cli.i18n.CliStrings;
-import org.apache.geode.management.internal.cli.result.InfoResultData;
-import org.apache.geode.management.internal.cli.result.ResultBuilder;
+import org.apache.geode.management.internal.cli.result.model.InfoResultModel;
+import org.apache.geode.management.internal.cli.result.model.ResultModel;
import org.apache.geode.management.internal.security.ResourceOperation;
import org.apache.geode.security.ResourcePermission;
public class DefineIndexCommand extends InternalGfshCommand {
@CliCommand(value = CliStrings.DEFINE_INDEX, help = CliStrings.DEFINE_INDEX__HELP)
@CliMetaData(relatedTopic = {CliStrings.TOPIC_GEODE_REGION, CliStrings.TOPIC_GEODE_DATA})
- // TODO : Add optionContext for indexName
@ResourceOperation(resource = ResourcePermission.Resource.CLUSTER,
operation = ResourcePermission.Operation.MANAGE, target = ResourcePermission.Target.QUERY)
- public Result defineIndex(
+ public ResultModel defineIndex(
@CliOption(key = CliStrings.DEFINE_INDEX_NAME, mandatory = true,
help = CliStrings.DEFINE_INDEX__HELP) final String indexName,
@CliOption(key = CliStrings.DEFINE_INDEX__EXPRESSION, mandatory = true,
@@ -47,18 +45,22 @@ public class DefineIndexCommand extends InternalGfshCommand {
optionContext = ConverterHint.INDEX_TYPE,
help = CliStrings.DEFINE_INDEX__TYPE__HELP) final IndexType indexType) {
- Result result;
+ ResultModel result = new ResultModel();
+
+ RegionConfig.Index indexInfo = new RegionConfig.Index();
+ indexInfo.setName(indexName);
+ indexInfo.setExpression(indexedExpression);
+ indexInfo.setFromClause(regionPath);
+ indexInfo.setType(indexType.getName());
- IndexInfo indexInfo = new IndexInfo(indexName, indexedExpression, regionPath, indexType);
IndexDefinition.indexDefinitions.add(indexInfo);
- final InfoResultData infoResult = ResultBuilder.createInfoResultData();
+ InfoResultModel infoResult = result.addInfo();
infoResult.addLine(CliStrings.DEFINE_INDEX__SUCCESS__MSG);
infoResult.addLine(CliStrings.format(CliStrings.DEFINE_INDEX__NAME__MSG, indexName));
infoResult
.addLine(CliStrings.format(CliStrings.DEFINE_INDEX__EXPRESSION__MSG, indexedExpression));
infoResult.addLine(CliStrings.format(CliStrings.DEFINE_INDEX__REGIONPATH__MSG, regionPath));
- result = ResultBuilder.buildResult(infoResult);
return result;
}
diff --git a/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/IndexDefinition.java b/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/IndexDefinition.java
index 2cf9f83..1f607c5 100644
--- a/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/IndexDefinition.java
+++ b/geode-core/src/main/java/org/apache/geode/management/internal/cli/commands/IndexDefinition.java
@@ -19,9 +19,20 @@ import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
-import org.apache.geode.management.internal.cli.domain.IndexInfo;
+import org.apache.geode.cache.configuration.RegionConfig;
+import org.apache.geode.cache.query.IndexType;
class IndexDefinition {
- static final Set<IndexInfo> indexDefinitions =
- Collections.synchronizedSet(new HashSet<IndexInfo>());
+ static final Set<RegionConfig.Index> indexDefinitions =
+ Collections.synchronizedSet(new HashSet<>());
+
+ static void addIndex(String name, String expression, String fromClause, IndexType type) {
+ RegionConfig.Index index = new RegionConfig.Index();
+ index.setName(name);
+ index.setFromClause(fromClause);
+ index.setType(type.getName());
+ index.setExpression(expression);
+ indexDefinitions.add(index);
+
+ }
}
diff --git a/geode-core/src/main/java/org/apache/geode/management/internal/cli/domain/IndexInfo.java b/geode-core/src/main/java/org/apache/geode/management/internal/cli/domain/IndexInfo.java
deleted file mode 100644
index e353164..0000000
--- a/geode-core/src/main/java/org/apache/geode/management/internal/cli/domain/IndexInfo.java
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one or more contributor license
- * agreements. See the NOTICE file distributed with this work for additional information regarding
- * copyright ownership. The ASF licenses this file to You under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance with the License. You may obtain a
- * copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software distributed under the License
- * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
- * or implied. See the License for the specific language governing permissions and limitations under
- * the License.
- */
-package org.apache.geode.management.internal.cli.domain;
-
-import java.io.Serializable;
-
-import org.apache.geode.cache.query.IndexType;
-
-/***
- * Data class used to pass index related information to functions that create or destroy indexes
- *
- */
-public class IndexInfo implements Serializable {
-
- private static final long serialVersionUID = 1L;
-
- private String indexName;
- private String indexedExpression = null;
- private String regionPath = null;
- private IndexType indexType = IndexType.FUNCTIONAL;
- private boolean ifExists;
-
- public IndexInfo(String indexName) {
- this.indexName = indexName;
- }
-
- /***
- * Used for passing index information for destroying index.
- *
- */
- public IndexInfo(String indexName, String regionPath) {
- this.indexName = indexName;
- this.regionPath = regionPath;
- }
-
- public IndexInfo(String indexName, String indexedExpression, String regionPath) {
- this.indexName = indexName;
- this.indexedExpression = indexedExpression;
- this.regionPath = regionPath;
- }
-
- public IndexInfo(String indexName, String indexedExpression, String regionPath,
- IndexType indexType) {
- this.indexName = indexName;
- this.indexedExpression = indexedExpression;
- this.regionPath = regionPath;
- this.indexType = indexType;
- }
-
- public String getIndexName() {
- return indexName;
- }
-
- public void setIndexName(String indexName) {
- this.indexName = indexName;
- }
-
- public String getIndexedExpression() {
- return indexedExpression;
- }
-
- public void setIndexedExpression(String indexedExpression) {
- this.indexedExpression = indexedExpression;
- }
-
- public String getRegionPath() {
- return this.regionPath;
- }
-
- public void setRegionPath(String regionPath) {
- this.regionPath = regionPath;
- }
-
- public IndexType getIndexType() {
- return indexType;
- }
-
- public void setIndexType(IndexType indexType) {
- this.indexType = indexType;
- }
-
- public boolean isIfExists() {
- return ifExists;
- }
-
- public void setIfExists(boolean ifExists) {
- this.ifExists = ifExists;
- }
-
- public String toString() {
- StringBuffer sb = new StringBuffer();
- sb.append("Index Name : ");
- sb.append(this.indexName);
- sb.append("\nIndexed Expression : ");
- sb.append(this.indexedExpression);
- sb.append("\nRegion Path : ");
- sb.append(this.regionPath);
- sb.append("\nIndex Type : ");
- sb.append(this.indexType.getName());
- return sb.toString();
- }
-
-}
diff --git a/geode-core/src/main/java/org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunction.java b/geode-core/src/main/java/org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunction.java
index 12d5c33..f98e46f 100644
--- a/geode-core/src/main/java/org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunction.java
+++ b/geode-core/src/main/java/org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunction.java
@@ -15,12 +15,13 @@
package org.apache.geode.management.internal.cli.functions;
import java.util.ArrayList;
-import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;
+import java.util.stream.Collectors;
import org.apache.geode.cache.Cache;
+import org.apache.geode.cache.configuration.RegionConfig;
import org.apache.geode.cache.execute.FunctionContext;
import org.apache.geode.cache.execute.ResultSender;
import org.apache.geode.cache.query.Index;
@@ -28,44 +29,35 @@ import org.apache.geode.cache.query.IndexType;
import org.apache.geode.cache.query.MultiIndexCreationException;
import org.apache.geode.cache.query.QueryService;
import org.apache.geode.internal.cache.execute.InternalFunction;
-import org.apache.geode.internal.cache.xmlcache.CacheXml;
-import org.apache.geode.management.internal.cli.domain.IndexInfo;
import org.apache.geode.management.internal.cli.i18n.CliStrings;
-import org.apache.geode.management.internal.configuration.domain.XmlEntity;
-public class CreateDefinedIndexesFunction implements InternalFunction {
- private static final long serialVersionUID = 1L;
+public class CreateDefinedIndexesFunction implements InternalFunction<Set<RegionConfig.Index>> {
+
+ private static final long serialVersionUID = 6756381106602823693L;
@Override
public String getId() {
return CreateDefinedIndexesFunction.class.getName();
}
- XmlEntity createXmlEntity(final String regionName) {
- return new XmlEntity(CacheXml.REGION, "name", regionName);
- }
-
@Override
- public void execute(FunctionContext context) {
- Cache cache;
- String memberId = null;
- boolean lastResultSent = Boolean.FALSE;
+ public void execute(FunctionContext<Set<RegionConfig.Index>> context) {
+ Cache cache = context.getCache();
+ QueryService queryService = cache.getQueryService();
+ ResultSender<CliFunctionResult> sender = context.getResultSender();
+ String memberId = cache.getDistributedSystem().getDistributedMember().getId();
+ Set<RegionConfig.Index> indexDefinitions = context.getArguments();
try {
- cache = context.getCache();
- ResultSender sender = context.getResultSender();
- QueryService queryService = cache.getQueryService();
- memberId = cache.getDistributedSystem().getDistributedMember().getId();
- Set<IndexInfo> indexDefinitions = (Set<IndexInfo>) context.getArguments();
-
- for (IndexInfo indexDefinition : indexDefinitions) {
- String indexName = indexDefinition.getIndexName();
- String regionPath = indexDefinition.getRegionPath();
- String indexedExpression = indexDefinition.getIndexedExpression();
+ for (RegionConfig.Index indexDefinition : indexDefinitions) {
+ String indexName = indexDefinition.getName();
+ String regionPath = indexDefinition.getFromClause();
+ String indexedExpression = indexDefinition.getExpression();
+ IndexType indexType = IndexType.valueOfSynonym(indexDefinition.getType());
- if (indexDefinition.getIndexType() == IndexType.PRIMARY_KEY) {
+ if (indexType == IndexType.PRIMARY_KEY) {
queryService.defineKeyIndex(indexName, indexedExpression, regionPath);
- } else if (indexDefinition.getIndexType() == IndexType.HASH) {
+ } else if (indexType == IndexType.HASH) {
queryService.defineHashIndex(indexName, indexedExpression, regionPath);
} else {
queryService.defineIndex(indexName, indexedExpression, regionPath);
@@ -73,52 +65,40 @@ public class CreateDefinedIndexesFunction implements InternalFunction {
}
List<Index> indexes = queryService.createDefinedIndexes();
- // Build the results with one XmlEntity per region.
- List<String> processedRegions = new ArrayList<>();
- List<CliFunctionResult> functionResults = new ArrayList<>();
- for (Index index : indexes) {
- String regionName = index.getRegion().getName();
-
- if (!processedRegions.contains(regionName)) {
- XmlEntity xmlEntity = createXmlEntity(regionName);
- functionResults.add(new CliFunctionResult(memberId, xmlEntity));
- processedRegions.add(regionName);
+ if (!indexes.isEmpty()) {
+ for (Index index : indexes) {
+ sender.sendResult(
+ new CliFunctionResult(memberId, true, "Created index " + index.getName()));
}
+ } else {
+ sender.sendResult(
+ new CliFunctionResult(memberId, true, CliStrings.DEFINE_INDEX__FAILURE__MSG));
}
- for (Iterator<CliFunctionResult> iterator = functionResults.iterator(); iterator.hasNext();) {
- CliFunctionResult cliFunctionResult = iterator.next();
+ } catch (MultiIndexCreationException multiIndexCreationException) {
+ // Some indexes may have been created, so let's get those
+ List<String> failedIndexes =
+ new ArrayList<>(multiIndexCreationException.getFailedIndexNames());
+ List<String> createdIndexes =
+ indexDefinitions.stream().filter(i -> !failedIndexes.contains(i.getName()))
+ .map(RegionConfig.Index::getName).collect(Collectors.toList());
- if (iterator.hasNext()) {
- sender.sendResult(cliFunctionResult);
- } else {
- sender.lastResult(cliFunctionResult);
- lastResultSent = Boolean.TRUE;
- }
+ for (String index : createdIndexes) {
+ sender.sendResult(new CliFunctionResult(memberId, true, "Created index " + index));
}
- if (!lastResultSent) {
- // No indexes were created and no exceptions were thrown during the process.
- // We still need to make sure the function returns to the caller.
- sender.lastResult(
- new CliFunctionResult(memberId, true, CliStrings.DEFINE_INDEX__FAILURE__MSG));
- }
- } catch (MultiIndexCreationException multiIndexCreationException) {
- StringBuffer sb = new StringBuffer();
- sb.append("Index creation failed for indexes: ").append("\n");
- for (Map.Entry<String, Exception> failedIndex : multiIndexCreationException.getExceptionsMap()
+ for (Map.Entry<String, Exception> ex : multiIndexCreationException.getExceptionsMap()
.entrySet()) {
- sb.append(failedIndex.getKey()).append(" : ").append(failedIndex.getValue().getMessage())
- .append("\n");
+ sender.sendResult(new CliFunctionResult(memberId, false, String
+ .format("Failed to create index %s: %s", ex.getKey(), ex.getValue().getMessage())));
}
- context.getResultSender()
- .lastResult(new CliFunctionResult(memberId, multiIndexCreationException, sb.toString()));
- } catch (Exception exception) {
- String exceptionMessage = CliStrings.format(CliStrings.EXCEPTION_CLASS_AND_MESSAGE,
- exception.getClass().getName(), exception.getMessage());
- context.getResultSender()
- .lastResult(new CliFunctionResult(memberId, exception, exceptionMessage));
+ } catch (Exception ex) {
+ sender.sendResult(new CliFunctionResult(memberId, false, ex.getMessage()));
+ } finally {
+ queryService.clearDefinedIndexes();
}
+
+ sender.lastResult(null);
}
}
diff --git a/geode-core/src/main/java/org/apache/geode/management/internal/cli/remote/CommandExecutor.java b/geode-core/src/main/java/org/apache/geode/management/internal/cli/remote/CommandExecutor.java
index 9b3208b..ace6a86 100755
--- a/geode-core/src/main/java/org/apache/geode/management/internal/cli/remote/CommandExecutor.java
+++ b/geode-core/src/main/java/org/apache/geode/management/internal/cli/remote/CommandExecutor.java
@@ -140,7 +140,7 @@ public class CommandExecutor {
try {
gfshCommand.updateClusterConfig(group, cc, resultModel.getConfigObject());
infoResultModel
- .addLine("Changes to configuration for group '" + group + "' is persisted.");
+ .addLine("Changes to configuration for group '" + group + "' are persisted.");
} catch (Exception e) {
String message = "failed to update cluster config for " + group;
logger.error(message, e);
diff --git a/geode-core/src/main/java/org/apache/geode/management/internal/cli/result/model/ResultModel.java b/geode-core/src/main/java/org/apache/geode/management/internal/cli/result/model/ResultModel.java
index a7059d9..573d5d9 100644
--- a/geode-core/src/main/java/org/apache/geode/management/internal/cli/result/model/ResultModel.java
+++ b/geode-core/src/main/java/org/apache/geode/management/internal/cli/result/model/ResultModel.java
@@ -214,6 +214,9 @@ public class ResultModel {
boolean atLeastOneSuccess = false;
section.setColumnHeader("Member", "Status", "Message");
for (CliFunctionResult functionResult : functionResults) {
+ if (functionResult == null) {
+ continue;
+ }
section.addRow(functionResult.getMemberIdOrName(), functionResult.getStatus(skipIgnored),
functionResult.getStatusMessage());
if (functionResult.isSuccessful()) {
diff --git a/geode-core/src/main/resources/org/apache/geode/internal/sanctioned-geode-core-serializables.txt b/geode-core/src/main/resources/org/apache/geode/internal/sanctioned-geode-core-serializables.txt
index 1d89eb0..623d59f 100644
--- a/geode-core/src/main/resources/org/apache/geode/internal/sanctioned-geode-core-serializables.txt
+++ b/geode-core/src/main/resources/org/apache/geode/internal/sanctioned-geode-core-serializables.txt
@@ -511,7 +511,6 @@ org/apache/geode/management/internal/cli/domain/EvictionAttributesInfo,true,1,ev
org/apache/geode/management/internal/cli/domain/FixedPartitionAttributesInfo,true,1,isPrimary:boolean,numBuckets:int,partitionName:java/lang/String
org/apache/geode/management/internal/cli/domain/IndexDetails,true,-2198907141534201288,fromClause:java/lang/String,indexName:java/lang/String,indexStatisticsDetails:org/apache/geode/management/internal/cli/domain/IndexDetails$IndexStatisticsDetails,indexType:org/apache/geode/cache/query/IndexType,indexedExpression:java/lang/String,isValid:boolean,memberId:java/lang/String,memberName:java/lang/String,projectionAttributes:java/lang/String,regionName:java/lang/String,regionPath:java/lang/String
org/apache/geode/management/internal/cli/domain/IndexDetails$IndexStatisticsDetails,false,numberOfKeys:java/lang/Long,numberOfUpdates:java/lang/Long,numberOfValues:java/lang/Long,totalUpdateTime:java/lang/Long,totalUses:java/lang/Long
-org/apache/geode/management/internal/cli/domain/IndexInfo,true,1,ifExists:boolean,indexName:java/lang/String,indexType:org/apache/geode/cache/query/IndexType,indexedExpression:java/lang/String,regionPath:java/lang/String
org/apache/geode/management/internal/cli/domain/MemberConfigurationInfo,false,cacheAttributes:java/util/Map,cacheServerAttributes:java/util/List,gfePropsRuntime:java/util/Map,gfePropsSetFromFile:java/util/Map,gfePropsSetUsingApi:java/util/Map,gfePropsSetWithDefaults:java/util/Map,jvmInputArguments:java/util/List,pdxAttributes:java/util/Map,systemProperties:java/util/Properties
org/apache/geode/management/internal/cli/domain/MemberInformation,true,1,cacheServerList:java/util/List,cacheXmlFilePath:java/lang/String,clientCount:int,cpuUsage:double,groups:java/lang/String,heapUsage:java/lang/String,host:java/lang/String,hostedRegions:java/util/Set,id:java/lang/String,initHeapSize:java/lang/String,isServer:boolean,locatorBindAddress:java/lang/String,locatorPort:int,locators:java/lang/String,logFilePath:java/lang/String,maxHeapSize:java/lang/String,name:java/lang/Str [...]
org/apache/geode/management/internal/cli/domain/MemberResult,true,1,errorMessage:java/lang/String,exceptionMessage:java/lang/String,isSuccessful:boolean,memberNameOrId:java/lang/String,opPossible:boolean,successMessage:java/lang/String
@@ -533,7 +532,7 @@ org/apache/geode/management/internal/cli/functions/CloseDurableCqFunction,true,1
org/apache/geode/management/internal/cli/functions/ContinuousQueryFunction,true,1
org/apache/geode/management/internal/cli/functions/ContinuousQueryFunction$ClientInfo,true,1,isDurable:java/lang/String,primaryServer:java/lang/String,secondaryServer:java/lang/String,this$0:org/apache/geode/management/internal/cli/functions/ContinuousQueryFunction
org/apache/geode/management/internal/cli/functions/CreateAsyncEventQueueFunction,true,1
-org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunction,true,1
+org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunction,true,6756381106602823693
org/apache/geode/management/internal/cli/functions/CreateDiskStoreFunction,true,1
org/apache/geode/management/internal/cli/functions/CreateIndexFunction,true,1
org/apache/geode/management/internal/cli/functions/CreateJndiBindingFunction,false
diff --git a/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommandDUnitTest.java b/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommandDUnitTest.java
index a606a87..77f6fa1 100644
--- a/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommandDUnitTest.java
+++ b/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommandDUnitTest.java
@@ -17,7 +17,13 @@ package org.apache.geode.management.internal.cli.commands;
import static org.assertj.core.api.Assertions.assertThat;
+import java.util.List;
+import java.util.Map;
+import java.util.stream.Collectors;
+
import org.junit.Before;
+import org.junit.BeforeClass;
+import org.junit.ClassRule;
import org.junit.Rule;
import org.junit.Test;
import org.junit.experimental.categories.Category;
@@ -25,10 +31,14 @@ import org.junit.rules.TestName;
import org.apache.geode.cache.Cache;
import org.apache.geode.cache.Region;
+import org.apache.geode.cache.configuration.RegionConfig;
+import org.apache.geode.cache.query.Index;
import org.apache.geode.cache.query.QueryService;
import org.apache.geode.distributed.Locator;
import org.apache.geode.distributed.internal.InternalConfigurationPersistenceService;
import org.apache.geode.distributed.internal.InternalLocator;
+import org.apache.geode.management.cli.Result;
+import org.apache.geode.management.internal.cli.result.CommandResult;
import org.apache.geode.test.dunit.rules.ClusterStartupRule;
import org.apache.geode.test.dunit.rules.MemberVM;
import org.apache.geode.test.junit.categories.DistributedTest;
@@ -39,25 +49,29 @@ import org.apache.geode.test.junit.rules.serializable.SerializableTestName;
@Category({DistributedTest.class, OQLIndexTest.class})
public class CreateDefinedIndexesCommandDUnitTest {
- private MemberVM locator, server1, server2, server3;
+ private static MemberVM locator, server1, server2, server3;
- @Rule
- public GfshCommandRule gfsh = new GfshCommandRule();
+ @ClassRule
+ public static GfshCommandRule gfsh = new GfshCommandRule();
- @Rule
- public ClusterStartupRule clusterStartupRule = new ClusterStartupRule();
+ @ClassRule
+ public static ClusterStartupRule clusterStartupRule = new ClusterStartupRule();
@Rule
public TestName testName = new SerializableTestName();
- @Before
- public void before() throws Exception {
+ @BeforeClass
+ public static void beforeClass() throws Exception {
locator = clusterStartupRule.startLocatorVM(0);
- server1 = clusterStartupRule.startServerVM(1, locator.getPort());
- server2 = clusterStartupRule.startServerVM(2, locator.getPort());
- server3 = clusterStartupRule.startServerVM(3, "group1", locator.getPort());
+ server1 = clusterStartupRule.startServerVM(1, "group1", locator.getPort());
+ server2 = clusterStartupRule.startServerVM(2, "group1", locator.getPort());
+ server3 = clusterStartupRule.startServerVM(3, "group2", locator.getPort());
gfsh.connectAndVerify(locator);
+ }
+
+ @Before
+ public void before() {
gfsh.executeAndAssertThat("clear defined indexes").statusIsSuccess()
.containsOutput("Index definitions successfully cleared");
}
@@ -77,18 +91,24 @@ public class CreateDefinedIndexesCommandDUnitTest {
assertThat(cache.getRegion(regionName)).isNull();
}, server1, server2, server3);
+ String indexName = "index_" + regionName;
gfsh.executeAndAssertThat("define index --name=index_" + regionName
+ " --expression=value1 --region=" + regionName + "1").statusIsSuccess()
.containsOutput("Index successfully defined");
- gfsh.executeAndAssertThat("create defined indexes").statusIsError()
- .containsOutput("RegionNotFoundException");
+ CommandResult result = gfsh.executeCommand("create defined indexes");
+ assertThat(result.getStatus()).isEqualTo(Result.Status.ERROR);
+ Map<String, List<String>> table =
+ result.getMapFromTableContent(CreateDefinedIndexesCommand.CREATE_DEFINED_INDEXES_SECTION);
+ assertThat(table.get("Status")).contains("ERROR", "ERROR", "ERROR");
VMProvider.invokeInEveryMember(() -> {
Cache cache = ClusterStartupRule.getCache();
QueryService queryService = cache.getQueryService();
- assertThat(queryService.getIndexes().isEmpty()).isTrue();
+ List<String> currentIndexes =
+ queryService.getIndexes().stream().map(Index::getName).collect(Collectors.toList());
+ assertThat(currentIndexes).doesNotContain(indexName);
}, server1, server2, server3);
}
@@ -123,8 +143,13 @@ public class CreateDefinedIndexesCommandDUnitTest {
"define index --name=" + index2Name + " --expression=value2 --region=" + region2Name)
.statusIsSuccess().containsOutput("Index successfully defined");
- gfsh.executeAndAssertThat("create defined indexes").statusIsSuccess()
- .containsOutput("Indexes successfully created");
+ CommandResult result = gfsh.executeCommand("create defined indexes");
+ assertThat(result.getStatus()).isEqualTo(Result.Status.OK);
+ Map<String, List<String>> table =
+ result.getMapFromTableContent(CreateDefinedIndexesCommand.CREATE_DEFINED_INDEXES_SECTION);
+ assertThat(table.get("Member").size()).isEqualTo(6);
+ assertThat(result.getMessageFromContent())
+ .contains("Changes to configuration for group 'cluster' are persisted");
VMProvider.invokeInEveryMember(() -> {
Cache cache = ClusterStartupRule.getCache();
@@ -142,9 +167,15 @@ public class CreateDefinedIndexesCommandDUnitTest {
// Make sure the indexes exist in the cluster config
InternalConfigurationPersistenceService sharedConfig =
((InternalLocator) Locator.getLocator()).getConfigurationPersistenceService();
- assertThat(sharedConfig.getConfiguration("cluster").getCacheXmlContent()).contains(index1Name,
- index2Name);
- assertThat(sharedConfig.getConfiguration("group1")).isNull();
+ RegionConfig region1Config =
+ sharedConfig.getCacheConfig("cluster").findRegionConfiguration(region1Name);
+ assertThat(region1Config.getIndexes().stream().map(RegionConfig.Index::getName)
+ .collect(Collectors.toList())).contains(index1Name);
+
+ RegionConfig region2Config =
+ sharedConfig.getCacheConfig("cluster").findRegionConfiguration(region2Name);
+ assertThat(region2Config.getIndexes().stream().map(RegionConfig.Index::getName)
+ .collect(Collectors.toList())).contains(index2Name);
});
}
@@ -155,27 +186,29 @@ public class CreateDefinedIndexesCommandDUnitTest {
String index1Name = "index_" + region1Name;
String index2Name = "index_" + region2Name;
- gfsh.executeAndAssertThat(
- "create region --name=" + region1Name + " --type=REPLICATE --group=group1")
- .statusIsSuccess()
- .containsOutput("Region \"/" + region1Name + "\" created on \"server-3\"");
+ CommandResult result = gfsh
+ .executeCommand("create region --name=" + region1Name + " --type=REPLICATE --group=group1");
+ assertThat(result.getStatus()).isEqualTo(Result.Status.OK);
+ assertThat(result.getMapFromTableContent("0", "0").get("Member")).contains("server-1",
+ "server-2");
- gfsh.executeAndAssertThat(
- "create region --name=" + region2Name + " --type=REPLICATE --group=group1")
- .statusIsSuccess()
- .containsOutput("Region \"/" + region2Name + "\" created on \"server-3\"");
+ result = gfsh
+ .executeCommand("create region --name=" + region2Name + " --type=REPLICATE --group=group1");
+ assertThat(result.getStatus()).isEqualTo(Result.Status.OK);
+ assertThat(result.getMapFromTableContent("0", "0").get("Member")).contains("server-1",
+ "server-2");
VMProvider.invokeInEveryMember(() -> {
Cache cache = ClusterStartupRule.getCache();
assertThat(cache.getRegion(region1Name)).isNull();
assertThat(cache.getRegion(region2Name)).isNull();
- }, server1, server2);
+ }, server3);
VMProvider.invokeInEveryMember(() -> {
Cache cache = ClusterStartupRule.getCache();
assertThat(cache.getRegion(region1Name)).isNotNull();
assertThat(cache.getRegion(region2Name)).isNotNull();
- }, server3);
+ }, server1, server2);
gfsh.executeAndAssertThat(
"define index --name=" + index1Name + " --expression=value1 --region=" + region1Name)
@@ -186,7 +219,7 @@ public class CreateDefinedIndexesCommandDUnitTest {
.statusIsSuccess().containsOutput("Index successfully defined");
gfsh.executeAndAssertThat("create defined indexes --group=group1").statusIsSuccess()
- .containsOutput("Indexes successfully created");
+ .containsOutput("Changes to configuration for group 'group1' are persisted.");
VMProvider.invokeInEveryMember(() -> {
Cache cache = ClusterStartupRule.getCache();
@@ -198,7 +231,7 @@ public class CreateDefinedIndexesCommandDUnitTest {
assertThat(queryService.getIndexes(region2).size()).isEqualTo(1);
assertThat(queryService.getIndex(region1, index1Name)).isNotNull();
assertThat(queryService.getIndex(region2, index2Name)).isNotNull();
- }, server3);
+ }, server1, server2);
locator.invoke(() -> {
// Make sure the indexes exist in the cluster config
@@ -206,7 +239,67 @@ public class CreateDefinedIndexesCommandDUnitTest {
((InternalLocator) Locator.getLocator()).getConfigurationPersistenceService();
assertThat(sharedConfig.getConfiguration("group1").getCacheXmlContent()).contains(index2Name,
index1Name);
- assertThat(sharedConfig.getConfiguration("cluster").getCacheXmlContent()).isNullOrEmpty();
});
}
+
+ @Test
+ public void disjointRegionsAndGroupsFailsToDefineIndexes() {
+ String region1Name = testName.getMethodName() + "1";
+ String region2Name = testName.getMethodName() + "2";
+ String index1Name = "index_" + region1Name;
+ String index2Name = "index_" + region2Name;
+
+ CommandResult result = gfsh
+ .executeCommand("create region --name=" + region1Name + " --type=REPLICATE --group=group1");
+ assertThat(result.getStatus()).isEqualTo(Result.Status.OK);
+ assertThat(result.getMapFromTableContent("0", "0").get("Member")).contains("server-1",
+ "server-2");
+
+ result = gfsh
+ .executeCommand("create region --name=" + region2Name + " --type=REPLICATE --group=group2");
+ assertThat(result.getStatus()).isEqualTo(Result.Status.OK);
+ assertThat(result.getMapFromTableContent("0", "0").get("Member")).contains("server-3");
+
+ gfsh.executeAndAssertThat(
+ "define index --name=" + index1Name + " --expression=value1 --region=" + region1Name)
+ .statusIsSuccess().containsOutput("Index successfully defined");
+
+ gfsh.executeAndAssertThat(
+ "define index --name=" + index2Name + " --expression=value1 --region=" + region2Name)
+ .statusIsSuccess().containsOutput("Index successfully defined");
+
+ result = gfsh.executeCommand("create defined indexes --group=group1,group2");
+ assertThat(result.getStatus()).isEqualTo(Result.Status.ERROR);
+ assertThat(
+ result.getMapFromTableContent(CreateDefinedIndexesCommand.CREATE_DEFINED_INDEXES_SECTION)
+ .get("Status")).contains("ERROR", "ERROR", "ERROR");
+
+ VMProvider.invokeInEveryMember(() -> {
+ Cache cache = ClusterStartupRule.getCache();
+ QueryService queryService = cache.getQueryService();
+ Region region1 = cache.getRegion(region1Name);
+
+ // Returns null instead of an empty collection if there are no indexes...
+ assertThat(queryService.getIndexes(region1)).isNull();
+ }, server1, server2);
+
+ VMProvider.invokeInEveryMember(() -> {
+ Cache cache = ClusterStartupRule.getCache();
+ QueryService queryService = cache.getQueryService();
+ Region region2 = cache.getRegion(region2Name);
+
+ assertThat(queryService.getIndexes(region2)).isNull();
+ }, server3);
+
+ locator.invoke(() -> {
+ // Make sure the indexes do not exist in the cluster config
+ InternalConfigurationPersistenceService sharedConfig =
+ ((InternalLocator) Locator.getLocator()).getConfigurationPersistenceService();
+ assertThat(sharedConfig.getConfiguration("group1").getCacheXmlContent())
+ .doesNotContain(index1Name);
+ assertThat(sharedConfig.getConfiguration("group2").getCacheXmlContent())
+ .doesNotContain(index2Name);
+ });
+ }
+
}
diff --git a/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommandTest.java b/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommandTest.java
index e8ecaeb..90661ed 100644
--- a/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommandTest.java
+++ b/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateDefinedIndexesCommandTest.java
@@ -21,14 +21,16 @@ import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.never;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
+import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
import java.util.Set;
import org.junit.Before;
@@ -41,10 +43,8 @@ import org.apache.geode.cache.execute.ResultCollector;
import org.apache.geode.cache.query.IndexType;
import org.apache.geode.distributed.DistributedMember;
import org.apache.geode.distributed.internal.InternalConfigurationPersistenceService;
-import org.apache.geode.management.internal.cli.domain.IndexInfo;
import org.apache.geode.management.internal.cli.functions.CliFunctionResult;
import org.apache.geode.management.internal.cli.result.CommandResult;
-import org.apache.geode.management.internal.configuration.domain.XmlEntity;
import org.apache.geode.test.junit.categories.UnitTest;
import org.apache.geode.test.junit.rules.GfshParserRule;
@@ -74,8 +74,7 @@ public class CreateDefinedIndexesCommandTest {
@Test
public void noMembers() throws Exception {
- IndexDefinition.indexDefinitions
- .add(new IndexInfo("indexName", "indexedExpression", "TestRegion", IndexType.FUNCTIONAL));
+ IndexDefinition.addIndex("indexName", "indexedExpression", "TestRegion", IndexType.FUNCTIONAL);
doReturn(Collections.EMPTY_SET).when(command).findMembers(any(), any());
result = gfshParser.executeCommandWithInstance(command, "create defined indexes");
assertThat(result.getStatus()).isEqualTo(ERROR);
@@ -94,17 +93,14 @@ public class CreateDefinedIndexesCommandTest {
doReturn(Arrays.asList(new CliFunctionResult(member.getId(), new Exception("MockException"),
"Exception Message."))).when(resultCollector).getResult();
- IndexDefinition.indexDefinitions
- .add(new IndexInfo("index1", "value1", "TestRegion", IndexType.FUNCTIONAL));
+ IndexDefinition.addIndex("index1", "value1", "TestRegion", IndexType.FUNCTIONAL);
result = gfshParser.executeCommandWithInstance(command, "create defined indexes");
assertThat(result.getStatus()).isEqualTo(ERROR);
- verify(command, never()).persistClusterConfiguration(any(), any());
}
@Test
public void creationSuccess() throws Exception {
- XmlEntity xmlEntity = mock(XmlEntity.class);
DistributedMember member = mock(DistributedMember.class);
when(member.getId()).thenReturn("memberId");
InternalConfigurationPersistenceService mockService =
@@ -112,23 +108,20 @@ public class CreateDefinedIndexesCommandTest {
doReturn(mockService).when(command).getConfigurationPersistenceService();
doReturn(Collections.singleton(member)).when(command).findMembers(any(), any());
- doReturn(Arrays.asList(new CliFunctionResult(member.getId(), xmlEntity))).when(resultCollector)
+ List<String> indexes = new ArrayList<>();
+ indexes.add("index1");
+ doReturn(Arrays.asList(new CliFunctionResult(member.getId(), indexes))).when(resultCollector)
.getResult();
- IndexDefinition.indexDefinitions
- .add(new IndexInfo("index1", "value1", "TestRegion", IndexType.FUNCTIONAL));
+ IndexDefinition.addIndex("index1", "value1", "TestRegion", IndexType.FUNCTIONAL);
result = gfshParser.executeCommandWithInstance(command, "create defined indexes");
assertThat(result.getStatus()).isEqualTo(OK);
- assertThat(result.failedToPersist()).isFalse();
- verify(command, Mockito.times(1)).persistClusterConfiguration(any(), any());
- assertThat(result.getMessageFromContent()).contains("Indexes successfully created");
+ verify(command, Mockito.times(0)).updateClusterConfig(any(), any(), any());
}
@Test
public void multipleIndexesOnMultipleRegions() throws Exception {
- XmlEntity xmlEntityRegion1 = mock(XmlEntity.class);
- XmlEntity xmlEntityRegion2 = mock(XmlEntity.class);
DistributedMember member1 = mock(DistributedMember.class);
DistributedMember member2 = mock(DistributedMember.class);
when(member1.getId()).thenReturn("memberId_1");
@@ -136,34 +129,25 @@ public class CreateDefinedIndexesCommandTest {
InternalConfigurationPersistenceService mockService =
mock(InternalConfigurationPersistenceService.class);
- CliFunctionResult member1Region1Result =
- new CliFunctionResult(member1.getId(), xmlEntityRegion1);
- CliFunctionResult member1Region2Result =
- new CliFunctionResult(member1.getId(), xmlEntityRegion2);
- CliFunctionResult member2Region1Result =
- new CliFunctionResult(member2.getId(), xmlEntityRegion2);
- CliFunctionResult member2Region2Result =
- new CliFunctionResult(member2.getId(), xmlEntityRegion2);
+ CliFunctionResult resultMember1 =
+ new CliFunctionResult(member1.getId(), Arrays.asList("index1", "index2"));
+ CliFunctionResult resultMember2 =
+ new CliFunctionResult(member2.getId(), Arrays.asList("index1", "index2"));
doReturn(mockService).when(command).getConfigurationPersistenceService();
- doReturn(new HashSet<>(Arrays.asList(new DistributedMember[] {member1, member2}))).when(command)
- .findMembers(any(), any());
- doReturn(Arrays.asList(new CliFunctionResult[] {member1Region1Result, member1Region2Result,
- member2Region1Result, member2Region2Result})).when(resultCollector).getResult();
+ doReturn(new HashSet<>(Arrays.asList(member1, member2))).when(command).findMembers(any(),
+ any());
+ doReturn(Arrays.asList(resultMember1, resultMember2)).when(resultCollector).getResult();
- IndexDefinition.indexDefinitions
- .add(new IndexInfo("index1", "value1", "TestRegion1", IndexType.FUNCTIONAL));
- IndexDefinition.indexDefinitions
- .add(new IndexInfo("index2", "value2", "TestRegion2", IndexType.FUNCTIONAL));
+ IndexDefinition.addIndex("index1", "value1", "TestRegion1", IndexType.FUNCTIONAL);
+ IndexDefinition.addIndex("index2", "value2", "TestRegion2", IndexType.FUNCTIONAL);
result = gfshParser.executeCommandWithInstance(command, "create defined indexes");
assertThat(result.getStatus()).isEqualTo(OK);
- assertThat(result.failedToPersist()).isFalse();
- // The command will receive 4 results from 2 members, but we need to persist only 2 (#regions)
- // of them.
- verify(command, Mockito.times(2)).persistClusterConfiguration(any(), any());
- assertThat(result.getMessageFromContent()).contains("Indexes successfully created");
+ Map<String, List<String>> table =
+ result.getMapFromTableContent(CreateDefinedIndexesCommand.CREATE_DEFINED_INDEXES_SECTION);
+ assertThat(table.get("Status")).contains("OK", "OK", "OK", "OK");
}
}
diff --git a/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateJndiBindingCommandTest.java b/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateJndiBindingCommandTest.java
index fd6ca25..d20c470 100644
--- a/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateJndiBindingCommandTest.java
+++ b/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/CreateJndiBindingCommandTest.java
@@ -204,7 +204,7 @@ public class CreateJndiBindingCommandTest {
gfsh.executeAndAssertThat(command,
COMMAND + " --type=SIMPLE --name=name --jdbc-driver-class=driver --connection-url=url")
.statusIsSuccess().containsOutput("No members found.")
- .containsOutput("Changes to configuration for group 'cluster' is persisted.");
+ .containsOutput("Changes to configuration for group 'cluster' are persisted.");
verify(clusterConfigService).updateCacheConfig(any(), any());
verify(command).updateClusterConfig(eq("cluster"), eq(cacheConfig), any());
diff --git a/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/DestroyJndiBindingCommandTest.java b/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/DestroyJndiBindingCommandTest.java
index 4caf03d..093c97e 100644
--- a/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/DestroyJndiBindingCommandTest.java
+++ b/geode-core/src/test/java/org/apache/geode/management/internal/cli/commands/DestroyJndiBindingCommandTest.java
@@ -134,7 +134,7 @@ public class DestroyJndiBindingCommandTest {
gfsh.executeAndAssertThat(command, COMMAND + " --name=name").statusIsSuccess()
.containsOutput("No members found.")
- .containsOutput("Changes to configuration for group 'cluster' is persisted.");
+ .containsOutput("Changes to configuration for group 'cluster' are persisted.");
verify(ccService).updateCacheConfig(any(), any());
verify(command).updateClusterConfig(eq("cluster"), eq(cacheConfig), any());
diff --git a/geode-core/src/test/java/org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunctionTest.java b/geode-core/src/test/java/org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunctionTest.java
index 677ae6b..894fef4 100644
--- a/geode-core/src/test/java/org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunctionTest.java
+++ b/geode-core/src/test/java/org/apache/geode/management/internal/cli/functions/CreateDefinedIndexesFunctionTest.java
@@ -16,7 +16,6 @@
package org.apache.geode.management.internal.cli.functions;
import static org.assertj.core.api.Assertions.assertThat;
-import static org.mockito.Mockito.any;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.spy;
@@ -36,6 +35,7 @@ import org.junit.experimental.categories.Category;
import org.apache.geode.cache.Cache;
import org.apache.geode.cache.Region;
+import org.apache.geode.cache.configuration.RegionConfig;
import org.apache.geode.cache.execute.FunctionContext;
import org.apache.geode.cache.execute.ResultSender;
import org.apache.geode.cache.query.Index;
@@ -48,8 +48,6 @@ import org.apache.geode.cache.query.internal.index.CompactMapRangeIndex;
import org.apache.geode.cache.query.internal.index.HashIndex;
import org.apache.geode.cache.query.internal.index.PrimaryKeyIndex;
import org.apache.geode.internal.cache.execute.FunctionContextImpl;
-import org.apache.geode.management.internal.cli.domain.IndexInfo;
-import org.apache.geode.management.internal.configuration.domain.XmlEntity;
import org.apache.geode.test.fake.Fakes;
import org.apache.geode.test.junit.categories.UnitTest;
@@ -61,7 +59,7 @@ public class CreateDefinedIndexesFunctionTest {
private FunctionContext context;
private QueryService queryService;
private TestResultSender resultSender;
- private Set<IndexInfo> indexDefinitions;
+ private Set<RegionConfig.Index> indexDefinitions;
private CreateDefinedIndexesFunction function;
@Before
@@ -75,9 +73,30 @@ public class CreateDefinedIndexesFunctionTest {
doReturn(queryService).when(cache).getQueryService();
indexDefinitions = new HashSet<>();
- indexDefinitions.add(new IndexInfo("index1", "value1", "/Region1", IndexType.HASH));
- indexDefinitions.add(new IndexInfo("index2", "value2", "/Region2", IndexType.FUNCTIONAL));
- indexDefinitions.add(new IndexInfo("index3", "value3", "/Region1", IndexType.PRIMARY_KEY));
+ indexDefinitions.add(new RegionConfig.Index() {
+ {
+ setName("index1");
+ setExpression("value1");
+ setFromClause("/Region1");
+ setType(IndexType.HASH.getName());
+ }
+ });
+ indexDefinitions.add(new RegionConfig.Index() {
+ {
+ setName("index2");
+ setExpression("value2");
+ setFromClause("/Region2");
+ setType(IndexType.FUNCTIONAL.getName());
+ }
+ });
+ indexDefinitions.add(new RegionConfig.Index() {
+ {
+ setName("index3");
+ setExpression("value3");
+ setFromClause("/Region1");
+ setType(IndexType.PRIMARY_KEY.getName());
+ }
+ });
}
@Test
@@ -89,7 +108,7 @@ public class CreateDefinedIndexesFunctionTest {
List<?> results = resultSender.getResults();
assertThat(results).isNotNull();
- assertThat(results.size()).isEqualTo(1);
+ assertThat(results.size()).isEqualTo(2);
Object firstResult = results.get(0);
assertThat(firstResult).isInstanceOf(CliFunctionResult.class);
assertThat(((CliFunctionResult) firstResult).isSuccessful()).isTrue();
@@ -107,7 +126,7 @@ public class CreateDefinedIndexesFunctionTest {
List<?> results = resultSender.getResults();
assertThat(results).isNotNull();
- assertThat(results.size()).isEqualTo(1);
+ assertThat(results.size()).isEqualTo(2);
Object firstResult = results.get(0);
assertThat(firstResult).isInstanceOf(CliFunctionResult.class);
assertThat(((CliFunctionResult) firstResult).isSuccessful()).isTrue();
@@ -129,16 +148,21 @@ public class CreateDefinedIndexesFunctionTest {
List<?> results = resultSender.getResults();
assertThat(results).isNotNull();
- assertThat(results.size()).isEqualTo(1);
- Object firstResult = results.get(0);
- assertThat(firstResult).isNotNull();
- assertThat(firstResult).isInstanceOf(CliFunctionResult.class);
- assertThat(((CliFunctionResult) firstResult).isSuccessful()).isFalse();
- assertThat(((CliFunctionResult) firstResult).getSerializables().length).isEqualTo(1);
- assertThat(((CliFunctionResult) firstResult).getSerializables()[0]).isNotNull();
- assertThat(((CliFunctionResult) firstResult).getSerializables()[0].toString()).contains(
- "Index creation failed for indexes", "index1", "Mock Failure", "index3",
- "Another Mock Failure");
+ assertThat(results.size()).isEqualTo(4);
+
+ CliFunctionResult result1 = (CliFunctionResult) results.get(0);
+ assertThat(result1.isSuccessful()).isTrue();
+ assertThat(result1.getStatusMessage()).isEqualTo("Created index index2");
+
+ CliFunctionResult result2 = (CliFunctionResult) results.get(1);
+ assertThat(result2.isSuccessful()).isFalse();
+ assertThat(result2.getStatusMessage())
+ .isEqualTo("Failed to create index index1: Mock Failure.");
+
+ CliFunctionResult result3 = (CliFunctionResult) results.get(2);
+ assertThat(result3.isSuccessful()).isFalse();
+ assertThat(result3.getStatusMessage())
+ .isEqualTo("Failed to create index index3: Another Mock Failure.");
}
@Test
@@ -151,15 +175,11 @@ public class CreateDefinedIndexesFunctionTest {
List<?> results = resultSender.getResults();
assertThat(results).isNotNull();
- assertThat(results.size()).isEqualTo(1);
- Object firstResult = results.get(0);
- assertThat(firstResult).isNotNull();
- assertThat(firstResult).isInstanceOf(CliFunctionResult.class);
- assertThat(((CliFunctionResult) firstResult).isSuccessful()).isFalse();
- assertThat(((CliFunctionResult) firstResult).getSerializables().length).isEqualTo(1);
- assertThat(((CliFunctionResult) firstResult).getSerializables()[0]).isNotNull();
- assertThat(((CliFunctionResult) firstResult).getSerializables()[0].toString())
- .contains("RuntimeException", "Mock Exception");
+ assertThat(results.size()).isEqualTo(2);
+ CliFunctionResult firstResult = (CliFunctionResult) results.get(0);
+
+ assertThat(firstResult.isSuccessful()).isFalse();
+ assertThat(firstResult.getStatusMessage()).isEqualTo("Mock Exception");
}
@Test
@@ -176,7 +196,6 @@ public class CreateDefinedIndexesFunctionTest {
when(index3.getName()).thenReturn("index3");
when(index3.getRegion()).thenReturn(region1);
- doReturn(mock(XmlEntity.class)).when(function).createXmlEntity(any());
when(queryService.createDefinedIndexes()).thenReturn(Arrays.asList(index1, index2, index3));
context = new FunctionContextImpl(cache, CreateDefinedIndexesFunction.class.getName(),
indexDefinitions, resultSender);
@@ -185,18 +204,12 @@ public class CreateDefinedIndexesFunctionTest {
List<?> results = resultSender.getResults();
assertThat(results).isNotNull();
- assertThat(results.size()).isEqualTo(2);
+ assertThat(results.size()).isEqualTo(4);
Object firstIndex = results.get(0);
assertThat(firstIndex).isNotNull();
assertThat(firstIndex).isInstanceOf(CliFunctionResult.class);
assertThat(((CliFunctionResult) firstIndex).isSuccessful());
-
- Object secondIndex = results.get(0);
- assertThat(secondIndex).isNotNull();
- assertThat(secondIndex).isInstanceOf(CliFunctionResult.class);
- assertThat(((CliFunctionResult) secondIndex).isSuccessful()).isTrue();
- assertThat(((CliFunctionResult) secondIndex).getXmlEntity()).isNotNull();
}
private static class TestResultSender implements ResultSender {
--
To stop receiving notification emails like this one, please contact
jensdeppe@apache.org.