> For clean Markdown of any page, append .md to the page URL.
> For a complete documentation index, see https://docs.nvidia.com/infra-controller/llms.txt.
> For AI client integration (Claude Code, Cursor, etc.), connect to the MCP server at https://docs.nvidia.com/infra-controller/_mcp/server.

# Update VPC routing profile

PATCH https://nico-rest-api.nico.svc.cluster.local/v2/org/{org}/nico/vpc/{vpcId}/routing-profile
Content-Type: application/json

Change an existing FNN VPC to a configured routing profile with the opposite internal setting. Submit the destination `routingProfile` and optional exact `vni`; REST reads the current Core version internally and submits one change using that version. Core atomically changes the profile and active VNI, advances the version, and retains the old allocation. VPC identity, Instances, addresses, prefixes, NSGs, metadata, and the creation-time requested VNI are preserved.

Requires the same Infrastructure Provider ownership, registered Site, and `PROVIDER_ADMIN` authorization as [routing-state inspection](#tag/VPC/operation/get-vpc-routing-profile). Core also enforces the Tenant's permitted access tier; Provider authorization does not permit broader Tenant routing access. Named source and destination profiles, nonoverlapping internal and external pools, and VNIs in 1..16777215 are required. Site-global VNIs, substantive VPC or interface routing overrides, and tenant-managed SitePrefix attachments are unsupported. Every serving Core must support the requested operation, including exact VNI selection; response validation cannot undo a change made by an older Core that ignores the exact VNI.

REST makes no change if the initial read fails. A concurrent VPC update between the read and change returns 412 without rereading or retrying. Authorization, the read, and the change share one 50-second budget from handler entry within the HTTP request deadline. REST does not submit the change if its request context has expired before dispatch; a submitted workflow may outlive the caller. A timeout, lost response, or invalid acknowledgement after submission can leave a committed change; inspect the authoritative routing state before deciding on another request. Neither the mutation nor the full sequence is automatically retried. Each separate HTTP request is a new action, not a replay or deduplicated retry of a previous request.

A 200 response confirms the Core configuration transaction, not restored traffic. Prevent attachment, peering, deletion, and profile-definition changes until all attached and directly peered DPUs and fabric routes have been independently verified and the inactive allocation released. Neither REST nor Core enforces this hold or verifies convergence. Release is a [separate operator action](#tag/VPC/operation/release-vpc-inactive-vni). A later change back must pass current validation; retaining the allocation does not guarantee reversal. External routing does not allocate public addresses or configure NAT, fabric routes, or NSGs.

Reference: https://docs.nvidia.com/infra-controller/rest-api-reference/api-reference/vpc/update-vpc-routing-profile

## Authentication

- `Authorization` header (bearer token, required) — ``` export JWT_BEARER_TOKEN="<jwt-bearer-token>" # Example org name: "acme-inc export ORG_NAME=<org-name> # Use the JWT bearer token in your API request auth header: curl -v -X GET -H "Content-Type: application/json" -H "Authorization: Bearer $JWT_BEARER_TOKEN" https://nico-rest-api.nico.svc.cluster.local/v2/org/$ORG_NAME/nico/user/current ```

## Request

### Path parameters

- `org` (string, required) — Name of the Infrastructure Provider Org
- `vpcId` (string, required) — REST ID of the VPC

### Body (application/json)

This endpoint expects an object.

- `routingProfile` (string, required) — Required Site-configured destination profile with the opposite internal setting from the current profile. The REST aliases `external`, `internal`, and `privileged-internal` map to Core's `EXTERNAL`, `INTERNAL`, and `PRIVILEGED_INTERNAL` names. Other configured names are passed unchanged; this is not a closed enum.
- `vni` (integer, optional, nullable) — Optional exact destination VNI. Omission or null reuses an allocation retained in the destination pool, otherwise allocates automatically. An exact request must match a retained destination allocation if present; otherwise it must name a free materialized entry in the destination pool, regardless of that entry's automatic-allocation setting. A mismatched, occupied, missing, or already active VNI is rejected without fallback.

## Response

### 200

Committed routing state, including the retained previous allocation; dataplane convergence is not verified

- `vpcId` (string, required) — REST ID of the VPC selected in the request, which may differ from its Site-local Core ID.
- `version` (string, required) — Core VPC version observed with these allocations. Use this exact value when approving release of the observed inactive VNI; it is not a DPU-applied version.
- `routingProfile` (string, required, nullable) — Persisted profile name, or null when no named profile is stored. Known Core names are returned as the REST aliases `external`, `internal`, and `privileged-internal`; other names are unchanged. The name can be returned even when its Site definition is unavailable.
- `activeVni` (uint, required) — Persisted active VNI verified against pool ownership. Inspection accepts nonnegative values, including zero and values outside the profile-change range; successful inspection does not imply a profile change is supported.
- `retainedAllocation` (object, required, nullable) — Allocation owned by this VPC in the other pool, or null when the valid active allocation is its only allocation. Inconsistent ownership is an error, not a null result.
  - `poolName` (enum, required) — Resource pool containing the retained allocation.
    - Allowed values: `vpc-vni`, `external-vpc-vni`
  - `vni` (uint, required) — Persisted nonnegative VNI, distinct from the active VNI. Inspection does not establish whether it is valid for a profile change or release.

## Errors

### 400 Bad Request Error

Error response when request data cannot be validated

- `source` (enum, optional) — Source of the error.
  - Allowed values: `nico`
- `message` (string, optional) — Message describing the error
- `data` (object, optional, nullable) — Additional data about the error

### 403 Forbidden Error

Error response when user is not authorized to call an endpoint or retrieve/modify objects

- `source` (enum, optional) — Source of the error.
  - Allowed values: `nico`
- `message` (string, optional) — Message describing the error
- `data` (object, optional, nullable) — Additional data about the error

### 404 Not Found Error

Error response when requested object is not found

- `source` (enum, optional) — Source of the error.
  - Allowed values: `nico`
- `message` (string, optional) — Message describing the error
- `data` (object, optional, nullable) — Additional data about the error

### 412 Precondition Failed Error

Response when the API handler encounters an unexpected error

- `source` (enum, optional) — Source of the error.
  - Allowed values: `nico`
- `message` (string, optional) — Message describing the error
- `data` (object, optional, nullable) — Additional data about the error

### 429 Too Many Requests Error

Error response when the Controller cannot allocate a requested resource because capacity is exhausted

- `source` (enum, optional) — Source of the error.
  - Allowed values: `nico`
- `message` (string, optional) — Message describing the error
- `data` (object, optional, nullable) — Additional data about the error

### 500 Internal Server Error

Response when the API handler encounters an unexpected error

- `source` (enum, optional) — Source of the error.
  - Allowed values: `nico`
- `message` (string, optional) — Message describing the error
- `data` (object, optional, nullable) — Additional data about the error

### 501 Not Implemented Error

Response when the API handler encounters an unexpected error

- `source` (enum, optional) — Source of the error.
  - Allowed values: `nico`
- `message` (string, optional) — Message describing the error
- `data` (object, optional, nullable) — Additional data about the error

### 503 Service Unavailable Error

Response when the API handler encounters an unexpected error

- `source` (enum, optional) — Source of the error.
  - Allowed values: `nico`
- `message` (string, optional) — Message describing the error
- `data` (object, optional, nullable) — Additional data about the error

### 504 Gateway Timeout Error

Response when the API handler encounters an unexpected error

- `source` (enum, optional) — Source of the error.
  - Allowed values: `nico`
- `message` (string, optional) — Message describing the error
- `data` (object, optional, nullable) — Additional data about the error

## Examples

### automatic-vni

**Request**

```json
{
  "routingProfile": "external"
}
```

**Response**

```json
{
  "vpcId": "497f6eca-6276-4993-bfeb-53cbbbba6f08",
  "version": "V2-T1789147200000000",
  "routingProfile": "external",
  "activeVni": 51000,
  "retainedAllocation": {
    "poolName": "vpc-vni",
    "vni": 12001
  }
}
```

**SDK Code**

```python automatic-vni
import requests

url = "https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile"

payload = { "routingProfile": "external" }
headers = {
    "Authorization": "Bearer <token>",
    "Content-Type": "application/json"
}

response = requests.patch(url, json=payload, headers=headers)

print(response.json())
```

```javascript automatic-vni
const url = 'https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile';
const options = {
  method: 'PATCH',
  headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
  body: '{"routingProfile":"external"}'
};

try {
  const response = await fetch(url, options);
  const data = await response.json();
  console.log(data);
} catch (error) {
  console.error(error);
}
```

```go automatic-vni
package main

import (
	"fmt"
	"strings"
	"net/http"
	"io"
)

func main() {

	url := "https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile"

	payload := strings.NewReader("{\n  \"routingProfile\": \"external\"\n}")

	req, _ := http.NewRequest("PATCH", url, payload)

	req.Header.Add("Authorization", "Bearer <token>")
	req.Header.Add("Content-Type", "application/json")

	res, _ := http.DefaultClient.Do(req)

	defer res.Body.Close()
	body, _ := io.ReadAll(res.Body)

	fmt.Println(res)
	fmt.Println(string(body))

}
```

```ruby automatic-vni
require 'uri'
require 'net/http'

url = URI("https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile")

http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true

request = Net::HTTP::Patch.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n  \"routingProfile\": \"external\"\n}"

response = http.request(request)
puts response.read_body
```

```java automatic-vni
import com.mashape.unirest.http.HttpResponse;
import com.mashape.unirest.http.Unirest;

HttpResponse<String> response = Unirest.patch("https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile")
  .header("Authorization", "Bearer <token>")
  .header("Content-Type", "application/json")
  .body("{\n  \"routingProfile\": \"external\"\n}")
  .asString();
```

```php automatic-vni
<?php
require_once('vendor/autoload.php');

$client = new \GuzzleHttp\Client();

$response = $client->request('PATCH', 'https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile', [
  'body' => '{
  "routingProfile": "external"
}',
  'headers' => [
    'Authorization' => 'Bearer <token>',
    'Content-Type' => 'application/json',
  ],
]);

echo $response->getBody();
```

```csharp automatic-vni
using RestSharp;

var client = new RestClient("https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile");
var request = new RestRequest(Method.PATCH);
request.AddHeader("Authorization", "Bearer <token>");
request.AddHeader("Content-Type", "application/json");
request.AddParameter("application/json", "{\n  \"routingProfile\": \"external\"\n}", ParameterType.RequestBody);
IRestResponse response = client.Execute(request);
```

```swift automatic-vni
import Foundation

let headers = [
  "Authorization": "Bearer <token>",
  "Content-Type": "application/json"
]
let parameters = ["routingProfile": "external"] as [String : Any]

let postData = JSONSerialization.data(withJSONObject: parameters, options: [])

let request = NSMutableURLRequest(url: NSURL(string: "https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile")! as URL,
                                        cachePolicy: .useProtocolCachePolicy,
                                    timeoutInterval: 10.0)
request.httpMethod = "PATCH"
request.allHTTPHeaderFields = headers
request.httpBody = postData as Data

let session = URLSession.shared
let dataTask = session.dataTask(with: request as URLRequest, completionHandler: { (data, response, error) -> Void in
  if (error != nil) {
    print(error as Any)
  } else {
    let httpResponse = response as? HTTPURLResponse
    print(httpResponse)
  }
})

dataTask.resume()
```

### exact-vni

**Request**

```json
{
  "routingProfile": "external",
  "vni": 51000
}
```

**Response**

```json
{
  "vpcId": "497f6eca-6276-4993-bfeb-53cbbbba6f08",
  "version": "V2-T1789147200000000",
  "routingProfile": "external",
  "activeVni": 51000,
  "retainedAllocation": {
    "poolName": "vpc-vni",
    "vni": 12001
  }
}
```

**SDK Code**

```python exact-vni
import requests

url = "https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile"

payload = {
    "routingProfile": "external",
    "vni": 51000
}
headers = {
    "Authorization": "Bearer <token>",
    "Content-Type": "application/json"
}

response = requests.patch(url, json=payload, headers=headers)

print(response.json())
```

```javascript exact-vni
const url = 'https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile';
const options = {
  method: 'PATCH',
  headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
  body: '{"routingProfile":"external","vni":51000}'
};

try {
  const response = await fetch(url, options);
  const data = await response.json();
  console.log(data);
} catch (error) {
  console.error(error);
}
```

```go exact-vni
package main

import (
	"fmt"
	"strings"
	"net/http"
	"io"
)

func main() {

	url := "https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile"

	payload := strings.NewReader("{\n  \"routingProfile\": \"external\",\n  \"vni\": 51000\n}")

	req, _ := http.NewRequest("PATCH", url, payload)

	req.Header.Add("Authorization", "Bearer <token>")
	req.Header.Add("Content-Type", "application/json")

	res, _ := http.DefaultClient.Do(req)

	defer res.Body.Close()
	body, _ := io.ReadAll(res.Body)

	fmt.Println(res)
	fmt.Println(string(body))

}
```

```ruby exact-vni
require 'uri'
require 'net/http'

url = URI("https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile")

http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true

request = Net::HTTP::Patch.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n  \"routingProfile\": \"external\",\n  \"vni\": 51000\n}"

response = http.request(request)
puts response.read_body
```

```java exact-vni
import com.mashape.unirest.http.HttpResponse;
import com.mashape.unirest.http.Unirest;

HttpResponse<String> response = Unirest.patch("https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile")
  .header("Authorization", "Bearer <token>")
  .header("Content-Type", "application/json")
  .body("{\n  \"routingProfile\": \"external\",\n  \"vni\": 51000\n}")
  .asString();
```

```php exact-vni
<?php
require_once('vendor/autoload.php');

$client = new \GuzzleHttp\Client();

$response = $client->request('PATCH', 'https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile', [
  'body' => '{
  "routingProfile": "external",
  "vni": 51000
}',
  'headers' => [
    'Authorization' => 'Bearer <token>',
    'Content-Type' => 'application/json',
  ],
]);

echo $response->getBody();
```

```csharp exact-vni
using RestSharp;

var client = new RestClient("https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile");
var request = new RestRequest(Method.PATCH);
request.AddHeader("Authorization", "Bearer <token>");
request.AddHeader("Content-Type", "application/json");
request.AddParameter("application/json", "{\n  \"routingProfile\": \"external\",\n  \"vni\": 51000\n}", ParameterType.RequestBody);
IRestResponse response = client.Execute(request);
```

```swift exact-vni
import Foundation

let headers = [
  "Authorization": "Bearer <token>",
  "Content-Type": "application/json"
]
let parameters = [
  "routingProfile": "external",
  "vni": 51000
] as [String : Any]

let postData = JSONSerialization.data(withJSONObject: parameters, options: [])

let request = NSMutableURLRequest(url: NSURL(string: "https://nico-rest-api.nico.svc.cluster.local/v2/org/org/nico/vpc/vpcId/routing-profile")! as URL,
                                        cachePolicy: .useProtocolCachePolicy,
                                    timeoutInterval: 10.0)
request.httpMethod = "PATCH"
request.allHTTPHeaderFields = headers
request.httpBody = postData as Data

let session = URLSession.shared
let dataTask = session.dataTask(with: request as URLRequest, completionHandler: { (data, response, error) -> Void in
  if (error != nil) {
    print(error as Any)
  } else {
    let httpResponse = response as? HTTPURLResponse
    print(httpResponse)
  }
})

dataTask.resume()
```