---
title: ALTER INDEX
description: The ALTER INDEX statement moves the placement of an existing index
  or replica among different GSI nodes.
pubDate: 2026-08-17T09:53:44.266Z
antora:
  editUrl: https://github.com/couchbaselabs/docs-devex/edit/release/8.0/modules/n1ql/pages/n1ql-language-reference/alterindex.adoc
  xref: xref:server:n1ql:n1ql-language-reference/alterindex.adoc[]
---

[Consult the llms.txt file for a full list of contents](/llms.txt)
[View original HTML](/server/current/n1ql/n1ql-language-reference/alterindex.html)

# ALTER INDEX

> The ALTER INDEX statement moves the placement of an existing index or replica among different GSI nodes. 

The [ALTER VECTOR INDEX](altervectorindex.md) statement is a synonym for the ALTER INDEX statement. Both statements have the same functionality.

## [](#purpose)Purpose

You can use the `ALTER INDEX` statement to change the placement of an existing index or replica among different GSI nodes, to increase or decrease the number of replicas, or to drop a specified index replica temporarily. You can also use it to perform the same alterations to a partitioned index and any replica partitions. You may use this statement when you encounter any of the following situations:

* An imbalance occurs due to a particular index growing faster than expected and is needed on a different node.
* An imbalance occurs due to a cluster of indexes being dropped on a single node.
* A machine is scheduled for removal, so its indexes need to move off its current node.
* The automated process of rebalancing does not give the expected results.
* Other types of scaling up or scaling down are needed.

For example, if a node fails, you can use the `ALTER INDEX` statement to move an index to another node. See [Examples](#examples) below.

> [!NOTE]
> The ALTER INDEX move operation is asynchronous. As soon as the move alter index command is executed, the command returns. If there is no error in the input, the move operation can be tracked through the console UI and any error can be found in the Console logs and Indexer logs.

If a node goes down while an ALTER INDEX operation is happening, then the index would rollback to its original node (not affecting queries) and a notification would appear.

> [!IMPORTANT]
> It's not possible to move an index or index replica and change the number of index replicas at the same time.

## [](#prerequisites)Prerequisites

Only users with the RBAC role of `Administrator` are allowed to run the `ALTER INDEX` statement.

This statement is applicable only for Standard GSI (Plasma) and MOI Indexes; and hence supported only for Couchbase Server Enterprise Edition nodes. (Not applicable for Forest DB.)

Altering indexes is only supported in Couchbase Server 5.5 and later; if any nodes in the cluster are running a version of Couchbase Server earlier than 5.5, then this statement will not work.

In addition, altering the number of replicas or deleting an index replica is only supported in Couchbase Server 6.5 and later; if any nodes in the cluster are running a version of Couchbase Server earlier than 6.5, then these operations will not work.

## [](#syntax)Syntax

```ebnf
alter-index ::= 'ALTER' 'INDEX' ( index-path '.' index-name |
                index-name 'ON' keyspace-ref ) index-using? index-with
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/alter-index.png) 

The ALTER INDEX statement provides 2 possible syntaxes for specifying the index and the keyspace where the index is located.

| index-name   | (Required) A unique name that identifies the index.                                                                      |
| ------------ | ------------------------------------------------------------------------------------------------------------------------ |
| index-path   | (Optional) One possible syntax for specifying the keyspace. See [Index Path](#index-path).                               |
| keyspace-ref | (Optional) The other possible syntax for specifying the keyspace. See [Index Name ON Keyspace Reference](#keyspace-ref). |
| index-using  | (Optional) Specifies the index type. See [USING Clause](#index-using).                                                   |
| index-with   | (Required) Specifies options for the index. See [WITH Clause](#index-with).                                              |

### [](#index-path)Index Path

```ebnf
index-path ::= keyspace-full | keyspace-prefix | keyspace-partial
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/index-path.png) 

You can use a dotted notation to specify the index and the keyspace on which the index is built. This syntax provides compatibility with legacy versions of Couchbase Server. The index path may be a [full keyspace path](#keyspace-full-index), a [keyspace prefix](#keyspace-prefix-index), or a [keyspace partial](#keyspace-partial-index).

> [!NOTE]
> If there is a hyphen (-) inside the index name or any part of the index path, you must wrap the index name or that part of the index path in backticks (\` \`). See the examples on this page.

#### [](#keyspace-full-index)Index Path: Full Keyspace

```ebnf
keyspace-full ::= namespace ':' bucket '.' scope '.' collection
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/keyspace-full.png) 

If the index is built on a named collection, the index path may be a full keyspace path, including namespace, bucket, scope, and collection, followed by the index name. In this case, the [query context](../n1ql-intro/queriesandresults.md#query-context) is ignored.

| namespace  | (Required) An [identifier](identifiers.md) that refers to the [namespace](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace. Currently, only the default namespace is available. |
| ---------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| bucket     | (Required) An [identifier](identifiers.md) that refers to the [bucket name](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace.                                                   |
| scope      | (Required) An [identifier](identifiers.md) that refers to the [scope name](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace.                                                    |
| collection | (Required) An [identifier](identifiers.md) that refers to the [collection name](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace.                                               |

For example, `` default:`travel-sample`.inventory.airline.`idx-name` `` indicates the `idx-name` index on the `airline` collection in the `inventory` scope in the `` default:`travel-sample` `` bucket.

#### [](#keyspace-prefix-index)Index Path: Keyspace Prefix

```ebnf
keyspace-prefix ::= ( namespace ':' )? bucket
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/keyspace-prefix.png) 

If the index is built on the default collection in the default scope within a bucket, the index path may be just an optional namespace and the bucket name, followed by the index name. In this case, the [query context](../n1ql-intro/queriesandresults.md#query-context) should not be set.

| namespace | (Optional) An [identifier](identifiers.md) that refers to the [namespace](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace. Currently, only the default namespace is available. If the namespace name is omitted, the default namespace in the current session is used. |
| --------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| bucket    | (Required) An [identifier](identifiers.md) that refers to the [bucket name](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace.                                                                                                                                           |

For example, `` default:`travel-sample`.def_type `` indicates the `def_type` index on the default collection in the default scope in the `` default:`travel-sample` `` bucket.

#### [](#keyspace-partial-index)Index Path: Keyspace Partial

```ebnf
keyspace-partial ::= collection
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/keyspace-partial.png) 

Alternatively, if the keyspace is a named collection, the index path may be just the collection name, followed by the index name. In this case, you must set the [query context](../n1ql-intro/queriesandresults.md#query-context) to indicate the required namespace, bucket, and scope.

| collection | (Required) An [identifier](identifiers.md) that refers to the [collection name](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace. |
| ---------- | ------------------------------------------------------------------------------------------------------------------------------------------------------ |

For example, `` airline.`idx-name` `` indicates the `idx-name` index on the `airline` collection, assuming that the query context is set.

### [](#keyspace-ref)Index Name ON Keyspace Reference

```ebnf
keyspace-ref ::= keyspace-path | keyspace-partial
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/keyspace-ref.png) 

You can use the index name with the `ON` keyword and a keyspace reference to specify the keyspace on which the index is built. The keyspace reference may be a [keyspace path](#keyspace-path) or a [keyspace partial](#keyspace-partial).

> [!NOTE]
> If there is a hyphen (-) inside the index name or any part of the keyspace reference, you must wrap the index name or that part of the keyspace reference in backticks (\` \`). See the examples on this page.

#### [](#keyspace-path)Keyspace Reference: Keyspace Path

```ebnf
keyspace-path ::= ( namespace ':' )? bucket ( '.' scope '.' collection )?
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/keyspace-path.png) 

If the keyspace is a named collection, or the default collection in the default scope within a bucket, the keyspace reference may be a keyspace path. In this case, the [query context](../n1ql-intro/queriesandresults.md#query-context) should not be set.

| namespace  | (Optional) An [identifier](identifiers.md) that refers to the [namespace](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace. Currently, only the default namespace is available. If the namespace name is omitted, the default namespace in the current session is used. |
| ---------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| bucket     | (Required) An [identifier](identifiers.md) that refers to the [bucket name](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace.                                                                                                                                           |
| scope      | (Optional) An [identifier](identifiers.md) that refers to the [scope name](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace. If omitted, the bucket's default scope is used.                                                                                            |
| collection | (Optional) An [identifier](identifiers.md) that refers to the [collection name](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace. If omitted, the default collection in the bucket's default scope is used.                                                             |

For example, `` def_type ON default:`travel-sample` `` indicates the `def_type` index on the default collection in the default scope in the `` default:`travel-sample` `` bucket.

Similarly, `` `idx-name` ON default:`travel-sample`.inventory.airline `` indicates the `idx-name` index on the `airline` collection in the `inventory` scope in the `` default:`travel-sample` `` bucket.

#### [](#keyspace-partial)Keyspace Reference: Keyspace Partial

```ebnf
keyspace-partial ::= collection
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/keyspace-partial.png) 

Alternatively, if the keyspace is a named collection, the keyspace reference may be just the collection name. In this case, you must set the [query context](../n1ql-intro/queriesandresults.md#query-context) to indicate the required namespace, bucket, and scope.

| collection | (Required) An [identifier](identifiers.md) that refers to the [collection name](../n1ql-intro/queriesandresults.md#logical-hierarchy) of the keyspace. |
| ---------- | ------------------------------------------------------------------------------------------------------------------------------------------------------ |

For example, `` `idx-name` ON airline `` indicates the `idx-name` index on the `airline` collection, assuming the query context is set.

### [](#index-using)USING Clause

```ebnf
index-using ::= 'USING' 'GSI'
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/index-using.png) 

The index type for a secondary index must be Global Secondary Index (GSI). The `USING GSI` keywords are optional and may be omitted.

### [](#index-with)WITH Clause

```ebnf
index-with ::= 'WITH' expr
```

![Syntax diagram: see source code listing](../_images/n1ql-language-reference/index-with.png) 

Use the `WITH` clause to specify additional options.

| expr | An object with the following properties. |
| ---- | ---------------------------------------- |

| Name                        | Description                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          | Schema                                     |
| --------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------ |
| **action** _required_       | A string denoting the operation to be performed. The possible values are: move Moves an index (or its replicas) to a different node while not making any changes to the index topology — for example, the number of replicas remains the same. You must use the nodes property to specify the target node or nodes. replica\_count Alters the number of replicas. You must use the num\_replica property to specify the required number of replicas. You can use the nodes property to restrict the placement of index replicas to the specified nodes. The planner decides where to place any new index replicas on the available index nodes, based on the server load. drop\_replica Drops a specified replica temporarily; for example, to repair a replica. You must use the replicaId property to specify the replica to drop. | enum (move, replica\_count, drop\_replica) |
| **num\_replica** _optional_ | Required if action is set to replica\_count. An integer specifying the number of replicas of the index. The index service will automatically distribute these indexes amongst the index nodes in the cluster for load balancing and high availability purposes. The index service attempts to distribute the replicas based on the server groups in use in the cluster where possible. (You can restrict the number of index nodes available for index and index replica placement using the nodes property, described below.)                                                                                                                                                                                                                                                                                                       | Integer                                    |
| **nodes** _optional_        | Required if action is set to move;Optional if action is set to replica\_count. An array of strings, specifying a list of nodes. If action is set to move, the node list determines the new destination nodes for the index and its replicas. If action is set to replica\_count and you're increasing the number of replicas, the node list restricts the set of nodes available for placement of the index and its replicas. However, if action is set to replica\_count and you're decreasing the number of replicas, the nodes property is ignored. You cannot use this property if you have enabled file-based index rebalancing. See [Index Rebalance Methods](../../learn/clusters-and-availability/rebalance.md#index-rebalance-methods).                                                                                     | String array                               |
| **replicaId** _optional_    | Required if action is set to drop\_replica. An integer, specifying a replica ID.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     | Integer                                    |

## [](#usage)Usage

If you attempt to alter an index which is still scheduled for background creation, the request fails.

The statement will not work while the cluster is undergoing a rebalance.

### [](#moving-an-index-or-index-replicas)Moving an Index or Index Replicas

When moving an index or index replicas, the number of destination nodes must be the same as the number of nodes on which the index and any replicas are currently placed. You must specify the full node list, even if you only need to move a single replica.

Likewise, when moving a partitioned index, the number of destination nodes must be the same as the number of nodes on which the index partitions and any replicas are currently placed. You cannot use this statement to repartition an index across a different number of nodes.

The source and destination node ranges may overlap, for example you may move a partitioned index from `["192.168.0.15:9000", "27.0.0.1:9001"]` to `["192.168.0.15:9000", "127.0.0.1:9002"]`.

### [](#changing-the-replica-count)Changing the Replica Count

When changing the number of replicas, the specified number of replicas must be less than the number of index nodes available for placement. If the specified number of replicas is greater than or equal to the number of index nodes available for placement, then the operation will fail.

If you specify a node list when changing the number of replicas, the specified nodes must include all of the nodes on which the index or index partitions and any index replicas are currently placed.

When increasing the number of replicas, whether you specify a node list or not, no single index node will host more than 1 replica of the same index, or the same partition of the same index. Replicas are distributed across the available server groups.

When reducing the number of replicas, the index service will first drop unhealthy replicas, where an unhealthy replica is a replica with missing partitions. After all unhealthy replicas are dropped, the index service will if necessary drop replicas with the highest replica ID. An unhealthy replica may not have the highest replica ID, so after an index reduction there may be gaps in the sequence of replica IDs — for example, 1, 2, 4, where replica ID 3 was dropped.

### [](#dropping-a-specific-replica)Dropping a Specific Replica

When dropping a replica, the index topology does not change. The indexing service remembers the number of partitions and replicas specified for this index. Given sufficient capacity, the dropped replica is rebuilt after the next rebalance — although it may be placed on a different index node, depending on the resource usage statistics of the available nodes.

To find the ID of an index replica and see which node it's placed on, you can use the [Indexes screen in the Couchbase Web Console](../../manage/manage-ui/manage-ui.md#console-indexes) or query the [system:indexes](../n1ql-intro/sysinfo.md#querying-indexes) catalog.

When dropping a replica, it's possible to leave a server group with no replica. For a partitioned index, run a rebalance to move a replica into the vacant server group.

### [](#index-redistribution)Index Redistribution

Using this statement to move 1 index at a time may be cumbersome if there are a lot of indexes to be moved. The index redistribution setting enables you to specify how Couchbase Server redistributes indexes automatically on rebalance. For more information, see [Rebalance](../../learn/clusters-and-availability/rebalance.md#rebalancing-the-index-service).

## [](#return-value)Return Value

If the statement succeeds, then:

* The query returns an empty array.
* The index alteration is visible in the Query Workbench.
* After the movement is complete, the new indexes begin to service query scans.
* The command line displays the new index nodes.

If the statement fails, then:

* The original indexes continue to service query scans.
* The UI Log and Query Workbench has the appropriate error message.
* Some common errors include:

| Error Message                                                                                               | Possible Cause                                                                                    |
| ----------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------- |
| GSI index xxxxxxxx not found                                                                                | Mistyped an index name                                                                            |
| Missing Node Information For Move Index                                                                     | Mistyped "node" instead of "nodes" Mistyped punctuation or other item                             |
| No Index Movement Required for Specified Destination List                                                   | Entered the current node instead of the target node                                               |
| syntax error - at \\",\\"                                                                                   | Missed a double-quote mark (")                                                                    |
| Unable to find Index service for destination xxx.xxx.xxx.xxx:8091 or destination is not part of the cluster | Address does not exist or was mistyped Node is not running Node not properly added to the cluster |
| Unsupported action value                                                                                    | Mistyped the "action"                                                                             |

## [](#examples)Examples

When using the below examples, make sure that an up-to-date version of Couchbase Server Enterprise Edition is already running on the named nodes.

To try the examples in this section, set the query context to the `inventory` scope in the travel sample dataset. For more information, see [Query Context](../n1ql-intro/queriesandresults.md#query-context).

Example 1\. Move the `def_inventory_airport_faa` index from one node to another

Create a cluster of 3 nodes and then go to **Settings** **Sample buckets** to install the `travel-sample` bucket. The indexes are then installed in a round-robin fashion and distributed over the 3 nodes.

![The Indexes tab showing def_inventory_airport_faa on 192.168.10.10](../_images/alter-index_servers_step1.png) 

Then move the `def_inventory_airport_faa` index from its original node (192.168.10.**10** in this example) to a new node (192.168.10.**11** in this example).

```sqlpp
ALTER INDEX def_inventory_airport_faa ON airport
WITH {"action": "move", "nodes": ["192.168.10.11:8091"]};
```

You should see:

```json
{
  "results": []
}
```

![The Indexes tab showing def_inventory_airport_faa on 192.168.10.11](../_images/alter-index_servers_step2.png) 

Example 2\. Create and move an index replica from one node to another

Create an index on node 192.168.10.10 with a replica on node 192.168.10.11, then move its replica from node 192.168.10.**11** to 192.168.10.**12**.

```sqlpp
CREATE INDEX country_idx ON airport(country, city)
       USING GSI
       WITH {"nodes": ["192.168.10.10:8091", "192.168.10.11:8091"]};

ALTER INDEX country_idx ON airport
WITH {"action": "move", "nodes": ["192.168.10.10:8091", "192.168.10.12:8091"]};
```

Example 3\. Moving multiple replicas

Create an index on node 192.168.10.10 with replicas on nodes 192.168.10.**11** and 192.168.10.**12**, then move the replicas to nodes 192.168.10.**13** and 192.168.10.**14**.

```sqlpp
CREATE INDEX country_idx ON airport(country, city)
WITH {"nodes": ["192.168.10.10:8091", "192.168.10.11:8091", "192.168.10.12:8091"]};

ALTER INDEX country_idx ON airport
WITH {"action": "move",
      "nodes": ["192.168.10.10:8091", "192.168.10.13:8091", "192.168.10.14:8091"]};
```

Example 4\. Increasing the number of replicas

Create an index on node 192.168.10.10 with replicas on nodes 192.168.10.**11** and 192.168.10.**12**, then increase the number of replicas to 4 and specify that new replicas may be placed on any available index nodes in the cluster.

```sqlpp
CREATE INDEX country_idx ON airport(country, city)
WITH {"nodes": ["192.168.10.10:8091", "192.168.10.11:8091", "192.168.10.12:8091"]};

ALTER INDEX country_idx ON airport
WITH {"action": "replica_count", "num_replica": 4};
```

Example 5\. Increasing the number of replicas and restricting the nodes

Create an index on node 192.168.10.10 with replicas on nodes 192.168.10.**11** and 192.168.10.**12**, then increase the number of replicas to 4, and specify that replicas may now also be placed on nodes 192.168.10.**13** and 192.168.10.**14**.

```sqlpp
CREATE INDEX country_idx ON airport(country, city)
WITH {"nodes": ["192.168.10.10:8091", "192.168.10.11:8091", "192.168.10.12:8091"]};

ALTER INDEX country_idx ON airport
WITH {"action": "replica_count",
      "num_replica": 4,
      "nodes": ["192.168.10.10:8091",
                "192.168.10.11:8091",
                "192.168.10.12:8091",
                "192.168.10.13:8091",
                "192.168.10.14:8091"]};
```

Example 6\. Decreasing the number of replicas

Create an index on node 192.168.10.10 with replicas on nodes 192.168.10.**11** and 192.168.10.**12**, then decrease the number of replicas to 1.

```sqlpp
CREATE INDEX country_idx ON airport(country, city)
WITH {"nodes": ["192.168.10.10:8091", "192.168.10.11:8091", "192.168.10.12:8091"]};

ALTER INDEX country_idx ON airport
WITH {"action": "replica_count", "num_replica": 1};
```

Example 7\. Dropping a specific replica

Create an index with 2 replicas, and specify that nodes 192.168.10.10, 192.168.10.11, 192.168.10.12, and 192.168.10.13 should be available for index and replica placement. Then delete replica 2.

```sqlpp
CREATE INDEX country_idx ON airport(country, city)
USING GSI
WITH {"num_replica": 2,
      "nodes": ["192.168.10.10:8091",
                "192.168.10.11:8091",
                "192.168.10.12:8091",
                "192.168.10.13:8091"]};

ALTER INDEX country_idx ON airport
WITH {"action": "drop_replica", "replicaId": 2};
```

## [](#related-links)Related Links

* [Primary and Secondary Index Reference](../../indexes/indexing-overview.md)
* [Filtered Search Using Composite Vector Indexes](../../vector-index/composite-vector-index.md)
* [Vector Search Using Hyperscale Vector Indexes](../../vector-index/hyperscale-vector-index.md)
* [CREATE PRIMARY INDEX](createprimaryindex.md)| [CREATE INDEX](createindex.md)| [CREATE VECTOR INDEX](createvectorindex.md)
* [BUILD INDEX](build-index.md)
* [ALTER VECTOR INDEX](altervectorindex.md)
* [DROP PRIMARY INDEX](dropprimaryindex.md)| [DROP INDEX](dropindex.md)| [DROP VECTOR INDEX](dropvectorindex.md)