YugabyteDB has long supported PostgreSQL-compatible tablespaces to help control where data lives in a distributed cluster. This is especially useful when you want to place specific tables or indexes in particular regions or availability zones, for performance, cost, or regulatory reasons.
But with a recent enhancement (#26671) starting in YugabyteDB 2024.2.4.0, things just got a lot more flexible!
What’s New: Use * Wildcards in Tablespace Placement
Previously, you had to explicitly list every zone in the placement block of a tablespace. Now, you can use the * wildcard to match all zones within a region, or even all regions.
Example:
Let’s say you want a table to live in any zone in the us-west1 region. You can now define your tablespace like this:
CREATE TABLESPACE ts_uswest
WITH (replica_placement =
'{"num_replicas": 3,
"placement_blocks": [
{"cloud": "gcp", "region": "us-west1", "zone": "*", "min_num_replicas": 3}
]
}');
Or go even broader with:
{"cloud": "gcp", "region": "*", "zone": "*"}
This means fewer lines of configuration, easier scaling, and more flexibility when adding or removing zones!
Why This Matters
✅ Great for multi-AZ deployments where zones may vary
✅ Useful when regions have dynamic topology
✅ Simplifies replica placement policies during expansion or failover planning
Bonus Tip: Combine this with yb_tserver gflags like placement_cloud, placement_region, and placement_zone for full control over where tablets land in your cluster!
Example:
yugabyte=# SELECT split_part(version(), '-', 3) "YB Version";
YB Version
------------
2024.2.4.0
(1 row)
yugabyte=# SELECT host, cloud, region, zone FROM yb_servers() ORDER BY region, zone;
host | cloud | region | zone
-----------+-------+---------+-------
127.0.0.1 | gcp | region1 | zone1
127.0.0.4 | gcp | region1 | zone2
127.0.0.7 | gcp | region1 | zone3
127.0.0.2 | gcp | region2 | zone1
127.0.0.5 | gcp | region2 | zone2
127.0.0.8 | gcp | region2 | zone3
127.0.0.3 | gcp | region3 | zone1
127.0.0.6 | gcp | region3 | zone2
127.0.0.9 | gcp | region3 | zone3
(9 rows)
yugabyte=# CREATE TABLESPACE region1_zoneless
yugabyte-# WITH (replica_placement='{"num_replicas": 3, "placement_blocks": [
yugabyte'# {"cloud":"gcp","region":"region1","zone":"*","min_num_replicas":3}
yugabyte'# ]}');
CREATE TABLESPACE
yugabyte=# CREATE TABLESPACE region2_zoneless
yugabyte-# WITH (replica_placement='{"num_replicas": 1, "placement_blocks": [
yugabyte'# {"cloud":"gcp","region":"region2","zone":"*","min_num_replicas":1}
yugabyte'# ]}');
CREATE TABLESPACE
yugabyte-# WITH (replica_placement='{"num_replicas": 3, "placement_blocks": [
yugabyte'# {"cloud":"gcp","region":"*","zone":"zone1","min_num_replicas":3}
yugabyte'# ]}');
ERROR: A wildcard '*' at region level should be followed by a wildcard at zone level
yugabyte=# CREATE TABLESPACE gcp_regionless_zoneless
yugabyte-# WITH (replica_placement='{"num_replicas": 3, "placement_blocks": [
yugabyte'# {"cloud":"gcp","region":"*","zone":"*","min_num_replicas":3}
yugabyte'# ]}');
CREATE TABLESPACE
Have Fun!
