From a0cfaafb812b2fa46e2873f2388f1002cd88ba34 Mon Sep 17 00:00:00 2001 From: Ilya Kogan Date: Thu, 10 Sep 2026 02:31:21 +0000 Subject: [PATCH] Add ability to have seperate OHIO helm repository configuration. --- AGENTS.md | 119 +++++++++++++++++++++++++++++++++++++++++++++ README.md | 8 ++- setup-container.sh | 16 +++++- 3 files changed, 140 insertions(+), 3 deletions(-) create mode 100644 AGENTS.md diff --git a/AGENTS.md b/AGENTS.md new file mode 100644 index 0000000..7802e53 --- /dev/null +++ b/AGENTS.md @@ -0,0 +1,119 @@ +# Repository Guide + +## Overview + +This repository builds the `ghcr.io/ohioit/vscode-devcontainer-base` image, a reusable Ubuntu +24.04 base for VS Code Development Containers. It supplies common development utilities, +Kubernetes tooling, an Ohio-oriented authentication/bootstrap script, and a configured Zsh +environment. The image is intended to work with the `docker-outside-of-docker` devcontainer +feature; it does not provide Docker itself. + +## Repository Layout + +- `Dockerfile` is the image definition. It declares tool versions, installs apt packages, creates + the passwordless-sudo `vscode` user, runs the installation scripts, and installs the entrypoint + and startup scripts. +- `install-system-dependencies.sh` downloads and installs tooling that is available system-wide, + it runs as root during the build. +- `install-user-dependencies.sh` runs as `vscode`. It installs user specific tools like shell + customizations and anything that would live in ~. It also invokes `adp-connect` for ADP tooling. +- `adp-connect.sh` is a standalone interactive bootstrap utility. It handles authentication and + configuration for Rancher, Artifactory, Argo CD, GitHub, and related developer tooling. It can + also be downloaded and used outside the image, which is its primary intent. +- `docker-entrypoint.sh` changes from root to a login shell for `vscode` when the image is run + directly. +- `setup-container.sh` configures host-mounted state after startup, including kubeconfig and Helm + repositories, and runs devcontainer lifecycle hooks. +- `zshrc.zsh`, `zsh-aliases.zsh`, and `p10k.zsh` define the interactive shell experience. +- `debug-webserver.py` is a small Flask server for container debugging. +- `skaffold.yaml` defines the local image build and push workflow. +- `README.md` is the end-user source of truth for workstation setup, credentials, and usage. + +## Build and Development + +Use the workspace task or run this command to develop and push the image through Skaffold: + +```bash +skaffold build -p local +``` + +For one-off image work, `docker build` uses the `Dockerfile` in the repository root. Changes to +the installation scripts should be considered image-build changes; test them in a rebuilt image +when possible. Do not add Docker socket mounts to example devcontainer configurations: the +documented `docker-outside-of-docker` feature owns that integration. + +Note: When testing the image, DO NOT simply run `skaffold build` or `skaffold build -p local` as it +will push a new latest. Be sure to add the `--push=false` argument to skaffold to avoid pushing the image +to the public registry. + +## Runtime Model + +The final image starts as root, then `docker-entrypoint.sh` opens a login shell as `vscode`. +`setup-container.sh` expects an optional `HOST_HOME` mount and creates or refreshes configuration +under `/home/vscode`. It runs image hooks from: + +```text +/usr/local/lib/devcontainer/hooks.d/pre-start +/usr/local/lib/devcontainer/hooks.d/post-start +``` + +It also runs equivalent host hooks from `${HOST_HOME}/.devcontainer/hooks.d/` when available. +Preserve the `vscode:vscode` ownership of files copied into `/home/vscode`. + +## Host Kubernetes and Helm Configuration + +When `HOST_HOME` is available, startup copies `${HOST_HOME}/.kube/config` to +`/home/vscode/.kube/config`. It selects a Helm repository configuration from these host paths: + +```text +${HOST_HOME}/.config/helm/repositories.yaml +${HOST_HOME}/Library/Preferences/helm/repositories.yaml +``` + +An optional sibling `repositories-ohio.yaml` is merged with the selected `repositories.yaml` +before the script processes dependencies from `/workspaces/*/helm/Chart.yaml`. Chart-derived +repositories are only added when neither their URL nor their generated name is already configured; +this avoids replacing repositories supplied by either host file. OCI dependencies are skipped. + +## Shell Script Conventions + +- Shell scripts use Bash. Keep existing four-space indentation and quote variable expansions. +- Use `set -e` in installer scripts where a failed command must abort image construction. +- Scripts that run during the image build must be non-interactive. `adp-connect.sh` intentionally + supports interactive use, but its image-build invocation supplies flags for unattended setup. +- Keep downloads architecture-aware by using the variables established in the relevant script. +- Update `README.md` whenever image behavior, supported configuration paths, or user workflows + change. + +## YAML and yq + +The repository uses Mike Farah `yq` v4 syntax. For multi-file YAML transformations, use +`yq eval-all`, not jq-style slurp assumptions. The Helm repository merge currently uses: + +```bash +yq eval-all '. as $repository_config ireduce ({}; . *+ $repository_config)' \ + repositories.yaml repositories-ohio.yaml +``` + +`ireduce` deep-merges the documents and `*+` appends arrays, preserving both `repositories` +lists. `-s` with jq's `add` operator is not valid for the installed `yq` version. + +## Validation + +Run focused checks for modified scripts: + +```bash +bash -n setup-container.sh +bash -n install-system-dependencies.sh +bash -n install-user-dependencies.sh +shellcheck setup-container.sh install-system-dependencies.sh install-user-dependencies.sh +git diff --check +``` + +For a Helm merge change, run the exact `yq eval-all` expression against two small YAML fixtures +and verify that each file's repository entries remain in the result. Build the image or run the +Skaffold workflow for changes affecting `Dockerfile`, package installation, entrypoint behavior, +or tooling versions. + +When subtantive changes to the container are made, instruct the user to rebuild the devcontainer +to test changes. diff --git a/README.md b/README.md index 4176b65..a2c69c0 100644 --- a/README.md +++ b/README.md @@ -158,11 +158,17 @@ container, you will need to copy this file out of the container onto your system > NOTE: The below commands will erase any configured helm repositories on your host. If > you have some, you should run the above command on your host instead. +To keep Ohio-specific repositories separate, optionally place them in a +`repositories-ohio.yaml` file beside `repositories.yaml` on your host. Container startup +merges its repositories with `repositories.yaml` before it adds repositories inferred from +project `Chart.yaml` dependencies. Existing repositories from either file are not replaced +by those inferred dependencies. + #### Linux/Windows ```bash test -d "${HOST_HOME}"/.config/helm || mkdir -p "${HOST_HOME}"/.config/helm -cp ~/.config/helm/repositories.yaml "${HOST_HOME}/.config/repositories.yaml +cp ~/.config/helm/repositories.yaml "${HOST_HOME}/.config/helm/repositories.yaml ``` #### Mac OS diff --git a/setup-container.sh b/setup-container.sh index c70d79a..4a6a2be 100644 --- a/setup-container.sh +++ b/setup-container.sh @@ -39,6 +39,7 @@ else HELM_REPOSITORIES_YAML=/home/vscode/.config/helm/repositories.yaml HOST_HELM_REPOSITORIES_YAML="" + HOST_HELM_REPOSITORIES_OHIO_YAML="" for HOST_HELM in "${HOST_HOME}/.config/helm/repositories.yaml" "${HOST_HOME}/Library/Preferences/helm/repositories.yaml"; do if [[ -e "${HOST_HELM}" ]]; then HOST_HELM_REPOSITORIES_YAML="${HOST_HELM}" @@ -49,6 +50,15 @@ else if [[ -n "${HOST_HELM_REPOSITORIES_YAML}" ]]; then sudo cp "${HOST_HELM_REPOSITORIES_YAML}" "${HELM_REPOSITORIES_YAML}" sudo chown vscode:vscode "${HELM_REPOSITORIES_YAML}" + + HOST_HELM_REPOSITORIES_OHIO_YAML="$(dirname "${HOST_HELM_REPOSITORIES_YAML}")/repositories-ohio.yaml" + if [[ -e "${HOST_HELM_REPOSITORIES_OHIO_YAML}" ]]; then + echo "✓ Found Ohio Helm repositories configuration at ${HOST_HELM_REPOSITORIES_OHIO_YAML}" + yq eval-all '. as $repository_config ireduce ({}; . *+ $repository_config)' \ + "${HELM_REPOSITORIES_YAML}" "${HOST_HELM_REPOSITORIES_OHIO_YAML}" > /tmp/repositories.yaml + sudo mv /tmp/repositories.yaml "${HELM_REPOSITORIES_YAML}" + sudo chown vscode:vscode "${HELM_REPOSITORIES_YAML}" + fi else echo "Note: No user helm repositories were found in ${HOST_HOME}/.config/helm/repositories.yaml. You will not be able to use helm charts in Artifactory until this is setup." 1>&2 fi @@ -63,8 +73,10 @@ else if ! [[ -e "${HELM_REPOSITORIES_YAML}" ]] || ! (yq -r '.repositories[].url' "${HELM_REPOSITORIES_YAML}" | grep -q '^'"${DEPENDENCY}"'$'); then DEPENDENCY_NAME=$(echo "${DEPENDENCY}" | sed -r 's/https?:\/\/(.*)/\1/' | sed -r 's/[\,\/]/-/g') - echo "Adding Helm repository for ${DEPENDENCY_NAME} from current project." - helm repo add "${DEPENDENCY_NAME}" "${DEPENDENCY}" + if ! yq -r '.repositories[].name' "${HELM_REPOSITORIES_YAML}" | grep -q '^'"${DEPENDENCY_NAME}"'$'; then + echo "Adding Helm repository for ${DEPENDENCY_NAME} from current project." + helm repo add "${DEPENDENCY_NAME}" "${DEPENDENCY}" + fi fi done fi