Skip to content
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),

### Fixed
- Fix bytes parameter on `_cat/recovery` ([#17598](https://github.com/opensearch-project/OpenSearch/pull/17598))
- Fix slow performance of FeatureFlag checks ([#17611](https://github.com/opensearch-project/OpenSearch/pull/17611))

### Security

Expand Down
3 changes: 2 additions & 1 deletion DEVELOPER_GUIDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -594,7 +594,8 @@ Rapidly developing new features often benefit from several release cycles before
uses an Experimental Development process leveraging [Feature Flags](https://featureflags.io/feature-flags/). This allows a feature to be developed using the same process as
a LTS feature but with additional guard rails and communication mechanisms to signal to the users and development community the feature is not yet stable, may change in a future
release, or be removed altogether. Any Developer or User APIs implemented along with the experimental feature should be marked with `@ExperimentalApi` (or documented as
`@opensearch.experimental`) annotation to signal the implementation is not subject to LTS and does not follow backwards compatibility guidelines.
`@opensearch.experimental`) annotation to signal the implementation is not subject to LTS and does not follow backwards compatibility guidelines. When writing tests for
functionality gated behind a feature flag please refer to `FeatureFlags.TestUtils` and the `@LockFeatureFlag` annotation.

#### API Compatibility Checks

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,15 +36,12 @@
import org.apache.lucene.index.IndexableField;
import org.opensearch.cluster.metadata.IndexMetadata;
import org.opensearch.common.settings.Settings;
import org.opensearch.common.util.FeatureFlags;
import org.opensearch.common.xcontent.XContentFactory;
import org.opensearch.core.common.bytes.BytesReference;
import org.opensearch.core.xcontent.MediaTypeRegistry;
import org.opensearch.core.xcontent.XContentBuilder;
import org.opensearch.index.compositeindex.datacube.startree.StarTreeIndexSettings;
import org.opensearch.plugins.Plugin;
import org.junit.AfterClass;
import org.junit.BeforeClass;

import java.io.IOException;
import java.util.Arrays;
Expand Down Expand Up @@ -98,16 +95,7 @@ public void testExistsQueryDocValuesDisabled() throws IOException {
assertParseMinimalWarnings();
}

@BeforeClass
public static void createMapper() {
FeatureFlags.initializeFeatureFlags(Settings.builder().put(STAR_TREE_INDEX, "true").build());
}

@AfterClass
public static void clearMapper() {
FeatureFlags.initializeFeatureFlags(Settings.EMPTY);
}

@LockFeatureFlag(STAR_TREE_INDEX)
public void testScaledFloatWithStarTree() throws Exception {

double scalingFactorField1 = randomDouble() * 100;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,26 +14,20 @@
import org.opensearch.arrow.flight.bootstrap.FlightService;
import org.opensearch.arrow.flight.bootstrap.FlightStreamPlugin;
import org.opensearch.cluster.node.DiscoveryNode;
import org.opensearch.common.util.FeatureFlags;
import org.opensearch.plugins.Plugin;
import org.opensearch.test.FeatureFlagSetter;
import org.opensearch.test.OpenSearchIntegTestCase;
import org.junit.BeforeClass;

import java.util.Collection;
import java.util.Collections;
import java.util.concurrent.TimeUnit;

import static org.opensearch.common.util.FeatureFlags.ARROW_STREAMS;

@OpenSearchIntegTestCase.ClusterScope(scope = OpenSearchIntegTestCase.Scope.SUITE, numDataNodes = 5)
public class ArrowFlightServerIT extends OpenSearchIntegTestCase {

private FlightClientManager flightClientManager;

@BeforeClass
public static void setupFeatureFlags() {
FeatureFlagSetter.set(FeatureFlags.ARROW_STREAMS_SETTING.getKey());
}

@Override
protected Collection<Class<? extends Plugin>> nodePlugins() {
return Collections.singleton(FlightStreamPlugin.class);
Expand All @@ -48,6 +42,7 @@ public void setUp() throws Exception {
flightClientManager = flightService.getFlightClientManager();
}

@LockFeatureFlag(ARROW_STREAMS)
public void testArrowFlightEndpoint() throws Exception {
for (DiscoveryNode node : getClusterState().nodes()) {
try (FlightClient flightClient = flightClientManager.getFlightClient(node.getId()).get()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,9 +19,7 @@
import org.opensearch.common.network.NetworkService;
import org.opensearch.common.settings.Setting;
import org.opensearch.common.settings.Settings;
import org.opensearch.common.util.FeatureFlags;
import org.opensearch.plugins.SecureTransportSettingsProvider;
import org.opensearch.test.FeatureFlagSetter;
import org.opensearch.test.OpenSearchTestCase;
import org.opensearch.threadpool.ExecutorBuilder;
import org.opensearch.threadpool.ThreadPool;
Expand All @@ -31,19 +29,18 @@
import java.util.List;
import java.util.function.Supplier;

import static org.opensearch.common.util.FeatureFlags.ARROW_STREAMS_SETTING;
import static org.opensearch.common.util.FeatureFlags.ARROW_STREAMS;
import static org.opensearch.plugins.NetworkPlugin.AuxTransport.AUX_TRANSPORT_TYPES_KEY;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;

public class FlightStreamPluginTests extends OpenSearchTestCase {
private Settings settings;
private final Settings settings = Settings.EMPTY;
private ClusterService clusterService;

@Override
public void setUp() throws Exception {
super.setUp();
settings = Settings.builder().put(ARROW_STREAMS_SETTING.getKey(), true).build();
clusterService = mock(ClusterService.class);
ClusterState clusterState = mock(ClusterState.class);
DiscoveryNodes nodes = mock(DiscoveryNodes.class);
Expand All @@ -52,9 +49,8 @@ public void setUp() throws Exception {
when(nodes.getLocalNodeId()).thenReturn("test-node");
}

@LockFeatureFlag(ARROW_STREAMS)
public void testPluginEnabled() throws IOException {
FeatureFlags.initializeFeatureFlags(settings);
FeatureFlagSetter.set(ARROW_STREAMS_SETTING.getKey());
FlightStreamPlugin plugin = new FlightStreamPlugin(settings);
Collection<Object> components = plugin.createComponents(
null,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,6 @@
import org.opensearch.core.action.ActionListener;
import org.opensearch.core.common.transport.BoundTransportAddress;
import org.opensearch.core.common.transport.TransportAddress;
import org.opensearch.test.FeatureFlagSetter;
import org.opensearch.test.OpenSearchTestCase;
import org.opensearch.threadpool.ThreadPool;
import org.opensearch.transport.client.Client;
Expand All @@ -55,6 +54,7 @@
import io.netty.util.NettyRuntime;

import static org.opensearch.arrow.flight.bootstrap.FlightClientManager.LOCATION_TIMEOUT_MS;
import static org.opensearch.common.util.FeatureFlags.ARROW_STREAMS;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.doAnswer;
Expand All @@ -64,6 +64,7 @@

@SuppressWarnings("unchecked")
public class FlightClientManagerTests extends OpenSearchTestCase {
private static FeatureFlags.TestUtils.FlagWriteLock ffLock = null;

private static BufferAllocator allocator;
private static EventLoopGroup elg;
Expand All @@ -78,6 +79,7 @@ public class FlightClientManagerTests extends OpenSearchTestCase {

@BeforeClass
public static void setupClass() throws Exception {
ffLock = new FeatureFlags.TestUtils.FlagWriteLock(ARROW_STREAMS);
ServerConfig.init(Settings.EMPTY);
allocator = new RootAllocator();
elg = ServerConfig.createELG("test-grpc-worker-elg", NettyRuntime.availableProcessors() * 2);
Expand All @@ -89,7 +91,6 @@ public void setUp() throws Exception {
super.setUp();
locationUpdaterExecutor = Executors.newScheduledThreadPool(1);

FeatureFlagSetter.set(FeatureFlags.ARROW_STREAMS_SETTING.getKey());
clusterService = mock(ClusterService.class);
client = mock(Client.class);
state = getDefaultState();
Expand Down Expand Up @@ -176,6 +177,7 @@ private DiscoveryNode createNode(String nodeId, String host, int port) throws Ex
@AfterClass
public static void tearClass() {
allocator.close();
ffLock.close();
}

public void testGetFlightClientForExistingNode() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,6 @@
import org.opensearch.common.settings.Settings;
import org.opensearch.common.util.FeatureFlags;
import org.opensearch.core.common.transport.TransportAddress;
import org.opensearch.test.FeatureFlagSetter;
import org.opensearch.test.OpenSearchTestCase;
import org.opensearch.threadpool.ThreadPool;
import org.opensearch.transport.client.Client;
Expand All @@ -32,10 +31,12 @@
import java.util.concurrent.ExecutorService;
import java.util.concurrent.atomic.AtomicInteger;

import static org.opensearch.common.util.FeatureFlags.ARROW_STREAMS;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;

public class FlightServiceTests extends OpenSearchTestCase {
FeatureFlags.TestUtils.FlagWriteLock ffLock = null;

private Settings settings;
private ClusterService clusterService;
Expand All @@ -47,7 +48,7 @@ public class FlightServiceTests extends OpenSearchTestCase {
@Override
public void setUp() throws Exception {
super.setUp();
FeatureFlagSetter.set(FeatureFlags.ARROW_STREAMS_SETTING.getKey());
ffLock = new FeatureFlags.TestUtils.FlagWriteLock(ARROW_STREAMS);
int availablePort = getBasePort(9500) + port.addAndGet(1);
settings = Settings.EMPTY;
localNode = createNode(availablePort);
Expand Down Expand Up @@ -147,6 +148,7 @@ public void testLifecycleStateTransitions() throws Exception {
@Override
public void tearDown() throws Exception {
super.tearDown();
ffLock.close();
}

private DiscoveryNode createNode(int port) throws Exception {
Expand Down
Loading
Loading