Repository: redpanda-data/redpanda
Pull request #25888: [UX-104] rpk: differentiate fips connect package download
Author: login: r-vasquez
Labels: name: area/rpk
name: area/build
Created: 2025-04-22T19:28:52Z | Merged: 2025-04-25T15:16:57Z

This PR introduces a new package to detect whether the `fips` build tag is present, allowing us to identify FIPS builds of rpk.

It also updates the plugin download logic to support a separate namespace for FIPS-compatible connect binaries. These are now retrieved from:

```
https://rpk-plugins.redpanda.com/connect-fips/manifest.json
```

As a result, when running rpk-fips, the appropriate connect-fips plugin version will be downloaded automatically.

Fixes UX-104

## Backports Required

<!-- Checking at least one of the checkboxes is REQUIRED if this PR is not a backport. -->

- [ ] none - not a bug fix
- [ ] none - this is a backport
- [ ] none - issue does not exist in previous branches
- [ ] none - papercut/not impactful enough to backport
- [ ] v25.1.x
- [ ] v24.3.x
- [ ] v24.2.x
- [ ] v24.1.x

## Release Notes

### Improvements

* rpk: FIPS versions of rpk will download the FIPS-compatible binaries of Redpanda Connect.



Diff:
diff --git a/.bazelrc b/.bazelrc
index ab4a536c8bb3d..422f1ff593324 100644
--- a/.bazelrc
+++ b/.bazelrc
@@ -16,7 +16,7 @@ common --@rules_python//python/config_settings:bootstrap_impl=script
 # By default build without CGO
 build --@rules_go//go/config:pure
 
-build:gofips --@rules_go//go/toolchain:sdk_name=go_sdk_with_systemcrypto
+build:gofips --//bazel:gofips=True --@rules_go//go/toolchain:sdk_name=go_sdk_with_systemcrypto
 build:gofips --@rules_go//go/config:pure=false
 
 # Improve caching and readability of filepaths that the compiler uses by not using
diff --git a/bazel/BUILD b/bazel/BUILD
index fec73bb74213a..b0fcf207a8b45 100644
--- a/bazel/BUILD
+++ b/bazel/BUILD
@@ -1,5 +1,17 @@
 load("@bazel_skylib//rules:common_settings.bzl", "bool_flag")
 
+bool_flag(
+    name = "gofips",
+    build_setting_default = False,
+)
+
+config_setting(
+    name = "gofips_enabled",
+    flag_values = {
+        ":gofips": "true",
+    },
+)
+
 bool_flag(
     name = "has_sanitizers",
     build_setting_default = False,
diff --git a/src/go/.goreleaser.yaml b/src/go/.goreleaser.yaml
index f759c1cda4c69..0fe03298f1e17 100644
--- a/src/go/.goreleaser.yaml
+++ b/src/go/.goreleaser.yaml
@@ -29,6 +29,8 @@ builds:
       - -X github.com/redpanda-data/redpanda/src/go/rpk/pkg/cli/container/common.tag={{.Tag}}
     env:
       - 'CGO_ENABLED={{ if index .Env "CGO_ENABLED" }}{{ .Env.CGO_ENABLED }}{{ else }}0{{ end }}'
+    tags:
+      - fips
     goos:
       - linux
     goarch:
diff --git a/src/go/rpk/cmd/rpk/BUILD b/src/go/rpk/cmd/rpk/BUILD
index 0865bbb0f315c..441825728d48f 100644
--- a/src/go/rpk/cmd/rpk/BUILD
+++ b/src/go/rpk/cmd/rpk/BUILD
@@ -11,6 +11,10 @@ go_library(
 go_binary(
     name = "rpk",
     embed = [":rpk_lib"],
+    gotags = select({
+        "//bazel:gofips_enabled": ["fips"],
+        "//conditions:default": [],
+    }),
     visibility = ["//visibility:public"],
     x_defs = {
         "github.com/redpanda-data/redpanda/src/go/rpk/pkg/cli/version.version": "{STABLE_GIT_LATEST_TAG}",
diff --git a/src/go/rpk/pkg/cli/connect/BUILD b/src/go/rpk/pkg/cli/connect/BUILD
index 043e241508bfb..d842a7ed101ef 100644
--- a/src/go/rpk/pkg/cli/connect/BUILD
+++ b/src/go/rpk/pkg/cli/connect/BUILD
@@ -14,6 +14,7 @@ go_library(
     deps = [
         "//src/go/rpk/pkg/cobraext",
         "//src/go/rpk/pkg/config",
+        "//src/go/rpk/pkg/fips",
         "//src/go/rpk/pkg/httpapi",
         "//src/go/rpk/pkg/os",
         "//src/go/rpk/pkg/out",
diff --git a/src/go/rpk/pkg/cli/connect/client.go b/src/go/rpk/pkg/cli/connect/client.go
index 85dcc2fd6cb5d..9ee51f90b8d76 100644
--- a/src/go/rpk/pkg/cli/connect/client.go
+++ b/src/go/rpk/pkg/cli/connect/client.go
@@ -17,6 +17,7 @@ import (
 	"os"
 	"runtime"
 
+	"github.com/redpanda-data/redpanda/src/go/rpk/pkg/fips"
 	"github.com/redpanda-data/redpanda/src/go/rpk/pkg/httpapi"
 	"github.com/redpanda-data/redpanda/src/go/rpk/pkg/plugin"
 )
@@ -92,7 +93,11 @@ func newRepoClient() (*connectRepoClient, error) {
 
 func (c *connectRepoClient) Manifest(ctx context.Context) (*connectManifest, error) {
 	var manifest connectManifest
-	err := c.cl.Get(ctx, fmt.Sprintf("%v/connect/manifest.json", getPluginURL()), nil, &manifest)
+	path := fmt.Sprintf("%v/connect/manifest.json", getPluginURL())
+	if fips.IsEnabled() {
+		path = fmt.Sprintf("%v/connect-fips/manifest.json", getPluginURL())
+	}
+	err := c.cl.Get(ctx, path, nil, &manifest)
 	if err != nil {
 		return nil, fmt.Errorf("unable to retrieve Redpanda Connect manifest: %v", err)
 	}
diff --git a/src/go/rpk/pkg/fips/BUILD b/src/go/rpk/pkg/fips/BUILD
new file mode 100644
index 0000000000000..cc9fc89c0289a
--- /dev/null
+++ b/src/go/rpk/pkg/fips/BUILD
@@ -0,0 +1,13 @@
+# gazelle:ignore
+# This file depends on a build tag and gazelle tries to edit this file.
+load("@rules_go//go:def.bzl", "go_library")
+
+go_library(
+    name = "fips",
+    srcs = [
+        "disabled.go",
+        "enabled.go",
+    ],
+    importpath = "github.com/redpanda-data/redpanda/src/go/rpk/pkg/fips",
+    visibility = ["//visibility:public"],
+)
diff --git a/src/go/rpk/pkg/fips/disabled.go b/src/go/rpk/pkg/fips/disabled.go
new file mode 100644
index 0000000000000..bfa539ed39caa
--- /dev/null
+++ b/src/go/rpk/pkg/fips/disabled.go
@@ -0,0 +1,16 @@
+// Copyright 2025 Redpanda Data, Inc.
+//
+// Use of this software is governed by the Business Source License
+// included in the file licenses/BSL.md
+//
+// As of the Change Date specified in that file, in accordance with
+// the Business Source License, use of this software will be governed
+// by the Apache License, Version 2.0
+
+//go:build !fips
+
+package fips
+
+func IsEnabled() bool {
+	return false
+}
diff --git a/src/go/rpk/pkg/fips/enabled.go b/src/go/rpk/pkg/fips/enabled.go
new file mode 100644
index 0000000000000..3fcbfbd95af4a
--- /dev/null
+++ b/src/go/rpk/pkg/fips/enabled.go
@@ -0,0 +1,16 @@
+// Copyright 2025 Redpanda Data, Inc.
+//
+// Use of this software is governed by the Business Source License
+// included in the file licenses/BSL.md
+//
+// As of the Change Date specified in that file, in accordance with
+// the Business Source License, use of this software will be governed
+// by the Apache License, Version 2.0
+
+//go:build fips
+
+package fips
+
+func IsEnabled() bool {
+	return true
+}


Reviews:
user: login: r-vasquez
state: COMMENTED
author_association: CONTRIBUTOR
submitted_at: 2025-04-22T19:29:39Z
user: login: andresaristizabal
state: DISMISSED
author_association: CONTRIBUTOR
submitted_at: 2025-04-23T01:12:11Z
user: login: clee
body: One thing
state: CHANGES_REQUESTED
author_association: CONTRIBUTOR
submitted_at: 2025-04-23T16:30:30Z
user: login: rockwotj
state: DISMISSED
author_association: CONTRIBUTOR
submitted_at: 2025-04-23T21:00:14Z
user: login: clee
state: DISMISSED
author_association: CONTRIBUTOR
submitted_at: 2025-04-23T23:02:51Z
user: login: clee
state: APPROVED
author_association: CONTRIBUTOR
submitted_at: 2025-04-24T17:27:09Z
user: login: rockwotj
state: APPROVED
author_association: CONTRIBUTOR
submitted_at: 2025-04-24T17:53:17Z

Review comments:
diff_hunk: @@ -29,6 +29,8 @@ builds:
       - -X github.com/redpanda-data/redpanda/src/go/rpk/pkg/cli/container/common.tag={{.Tag}}
     env:
       - 'CGO_ENABLED={{ if index .Env "CGO_ENABLED" }}{{ .Env.CGO_ENABLED }}{{ else }}0{{ end }}'
+    tags:
+      - fips
path: src/go/.goreleaser.yaml
user: login: r-vasquez
body: Just double checking `rpk-linux-microsoft-go` is the fips build for rpk, right @clee ?
created_at: 2025-04-22T19:29:39Z
author_association: CONTRIBUTOR
path: src/go/rpk/pkg/fips/enabled.go
user: login: andresaristizabal
body: why do we need those functions is a separate files?
created_at: 2025-04-23T01:08:55Z
author_association: CONTRIBUTOR
path: src/go/rpk/pkg/fips/enabled.go
user: login: andresaristizabal
body: I suppose it is related with `// go:build fips`?
created_at: 2025-04-23T01:10:12Z
author_association: CONTRIBUTOR
path: src/go/rpk/pkg/fips/enabled.go
user: login: andresaristizabal
body: O isee, we are going to build one of them based on fips tag, nice, I didn't know that
created_at: 2025-04-23T01:12:06Z
author_association: CONTRIBUTOR
diff_hunk: @@ -0,0 +1,8 @@
+load("@rules_go//go:def.bzl", "go_library")
+
+go_library(
+    name = "fips",
+    srcs = ["disabled.go"],
path: src/go/rpk/pkg/fips/BUILD
user: login: clee
body: We should use `select` here with `config=gofips` to set `srcs = ["enabled.go"]` (so that the rpk-fips build in bazel also works properly)
created_at: 2025-04-23T16:03:36Z
author_association: CONTRIBUTOR

PR comments:
user: login: vbotbuildovich
created_at: 2025-04-22T22:49:43Z
body: <!--FAILURES SLASH COMMAND https://buildkite.com/redpanda/redpanda/builds/64883-->
<!--b272c1ab-b931-497d-92f5-417aef957f80-->
<!--b5374e42-adbd-4c8c-8fec-288d8935f663-->
<!--fc9eddd6-41a6-4d36-93ab-42ddabcc341a-->
<!--title-->
## Retry command for [Build#64883](https://buildkite.com/redpanda/redpanda/builds/64883)
please wait until all jobs are finished before running the slash command
<!--/title-->
<!--body-->
```


/ci-repeat 1
tests/rptest/tests/maintenance_test.py::MaintenanceTest.test_maintenance_sticky@{"use_rpk":true}
tests/rptest/tests/datalake/cluster_restore_test.py::DatalakeClusterRestoreTest.test_restore_partition_spec@{"catalog_type":"rest_hadoop","cloud_storage_type":1}
tests/rptest/tests/node_pool_migration_test.py::NodePoolMigrationTest.test_migrating_redpanda_nodes_to_new_pool@{"balancing_mode":"off","cleanup_policy":"compact,delete","test_mode":"tiered_storage_fast_moves"}
```
<!--/body-->
author_association: COLLABORATOR
user: login: vbotbuildovich
created_at: 2025-04-22T23:49:39Z
body: <!--TEST RESULTS-->
<!--216cb9b0-76e1-4aa3-a4f0-256a4f7765d8-->
<!--TEST RESULTS-->
<!--8b4ed93a-40e7-42c9-a31e-eab95860df5c-->
<!--TEST RESULTS-->
<!--c55b4e90-43ae-4d75-842c-5ea65c2ec2ee-->
<!--TEST RESULTS-->
<!--0fece33f-0364-46d7-bf09-5e1a5a3c3524-->
<!--title-->
## CI test results
<!--/title-->
<!--body-->
<details>
<summary>test results on <a href="https://buildkite.com/redpanda/redpanda/builds/64883">build#64883</a></summary>


| test_id | test_kind | job_url | test_status | passed |
|:-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|:------------|:------------------------------------------------------------------------------------------|:--------------|:---------|
| rptest.tests.datalake.cluster_restore_test.DatalakeClusterRestoreTest.test_restore_partition_spec.cloud_storage_type=CloudStorageType.S3.catalog_type=CatalogType.REST_HADOOP | ducktape | https://buildkite.com/redpanda/redpanda/builds/64883#01965f47-f3fd-4864-8d1c-72250e7d1455 | FLAKY | 18/21 |
| rptest.tests.maintenance_test.MaintenanceTest.test_maintenance_sticky.use_rpk=True | ducktape | https://buildkite.com/redpanda/redpanda/builds/64883#01965f44-454c-434b-9ff3-a48da0e10f2b | FLAKY | 20/21 |
| rptest.tests.node_pool_migration_test.NodePoolMigrationTest.test_migrating_redpanda_nodes_to_new_pool.balancing_mode=off.test_mode=TestMode.FAST_MOVES.cleanup_policy=compact.delete | ducktape | https://buildkite.com/redpanda/redpanda/builds/64883#01965f47-f3fe-4408-9969-cacf657032e1 | FLAKY | 19/21 |
</details>
<details>
<summary>test results on <a href="https://buildkite.com/redpanda/redpanda/builds/64972">build#64972</a></summary>


| test_id | test_kind | job_url | test_status | passed |
|:------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|:------------|:------------------------------------------------------------------------------------------|:--------------|:---------|
| rptest.tests.availability_test.AvailabilityTests.test_recovery_after_catastrophic_failure | ducktape | https://buildkite.com/redpanda/redpanda/builds/64972#019664c4-5576-479f-a551-51f5057a9365 | FLAKY | 20/21 |
| rptest.tests.data_migrations_api_test.DataMigrationsApiTest.test_migrated_topic_data_integrity.transfer_leadership=True.params=.cancellation.dir.in.stage.preparing.use_alias.False | ducktape | https://buildkite.com/redpanda/redpanda/builds/64972#019664c4-5577-402b-bb83-e42aa7adb58d | FLAKY | 19/21 |
| rptest.tests.maintenance_test.MaintenanceCycleTest.test_leader_distribution.use_rpk=False | ducktape | https://buildkite.com/redpanda/redpanda/builds/64972#019664c4-5575-4318-afc3-17a001640621 | FLAKY | 20/21 |
| rptest.tests.upgrade_test.UpgradeBackToBackTest.test_upgrade_with_all_workloads.single_upgrade=False | ducktape | https://buildkite.com/redpanda/redpanda/builds/64972#019664c4-5576-4960-a3c7-3199764a9e6f | FLAKY | 14/21 |
</details>
<details>
<summary>test results on <a href="https://buildkite.com/redpanda/redpanda/builds/65033">build#65033</a></summary>


| test_id | test_kind | job_url | test_status | passed |
|:-----------------------------------------------------------------------------------------------------|:------------|:------------------------------------------------------------------------------------------|:--------------|:---------|
| gtest_raft_rpunit.gtest_raft_rpunit | unit | https://buildkite.com/redpanda/redpanda/builds/65033#019668d6-1466-4da1-bbdb-374165d5d336 | FLAKY | 1/2 |
| rptest.tests.scaling_up_test.ScalingUpTest.test_scaling_up_with_recovered_topic | ducktape | https://buildkite.com/redpanda/redpanda/builds/65033#01966921-fd95-4772-8c3f-2725e4e2ea9d | FLAKY | 16/21 |
| rptest.tests.upgrade_test.UpgradeBackToBackTest.test_upgrade_with_all_workloads.single_upgrade=False | ducktape | https://buildkite.com/redpanda/redpanda/builds/65033#0196692e-c11b-4f8f-bf81-a31e2848df7b | FLAKY | 8/21 |
| rptest.transactions.consumer_offsets_test.VerifyConsumerOffsets.test_consumer_group_offsets | ducktape | https://buildkite.com/redpanda/redpanda/builds/65033#0196692e-c11a-4d8a-b4e0-1515a976776f | FLAKY | 20/21 |
</details>
<details>
<summary>test results on <a href="https://buildkite.com/redpanda/redpanda/builds/65061">build#65061</a></summary>


| test_id                                                                                              | test_kind   | job_url                                                                                   | test_status   | passed   |
|:-----------------------------------------------------------------------------------------------------|:------------|:------------------------------------------------------------------------------------------|:--------------|:---------|
| gtest_raft_rpunit.gtest_raft_rpunit                                                                  | unit        | https://buildkite.com/redpanda/redpanda/builds/65061#019669da-d006-46ae-8b53-181f7f179941 | FLAKY         | 1/2      |
| kafka_server_rpfixture.kafka_server_rpfixture                                                        | unit        | https://buildkite.com/redpanda/redpanda/builds/65061#019669da-d006-46ae-8b53-181f7f179941 | FLAKY         | 1/2      |
| rptest.tests.upgrade_test.UpgradeBackToBackTest.test_upgrade_with_all_workloads.single_upgrade=False | ducktape    | https://buildkite.com/redpanda/redpanda/builds/65061#01966a21-a347-4942-8663-55505b8a1e76 | FLAKY         | 16/21    |
</details>
<!--/body-->
author_association: COLLABORATOR
user: login: andresaristizabal
created_at: 2025-04-23T01:14:36Z
body: /ci-repeat 1
tests/rptest/tests/maintenance_test.py::MaintenanceTest.test_maintenance_sticky
tests/rptest/tests/datalake/cluster_restore_test.py::DatalakeClusterRestoreTest.test_restore_partition_spec
tests/rptest/tests/node_pool_migration_test.py::NodePoolMigrationTest.test_migrating_redpanda_nodes_to_new_pool
author_association: CONTRIBUTOR
user: login: vbotbuildovich
created_at: 2025-04-24T00:18:43Z
body: <!--FAILURES SLASH COMMAND https://buildkite.com/redpanda/redpanda/builds/64972-->
<!--ea3db8a8-34e9-49b5-9a64-aad6fc6ae958-->
<!--56bbd3fb-f5bb-40b8-8c26-e0146799b2af-->
<!--c623bb2a-fb62-4817-990d-7b8c34a1571f-->
<!--title-->
## Retry command for [Build#64972](https://buildkite.com/redpanda/redpanda/builds/64972)
please wait until all jobs are finished before running the slash command
<!--/title-->
<!--body-->
```


/ci-repeat 1
tests/rptest/tests/availability_test.py::AvailabilityTests.test_recovery_after_catastrophic_failure
tests/rptest/tests/maintenance_test.py::MaintenanceCycleTest.test_leader_distribution@{"use_rpk":false}
tests/rptest/tests/upgrade_test.py::UpgradeBackToBackTest.test_upgrade_with_all_workloads@{"single_upgrade":false}
```
<!--/body-->
author_association: COLLABORATOR
user: login: vbotbuildovich
created_at: 2025-04-24T20:51:17Z
body: <!--FAILURES SLASH COMMAND https://buildkite.com/redpanda/redpanda/builds/65033-->
<!--1c9cc1eb-99a2-4a84-a984-b143021b1dd6-->
<!--7c71e731-6abd-4368-962a-7a8445c8cc96-->
<!--title-->
## Retry command for [Build#65033](https://buildkite.com/redpanda/redpanda/builds/65033)
please wait until all jobs are finished before running the slash command
<!--/title-->
<!--body-->
```

/ci-repeat 1
tests/rptest/transactions/consumer_offsets_test.py::VerifyConsumerOffsets.test_consumer_group_offsets
tests/rptest/tests/upgrade_test.py::UpgradeBackToBackTest.test_upgrade_with_all_workloads@{"single_upgrade":false}
```
<!--/body-->
author_association: COLLABORATOR
user: login: r-vasquez
created_at: 2025-04-24T22:09:32Z
body: /ci-repeat 1
tests/rptest/transactions/consumer_offsets_test.py::VerifyConsumerOffsets.test_consumer_group_offsets
tests/rptest/tests/upgrade_test.py::UpgradeBackToBackTest.test_upgrade_with_all_workloads
author_association: CONTRIBUTOR
user: login: r-vasquez
created_at: 2025-04-25T15:44:19Z
body: /backport v25.1.x
author_association: CONTRIBUTOR