Site Recoveryfor OpenStack
Guide

Site Commands

openstack dr site create, list, show, delete

master

Overview

Site commands let you register and manage the two independent OpenStack deployments that form your disaster recovery topology. Every Protection Group, Consistency Group, and DR operation is anchored to a registered site, so registering sites is always the first step in a Trilio Site Recovery deployment. The four commands covered here — create, list, show, and delete — are admin-only operations executed against the local Protector API; they do not contact the peer site directly. Because primary and secondary designations are workload-relative and swap on failover, you register both sites on each Protector instance to give the service a complete picture of the replication topology.


Prerequisites

Before running any openstack dr site command:

  • Two independent OpenStack clouds — each with its own Nova, Cinder, Neutron, and Keystone endpoints. They can be separate regions of the same cluster or fully separate clusters.
  • Protector services running on both sitesprotector-api and protector-engine must be active and reachable. Verify with systemctl status protector-api protector-engine on each controller.
  • protectorclient OSC plugin installed — the openstack dr site subcommand group is provided by this plugin. Confirm with openstack dr --help.
  • Admin credentials — all site management commands require the admin role. Source your admin OpenRC or ensure your clouds.yaml entry has admin privileges for the site you are targeting.
  • Network reachability between sites — the Protector API on each site must be able to reach the other site's Keystone endpoint (default port 5000) and Protector API endpoint (default port 8788) so that subsequent Protection Group operations can sync metadata.
  • clouds.yaml configured for both sites — the CLI plugin authenticates to both endpoints during metadata sync operations. A minimal two-entry clouds.yaml is shown in the Examples section.

Installation

The openstack dr site commands are part of the protectorclient OSC plugin. If you completed the Protector deployment guide, the plugin is already present. If not, install it now.

Step 1 — Install the OSC plugin

pip install python-protectorclient

Step 2 — Verify the plugin is registered

openstack dr --help

You should see site listed under the dr command group. If the subcommand is missing, ensure the plugin package installed successfully and that you are using the same Python environment as the openstack CLI.

Step 3 — Confirm API connectivity for each site

# Test Site A
openstack --os-cloud site-a catalog show protector

# Test Site B
openstack --os-cloud site-b catalog show protector

Both commands should return an endpoint URL on port 8788. A EndpointNotFound error means the Protector service endpoint was not registered in Keystone — see the deployment guide for the openstack endpoint create steps.

Step 4 — Source admin credentials

Site commands require admin. Use an OpenRC file or specify --os-cloud with an admin-credentialed entry in clouds.yaml:

# Option A: OpenRC
source ~/admin-openrc

# Option B: clouds.yaml entry
export OS_CLOUD=site-a-admin

Configuration

Site registration stores the following attributes in the Protector database. Understanding each field helps you avoid misconfiguration that blocks Protection Group creation later.

FieldRequiredValid valuesEffect
nameYesAny unique stringHuman-readable identifier used in all Protection Group commands (--primary-site, --secondary-site). Must be unique across all registered sites on the local Protector instance.
descriptionNoFree textStored as metadata; displayed in site show output. Useful for recording datacenter location or ownership.
site-typeYesprimary, secondaryDeclares the initial role of this site in the replication pair. This designation is workload-relative and dynamic — it swaps automatically when a failover completes. Register the site where your VMs currently run as primary and the DR target as secondary.
auth-urlYesKeystone v3 URLThe Keystone identity endpoint for this site (e.g., http://10.0.1.10:5000/v3). Protector uses this URL when authenticating cross-site during DR operations. Must be reachable from both sites' Protector engines.
region-nameNoOpenStack region stringRequired when the target cloud has multiple regions. Protector appends this to API discovery so it contacts the correct Nova, Cinder, and Neutron endpoints for that region. Omit for single-region deployments.

Status field (read-only)

The status field is set by Protector, not by you:

StatusMeaning
activeSite is reachable and functioning normally.
unreachableProtector cannot contact the site's endpoints. Modifications to Protection Groups anchored to this site are blocked until the site returns to active.
errorA validation or internal error occurred. Check Protector engine logs.

Because metadata sync between sites is strict — a Protection Group modification is rejected if the peer site is unreachable — keeping both sites in active status is a prerequisite for normal operations. Use openstack dr site validate after registration to confirm reachability before creating Protection Groups.


Usage

All four site commands target the local Protector API. You run them while authenticated to the site you want to manage. For initial setup, run the full registration sequence on both sites — each site's Protector instance needs entries for both itself and its peer so that DR operations can reference site objects by name.

Register a site

openstack dr site create \
  --name <name> \
  --site-type <primary|secondary> \
  --auth-url <keystone-v3-url> \
  [--description <text>] \
  [--region-name <region>]

You must run this command once per site on each Protector instance. For a two-site topology (Site A and Site B), you register Site A and Site B on Site A's Protector, then register Site A and Site B again on Site B's Protector.

List registered sites

openstack dr site list

Returns all sites registered on the local Protector instance with their IDs, names, types, and current status. Use this to confirm registration succeeded and to retrieve UUIDs for use in other commands.

Inspect a site

openstack dr site show <site-id-or-name>

Displays the full attribute set for a single site, including the status, capabilities JSON blob, and timestamps. Run this after registration to verify all fields were stored correctly, and during troubleshooting to check whether a site has gone unreachable.

Delete a site

openstack dr site delete <site-id-or-name>

Removes the site record from the local Protector database. This operation is blocked if any Protection Group references this site as its primary or secondary site — you must delete or reassign those Protection Groups first. Deleting a site record does not affect the remote OpenStack cloud itself.


Examples

Example 1 — Configure clouds.yaml for a two-site topology

Before running any site commands, add both sites to ~/.config/openstack/clouds.yaml:

clouds:
  site-a:
    auth:
      auth_url: http://10.0.1.10:5000/v3
      project_name: admin
      username: admin
      password: changeme
      user_domain_name: Default
      project_domain_name: Default
    region_name: RegionOne

  site-b:
    auth:
      auth_url: http://10.0.2.10:5000/v3
      project_name: admin
      username: admin
      password: changeme
      user_domain_name: Default
      project_domain_name: Default
    region_name: RegionOne

Example 2 — Register both sites on Site A's Protector

Authenticate to Site A and register both sites so that Site A's Protector knows the full topology:

export OS_CLOUD=site-a

# Register Site A itself
openstack dr site create \
  --name site-a \
  --description "Primary datacenter - Boston" \
  --site-type primary \
  --auth-url http://10.0.1.10:5000/v3 \
  --region-name RegionOne

Expected output:

+-------------+--------------------------------------+
| Field       | Value                                |
+-------------+--------------------------------------+
| id          | a1b2c3d4-e5f6-7890-abcd-ef1234567890 |
| name        | site-a                               |
| description | Primary datacenter - Boston          |
| site_type   | primary                              |
| auth_url    | http://10.0.1.10:5000/v3             |
| region_name | RegionOne                            |
| status      | active                               |
| created_at  | 2025-06-01T09:00:00Z                 |
+-------------+--------------------------------------+
# Register Site B as the secondary
openstack dr site create \
  --name site-b \
  --description "Secondary datacenter - Seattle" \
  --site-type secondary \
  --auth-url http://10.0.2.10:5000/v3 \
  --region-name RegionOne

Expected output:

+-------------+--------------------------------------+
| Field       | Value                                |
+-------------+--------------------------------------+
| id          | f0e9d8c7-b6a5-4321-fedc-ba0987654321 |
| name        | site-b                               |
| description | Secondary datacenter - Seattle       |
| site_type   | secondary                            |
| auth_url    | http://10.0.2.10:5000/v3             |
| region_name | RegionOne                            |
| status      | active                               |
| created_at  | 2025-06-01T09:01:00Z                 |
+-------------+--------------------------------------+

Example 3 — Mirror the registration on Site B's Protector

Switch to Site B's credentials and repeat. Note that site-type values mirror: Site A is registered as primary here too, because primary/secondary labels describe the initial workload placement, not which Protector you are talking to.

export OS_CLOUD=site-b

openstack dr site create \
  --name site-a \
  --description "Primary datacenter - Boston" \
  --site-type primary \
  --auth-url http://10.0.1.10:5000/v3 \
  --region-name RegionOne

openstack dr site create \
  --name site-b \
  --description "Secondary datacenter - Seattle" \
  --site-type secondary \
  --auth-url http://10.0.2.10:5000/v3 \
  --region-name RegionOne

Example 4 — List registered sites

export OS_CLOUD=site-a
openstack dr site list

Expected output:

+--------------------------------------+--------+-----------+--------+
| ID                                   | Name   | Site Type | Status |
+--------------------------------------+--------+-----------+--------+
| a1b2c3d4-e5f6-7890-abcd-ef1234567890 | site-a | primary   | active |
| f0e9d8c7-b6a5-4321-fedc-ba0987654321 | site-b | secondary | active |
+--------------------------------------+--------+-----------+--------+

Example 5 — Inspect a site by name

openstack dr site show site-b

Expected output:

+--------------+--------------------------------------+
| Field        | Value                                |
+--------------+--------------------------------------+
| id           | f0e9d8c7-b6a5-4321-fedc-ba0987654321 |
| name         | site-b                               |
| description  | Secondary datacenter - Seattle       |
| site_type    | secondary                            |
| auth_url     | http://10.0.2.10:5000/v3             |
| region_name  | RegionOne                            |
| status       | active                               |
| capabilities | {}                                   |
| created_at   | 2025-06-01T09:01:00Z                 |
| updated_at   | 2025-06-01T09:01:00Z                 |
+--------------+--------------------------------------+

Example 6 — Delete a site

Remove a site that has no Protection Groups referencing it:

openstack dr site delete site-b

No output is produced on success. Confirm deletion:

openstack dr site list

The deleted site no longer appears in the list.


Troubleshooting

Issue: openstack dr site — command not found

Symptom: Running openstack dr site create returns 'dr' is not an openstack command.

Likely cause: The protectorclient OSC plugin is not installed or not installed in the same Python environment as the openstack CLI.

Fix:

pip install python-protectorclient
# Verify
openstack dr --help

If you are using a virtualenv, ensure you activate it before running the openstack command.


Issue: 403 Forbidden when running site commands

Symptom: The command returns an HTTP 403 error.

Likely cause: Site management commands (/v1/admin/sites) require the admin role. Your current credentials do not have admin privileges on the target Protector.

Fix: Source your admin OpenRC or switch to an admin-credentialed clouds.yaml entry:

source ~/admin-openrc
# or
export OS_CLOUD=site-a-admin

Issue: Site is created but status shows unreachable

Symptom: openstack dr site show <site> returns status: unreachable immediately after creation.

Likely cause: The auth_url provided is not reachable from the Protector engine's network, or the Keystone service is down at that URL.

Fix:

  1. Verify the auth_url is correct and uses the /v3 path:
    curl -s http://10.0.2.10:5000/v3 | python3 -m json.tool
    
  2. Confirm the Protector engine host can reach the remote site's Keystone port:
    nc -zv 10.0.2.10 5000
    
  3. Check firewall rules between sites — both port 5000 (Keystone) and port 8788 (Protector API) must be open bidirectionally.
  4. Once reachability is restored, run the validate command to refresh status:
    openstack dr site validate <site-name>
    

Issue: openstack dr site delete fails with a conflict error

Symptom: Deletion is rejected with a message indicating the site is still referenced.

Likely cause: One or more Protection Groups list this site as their primary_site_id or secondary_site_id. The Protector service prevents orphaning Protection Groups by blocking site deletion.

Fix: List and delete (or reassign) all Protection Groups that reference this site before retrying:

# Find protection groups referencing the site
openstack dr protection-group list

# Delete each referencing protection group
openstack dr protection-group delete <pg-id>

# Then retry site deletion
openstack dr site delete <site-name>

Issue: Site registered on Site A, but Protection Group creation fails with "site not found" on Site B

Symptom: After registering sites on Site A's Protector, attempting to create a Protection Group from Site B returns an error that one of the site names cannot be resolved.

Likely cause: Site registration is local to each Protector instance. You registered the sites only on Site A's Protector but not on Site B's Protector.

Fix: Repeat the openstack dr site create commands while authenticated to Site B's Protector endpoint. Both Protector instances need entries for both sites. See Example 3 above.