This is an automated email from the ASF dual-hosted git repository.
dcapwell pushed a commit to branch cassandra-4.0
in repository https://gitbox.apache.org/repos/asf/cassandra.git
The following commit(s) were added to refs/heads/cassandra-4.0 by this push:
new 1bcfa08 DebuggableThreadPoolExecutor does not propagate client
warnings
1bcfa08 is described below
commit 1bcfa087f4521135ef101c694f5e6ada8347827c
Author: Jacek Lewandowski <[email protected]>
AuthorDate: Thu Nov 18 13:03:42 2021 -0800
DebuggableThreadPoolExecutor does not propagate client warnings
patch by Jacek Lewandowski; reviewed by Andres de la Peña, Berenguer Blasi,
David Capwell for CASSANDRA-17072
---
CHANGES.txt | 1 +
.../AbstractLocalAwareExecutorService.java | 11 +-
.../concurrent/DebuggableThreadPoolExecutor.java | 36 +++++--
.../statements/schema/AlterKeyspaceStatement.java | 8 --
.../statements/schema/CreateKeyspaceStatement.java | 13 +--
.../cassandra/db/compaction/CompactionManager.java | 2 +-
.../org/apache/cassandra/service/ClientWarn.java | 5 -
.../DebuggableThreadPoolExecutorTest.java | 76 +++++++++++++
.../cassandra/concurrent/SEPExecutorTest.java | 25 +++++
.../schema/SchemaStatementWarningsTest.java | 117 +++++++++++++++++++++
10 files changed, 254 insertions(+), 40 deletions(-)
diff --git a/CHANGES.txt b/CHANGES.txt
index cb8a8a9..1d72c0f 100644
--- a/CHANGES.txt
+++ b/CHANGES.txt
@@ -1,4 +1,5 @@
4.0.2
+ * DebuggableThreadPoolExecutor does not propagate client warnings
(CASSANDRA-17072)
* internode_send_buff_size_in_bytes and internode_recv_buff_size_in_bytes
have new names. Backward compatibility with the old names added
(CASSANDRA-17141)
* Remove unused configuration parameters from cassandra.yaml (CASSANDRA-17132)
* Queries performed with NODE_LOCAL consistency level do not update request
metrics (CASSANDRA-17052)
diff --git
a/src/java/org/apache/cassandra/concurrent/AbstractLocalAwareExecutorService.java
b/src/java/org/apache/cassandra/concurrent/AbstractLocalAwareExecutorService.java
index d666a36..e7bec19 100644
---
a/src/java/org/apache/cassandra/concurrent/AbstractLocalAwareExecutorService.java
+++
b/src/java/org/apache/cassandra/concurrent/AbstractLocalAwareExecutorService.java
@@ -32,8 +32,6 @@ import org.slf4j.LoggerFactory;
import org.apache.cassandra.utils.concurrent.SimpleCondition;
import org.apache.cassandra.utils.JVMStabilityInspector;
-import static org.apache.cassandra.tracing.Tracing.isTracing;
-
public abstract class AbstractLocalAwareExecutorService implements
LocalAwareExecutorService
{
private static final Logger logger =
LoggerFactory.getLogger(AbstractLocalAwareExecutorService.class);
@@ -98,7 +96,12 @@ public abstract class AbstractLocalAwareExecutorService
implements LocalAwareExe
protected <T> FutureTask<T> newTaskFor(Callable<T> callable)
{
- if (isTracing())
+ return newTaskFor(callable, ExecutorLocals.create());
+ }
+
+ protected <T> FutureTask<T> newTaskFor(Callable<T> callable,
ExecutorLocals locals)
+ {
+ if (locals != null)
{
if (callable instanceof LocalSessionFutureTask)
return (LocalSessionFutureTask<T>) callable;
@@ -218,7 +221,7 @@ public abstract class AbstractLocalAwareExecutorService
implements LocalAwareExe
public void execute(Runnable command)
{
- addTask(newTaskFor(command, ExecutorLocals.create()));
+ addTask(newTaskFor(command, null, ExecutorLocals.create()));
}
public void execute(Runnable command, ExecutorLocals locals)
diff --git
a/src/java/org/apache/cassandra/concurrent/DebuggableThreadPoolExecutor.java
b/src/java/org/apache/cassandra/concurrent/DebuggableThreadPoolExecutor.java
index a2de775..7d9da4d 100644
--- a/src/java/org/apache/cassandra/concurrent/DebuggableThreadPoolExecutor.java
+++ b/src/java/org/apache/cassandra/concurrent/DebuggableThreadPoolExecutor.java
@@ -36,8 +36,6 @@ import java.util.concurrent.TimeUnit;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-import static org.apache.cassandra.tracing.Tracing.isTracing;
-
/**
* This class encorporates some Executor best practices for Cassandra. Most
of the executors in the system
* should use or extend this. There are two main improvements over a vanilla
TPE:
@@ -169,20 +167,27 @@ public class DebuggableThreadPoolExecutor extends
ThreadPoolExecutor implements
execute(command);
}
+ private ExecutorLocals maybeCreateExecutorLocals(Object command)
+ {
+ return command instanceof LocalSessionWrapper ? null :
ExecutorLocals.create();
+ }
+
// execute does not call newTaskFor
@Override
public void execute(Runnable command)
{
- super.execute(isTracing() && !(command instanceof LocalSessionWrapper)
- ? LocalSessionWrapper.create(command)
+ ExecutorLocals locals = maybeCreateExecutorLocals(command);
+ super.execute(locals != null
+ ? LocalSessionWrapper.create(command, locals)
: command);
}
@Override
protected <T> RunnableFuture<T> newTaskFor(Runnable runnable, T result)
{
- if (isTracing() && !(runnable instanceof LocalSessionWrapper))
- return LocalSessionWrapper.create(runnable, result);
+ ExecutorLocals locals = maybeCreateExecutorLocals(runnable);
+ if (locals != null)
+ return LocalSessionWrapper.create(runnable, result, locals);
if (runnable instanceof RunnableFuture)
return new ForwardingRunnableFuture<>((RunnableFuture) runnable,
result);
return super.newTaskFor(runnable, result);
@@ -191,8 +196,9 @@ public class DebuggableThreadPoolExecutor extends
ThreadPoolExecutor implements
@Override
protected <T> RunnableFuture<T> newTaskFor(Callable<T> callable)
{
- if (isTracing() && !(callable instanceof LocalSessionWrapper))
- return LocalSessionWrapper.create(callable);
+ ExecutorLocals locals = maybeCreateExecutorLocals(callable);
+ if (locals != null)
+ return LocalSessionWrapper.create(callable, locals);
return super.newTaskFor(callable);
}
@@ -201,11 +207,11 @@ public class DebuggableThreadPoolExecutor extends
ThreadPoolExecutor implements
{
super.afterExecute(r, t);
- maybeResetTraceSessionWrapper(r);
+ maybeResetLocalSessionWrapper(r);
logExceptionsAfterExecute(r, t);
}
- protected static void maybeResetTraceSessionWrapper(Runnable r)
+ protected static void maybeResetLocalSessionWrapper(Runnable r)
{
if (r instanceof LocalSessionWrapper)
{
@@ -354,6 +360,11 @@ public class DebuggableThreadPoolExecutor extends
ThreadPoolExecutor implements
return create(command, null, ExecutorLocals.create());
}
+ static LocalSessionWrapper<Object> create(Runnable command,
ExecutorLocals locals)
+ {
+ return create(command, null, locals);
+ }
+
static <T> LocalSessionWrapper<T> create(Runnable command, T result)
{
return create(command, result, ExecutorLocals.create());
@@ -371,6 +382,11 @@ public class DebuggableThreadPoolExecutor extends
ThreadPoolExecutor implements
return new LocalSessionWrapper<>(command, ExecutorLocals.create());
}
+ static <T> LocalSessionWrapper<T> create(Callable<T> command,
ExecutorLocals locals)
+ {
+ return new LocalSessionWrapper<>(command, locals);
+ }
+
private void setupContext()
{
ExecutorLocals.set(locals);
diff --git
a/src/java/org/apache/cassandra/cql3/statements/schema/AlterKeyspaceStatement.java
b/src/java/org/apache/cassandra/cql3/statements/schema/AlterKeyspaceStatement.java
index c1b9bc2..f208e4a 100644
---
a/src/java/org/apache/cassandra/cql3/statements/schema/AlterKeyspaceStatement.java
+++
b/src/java/org/apache/cassandra/cql3/statements/schema/AlterKeyspaceStatement.java
@@ -42,7 +42,6 @@ import
org.apache.cassandra.schema.KeyspaceMetadata.KeyspaceDiff;
import org.apache.cassandra.schema.Keyspaces;
import org.apache.cassandra.schema.Keyspaces.KeyspacesDiff;
import org.apache.cassandra.service.ClientState;
-import org.apache.cassandra.service.ClientWarn;
import org.apache.cassandra.transport.Event.SchemaChange;
import org.apache.cassandra.transport.Event.SchemaChange.Change;
import org.apache.cassandra.utils.FBUtilities;
@@ -63,9 +62,6 @@ public final class AlterKeyspaceStatement extends
AlterSchemaStatement
public Keyspaces apply(Keyspaces schema)
{
- if (ClientWarn.instance.get() == null)
- ClientWarn.instance.captureWarnings();
- int previousNumWarnings = ClientWarn.instance.numWarnings();
attrs.validate();
KeyspaceMetadata keyspace = schema.getNullable(keyspaceName);
@@ -84,10 +80,6 @@ public final class AlterKeyspaceStatement extends
AlterSchemaStatement
Keyspaces res = schema.withAddedOrUpdated(newKeyspace);
- int newNumWarnings = ClientWarn.instance.numWarnings();
- if (newNumWarnings > previousNumWarnings)
-
clientWarnings.addAll(ClientWarn.instance.getWarnings().subList(previousNumWarnings,
newNumWarnings));
-
return res;
}
diff --git
a/src/java/org/apache/cassandra/cql3/statements/schema/CreateKeyspaceStatement.java
b/src/java/org/apache/cassandra/cql3/statements/schema/CreateKeyspaceStatement.java
index 806b50a..9aa27ce 100644
---
a/src/java/org/apache/cassandra/cql3/statements/schema/CreateKeyspaceStatement.java
+++
b/src/java/org/apache/cassandra/cql3/statements/schema/CreateKeyspaceStatement.java
@@ -41,7 +41,6 @@ import org.apache.cassandra.schema.Keyspaces;
import org.apache.cassandra.schema.Keyspaces.KeyspacesDiff;
import org.apache.cassandra.schema.Schema;
import org.apache.cassandra.service.ClientState;
-import org.apache.cassandra.service.ClientWarn;
import org.apache.cassandra.transport.Event.SchemaChange;
import org.apache.cassandra.transport.Event.SchemaChange.Change;
@@ -62,10 +61,6 @@ public final class CreateKeyspaceStatement extends
AlterSchemaStatement
public Keyspaces apply(Keyspaces schema)
{
- if (ClientWarn.instance.get() == null)
- ClientWarn.instance.captureWarnings();
- int previousNumWarnings = ClientWarn.instance.numWarnings();
-
attrs.validate();
if (!attrs.hasOption(Option.REPLICATION))
@@ -85,13 +80,7 @@ public final class CreateKeyspaceStatement extends
AlterSchemaStatement
throw ire("Unable to use given strategy class: LocalStrategy is
reserved for internal use.");
keyspace.params.validate(keyspaceName);
- Keyspaces keyspaces = schema.withAddedOrUpdated(keyspace);
-
- int newNumWarnings = ClientWarn.instance.numWarnings();
- if (newNumWarnings > previousNumWarnings)
-
clientWarnings.addAll(ClientWarn.instance.getWarnings().subList(previousNumWarnings,
newNumWarnings));
-
- return keyspaces;
+ return schema.withAddedOrUpdated(keyspace);
}
SchemaChange schemaChangeEvent(KeyspacesDiff diff)
diff --git a/src/java/org/apache/cassandra/db/compaction/CompactionManager.java
b/src/java/org/apache/cassandra/db/compaction/CompactionManager.java
index 8d4f136..933418e 100644
--- a/src/java/org/apache/cassandra/db/compaction/CompactionManager.java
+++ b/src/java/org/apache/cassandra/db/compaction/CompactionManager.java
@@ -1826,7 +1826,7 @@ public class CompactionManager implements
CompactionManagerMBean
@Override
public void afterExecute(Runnable r, Throwable t)
{
- DebuggableThreadPoolExecutor.maybeResetTraceSessionWrapper(r);
+ DebuggableThreadPoolExecutor.maybeResetLocalSessionWrapper(r);
if (t == null)
t = DebuggableThreadPoolExecutor.extractThrowable(r);
diff --git a/src/java/org/apache/cassandra/service/ClientWarn.java
b/src/java/org/apache/cassandra/service/ClientWarn.java
index ec79854..5a6a878 100644
--- a/src/java/org/apache/cassandra/service/ClientWarn.java
+++ b/src/java/org/apache/cassandra/service/ClientWarn.java
@@ -64,11 +64,6 @@ public class ClientWarn implements
ExecutorLocal<ClientWarn.State>
return state.warnings;
}
- public int numWarnings()
- {
- return getWarnings() == null ? 0 : getWarnings().size();
- }
-
public void resetWarnings()
{
warnLocal.remove();
diff --git
a/test/unit/org/apache/cassandra/concurrent/DebuggableThreadPoolExecutorTest.java
b/test/unit/org/apache/cassandra/concurrent/DebuggableThreadPoolExecutorTest.java
index 58200c9..43c0fdf 100644
---
a/test/unit/org/apache/cassandra/concurrent/DebuggableThreadPoolExecutorTest.java
+++
b/test/unit/org/apache/cassandra/concurrent/DebuggableThreadPoolExecutorTest.java
@@ -22,6 +22,8 @@ package org.apache.cassandra.concurrent;
import java.util.UUID;
+import java.util.concurrent.Callable;
+import java.util.concurrent.ConcurrentLinkedQueue;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.RunnableFuture;
@@ -31,16 +33,22 @@ import java.util.concurrent.atomic.AtomicReference;
import com.google.common.base.Throwables;
import com.google.common.net.InetAddresses;
import com.google.common.util.concurrent.ListenableFutureTask;
+import com.google.common.util.concurrent.Uninterruptibles;
import org.junit.Assert;
import org.junit.BeforeClass;
import org.junit.Test;
import org.apache.cassandra.config.DatabaseDescriptor;
import org.apache.cassandra.locator.InetAddressAndPort;
+import org.apache.cassandra.service.ClientWarn;
import org.apache.cassandra.tracing.TraceState;
import org.apache.cassandra.tracing.TraceStateImpl;
import org.apache.cassandra.tracing.Tracing;
+import org.apache.cassandra.utils.FBUtilities;
import org.apache.cassandra.utils.WrappedRunnable;
+import org.assertj.core.api.Assertions;
+
+import static java.util.concurrent.TimeUnit.MILLISECONDS;
public class DebuggableThreadPoolExecutorTest
{
@@ -79,6 +87,74 @@ public class DebuggableThreadPoolExecutorTest
}
@Test
+ public void testLocalStatePropagation()
+ {
+ DebuggableThreadPoolExecutor executor =
DebuggableThreadPoolExecutor.createWithFixedPoolSize("TEST", 1);
+ try
+ {
+ checkLocalStateIsPropagated(executor);
+ }
+ finally
+ {
+ executor.shutdown();
+ }
+ }
+
+ public static void checkLocalStateIsPropagated(LocalAwareExecutorService
executor)
+ {
+ checkClientWarningsArePropagated(executor, () -> executor.execute(()
-> ClientWarn.instance.warn("msg")));
+ checkClientWarningsArePropagated(executor, () -> executor.submit(() ->
ClientWarn.instance.warn("msg")));
+ checkClientWarningsArePropagated(executor, () -> executor.submit(() ->
ClientWarn.instance.warn("msg"), null));
+ checkClientWarningsArePropagated(executor, () ->
executor.submit((Callable<Void>) () -> {
+ ClientWarn.instance.warn("msg");
+ return null;
+ }));
+
+ checkTracingIsPropagated(executor, () -> executor.execute(() ->
Tracing.trace("msg")));
+ checkTracingIsPropagated(executor, () -> executor.submit(() ->
Tracing.trace("msg")));
+ checkTracingIsPropagated(executor, () -> executor.submit(() ->
Tracing.trace("msg"), null));
+ checkTracingIsPropagated(executor, () ->
executor.submit((Callable<Void>) () -> {
+ Tracing.trace("msg");
+ return null;
+ }));
+ }
+
+ public static void
checkClientWarningsArePropagated(LocalAwareExecutorService executor, Runnable
schedulingTask) {
+ ClientWarn.instance.captureWarnings();
+
Assertions.assertThat(ClientWarn.instance.getWarnings()).isNullOrEmpty();
+
+ ClientWarn.instance.warn("msg0");
+ long initCompletedTasks = executor.getCompletedTaskCount();
+ schedulingTask.run();
+ while (executor.getCompletedTaskCount() == initCompletedTasks)
Uninterruptibles.sleepUninterruptibly(10, MILLISECONDS);
+ ClientWarn.instance.warn("msg1");
+
+
Assertions.assertThat(ClientWarn.instance.getWarnings()).containsExactlyInAnyOrder("msg0",
"msg", "msg1");
+ }
+
+ public static void checkTracingIsPropagated(LocalAwareExecutorService
executor, Runnable schedulingTask) {
+ ClientWarn.instance.captureWarnings();
+
Assertions.assertThat(ClientWarn.instance.getWarnings()).isNullOrEmpty();
+
+ ConcurrentLinkedQueue<String> q = new ConcurrentLinkedQueue<>();
+ Tracing.instance.set(new
TraceState(FBUtilities.getLocalAddressAndPort(), UUID.randomUUID(),
Tracing.TraceType.NONE)
+ {
+ @Override
+ protected void traceImpl(String message)
+ {
+ q.add(message);
+ }
+ });
+ Tracing.trace("msg0");
+ long initCompletedTasks = executor.getCompletedTaskCount();
+ schedulingTask.run();
+ while (executor.getCompletedTaskCount() == initCompletedTasks)
Uninterruptibles.sleepUninterruptibly(10, MILLISECONDS);
+ Tracing.trace("msg1");
+
+ Assertions.assertThat(q.toArray()).containsExactlyInAnyOrder("msg0",
"msg", "msg1");
+ }
+
+ @Test
public void testExecuteFutureTaskWhileTracing()
{
LinkedBlockingQueue<Runnable> q = new LinkedBlockingQueue<Runnable>(1);
diff --git a/test/unit/org/apache/cassandra/concurrent/SEPExecutorTest.java
b/test/unit/org/apache/cassandra/concurrent/SEPExecutorTest.java
index b18c328..97e389c 100644
--- a/test/unit/org/apache/cassandra/concurrent/SEPExecutorTest.java
+++ b/test/unit/org/apache/cassandra/concurrent/SEPExecutorTest.java
@@ -30,15 +30,24 @@ import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.atomic.AtomicInteger;
import org.junit.Assert;
+import org.junit.BeforeClass;
import org.junit.Test;
+import org.apache.cassandra.config.DatabaseDescriptor;
import org.apache.cassandra.utils.FBUtilities;
import static java.util.concurrent.TimeUnit.MILLISECONDS;
import static java.util.concurrent.TimeUnit.MINUTES;
+import static
org.apache.cassandra.concurrent.DebuggableThreadPoolExecutorTest.checkLocalStateIsPropagated;
public class SEPExecutorTest
{
+ @BeforeClass
+ public static void beforeClass()
+ {
+ DatabaseDescriptor.daemonInitialization();
+ }
+
@Test
public void shutdownTest() throws Throwable
{
@@ -261,4 +270,20 @@ public class SEPExecutorTest
// Will return true if all of the LatchWaiters count down before the
timeout
Assert.assertTrue("Test tasks did not hit max concurrency goal",
concurrencyGoal.await(3L, TimeUnit.SECONDS));
}
+
+ @Test
+ public void testLocalStatePropagation() throws InterruptedException,
TimeoutException
+ {
+ SharedExecutorPool sharedPool = new SharedExecutorPool("TestPool");
+ try
+ {
+ LocalAwareExecutorService executor = sharedPool.newExecutor(1,
"TEST", "TEST");
+ checkLocalStateIsPropagated(executor);
+ }
+ finally
+ {
+ sharedPool.shutdownAndWait(1, TimeUnit.SECONDS);
+ }
+ }
+
}
diff --git
a/test/unit/org/apache/cassandra/schema/SchemaStatementWarningsTest.java
b/test/unit/org/apache/cassandra/schema/SchemaStatementWarningsTest.java
new file mode 100644
index 0000000..1978548
--- /dev/null
+++ b/test/unit/org/apache/cassandra/schema/SchemaStatementWarningsTest.java
@@ -0,0 +1,117 @@
+/*
+ * 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.cassandra.schema;
+
+import java.util.HashSet;
+import java.util.Queue;
+import java.util.Set;
+import java.util.UUID;
+import java.util.concurrent.ConcurrentLinkedQueue;
+
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+import org.apache.cassandra.cql3.CQLTester;
+import org.apache.cassandra.service.ClientWarn;
+import org.assertj.core.api.Assertions;
+import org.jboss.byteman.contrib.bmunit.BMRule;
+import org.jboss.byteman.contrib.bmunit.BMRules;
+import org.jboss.byteman.contrib.bmunit.BMUnitRunner;
+
+@RunWith(BMUnitRunner.class)
+public class SchemaStatementWarningsTest extends CQLTester
+{
+ private static volatile String msg1, msg2;
+ private static final Queue<String> injectedWarnings = new
ConcurrentLinkedQueue<>();
+
+ @Before
+ public void before()
+ {
+ msg1 = UUID.randomUUID().toString();
+ msg2 = UUID.randomUUID().toString();
+ }
+
+ @Test
+ @BMRules(rules = { @BMRule(name = "client warning 1",
+ targetClass = "CreateKeyspaceStatement",
+ targetMethod = "apply",
+ targetLocation = "AT INVOKE
KeyspaceParams.validate",
+ action =
"org.apache.cassandra.schema.SchemaStatementWarningsTest.addWarn()"),
+ @BMRule(name = "client warning 2",
+ targetClass = "CreateKeyspaceStatement",
+ targetMethod = "clientWarnings",
+ targetLocation = "AT EXIT",
+ action = "return
org.apache.cassandra.schema.SchemaStatementWarningsTest.addWarnToList($!)"),
+ @BMRule(name = "client warning 3",
+ targetClass = "AlterSchemaStatement",
+ targetMethod = "clientWarnings",
+ targetLocation = "AT EXIT",
+ action = "return
org.apache.cassandra.schema.SchemaStatementWarningsTest.addWarnToList($!)") })
+ public void testClientWarningsOnCreateKeyspace()
+ {
+ ClientWarn.instance.captureWarnings();
+ injectedWarnings.clear();
+ createKeyspace("CREATE KEYSPACE %s WITH replication = {'class':
'SimpleStrategy', 'replication_factor': 1}");
+
+ Assertions.assertThat(injectedWarnings).contains(msg1, msg2); //
failure here means the bm rules need to be updated
+
Assertions.assertThat(ClientWarn.instance.getWarnings()).containsExactlyInAnyOrder(msg1,
msg2);
+ }
+
+ @Test
+ @BMRules(rules = { @BMRule(name = "client warning 1",
+ targetClass = "CreateTableStatement",
+ targetMethod = "apply",
+ targetLocation = "AT INVOKE
TableMetadata.validate",
+ action =
"org.apache.cassandra.schema.SchemaStatementWarningsTest.addWarn()"),
+ @BMRule(name = "client warning 2",
+ targetClass = "CreateTableStatement",
+ targetMethod = "clientWarnings",
+ targetLocation = "AT EXIT",
+ action = "return
org.apache.cassandra.schema.SchemaStatementWarningsTest.addWarnToList($!)"),
+ @BMRule(name = "client warning 3",
+ targetClass = "AlterSchemaStatement",
+ targetMethod = "clientWarnings",
+ targetLocation = "AT EXIT",
+ action = "return
org.apache.cassandra.schema.SchemaStatementWarningsTest.addWarnToList($!)"),
+ })
+ public void testClientWarningsOnCreateTable()
+ {
+ ClientWarn.instance.captureWarnings();
+ injectedWarnings.clear();
+ createTable("CREATE TABLE %s (k int primary key, v int)");
+
+ Assertions.assertThat(injectedWarnings).contains(msg1, msg2); //
failure here means the bm rules need to be updated
+
Assertions.assertThat(ClientWarn.instance.getWarnings()).containsExactlyInAnyOrder(msg1,
msg2);
+ }
+
+ public static void addWarn()
+ {
+ ClientWarn.instance.warn(msg1);
+ injectedWarnings.add(msg1);
+ }
+
+ public static Set<String> addWarnToList(Set<String> warns)
+ {
+ warns = new HashSet<>(warns);
+ warns.add(msg2);
+ injectedWarnings.add(msg2);
+ return warns;
+ }
+}
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]