|
7 | 7 | "fmt" |
8 | 8 | "os" |
9 | 9 | "path/filepath" |
| 10 | + "strconv" |
10 | 11 | "strings" |
11 | 12 | "testing" |
12 | 13 | "time" |
@@ -1403,19 +1404,60 @@ func generateLocalTenantURI(cluster string) string { |
1403 | 1404 | return fmt.Sprintf("postgresql://root:root@localhost:26257?options=-ccluster%%3D%s", cluster) |
1404 | 1405 | } |
1405 | 1406 |
|
1406 | | -// generateExternalConnectionURI creates external connection URI using cockroach convert-url |
1407 | | -// This is used for cross-cluster connections (e.g., replication from primary to standby) |
1408 | | -// Format: cockroach convert-url 'postgresql://USERNAME:PASSWORD@HOST' [flags] |
| 1407 | +// generateExternalConnectionURI creates an external connection URI for cross-cluster PCR connections. |
| 1408 | +// It embeds the CA certificate inline so CRDB can verify TLS when using the stored external connection. |
| 1409 | +// Version-gated: |
| 1410 | +// - CRDB >= v26.2: uses 'cockroach convert-url --ca-cert --inline' (new command) |
| 1411 | +// - CRDB < v26.2: uses 'cockroach encode-uri --certs-dir' (old command) |
1409 | 1412 | func generateExternalConnectionURI(t *testing.T, kubectlOpts *k8s.KubectlOptions, pod string, connString string) string { |
| 1413 | + // Determine the CRDB version running in the pod. |
| 1414 | + versionOutput, err := execInCockroachdbContainer(t, kubectlOpts, pod, |
| 1415 | + "/cockroach/cockroach", "version", "--build-tag") |
| 1416 | + require.NoError(t, err, "failed to get CRDB version from pod") |
| 1417 | + version := strings.TrimSpace(versionOutput) |
| 1418 | + t.Logf("CRDB version in pod: %s", version) |
| 1419 | + |
| 1420 | + if crdbVersionAtLeast(version, 26, 2) { |
| 1421 | + // v26.2+: convert-url supports --ca-cert and --inline to embed the cert inline. |
| 1422 | + output, err := execInCockroachdbContainer(t, kubectlOpts, pod, |
| 1423 | + "/cockroach/cockroach", "convert-url", |
| 1424 | + "--url", connString, |
| 1425 | + "--ca-cert=/cockroach/cockroach-certs/ca.crt", |
| 1426 | + "--inline") |
| 1427 | + require.NoError(t, err, "failed to run cockroach convert-url") |
| 1428 | + return strings.TrimSpace(output) |
| 1429 | + } |
| 1430 | + |
| 1431 | + // Pre-v26.2: use encode-uri to embed the CA cert inline in the URL. |
1410 | 1432 | output, err := execInCockroachdbContainer(t, kubectlOpts, pod, |
1411 | | - "/cockroach/cockroach", "convert-url", |
1412 | | - "--url", connString, // Format: postgresql://user:pass@host:port |
1413 | | - "--ca-cert=/cockroach/cockroach-certs/ca.crt", |
1414 | | - "--inline") |
1415 | | - require.NoError(t, err) |
| 1433 | + "/cockroach/cockroach", "encode-uri", |
| 1434 | + connString, |
| 1435 | + "--certs-dir=/cockroach/cockroach-certs") |
| 1436 | + require.NoError(t, err, "failed to run cockroach encode-uri") |
1416 | 1437 | return strings.TrimSpace(output) |
1417 | 1438 | } |
1418 | 1439 |
|
| 1440 | +// crdbVersionAtLeast reports whether a CRDB version string (e.g. "v26.1.3") is >= major.minor. |
| 1441 | +func crdbVersionAtLeast(version string, major, minor int) bool { |
| 1442 | + v := strings.TrimPrefix(version, "v") |
| 1443 | + parts := strings.SplitN(v, ".", 3) |
| 1444 | + if len(parts) < 2 { |
| 1445 | + return false |
| 1446 | + } |
| 1447 | + maj, err := strconv.Atoi(parts[0]) |
| 1448 | + if err != nil { |
| 1449 | + return false |
| 1450 | + } |
| 1451 | + min, err := strconv.Atoi(parts[1]) |
| 1452 | + if err != nil { |
| 1453 | + return false |
| 1454 | + } |
| 1455 | + if maj != major { |
| 1456 | + return maj > major |
| 1457 | + } |
| 1458 | + return min >= minor |
| 1459 | +} |
| 1460 | + |
1419 | 1461 | // execInCockroachdbContainer runs any command inside the cockroachdb container of a pod. |
1420 | 1462 | // This is the base helper used by execSQL and execSQLOnVC. |
1421 | 1463 | func execInCockroachdbContainer(t *testing.T, kubectlOpts *k8s.KubectlOptions, pod string, cmd ...string) (string, error) { |
@@ -1608,7 +1650,7 @@ func (r *Region) ValidatePCR(t *testing.T, cfg *AdvancedValidationConfig) { |
1608 | 1650 | if primaryClusterDomain == "" { |
1609 | 1651 | primaryClusterDomain = CustomDomains[0] |
1610 | 1652 | } |
1611 | | - primaryHost := fmt.Sprintf("cockroachdb-public.%s.svc.%s:26257", primaryNamespace, CustomDomains[0]) |
| 1653 | + primaryHost := fmt.Sprintf("cockroachdb-public.%s.svc.%s:26257", primaryNamespace, primaryClusterDomain) |
1612 | 1654 | primaryConnString := fmt.Sprintf("postgresql://%s:%s@%s?options=-ccluster%%3Dsystem", pcrSourceUser, pcrSourcePassword, primaryHost) |
1613 | 1655 | t.Logf("Primary connection string format: postgresql://pcr_source:***@%s?options=-ccluster%%3Dsystem", primaryHost) |
1614 | 1656 |
|
|
0 commit comments