diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml index 1832fc4b..04beb572 100644 --- a/.github/workflows/release.yaml +++ b/.github/workflows/release.yaml @@ -50,12 +50,8 @@ jobs: owner: defenseunicorns repositories: homebrew-tap - - name: Download Runtime binaries for embedding - run: | - ./hack/update-uds-runtime-binaries.sh uds-runtime-linux-amd64 - ./hack/update-uds-runtime-binaries.sh uds-runtime-linux-arm64 - ./hack/update-uds-runtime-binaries.sh uds-runtime-darwin-amd64 - ./hack/update-uds-runtime-binaries.sh uds-runtime-darwin-arm64 + - name: Download Runtime assets for embedding + run: ./hack/download-uds-runtime-assets.sh - name: Run GoReleaser uses: goreleaser/goreleaser-action@286f3b13b1b49da4ac219696163fb8c1c93e1200 # v6.0.0 diff --git a/.github/workflows/test-schema-and-docs.yaml b/.github/workflows/test-schema-and-docs.yaml index 29e3ae77..58a1a549 100644 --- a/.github/workflows/test-schema-and-docs.yaml +++ b/.github/workflows/test-schema-and-docs.yaml @@ -21,8 +21,8 @@ jobs: - name: Install UDS CLI uses: ./.github/actions/install-uds-cli - - name: Pull UDS Runtime binary - run: ./hack/update-uds-runtime-binaries.sh uds-runtime-linux-amd64 + - name: Pull UDS Runtime Assets + run: ./hack/download-uds-runtime-assets.sh - name: Test schemas run: uds run schema:test diff --git a/.github/workflows/test-unit.yaml b/.github/workflows/test-unit.yaml index 6a8ec20e..064b8de2 100644 --- a/.github/workflows/test-unit.yaml +++ b/.github/workflows/test-unit.yaml @@ -36,8 +36,8 @@ jobs: - name: Install UDS CLI uses: ./.github/actions/install-uds-cli - - name: Pull UDS Runtime binary - run: ./hack/update-uds-runtime-binaries.sh uds-runtime-linux-amd64 + - name: Pull UDS Runtime Assets + run: ./hack/download-uds-runtime-assets.sh - name: Run unit tests run: uds run test:unit diff --git a/.gitignore b/.gitignore index 5650db29..8b94c6d9 100644 --- a/.gitignore +++ b/.gitignore @@ -36,3 +36,5 @@ out.txt *.gif *.mp4 src/cmd/bin +src/cmd/certs +*.pem diff --git a/docs/command-reference/uds_ui.md b/docs/command-reference/uds_ui.md index 6e1b8662..36e5f4b6 100644 --- a/docs/command-reference/uds_ui.md +++ b/docs/command-reference/uds_ui.md @@ -7,6 +7,10 @@ type: docs [beta] Launch UDS Runtime and view UI +### Synopsis + +[beta] Launch UDS Runtime and view UI + ``` uds ui [flags] ``` diff --git a/docs/quickstart-and-usage.md b/docs/quickstart-and-usage.md index ef5b6b07..0a5dfa3d 100644 --- a/docs/quickstart-and-usage.md +++ b/docs/quickstart-and-usage.md @@ -131,20 +131,21 @@ e.g. ```yaml core-slim-dev: -- docker.io/istio/pilot:1.22.3-distroless -- docker.io/istio/proxyv2:1.22.3-distroless -- ghcr.io/defenseunicorns/pepr/controller:v0.34.1 -- quay.io/keycloak/keycloak:24.0.5 -- ghcr.io/defenseunicorns/uds/identity-config:0.6.0 + - docker.io/istio/pilot:1.22.3-distroless + - docker.io/istio/proxyv2:1.22.3-distroless + - ghcr.io/defenseunicorns/pepr/controller:v0.34.1 + - quay.io/keycloak/keycloak:24.0.5 + - ghcr.io/defenseunicorns/uds/identity-config:0.6.0 init: -- library/registry:2.8.3 -- library/registry:2.8.3 -- ghcr.io/zarf-dev/zarf/agent:v0.38.2 + - library/registry:2.8.3 + - library/registry:2.8.3 + - ghcr.io/zarf-dev/zarf/agent:v0.38.2 ``` -*To extract only the image names and de-dupe*: +_To extract only the image names and de-dupe_: `uds inspect k3d-core-slim-dev:0.26.0 --list-images | yq '.[] | .[]'` | sort | uniq + ```yaml docker.io/istio/pilot:1.22.3-distroless docker.io/istio/proxyv2:1.22.3-distroless @@ -155,7 +156,6 @@ library/registry:2.8.3 quay.io/keycloak/keycloak:24.0.5 ``` - #### Viewing SBOMs There are 2 additional flags for the `uds inspect` command you can use to extract and view SBOMs: @@ -312,7 +312,9 @@ In a bundle, variables can come from 6 sources. Those sources and their preceden That is to say, variables set using the `--set` flag take precedence over all other variable sources. ### Configuring Zarf Init Packages + Zarf init packages that are typically deployed using `zarf init` have a few special flags that are attached to that command. These options can be configured like any other variable: specified in a `uds-config.yaml`, as an environment variable prefixed with `UDS_` or via the `--set` flag. + ```yaml # uds-config.yaml variables: @@ -505,7 +507,3 @@ uds scan -o defenseunicorns -n packages/uds/gitlab-runner -g 16.10.0-uds.0-upstr The `uds ui` command launches UDS Runtime, which provides a web-based user interface to view what is running in your K8s cluster. More information regarding UDS Runtime can be found [here](https://github.com/defenseunicorns/uds-runtime). To exit UDS Runtime, press `Ctrl+C`. - -{{% alert-note %}} -There is currently a known data loading [issue](https://github.com/defenseunicorns/uds-runtime/issues/365) with opening UDS Runtime via `uds ui` in multiple tabs or windows. If you encounter this issue, please ensure there is only one tab or window of UDS Runtime open at a time. -{{% /alert-note %}} diff --git a/go.mod b/go.mod index 45e5ff3b..d46d43c4 100644 --- a/go.mod +++ b/go.mod @@ -10,6 +10,7 @@ require ( github.com/defenseunicorns/pkg/exec v0.0.1 github.com/defenseunicorns/pkg/helpers/v2 v2.0.1 github.com/defenseunicorns/pkg/oci v1.0.2 + github.com/defenseunicorns/uds-runtime v0.6.1 github.com/defenseunicorns/uds-security-hub v0.0.7 github.com/fsnotify/fsnotify v1.7.0 github.com/goccy/go-yaml v1.12.0 @@ -69,6 +70,7 @@ require ( github.com/BurntSushi/toml v1.4.0 // indirect github.com/CycloneDX/cyclonedx-go v0.9.0 // indirect github.com/DataDog/zstd v1.5.5 // indirect + github.com/KyleBanks/depth v1.2.1 // indirect github.com/MakeNowJust/heredoc v1.0.0 // indirect github.com/Masterminds/goutils v1.1.1 // indirect github.com/Masterminds/semver v1.5.0 // indirect @@ -232,6 +234,7 @@ require ( github.com/glebarez/go-sqlite v1.21.2 // indirect github.com/glebarez/sqlite v1.11.0 // indirect github.com/go-chi/chi v4.1.2+incompatible // indirect + github.com/go-chi/chi/v5 v5.1.0 // indirect github.com/go-errors/errors v1.4.2 // indirect github.com/go-git/gcfg v1.5.1-0.20230307220236-3a3c6141e376 // indirect github.com/go-git/go-billy/v5 v5.5.0 // indirect @@ -449,6 +452,9 @@ require ( github.com/spiffe/go-spiffe/v2 v2.3.0 // indirect github.com/stretchr/objx v0.5.2 // indirect github.com/subosito/gotenv v1.6.0 // indirect + github.com/swaggo/files/v2 v2.0.1 // indirect + github.com/swaggo/http-swagger/v2 v2.0.2 // indirect + github.com/swaggo/swag v1.16.3 // indirect github.com/sylabs/sif/v2 v2.17.1 // indirect github.com/sylabs/squashfs v1.0.0 // indirect github.com/syndtr/goleveldb v1.0.1-0.20220721030215-126854af5e6d // indirect @@ -502,6 +508,7 @@ require ( golang.org/x/term v0.24.0 // indirect golang.org/x/text v0.18.0 // indirect golang.org/x/time v0.6.0 // indirect + golang.org/x/tools v0.25.0 // indirect golang.org/x/xerrors v0.0.0-20231012003039-104605ab7028 // indirect google.golang.org/api v0.195.0 // indirect google.golang.org/genproto v0.0.0-20240823204242-4ba0660f739c // indirect diff --git a/go.sum b/go.sum index e93c0f45..d4aae5c5 100644 --- a/go.sum +++ b/go.sum @@ -270,6 +270,8 @@ github.com/DATA-DOG/go-sqlmock v1.5.2/go.mod h1:88MAG/4G7SMwSE3CeA0ZKzrT5CiOU3OJ github.com/DataDog/datadog-go v3.2.0+incompatible/go.mod h1:LButxg5PwREeZtORoXG3tL4fMGNddJ+vMq1mwgfaqoQ= github.com/DataDog/zstd v1.5.5 h1:oWf5W7GtOLgp6bciQYDmhHHjdhYkALu6S/5Ni9ZgSvQ= github.com/DataDog/zstd v1.5.5/go.mod h1:g4AWEaM3yOg3HYfnJ3YIawPnVdXJh9QME85blwSAmyw= +github.com/KyleBanks/depth v1.2.1 h1:5h8fQADFrWtarTdtDudMmGsC7GPbOAu6RVB3ffsVFHc= +github.com/KyleBanks/depth v1.2.1/go.mod h1:jzSb9d0L43HxTQfT+oSA1EEp2q+ne2uh6XgeJcm8brE= github.com/MakeNowJust/heredoc v1.0.0 h1:cXCdzVdstXyiTqTvfqk9SDHpKNjxuom+DOlyEeQ4pzQ= github.com/MakeNowJust/heredoc v1.0.0/go.mod h1:mG5amYoWBHf8vpLOuehzbGGw0EHxpZZ6lCpQ4fNJ8LE= github.com/MarvinJWendt/testza v0.1.0/go.mod h1:7AxNvlfeHP7Z/hDQ5JtE3OKYT3XFUeLCDE2DQninSqs= @@ -632,6 +634,8 @@ github.com/defenseunicorns/pkg/kubernetes v0.3.0 h1:f4VSIaUdvn87/dhiZvRbUfHhcHa8 github.com/defenseunicorns/pkg/kubernetes v0.3.0/go.mod h1:FsuKQGpPZOnZWifBse7v787+avtIu2lte5LTsaojDkY= github.com/defenseunicorns/pkg/oci v1.0.2 h1:JRdFbKnJQiGVsMUWmcmm0ZS8aBmmAORXLGSAGkIGhBQ= github.com/defenseunicorns/pkg/oci v1.0.2/go.mod h1:z11UFenAd4HQRucaEp0uhoccor/6zbQiXEQq+Z7vtI0= +github.com/defenseunicorns/uds-runtime v0.6.1 h1:S4suI8HZ4HH3AJ2RNbOamYVlp4R9iRw9GIAJVbYj9RE= +github.com/defenseunicorns/uds-runtime v0.6.1/go.mod h1:un/UY3wqqUXg84sVZZ2adMy+V6JDk7KSYQBgyByfgdA= github.com/defenseunicorns/uds-security-hub v0.0.7 h1:4leg+FDagyoFdr3aSeFGlega4XG5+FwXnAdQsB2MebM= github.com/defenseunicorns/uds-security-hub v0.0.7/go.mod h1:4c1w8sRRyQfMDEQ3d+i3/7ENwQGgkNRkvjF5+4D2LZ4= github.com/deitch/magic v0.0.0-20230404182410-1ff89d7342da h1:ZOjWpVsFZ06eIhnh4mkaceTiVoktdU67+M7KDHJ268M= @@ -786,6 +790,8 @@ github.com/gliderlabs/ssh v0.3.7 h1:iV3Bqi942d9huXnzEF2Mt+CY9gLu8DNM4Obd+8bODRE= github.com/gliderlabs/ssh v0.3.7/go.mod h1:zpHEXBstFnQYtGnB8k8kQLol82umzn/2/snG7alWVD8= github.com/go-chi/chi v4.1.2+incompatible h1:fGFk2Gmi/YKXk0OmGfBh0WgmN3XB8lVnEyNz34tQRec= github.com/go-chi/chi v4.1.2+incompatible/go.mod h1:eB3wogJHnLi3x/kFX2A+IbTBlXxmMeXJVKy9tTv1XzQ= +github.com/go-chi/chi/v5 v5.1.0 h1:acVI1TYaD+hhedDJ3r54HyA6sExp3HfXq7QWEEY/xMw= +github.com/go-chi/chi/v5 v5.1.0/go.mod h1:DslCQbL2OYiznFReuXYUmQ2hGd1aDpCnlMNITLSKoi8= github.com/go-errors/errors v1.4.2 h1:J6MZopCL4uSllY1OfXM374weqZFFItUbrImctkmUxIA= github.com/go-errors/errors v1.4.2/go.mod h1:sIVyrIiJhuEF+Pj9Ebtd6P/rEYROXFi3BopGUQ5a5Og= github.com/go-git/gcfg v1.5.1-0.20230307220236-3a3c6141e376 h1:+zs/tPmkDkHx3U66DAb0lQFJrpS6731Oaa12ikc+DiI= @@ -1649,6 +1655,12 @@ github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8 github.com/subosito/gotenv v1.2.0/go.mod h1:N0PQaV/YGNqwC0u51sEeR/aUtSLEXKX9iv69rRypqCw= github.com/subosito/gotenv v1.6.0 h1:9NlTDc1FTs4qu0DDq7AEtTPNw6SVm7uBMsUCUjABIf8= github.com/subosito/gotenv v1.6.0/go.mod h1:Dk4QP5c2W3ibzajGcXpNraDfq2IrhjMIvMSWPKKo0FU= +github.com/swaggo/files/v2 v2.0.1 h1:XCVJO/i/VosCDsJu1YLpdejGsGnBE9deRMpjN4pJLHk= +github.com/swaggo/files/v2 v2.0.1/go.mod h1:24kk2Y9NYEJ5lHuCra6iVwkMjIekMCaFq/0JQj66kyM= +github.com/swaggo/http-swagger/v2 v2.0.2 h1:FKCdLsl+sFCx60KFsyM0rDarwiUSZ8DqbfSyIKC9OBg= +github.com/swaggo/http-swagger/v2 v2.0.2/go.mod h1:r7/GBkAWIfK6E/OLnE8fXnviHiDeAHmgIyooa4xm3AQ= +github.com/swaggo/swag v1.16.3 h1:PnCYjPCah8FK4I26l2F/KQ4yz3sILcVUN3cTlBFA9Pg= +github.com/swaggo/swag v1.16.3/go.mod h1:DImHIuOFXKpMFAQjcC7FG4m3Dg4+QuUgUzJmKjI/gRk= github.com/sylabs/sif/v2 v2.17.1 h1:p6Sl0LWyShXBj2SBsS1dMOMIMrZHe8pwBnBrYt6uo4M= github.com/sylabs/sif/v2 v2.17.1/go.mod h1:XUGB6AQUXGkms3qPOPdevctT3lBLRLWZNWHVnt5HMKE= github.com/sylabs/squashfs v1.0.0 h1:xAyMS21ogglkuR5HaY55PCfqY3H32ma9GkasTYo28Zg= diff --git a/hack/download-uds-runtime-assets.sh b/hack/download-uds-runtime-assets.sh new file mode 100755 index 00000000..b8455db0 --- /dev/null +++ b/hack/download-uds-runtime-assets.sh @@ -0,0 +1,67 @@ +#!/bin/bash +# Copyright 2024 Defense Unicorns +# SPDX-License-Identifier: AGPL-3.0-or-later OR LicenseRef-Defense-Unicorns-Commercial + + +OWNER="defenseunicorns" +REPO="uds-runtime" +BASE_PATH="./src/cmd/" +CERTS_PATH="${BASE_PATH}/certs" +ARCHIVE_NAME="uds-runtime-ui.tar.gz" +CURRENT_VERSION="v0.6.1" + +# Get the latest release version from GitHub API +LATEST_VERSION=$(curl -s "https://api.github.com/repos/$OWNER/$REPO/releases/latest" | jq -r .tag_name) + +# Create the base path directory if it doesn't exist +mkdir -p "$BASE_PATH" +mkdir -p "$CERTS_PATH" + +# Download the latest release archive +download_release() { + echo "Downloading $ARCHIVE_NAME for version $LATEST_VERSION" + curl -L "https://github.com/$OWNER/$REPO/releases/download/${LATEST_VERSION}/${ARCHIVE_NAME}" -o "${BASE_PATH}/${ARCHIVE_NAME}" +} + +# Extract the archive into the base path +extract_release() { + echo "Extracting $ARCHIVE_NAME" + tar -xzf "${BASE_PATH}/${ARCHIVE_NAME}" -C "$BASE_PATH" +} + +# Remove old files in the base path +clean_old_files() { + echo "Cleaning up old files" + rm -rf "${BASE_PATH:?}/ui" +} + +# Download raw certs files from the repository's main branch +download_certs() { + echo "Downloading certificates from hack/certs" + FILES=("cert.pem" "key.pem") + for file in "${FILES[@]}"; do + echo "Downloading $file" + curl -L "https://raw.githubusercontent.com/$OWNER/$REPO/main/hack/certs/$file" -o "${CERTS_PATH}/$file" + done +} + +# Check if the current version is different from the latest or the archive doesn't exist +if [[ "$LATEST_VERSION" != "$CURRENT_VERSION" ]] || [[ ! -f "${BASE_PATH}/${ARCHIVE_NAME}" ]]; then + echo "Updating UDS Runtime UI to version $LATEST_VERSION" + + # Clean up old files before downloading the new release + clean_old_files + + # Download and extract the latest release archive + download_release + extract_release + + # Update the current version + CURRENT_VERSION="$LATEST_VERSION" + echo "Updated to version $LATEST_VERSION" +else + echo "UDS Runtime UI is up to date." +fi + +# Download certs files +download_certs diff --git a/hack/update-uds-runtime-binaries.sh b/hack/update-uds-runtime-binaries.sh deleted file mode 100755 index f9b0ea76..00000000 --- a/hack/update-uds-runtime-binaries.sh +++ /dev/null @@ -1,71 +0,0 @@ -#!/bin/bash -# Copyright 2024 Defense Unicorns -# SPDX-License-Identifier: AGPL-3.0-or-later OR LicenseRef-Defense-Unicorns-Commercial - - -OWNER="defenseunicorns" -REPO="uds-runtime" - -BASE_PATH="./src/cmd/bin" -CURRENT_VERSION="v0.6.1" - -# Get the latest release version from GitHub API -LATEST_VERSION=$(curl -s "https://api.github.com/repos/$OWNER/$REPO/releases/latest" | jq -r .tag_name) - -# List of binaries and their paths -BINARIES=("uds-runtime-darwin-amd64" "uds-runtime-darwin-arm64" "uds-runtime-linux-amd64" "uds-runtime-linux-arm64") - -# Create the base path directory if it doesn't exist -mkdir -p "$BASE_PATH" - -# Update a specific binary -update_binary() { - local binary=$1 - echo "Downloading $binary" - curl -L "https://github.com/$OWNER/$REPO/releases/download/${LATEST_VERSION}/${binary}" -o "${BASE_PATH}/${binary}" - - # Make the binary executable - chmod +x "${BASE_PATH}/${binary}" -} - -# Check if a binary exists in the base path -binary_exists() { - local binary=$1 - [[ -f "${BASE_PATH}/${binary}" ]] -} - -# Remove all binaries except the specified one -remove_other_binaries() { - local keep_binary=$1 - for binary in "${BINARIES[@]}"; do - if [[ "$binary" != "$keep_binary" ]]; then - rm -f "${BASE_PATH}/${binary}" - fi - done -} - -# Ensure a binary name is passed in -if [ -z "$1" ]; then - echo "Error: A binary name must be provided." - echo "Usage: $0 " - exit 1 -fi - -# Remove all other binaries -remove_other_binaries "$1" - -# If the current version is different from the latest or a binary name is passed in and the binary doesn't exist -# or no binary name is passed in and none of the binaries exist then update the binary/binaries -if [[ "$LATEST_VERSION" != "$CURRENT_VERSION" ]] || ! binary_exists "$1"; then - echo "Updating UDS Runtime binaries to version $LATEST_VERSION" - - # Update the specified binary - update_binary "$1" - - # Update the current version variable - CURRENT_VERSION="$LATEST_VERSION" - echo "Updated current version to $LATEST_VERSION" - -else - echo "Binaries are up to date." -fi diff --git a/renovate.json b/renovate.json index 4f38b832..12e801c8 100644 --- a/renovate.json +++ b/renovate.json @@ -2,9 +2,7 @@ "enabled": true, "forkProcessing": "enabled", "$schema": "https://docs.renovatebot.com/renovate-schema.json", - "extends": [ - "config:base" - ], + "extends": ["config:base"], "ignorePaths": [], "timezone": "America/New_York", "repositories": ["defenseunicorns/uds-cli"], @@ -17,43 +15,38 @@ "rebaseWhen": "conflicted", "commitBodyTable": true, "suppressNotifications": ["prIgnoreNotification"], - "postUpdateOptions": [ - "gomodTidy" - ], + "postUpdateOptions": ["gomodTidy"], "packageRules": [ { "matchPackageNames": ["zarf-dev/zarf", "github.com/zarf-dev/zarf"], "groupName": "zarf" }, { - "matchPackageNames": ["stefanprodan/podinfo", "github.com/stefanprodan/podinfo", "podinfo"], + "matchPackageNames": [ + "stefanprodan/podinfo", + "github.com/stefanprodan/podinfo", + "podinfo" + ], "groupName": "podinfo" } ], "regexManagers": [ { - "fileMatch": [ - "uds-bundle.yaml", - "action.yaml" - ], + "fileMatch": ["uds-bundle.yaml", "action.yaml"], "matchStrings": [ "# renovate: datasource=(?.*) depName=(?.*)\\n\\s*(version|ref): (?.*)" ], "versioningTemplate": "semver" }, { - "fileMatch": [ - "zarf.yaml" - ], + "fileMatch": ["zarf.yaml"], "matchStrings": [ "# renovate: datasource=(?.*) depName=(?.*)\\n\\s*(-\\s.*:)(?.*)" ], "datasourceTemplate": "github-tags" }, { - "fileMatch": [ - "generate-schema\\.sh" - ], + "fileMatch": ["generate-schema\\.sh"], "matchStrings": [ "https://raw\\.githubusercontent\\.com/zarf-dev/zarf/v(?\\d+\\.\\d+\\.\\d+)/zarf\\.schema\\.json" ], @@ -61,8 +54,10 @@ "datasourceTemplate": "github-releases" }, { - "fileMatch": ["hack/update-uds-runtime-binaries.sh"], - "matchStrings": ["CURRENT_VERSION=\"v(?\\d+\\.\\d+\\.\\d+)\""], + "fileMatch": ["hack/download-uds-runtime-assets.sh"], + "matchStrings": [ + "CURRENT_VERSION=\"v(?\\d+\\.\\d+\\.\\d+)\"" + ], "depNameTemplate": "defenseunicorns/uds-runtime", "datasourceTemplate": "github-releases" } diff --git a/src/cmd/ui.go b/src/cmd/ui.go index 23037ed9..5f957d6d 100644 --- a/src/cmd/ui.go +++ b/src/cmd/ui.go @@ -5,116 +5,31 @@ package cmd import ( - "context" "embed" - "errors" - "fmt" - "os" - "os/exec" - "os/signal" - "path/filepath" - "runtime" - "syscall" + "log/slog" - "github.com/defenseunicorns/uds-cli/src/config/lang" - "github.com/spf13/cobra" - "github.com/zarf-dev/zarf/src/pkg/message" + ui "github.com/defenseunicorns/uds-runtime/pkg/api" ) -//go:embed bin/uds-runtime-* -var embeddedFiles embed.FS - -var uiCmd = &cobra.Command{ - Use: "ui", - Short: lang.CmdUIShort, - RunE: func(cmd *cobra.Command, _ []string) error { - ctx, cancel := context.WithCancel(cmd.Context()) - defer cancel() - - // Create a temporary file to hold the embedded runtime binary - tmpFile, err := os.CreateTemp("", "uds-runtime-*") - if err != nil { - return fmt.Errorf("failed to create temp file: %v", err) - } - tmpFilePath := tmpFile.Name() - - // Set up cleanup to run on both normal exit and interrupt - cleanupDone := make(chan struct{}) - go func() { - sigChan := make(chan os.Signal, 1) - signal.Notify(sigChan, os.Interrupt, syscall.SIGTERM) - select { - case <-sigChan: - cancel() - case <-ctx.Done(): - } - err := tmpFile.Close() - if err != nil && !errors.Is(err, os.ErrClosed) { - message.Debug("Failed to close temporary runtime bin: %v", err) - } - err = os.Remove(tmpFilePath) - if err != nil { - message.Debug("Failed to remove temporary runtime bin: %v", err) - } - message.Debug("Temporary runtime bin removed") - close(cleanupDone) - }() - - // Ensure cleanup happens even if the function returns early - defer func() { - cancel() - <-cleanupDone - message.Debug("Cleanup complete") - }() - - // Get the name of the runtime binary for the current OS and architecture - runtimeBinaryPath := fmt.Sprintf("bin/uds-runtime-%s-%s", runtime.GOOS, runtime.GOARCH) - - // Read the embedded runtime binary - data, err := embeddedFiles.ReadFile(runtimeBinaryPath) - if err != nil { - return err - } - - // Write the binary data to the temporary file - if _, err := tmpFile.Write(data); err != nil { - return fmt.Errorf("failed to write to temp file: %v", err) - } - if err := tmpFile.Close(); err != nil { - return fmt.Errorf("failed to close temp file: %v", err) - } - - // Make the temporary file executable - if err := os.Chmod(tmpFilePath, 0700); err != nil { - return fmt.Errorf("failed to make temp file executable: %v", err) - } - - // Validate the temporary file path - if !filepath.IsAbs(tmpFilePath) { - return fmt.Errorf("temporary file path is not absolute: %s", tmpFilePath) - } - - // Execute the runtime binary with context - execCmd := exec.CommandContext(ctx, tmpFilePath) - execCmd.Env = append(os.Environ(), "API_AUTH_DISABLED=false") - execCmd.Stdout = os.Stdout - execCmd.Stderr = os.Stderr - - if err := execCmd.Start(); err != nil { - return fmt.Errorf("failed to start binary: %v", err) - } - - // Wait for the command to finish - err = execCmd.Wait() - if err != nil && ctx.Err() == nil { - return fmt.Errorf("binary execution failed: %v", err) - } - - return nil - }, -} - -func init() { - initViper() - rootCmd.AddCommand(uiCmd) +//go:embed ui/build/* +var uiBuild embed.FS + +//go:embed certs/cert.pem +var localCert []byte + +//go:embed certs/key.pem +var localKey []byte + +func startUI() error { + r, incluster, err := ui.Setup(&uiBuild) + if err != nil { + slog.Error("failed to setup UI server", "error", err) + return err + } + err = ui.Serve(r, localCert, localKey, incluster) + if err != nil { + slog.Error("failed to serve UI", "error", err) + return err + } + return nil } diff --git a/src/cmd/vendored.go b/src/cmd/vendored.go index 8cba20aa..cbdbdeb6 100644 --- a/src/cmd/vendored.go +++ b/src/cmd/vendored.go @@ -91,6 +91,21 @@ var scanCmd = &cobra.Command{ DisableFlagParsing: true, } +// uds-runtime +var uiCmd = &cobra.Command{ + Use: "ui", + Short: lang.CmdUIShort, + Long: lang.CmdUIShort, + RunE: func(_ *cobra.Command, _ []string) error { + os.Args = os.Args[1:] // grab 'ui' and onward from the CLI args + if err := startUI(); err != nil { + return err + } + return nil + }, + DisableFlagParsing: true, +} + func init() { // grab Zarf version to make Zarf library checks happy if buildInfo, ok := debug.ReadBuildInfo(); ok { @@ -111,4 +126,5 @@ func init() { rootCmd.AddCommand(runnerCmd) rootCmd.AddCommand(zarfCmd) rootCmd.AddCommand(scanCmd) // uds-security-hub CLI command + rootCmd.AddCommand(uiCmd) } diff --git a/src/test/e2e/ui_test.go b/src/test/e2e/ui_test.go index f239c576..222cf998 100644 --- a/src/test/e2e/ui_test.go +++ b/src/test/e2e/ui_test.go @@ -15,7 +15,7 @@ import ( ) func TestUDSUI(t *testing.T) { - t.Run("Test uds ui command and file cleanup", func(t *testing.T) { + t.Run("Test uds ui command", func(t *testing.T) { // Create a context with a timeout of 10 seconds ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second) defer cancel() @@ -50,16 +50,13 @@ func TestUDSUI(t *testing.T) { case <-ctx.Done(): t.Fatal("Command did not exit after interrupt") case err := <-done: - // Command should exit with an error due to interrupt - require.NoError(t, err) + require.Error(t, err) } // Check stdout for Runtime output indicating that it's running as expected - require.Contains(t, stdout.String(), "GET http://127.0.0.1:8080") + require.Contains(t, stdout.String(), "GET https://runtime-local.uds.dev:8443") - // Check stderr for CLI output indicating server startup and cleanup + // Check stderr for CLI output indicating server startup require.Contains(t, stderr.String(), "Starting server") - require.Contains(t, stderr.String(), "Temporary runtime bin removed") - require.Contains(t, stderr.String(), "Cleanup complete") }) } diff --git a/tasks.yaml b/tasks.yaml index c7707d5a..eac3aa0e 100644 --- a/tasks.yaml +++ b/tasks.yaml @@ -68,7 +68,7 @@ tasks: actions: - task: get-versions - task: build-args - - cmd: ./hack/update-uds-runtime-binaries.sh uds-runtime-linux-amd64 + - cmd: ./hack/download-uds-runtime-assets.sh - cmd: CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -ldflags="${BUILD_ARGS}" -o build/uds main.go - name: build-cli-linux-arm @@ -76,7 +76,7 @@ tasks: actions: - task: get-versions - task: build-args - - cmd: ./hack/update-uds-runtime-binaries.sh uds-runtime-linux-arm64 + - cmd: ./hack/download-uds-runtime-assets.sh - cmd: CGO_ENABLED=0 GOOS=linux GOARCH=arm64 go build -ldflags="${BUILD_ARGS}" -o build/uds-arm main.go - name: build-cli-mac-intel @@ -84,7 +84,7 @@ tasks: actions: - task: get-versions - task: build-args - - cmd: ./hack/update-uds-runtime-binaries.sh uds-runtime-darwin-amd64 + - cmd: ./hack/download-uds-runtime-assets.sh - cmd: GOOS=darwin GOARCH=amd64 go build -ldflags="${BUILD_ARGS}" -o build/uds-mac-intel main.go - name: build-cli-mac-apple @@ -92,5 +92,5 @@ tasks: actions: - task: get-versions - task: build-args - - cmd: ./hack/update-uds-runtime-binaries.sh uds-runtime-darwin-arm64 + - cmd: ./hack/download-uds-runtime-assets.sh - cmd: GOOS=darwin GOARCH=arm64 go build -ldflags="${BUILD_ARGS}" -o build/uds-mac-apple main.go