diff --git oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/IndexConstants.java oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/IndexConstants.java
index d098292..0e65c69 100644
--- oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/IndexConstants.java
+++ oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/IndexConstants.java
@@ -125,4 +125,19 @@ public interface IndexConstants {
      */
     String REINDEX_RETAIN = "retainNodeInReindex";
 
+    /**
+     * Index type for disabled indexes
+     */
+    String TYPE_DISABLED = "disabled";
+
+    /**
+     * Multi value property referring to index paths which current index supersedes
+     */
+    String SUPERSEDED_INDEX_PATHS = "supersedes";
+
+    /**
+     * Boolean flag indicating that old indexes need to be disabled
+     */
+    String DISABLE_INDEXES_ON_NEXT_CYCLE = ":disableIndexesOnNextCycle";
+
 }
diff --git oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/IndexUpdate.java oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/IndexUpdate.java
index 11cbc99..ef1b0bf 100644
--- oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/IndexUpdate.java
+++ oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/IndexUpdate.java
@@ -56,6 +56,7 @@ import org.apache.jackrabbit.oak.plugins.index.NodeTraversalCallback.PathSource;
 import org.apache.jackrabbit.oak.plugins.index.progress.IndexingProgressReporter;
 import org.apache.jackrabbit.oak.plugins.index.progress.NodeCountEstimator;
 import org.apache.jackrabbit.oak.plugins.index.progress.TraversalRateEstimator;
+import org.apache.jackrabbit.oak.plugins.index.upgrade.IndexDisabler;
 import org.apache.jackrabbit.oak.spi.commit.CommitInfo;
 import org.apache.jackrabbit.oak.spi.commit.Editor;
 import org.apache.jackrabbit.oak.spi.state.NodeBuilder;
@@ -143,7 +144,7 @@ public class IndexUpdate implements Editor, PathSource {
         this.parent = null;
         this.name = null;
         this.path = "/";
-        this.rootState = new IndexUpdateRootState(provider, async, root, updateCallback, traversalCallback, commitInfo, corruptIndexHandler);
+        this.rootState = new IndexUpdateRootState(provider, async, root, builder, updateCallback, traversalCallback, commitInfo, corruptIndexHandler);
         this.builder = checkNotNull(builder);
     }
 
@@ -281,7 +282,10 @@ public class IndexUpdate implements Editor, PathSource {
                         clearCorruptFlag(definition, indexPath);
                         reindex.put(concat(getPath(), INDEX_DEFINITIONS_NAME, name), editor);
                     }
+
+                    rootState.indexDisabler.markDisableFlagIfRequired(indexPath, definition);
                 } else {
+                    rootState.indexDisabler.disableOldIndexes(indexPath, definition);
                     editors.add(editor);
                 }
             }
@@ -529,6 +533,7 @@ public class IndexUpdate implements Editor, PathSource {
         final String async;
         final NodeState root;
         final CommitInfo commitInfo;
+        final IndexDisabler indexDisabler;
         private boolean ignoreReindexFlags = IGNORE_REINDEX_FLAGS;
         final Set<IndexCommitCallback> indexCommitCallbacks = newIdentityHashSet();
         final CorruptIndexHandler corruptIndexHandler;
@@ -538,13 +543,15 @@ public class IndexUpdate implements Editor, PathSource {
         private MissingIndexProviderStrategy missingProvider = new MissingIndexProviderStrategy();
 
         private IndexUpdateRootState(IndexEditorProvider provider, String async, NodeState root,
-                                     IndexUpdateCallback updateCallback, NodeTraversalCallback traversalCallback,
+                                     NodeBuilder builder, IndexUpdateCallback updateCallback,
+                                     NodeTraversalCallback traversalCallback,
                                      CommitInfo commitInfo, CorruptIndexHandler corruptIndexHandler) {
             this.provider = checkNotNull(provider);
             this.async = async;
             this.root = checkNotNull(root);
             this.commitInfo = commitInfo;
             this.corruptIndexHandler = corruptIndexHandler;
+            this.indexDisabler = new IndexDisabler(builder);
             this.progressReporter = new IndexingProgressReporter(updateCallback, traversalCallback);
         }
 
diff --git oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/importer/IndexImporter.java oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/importer/IndexImporter.java
index 439bda2..0b231e4 100644
--- oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/importer/IndexImporter.java
+++ oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/importer/IndexImporter.java
@@ -36,6 +36,7 @@ import org.apache.jackrabbit.oak.plugins.index.IndexUpdate;
 import org.apache.jackrabbit.oak.plugins.index.IndexUpdateCallback;
 import org.apache.jackrabbit.oak.plugins.index.IndexUtils;
 import org.apache.jackrabbit.oak.plugins.index.importer.AsyncIndexerLock.LockToken;
+import org.apache.jackrabbit.oak.plugins.index.upgrade.IndexDisabler;
 import org.apache.jackrabbit.oak.spi.commit.EditorDiff;
 import org.apache.jackrabbit.oak.spi.commit.VisibleEditor;
 import org.apache.jackrabbit.oak.spi.state.NodeBuilder;
@@ -127,6 +128,7 @@ public class IndexImporter {
     void importIndexData() throws CommitFailedException, IOException {
         NodeState root = nodeStore.getRoot();
         NodeBuilder rootBuilder = root.builder();
+        IndexDisabler indexDisabler = new IndexDisabler(rootBuilder);
         for (IndexInfo indexInfo : asyncLaneToIndexMapping.values()) {
             log.info("Importing index data for {}", indexInfo.indexPath);
             NodeBuilder idxBuilder = indexDefinitionUpdater.apply(rootBuilder, indexInfo.indexPath);
@@ -141,6 +143,8 @@ public class IndexImporter {
             //TODO How to support CompositeNodeStore where some of the child nodes would be hidden
             incrementReIndexCount(idxBuilder);
             getImporter(indexInfo.type).importIndex(root, idxBuilder, indexInfo.indexDir);
+
+            indexDisabler.markDisableFlagIfRequired(indexInfo.indexPath, idxBuilder);
         }
         mergeWithConcurrentCheck(nodeStore, rootBuilder, indexEditorProvider);
     }
diff --git oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/upgrade/IndexDisabler.java oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/upgrade/IndexDisabler.java
new file mode 100644
index 0000000..4825731
--- /dev/null
+++ oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/index/upgrade/IndexDisabler.java
@@ -0,0 +1,155 @@
+/*
+ * 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.jackrabbit.oak.plugins.index.upgrade;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Set;
+
+import com.google.common.collect.Sets;
+import org.apache.jackrabbit.oak.api.PropertyState;
+import org.apache.jackrabbit.oak.api.Type;
+import org.apache.jackrabbit.oak.commons.PathUtils;
+import org.apache.jackrabbit.oak.spi.state.NodeBuilder;
+import org.apache.jackrabbit.oak.spi.state.NodeState;
+import org.apache.jackrabbit.oak.spi.state.NodeStateUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static java.util.Collections.emptyList;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.DECLARING_NODE_TYPES;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.SUPERSEDED_INDEX_PATHS;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.TYPE_DISABLED;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.TYPE_PROPERTY_NAME;
+
+public class IndexDisabler {
+    private static final Logger log = LoggerFactory.getLogger(IndexDisabler.class);
+    private final NodeBuilder rootBuilder;
+
+    public IndexDisabler(NodeBuilder rootBuilder) {
+        this.rootBuilder = rootBuilder;
+    }
+
+    public boolean markDisableFlagIfRequired(String currentIndexPath, NodeBuilder idxBuilder) {
+        boolean disableRequired = isAnyIndexToBeDisabled(currentIndexPath, idxBuilder);
+        if (disableRequired) {
+            idxBuilder.setProperty(DISABLE_INDEXES_ON_NEXT_CYCLE, true);
+        }
+        return disableRequired;
+    }
+
+    private boolean isAnyIndexToBeDisabled(String currentIndexPath, NodeBuilder idxBuilder) {
+        PropertyState indexPathsProp = idxBuilder.getProperty(SUPERSEDED_INDEX_PATHS);
+
+        if (indexPathsProp == null) {
+            return false;
+        }
+
+        Iterable<String> indexPaths = indexPathsProp.getValue(Type.STRINGS);
+        for (final String indexPath : indexPaths) {
+            if (isNodeTypePath(indexPath)) {
+                String nodeTypeName = PathUtils.getName(indexPath).substring(1);
+                String nodeTypeIndexPath = PathUtils.getParentPath(indexPath);
+
+                NodeState idxSate = NodeStateUtils.getNode(rootBuilder.getBaseState(), nodeTypeIndexPath);
+                if (idxSate.exists()
+                        && idxSate.hasProperty(DECLARING_NODE_TYPES)){
+                    Set<String> existingTypes = Sets.newHashSet(idxSate.
+                            getProperty(DECLARING_NODE_TYPES).getValue(Type.NAMES));
+                    if (existingTypes.contains(nodeTypeName)) {
+                        return true;
+                    }
+                }
+            } else {
+                NodeState idxSate = NodeStateUtils.getNode(rootBuilder.getBaseState(), indexPath);
+                if (idxSate.exists() && !TYPE_DISABLED.equals(idxSate.getString(TYPE_PROPERTY_NAME))) {
+                    return true;
+                }
+            }
+        }
+
+        return false;
+    }
+
+    public List<String> disableOldIndexes(String currentIndexPath, NodeBuilder idxBuilder) {
+        PropertyState indexPathsProp = idxBuilder.getProperty(SUPERSEDED_INDEX_PATHS);
+
+        if (indexPathsProp == null) {
+            return emptyList();
+        }
+
+        if (!idxBuilder.getBoolean(DISABLE_INDEXES_ON_NEXT_CYCLE)) {
+            return emptyList();
+        }
+
+        //Skip disabling for the cycle where reindexing just got completed
+        if (idxBuilder.isReplaced(DISABLE_INDEXES_ON_NEXT_CYCLE)){
+            return emptyList();
+        }
+
+        Iterable<String> indexPaths = indexPathsProp.getValue(Type.STRINGS);
+        List<String> disabledIndexes = new ArrayList<>();
+        for (final String indexPath : indexPaths) {
+            if (isNodeTypePath(indexPath)) {
+                String nodeTypeName = PathUtils.getName(indexPath).substring(1);
+                String nodeTypeIndexPath = PathUtils.getParentPath(indexPath);
+
+                NodeBuilder nodeTypeIndexBuilder = child(rootBuilder, nodeTypeIndexPath);
+                if (nodeTypeIndexBuilder.exists()
+                        && nodeTypeIndexBuilder.hasProperty(DECLARING_NODE_TYPES)){
+                    Set<String> existingTypes = Sets.newHashSet(nodeTypeIndexBuilder.
+                            getProperty(DECLARING_NODE_TYPES).getValue(Type.NAMES));
+                    if (existingTypes.remove(nodeTypeName)) {
+                        disabledIndexes.add(indexPath);
+                        nodeTypeIndexBuilder.setProperty(DECLARING_NODE_TYPES, existingTypes, Type.NAMES);
+                    }
+                }
+            } else {
+                NodeBuilder disabledIndexBuilder = child(rootBuilder, indexPath);
+                if (disabledIndexBuilder.exists()) {
+                    disabledIndexBuilder.setProperty(TYPE_PROPERTY_NAME, TYPE_DISABLED);
+                    disabledIndexes.add(indexPath);
+                }
+            }
+        }
+
+        if (!disabledIndexes.isEmpty()) {
+            log.info("Index at [{}] supersedes indexes {}. Marking those as disabled",
+                    currentIndexPath, disabledIndexes);
+            idxBuilder.removeProperty(DISABLE_INDEXES_ON_NEXT_CYCLE);
+        }
+
+        return disabledIndexes;
+    }
+
+    private static boolean isNodeTypePath(String indexPath) {
+        String lastPathSegment = PathUtils.getName(indexPath);
+        return lastPathSegment.startsWith("@");
+    }
+
+    private static NodeBuilder child(NodeBuilder nb, String path) {
+        for (String name : PathUtils.elements(checkNotNull(path))) {
+            nb = nb.getChildNode(name);
+        }
+        return nb;
+    }
+}
diff --git oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/IndexUpdateTest.java oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/IndexUpdateTest.java
index ff835d3..11ead04 100644
--- oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/IndexUpdateTest.java
+++ oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/IndexUpdateTest.java
@@ -27,6 +27,7 @@ import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.INDEX_DEFIN
 import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.REINDEX_ASYNC_PROPERTY_NAME;
 import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.REINDEX_COUNT;
 import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.REINDEX_PROPERTY_NAME;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.TYPE_PROPERTY_NAME;
 import static org.apache.jackrabbit.oak.plugins.index.IndexUtils.createIndexDefinition;
 import static org.apache.jackrabbit.oak.InitialContent.INITIAL_CONTENT;
 import static org.hamcrest.CoreMatchers.instanceOf;
@@ -875,6 +876,42 @@ public class IndexUpdateTest {
         }
     }
 
+    @Test
+    public void indexesDisabled() throws Exception{
+        NodeState before = builder.getNodeState();
+        createIndexDefinition(builder.child(INDEX_DEFINITIONS_NAME),
+                "fooIndex", true, false, ImmutableSet.of("foo"), null);
+        createIndexDefinition(builder.child(INDEX_DEFINITIONS_NAME),
+                "barIndex", true, false, ImmutableSet.of("bar"), null);
+        builder.child("testRoot").setProperty("foo", "abc");
+        NodeState after = builder.getNodeState();
+
+        NodeState indexed = HOOK.processCommit(before, after, CommitInfo.EMPTY);
+
+        before = indexed;
+        builder = indexed.builder();
+        NodeBuilder newIndex = createIndexDefinition(builder.child(INDEX_DEFINITIONS_NAME),
+                "newIndex", true, false, ImmutableSet.of("bar"), null);
+        newIndex.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS, asList("/oak:index/fooIndex"), Type.STRINGS);
+
+        after = builder.getNodeState();
+        indexed = HOOK.processCommit(before, after, CommitInfo.EMPTY);
+
+        //Post reindex also index should not be disabled
+        assertEquals("property", indexed.getChildNode("oak:index").getChildNode("fooIndex").getString(TYPE_PROPERTY_NAME));
+        assertTrue(indexed.getChildNode("oak:index").getChildNode("newIndex").getBoolean(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE));
+
+        before = indexed;
+        builder = indexed.builder();
+        builder.child("testRoot2").setProperty("foo", "abc");
+        after = builder.getNodeState();
+        indexed = HOOK.processCommit(before, after, CommitInfo.EMPTY);
+
+        //Index only disabled after next cycle
+        assertEquals(IndexConstants.TYPE_DISABLED, indexed.getChildNode("oak:index").getChildNode("fooIndex").getString(TYPE_PROPERTY_NAME));
+        assertFalse(indexed.getChildNode("oak:index").getChildNode("newIndex").getBoolean(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE));
+    }
+
     private static void markCorrupt(NodeBuilder builder, String indexName) {
         builder.getChildNode(INDEX_DEFINITIONS_NAME).getChildNode(indexName)
                 .setProperty(IndexConstants.CORRUPT_PROPERTY_NAME, ISO8601.format(Calendar.getInstance()));
diff --git oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/importer/IndexImporterTest.java oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/importer/IndexImporterTest.java
index 13ed77b..512dcd9 100644
--- oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/importer/IndexImporterTest.java
+++ oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/importer/IndexImporterTest.java
@@ -72,6 +72,8 @@ import static org.apache.jackrabbit.oak.InitialContent.INITIAL_CONTENT;
 import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.ASYNC_PROPERTY_NAME;
 import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.INDEX_DEFINITIONS_NAME;
 import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.REINDEX_COUNT;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.TYPE_DISABLED;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.TYPE_PROPERTY_NAME;
 import static org.apache.jackrabbit.oak.plugins.index.IndexUtils.createIndexDefinition;
 import static org.apache.jackrabbit.oak.plugins.index.importer.AsyncIndexerLock.NOOP_LOCK;
 import static org.apache.jackrabbit.oak.plugins.index.importer.IndexDefinitionUpdater.INDEX_DEFINITIONS_JSON;
@@ -331,6 +333,53 @@ public class IndexImporterTest {
         assertEquals(2, idx.getLong("reindexCount"));
     }
 
+    @Test
+    public void importData_DisabledIndexes() throws Exception{
+        NodeBuilder builder = store.getRoot().builder();
+        NodeBuilder idxa = createIndexDefinition(builder.child(INDEX_DEFINITIONS_NAME),
+                "fooIndex", true, false, ImmutableSet.of("foo"), null);
+        idxa.setProperty(ASYNC_PROPERTY_NAME, "async");
+        idxa.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS, asList("/oak:index/barIndex"), Type.STRINGS);
+
+        builder.child("a").setProperty("foo", "abc");
+        builder.child("b").setProperty("foo", "abc");
+        store.merge(builder, EmptyHook.INSTANCE, CommitInfo.EMPTY);
+
+        new AsyncIndexUpdate("async", store, provider).run();
+
+        String checkpoint = createIndexDirs("/oak:index/fooIndex");
+
+        builder = store.getRoot().builder();
+
+        createIndexDefinition(builder.child(INDEX_DEFINITIONS_NAME),
+                "barIndex", true, false, ImmutableSet.of("foo"), null);
+
+        builder.child("c").setProperty("foo", "abc");
+        builder.child("d").setProperty("foo", "abc");
+        store.merge(builder, EmptyHook.INSTANCE, CommitInfo.EMPTY);
+
+        new AsyncIndexUpdate("async", store, provider).run();
+
+        IndexImporterProvider importerProvider = new IndexImporterProvider() {
+            @Override
+            public void importIndex(NodeState root, NodeBuilder defn, File indexDir) {
+            }
+
+            @Override
+            public String getType() {
+                return "property";
+            }
+        };
+
+        IndexImporter importer = new IndexImporter(store, temporaryFolder.getRoot(), provider, NOOP_LOCK);
+        importer.addImporterProvider(importerProvider);
+
+        importer.importIndex();
+
+        NodeState idx = store.getRoot().getChildNode("oak:index").getChildNode("barIndex");
+        assertEquals(TYPE_DISABLED, idx.getString(TYPE_PROPERTY_NAME));
+    }
+
     private NodeState getFooIndexNodeState() throws CommitFailedException {
         NodeState root = INITIAL_CONTENT;
         // Add index definition
diff --git oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/upgrade/IndexDisablerTest.java oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/upgrade/IndexDisablerTest.java
new file mode 100644
index 0000000..4bb1019
--- /dev/null
+++ oak-core/src/test/java/org/apache/jackrabbit/oak/plugins/index/upgrade/IndexDisablerTest.java
@@ -0,0 +1,229 @@
+/*
+ * 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.jackrabbit.oak.plugins.index.upgrade;
+
+import java.util.List;
+import java.util.Set;
+
+import com.google.common.collect.ImmutableSet;
+import com.google.common.collect.Sets;
+import org.apache.jackrabbit.oak.api.PropertyState;
+import org.apache.jackrabbit.oak.api.Type;
+import org.apache.jackrabbit.oak.plugins.index.IndexConstants;
+import org.apache.jackrabbit.oak.spi.state.NodeBuilder;
+import org.junit.Test;
+
+import static java.util.Arrays.asList;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.DECLARING_NODE_TYPES;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.INDEX_DEFINITIONS_NAME;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.TYPE_DISABLED;
+import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.TYPE_PROPERTY_NAME;
+import static org.apache.jackrabbit.oak.plugins.index.IndexUtils.createIndexDefinition;
+import static org.apache.jackrabbit.oak.plugins.memory.EmptyNodeState.EMPTY_NODE;
+import static org.hamcrest.Matchers.containsInAnyOrder;
+import static org.junit.Assert.*;
+
+public class IndexDisablerTest {
+    private NodeBuilder builder = EMPTY_NODE.builder();
+    private NodeBuilder rootBuilder = EMPTY_NODE.builder();
+    private IndexDisabler disabler = new IndexDisabler(rootBuilder);
+
+    @Test
+    public void simpleIndex() throws Exception{
+        List<String> disabledIndexes = disabler.disableOldIndexes("/oak:index/foo", builder);
+        assertTrue(disabledIndexes.isEmpty());
+    }
+
+    @Test
+    public void disableIndexes() throws Exception{
+        rootBuilder.child("oak:index").child("fooIndex");
+
+        builder.setProperty(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE, true);
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex", "/oak:index/barIndex"), Type.STRINGS);
+
+        List<String> disabledIndexes = disabler.disableOldIndexes("/oak:index/foo", builder);
+        assertThat(disabledIndexes, containsInAnyOrder("/oak:index/fooIndex"));
+        assertFalse(builder.getBoolean(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE));
+        assertEquals(TYPE_DISABLED,
+                rootBuilder.getChildNode("oak:index").getChildNode("fooIndex").getString(TYPE_PROPERTY_NAME));
+
+        //Check no node created for non existing node
+        assertFalse(rootBuilder.getChildNode("oak:index").getChildNode("barIndex").exists());
+
+        builder = builder.getNodeState().builder();
+        List<String> disabledIndexes2 = disabler.disableOldIndexes("/oak:index/foo", builder);
+        assertTrue(disabledIndexes2.isEmpty());
+    }
+
+    /**
+     * Test that indexes are not disabled in same cycle
+     * as when reindexing is done
+     */
+    @Test
+    public void reindexCase() throws Exception{
+        rootBuilder.child("oak:index").child("fooIndex");
+
+        builder.setProperty(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE, true);
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex", "/oak:index/barIndex"), Type.STRINGS);
+
+        builder = builder.getNodeState().builder();
+
+        List<String> disabledIndexes = disabler.disableOldIndexes("/oak:index/foo", builder);
+        assertTrue(disabledIndexes.isEmpty());
+    }
+
+    @Test
+    public void nodeTypeIndexDisabling_noop() throws Exception{
+        builder.setProperty(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE, true);
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex/@bar"), Type.STRINGS);
+        List<String> disabledIndexes = disabler.disableOldIndexes("/oak:index/foo", builder);
+        assertTrue(disabledIndexes.isEmpty());
+    }
+
+    @Test
+    public void nodeTypeIndexDisabling_noDeclaringTypes() throws Exception{
+        builder.setProperty(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE, true);
+        rootBuilder.child("oak:index").child("fooIndex");
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex/@bar"), Type.STRINGS);
+        List<String> disabledIndexes = disabler.disableOldIndexes("/oak:index/foo", builder);
+        assertTrue(disabledIndexes.isEmpty());
+    }
+
+    @Test
+    public void nodeTypeIndexDisabling_typeNotExist() throws Exception{
+        createIndexDefinition(rootBuilder.child(INDEX_DEFINITIONS_NAME),
+                "fooIndex", true, false, ImmutableSet.of("foo"), asList("oak:TestNode"));
+        builder.setProperty(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE, true);
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex/@oak:BarType"), Type.STRINGS);
+        List<String> disabledIndexes = disabler.disableOldIndexes("/oak:index/foo", builder);
+        assertTrue(disabledIndexes.isEmpty());
+    }
+
+    @Test
+    public void nodeTypeIndexDisabling_typeExist() throws Exception{
+        createIndexDefinition(rootBuilder.child(INDEX_DEFINITIONS_NAME),
+                "fooIndex", true, false, ImmutableSet.of("foo"), asList("oak:TestNode", "oak:BarType"));
+
+        builder.setProperty(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE, true);
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex/@oak:BarType"), Type.STRINGS);
+        List<String> disabledIndexes = disabler.disableOldIndexes("/oak:index/foo", builder);
+        assertThat(disabledIndexes, containsInAnyOrder("/oak:index/fooIndex/@oak:BarType"));
+        assertFalse(builder.getBoolean(IndexConstants.DISABLE_INDEXES_ON_NEXT_CYCLE));
+
+
+        PropertyState declaringNodeType = rootBuilder.getChildNode(INDEX_DEFINITIONS_NAME).getChildNode("fooIndex").getProperty(DECLARING_NODE_TYPES);
+        assertEquals(Type.NAMES, declaringNodeType.getType());
+
+        Set<String> names = Sets.newHashSet(declaringNodeType.getValue(Type.NAMES));
+        assertThat(names, containsInAnyOrder("oak:TestNode"));
+    }
+
+    //~-------------------------------< anyIndexToBeDisabled >
+
+    @Test
+    public void indexToBeDisabled_Noop() throws Exception{
+        assertFalse(disabler.markDisableFlagIfRequired("/oak:index/foo", builder));
+        assertFalse(builder.getBoolean(DISABLE_INDEXES_ON_NEXT_CYCLE));
+    }
+
+    @Test
+    public void indexToBeDisabled_PathNotExists() throws Exception{
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex", "/oak:index/barIndex"), Type.STRINGS);
+        assertFalse(disabler.markDisableFlagIfRequired("/oak:index/foo", builder));
+        assertFalse(builder.getBoolean(DISABLE_INDEXES_ON_NEXT_CYCLE));
+    }
+
+    @Test
+    public void indexToBeDisabled_PathExistsButDisabled() throws Exception{
+        rootBuilder.child("oak:index").child("fooIndex").setProperty(TYPE_PROPERTY_NAME, TYPE_DISABLED);
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex", "/oak:index/barIndex"), Type.STRINGS);
+        assertFalse(disabler.markDisableFlagIfRequired("/oak:index/foo", builder));
+        assertFalse(builder.getBoolean(DISABLE_INDEXES_ON_NEXT_CYCLE));
+    }
+
+    @Test
+    public void indexToBeDisabled_PathExists() throws Exception{
+        rootBuilder.child("oak:index").child("fooIndex").setProperty(TYPE_PROPERTY_NAME, "property");
+        recreateDisabler();
+
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex", "/oak:index/barIndex"), Type.STRINGS);
+        assertTrue(disabler.markDisableFlagIfRequired("/oak:index/foo", builder));
+        assertTrue(builder.getBoolean(DISABLE_INDEXES_ON_NEXT_CYCLE));
+    }
+
+    @Test
+    public void nodeTypeIndexToBeDisabled_PathNotExists() throws Exception{
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex/@bar", "/oak:index/barIndex"), Type.STRINGS);
+        assertFalse(disabler.markDisableFlagIfRequired("/oak:index/foo", builder));
+        assertFalse(builder.getBoolean(DISABLE_INDEXES_ON_NEXT_CYCLE));
+    }
+
+    @Test
+    public void nodeTypeIndexToBeDisabled_DeclaringTypeNotExists() throws Exception{
+        rootBuilder.child("oak:index").child("fooIndex");
+        recreateDisabler();
+
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex/@bar", "/oak:index/barIndex"), Type.STRINGS);
+        assertFalse(disabler.markDisableFlagIfRequired("/oak:index/foo", builder));
+        assertFalse(builder.getBoolean(DISABLE_INDEXES_ON_NEXT_CYCLE));
+    }
+
+    @Test
+    public void nodeTypeIndexToBeDisabled_TypeNotExists() throws Exception{
+        createIndexDefinition(rootBuilder.child(INDEX_DEFINITIONS_NAME),
+                "fooIndex", true, false, ImmutableSet.of("foo"), asList("oak:TestNode"));
+        recreateDisabler();
+
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex/@bar", "/oak:index/barIndex"), Type.STRINGS);
+        assertFalse(disabler.markDisableFlagIfRequired("/oak:index/foo", builder));
+        assertFalse(builder.getBoolean(DISABLE_INDEXES_ON_NEXT_CYCLE));
+    }
+
+
+    @Test
+    public void nodeTypeIndexToBeDisabled_TypeExists() throws Exception{
+        createIndexDefinition(rootBuilder.child(INDEX_DEFINITIONS_NAME),
+                "fooIndex", true, false, ImmutableSet.of("foo"), asList("oak:TestNode"));
+        recreateDisabler();
+
+        builder.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS,
+                asList("/oak:index/fooIndex/@oak:TestNode", "/oak:index/barIndex"), Type.STRINGS);
+        assertTrue(disabler.markDisableFlagIfRequired("/oak:index/foo", builder));
+        assertTrue(builder.getBoolean(DISABLE_INDEXES_ON_NEXT_CYCLE));
+    }
+
+    private void recreateDisabler() {
+        disabler = new IndexDisabler(rootBuilder.getNodeState().builder());
+    }
+
+}
\ No newline at end of file
diff --git oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/IndexDefinitionBuilder.java oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/IndexDefinitionBuilder.java
index ddb9192..eb233f1 100644
--- oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/IndexDefinitionBuilder.java
+++ oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/IndexDefinitionBuilder.java
@@ -100,6 +100,11 @@ public final class IndexDefinitionBuilder {
         return this;
     }
 
+    public IndexDefinitionBuilder supersedes(String ... paths){
+        tree.setProperty(IndexConstants.SUPERSEDED_INDEX_PATHS, asList(paths), STRINGS);
+        return this;
+    }
+
     public IndexDefinitionBuilder codec(String codecName){
         tree.setProperty(LuceneIndexConstants.CODEC_NAME, checkNotNull(codecName));
         return this;
diff --git oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/IndexDefinitionBuilderTest.java oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/IndexDefinitionBuilderTest.java
index ceedaad..f54313c 100644
--- oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/IndexDefinitionBuilderTest.java
+++ oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/IndexDefinitionBuilderTest.java
@@ -63,6 +63,7 @@ public class IndexDefinitionBuilderTest {
     public void indexRule() throws Exception{
         builder.includedPaths("/a", "/b");
         builder.queryPaths("/c", "/d");
+        builder.supersedes("/e", "/f");
         builder.indexRule("nt:base")
                     .property("foo")
                         .ordered()
@@ -79,6 +80,7 @@ public class IndexDefinitionBuilderTest {
         assertTrue(state.getChildNode("indexRules").getChildNode("nt:base").exists());
         assertEquals(asList("/a", "/b"), state.getProperty(PathFilter.PROP_INCLUDED_PATHS).getValue(Type.STRINGS));
         assertEquals(asList("/c", "/d"), state.getProperty(IndexConstants.QUERY_PATHS).getValue(Type.STRINGS));
+        assertEquals(asList("/e", "/f"), state.getProperty(IndexConstants.SUPERSEDED_INDEX_PATHS).getValue(Type.STRINGS));
     }
 
     @Test
