Add .NET SDK installation phase
This commit is contained in:
parent
6ff3a79cea
commit
4655260986
@ -10,6 +10,55 @@ This file records chronological Atlas build and infrastructure milestones. Do no
|
||||
|
||||
### Phase
|
||||
|
||||
Phase 2 .NET development platform.
|
||||
|
||||
### Objective
|
||||
|
||||
Install the .NET SDKs required for Atlas and PlotDirector development.
|
||||
|
||||
### Changes
|
||||
|
||||
- Added `install/phases/10-dotnet.sh`.
|
||||
- Installed .NET 8 SDK `8.0.128`.
|
||||
- Installed .NET 10 SDK `10.0.109`.
|
||||
- Used the official Ubuntu .NET backports PPA for .NET 8.
|
||||
- Used the built-in Ubuntu `resolute-updates` and `resolute-security` package sources for .NET 10.
|
||||
- Did not install .NET 9, SQL Server, nginx, or Docker.
|
||||
|
||||
### Validation
|
||||
|
||||
- `bash -n install/phases/10-dotnet.sh` passed.
|
||||
- `install/phases/10-dotnet.sh --help` passed.
|
||||
- `install/phases/10-dotnet.sh --dry-run` passed.
|
||||
- `install/phases/10-dotnet.sh` installed the missing SDKs.
|
||||
- A second `install/phases/10-dotnet.sh` run detected both SDKs already installed.
|
||||
- `dotnet --info`, `dotnet --list-sdks`, and `dotnet --list-runtimes` passed.
|
||||
- Temporary .NET 8 and .NET 10 console projects built and ran outside the repository.
|
||||
- `scripts/system/validate-host.sh` passed after installation.
|
||||
|
||||
### Problems
|
||||
|
||||
- Initial package-candidate detection in `10-dotnet.sh` was corrected after it failed under `pipefail` before installing SDK packages.
|
||||
- No unresolved .NET installation problems recorded.
|
||||
|
||||
### Decisions
|
||||
|
||||
- Use Ubuntu package feeds for .NET SDK installation on Ubuntu 26.04.
|
||||
|
||||
### Git Commit
|
||||
|
||||
Not yet committed.
|
||||
|
||||
### Operator
|
||||
|
||||
Codex.
|
||||
|
||||
### Date
|
||||
|
||||
2026-07-10
|
||||
|
||||
### Phase
|
||||
|
||||
Phase 2A.
|
||||
|
||||
### Objective
|
||||
|
||||
@ -8,7 +8,8 @@ This guide describes the planned rebuild path for Atlas. At Phase 1, the reposit
|
||||
- Shared installation framework: present.
|
||||
- System discovery script: present.
|
||||
- Host validation script: present.
|
||||
- Component installation scripts: not yet created.
|
||||
- .NET installation script: present.
|
||||
- Other component installation scripts: not yet created.
|
||||
- Configuration templates: not yet created.
|
||||
- Operational scripts: not yet created.
|
||||
- Smoke tests: not yet created.
|
||||
@ -112,8 +113,9 @@ Planned bootstrap flow:
|
||||
4. Run `scripts/system/discover-system.sh`.
|
||||
5. Run `scripts/system/validate-host.sh`.
|
||||
6. Run `install/bootstrap.sh --dry-run`.
|
||||
7. Run ordered installation scripts from `install/phases/` when they exist.
|
||||
8. Run smoke tests from `tests/` when they exist.
|
||||
7. Run `install/phases/10-dotnet.sh` when .NET SDKs are required.
|
||||
8. Run additional ordered installation scripts from `install/phases/` when they exist.
|
||||
9. Run smoke tests from `tests/` when they exist.
|
||||
|
||||
Bootstrap command sequence is `TODO: Confirm during the relevant implementation phase.`
|
||||
|
||||
@ -137,6 +139,22 @@ These scripts do not exist yet. When created, each script must:
|
||||
- Document rollback expectations.
|
||||
- Include or reference validation steps.
|
||||
|
||||
Current .NET installation command:
|
||||
|
||||
```bash
|
||||
install/phases/10-dotnet.sh
|
||||
```
|
||||
|
||||
Current .NET verification commands:
|
||||
|
||||
```bash
|
||||
dotnet --info
|
||||
dotnet --list-sdks
|
||||
dotnet --list-runtimes
|
||||
```
|
||||
|
||||
The current installed SDKs are .NET 8 SDK `8.0.128` and .NET 10 SDK `10.0.109`.
|
||||
|
||||
## 8. Validation
|
||||
|
||||
Minimum rebuild validation should confirm:
|
||||
|
||||
@ -48,6 +48,21 @@ manifests/
|
||||
phases/
|
||||
```
|
||||
|
||||
Current Phase 2 installer:
|
||||
|
||||
```bash
|
||||
install/phases/10-dotnet.sh
|
||||
```
|
||||
|
||||
The .NET installer installs only the required .NET SDK packages and verifies them with `dotnet --list-sdks`.
|
||||
|
||||
Current installed SDKs:
|
||||
|
||||
- .NET 8 SDK `8.0.128`
|
||||
- .NET 10 SDK `10.0.109`
|
||||
|
||||
.NET 8 is installed from the official Ubuntu .NET backports PPA. .NET 10 is installed from the built-in Ubuntu package feeds.
|
||||
|
||||
Runtime output belongs outside the repository:
|
||||
|
||||
- `/var/log/atlas/install/`
|
||||
|
||||
@ -98,4 +98,3 @@ else
|
||||
fi
|
||||
|
||||
atlas_log_ok "Bootstrap scaffold completed"
|
||||
|
||||
|
||||
@ -41,4 +41,3 @@ atlas_pending_update_count() {
|
||||
atlas_reboot_required() {
|
||||
[[ -f /var/run/reboot-required ]]
|
||||
}
|
||||
|
||||
|
||||
@ -55,4 +55,3 @@ atlas_service_restart() {
|
||||
atlas_log_info "Restarting service ${service_name}"
|
||||
atlas_sudo_run systemctl restart "$service_name"
|
||||
}
|
||||
|
||||
|
||||
@ -65,4 +65,3 @@ atlas_gib_to_bytes() {
|
||||
local gib="$1"
|
||||
awk -v gib="$gib" 'BEGIN {printf "%.0f\n", gib * 1024 * 1024 * 1024}'
|
||||
}
|
||||
|
||||
|
||||
@ -29,4 +29,3 @@ awk|required|Text processing
|
||||
sed|required|Text processing
|
||||
grep|required|Text searching
|
||||
sudo|required|Non-interactive privileged command execution
|
||||
|
||||
|
||||
178
install/phases/10-dotnet.sh
Executable file
178
install/phases/10-dotnet.sh
Executable file
@ -0,0 +1,178 @@
|
||||
#!/usr/bin/env bash
|
||||
set -Eeuo pipefail
|
||||
|
||||
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
INSTALL_DIR="$(cd "${SCRIPT_DIR}/.." && pwd)"
|
||||
REPO_ROOT="$(cd "${INSTALL_DIR}/.." && pwd)"
|
||||
|
||||
# shellcheck source=install/lib/common.sh
|
||||
source "${INSTALL_DIR}/lib/common.sh"
|
||||
# shellcheck source=install/lib/logging.sh
|
||||
source "${INSTALL_DIR}/lib/logging.sh"
|
||||
# shellcheck source=install/lib/packages.sh
|
||||
source "${INSTALL_DIR}/lib/packages.sh"
|
||||
|
||||
atlas_set_script_name "10-dotnet.sh"
|
||||
atlas_install_error_trap
|
||||
|
||||
REQUIRED_OS_ID="ubuntu"
|
||||
REQUIRED_OS_VERSION="26.04"
|
||||
DOTNET_BACKPORTS_PPA="ppa:dotnet/backports"
|
||||
DOTNET_REQUIRED_PACKAGES=("dotnet-sdk-8.0" "dotnet-sdk-10.0")
|
||||
|
||||
usage() {
|
||||
cat <<'USAGE'
|
||||
Usage: install/phases/10-dotnet.sh [options]
|
||||
|
||||
Install the Atlas .NET development SDKs from official Ubuntu package feeds.
|
||||
|
||||
Required SDKs:
|
||||
dotnet-sdk-8.0
|
||||
dotnet-sdk-10.0
|
||||
|
||||
Options:
|
||||
--help Show this help text.
|
||||
--version Show script/framework version.
|
||||
--dry-run Show intended actions without making changes.
|
||||
--verbose Print additional diagnostic output.
|
||||
|
||||
USAGE
|
||||
}
|
||||
|
||||
while [[ "$#" -gt 0 ]]; do
|
||||
case "$1" in
|
||||
--help)
|
||||
usage
|
||||
exit "${ATLAS_EXIT_OK}"
|
||||
;;
|
||||
--version)
|
||||
atlas_print_version
|
||||
exit "${ATLAS_EXIT_OK}"
|
||||
;;
|
||||
--dry-run)
|
||||
atlas_enable_dry_run
|
||||
;;
|
||||
--verbose)
|
||||
atlas_enable_verbose
|
||||
;;
|
||||
*)
|
||||
atlas_usage_error "Unknown option: $1"
|
||||
exit "${ATLAS_EXIT_USAGE}"
|
||||
;;
|
||||
esac
|
||||
shift
|
||||
done
|
||||
|
||||
load_os_release() {
|
||||
if [[ ! -r /etc/os-release ]]; then
|
||||
atlas_log_error "/etc/os-release is not readable"
|
||||
exit "${ATLAS_EXIT_PREREQ}"
|
||||
fi
|
||||
# shellcheck disable=SC1091
|
||||
. /etc/os-release
|
||||
if [[ "${ID:-}" != "${REQUIRED_OS_ID}" || "${VERSION_ID:-}" != "${REQUIRED_OS_VERSION}" ]]; then
|
||||
atlas_log_error "Unsupported OS: ${PRETTY_NAME:-unknown}; expected Ubuntu 26.04"
|
||||
exit "${ATLAS_EXIT_PREREQ}"
|
||||
fi
|
||||
}
|
||||
|
||||
package_has_candidate() {
|
||||
local package_name="$1"
|
||||
local candidate
|
||||
candidate="$(apt-cache policy "$package_name" 2>/dev/null | awk -F: '/Candidate:/ {gsub(/^[ \t]+/, "", $2); print $2; exit}')"
|
||||
[[ -n "$candidate" && "$candidate" != "(none)" ]]
|
||||
}
|
||||
|
||||
backports_configured() {
|
||||
grep -RqsE 'ppa\\.launchpadcontent\\.net/dotnet/backports|LP-PPA-dotnet-backports|dotnet-ubuntu-backports' /etc/apt/sources.list /etc/apt/sources.list.d 2>/dev/null
|
||||
}
|
||||
|
||||
ensure_backports_if_needed() {
|
||||
if package_has_candidate dotnet-sdk-8.0; then
|
||||
atlas_log_info "dotnet-sdk-8.0 is available from configured package sources"
|
||||
return 0
|
||||
fi
|
||||
|
||||
if backports_configured; then
|
||||
atlas_log_info "Ubuntu .NET backports repository is configured; refreshing package metadata"
|
||||
atlas_sudo_run apt-get update
|
||||
return 0
|
||||
fi
|
||||
|
||||
atlas_log_info "dotnet-sdk-8.0 is not available; adding official Ubuntu .NET backports repository"
|
||||
if [[ "${ATLAS_DRY_RUN}" == "1" ]]; then
|
||||
atlas_log_info "Dry-run mode: would run add-apt-repository -y ${DOTNET_BACKPORTS_PPA}"
|
||||
atlas_log_info "Dry-run mode: would run apt-get update"
|
||||
return 0
|
||||
fi
|
||||
|
||||
atlas_require_command add-apt-repository
|
||||
atlas_sudo_run add-apt-repository -y "${DOTNET_BACKPORTS_PPA}"
|
||||
atlas_sudo_run apt-get update
|
||||
}
|
||||
|
||||
install_missing_sdks() {
|
||||
local missing=()
|
||||
local package_name
|
||||
|
||||
for package_name in "${DOTNET_REQUIRED_PACKAGES[@]}"; do
|
||||
if atlas_package_installed "$package_name"; then
|
||||
atlas_log_ok "${package_name} is already installed"
|
||||
else
|
||||
missing+=("$package_name")
|
||||
fi
|
||||
done
|
||||
|
||||
if [[ "${#missing[@]}" -eq 0 ]]; then
|
||||
atlas_log_ok "All required .NET SDK packages are installed"
|
||||
return 0
|
||||
fi
|
||||
|
||||
for package_name in "${missing[@]}"; do
|
||||
if [[ "${ATLAS_DRY_RUN}" == "1" ]]; then
|
||||
atlas_log_info "Dry-run mode: would verify package candidate for ${package_name}"
|
||||
continue
|
||||
fi
|
||||
if ! package_has_candidate "$package_name"; then
|
||||
atlas_log_error "No official configured package candidate found for ${package_name}"
|
||||
exit "${ATLAS_EXIT_PREREQ}"
|
||||
fi
|
||||
done
|
||||
|
||||
atlas_install_packages "${missing[@]}"
|
||||
}
|
||||
|
||||
verify_dotnet() {
|
||||
atlas_require_command dotnet
|
||||
dotnet --list-sdks | grep -q '^8\.' || {
|
||||
atlas_log_error ".NET 8 SDK was not found after installation"
|
||||
exit "${ATLAS_EXIT_VALIDATION}"
|
||||
}
|
||||
dotnet --list-sdks | grep -q '^10\.' || {
|
||||
atlas_log_error ".NET 10 SDK was not found after installation"
|
||||
exit "${ATLAS_EXIT_VALIDATION}"
|
||||
}
|
||||
atlas_log_ok ".NET SDK verification passed"
|
||||
}
|
||||
|
||||
main() {
|
||||
load_os_release
|
||||
atlas_require_sudo_noninteractive || {
|
||||
atlas_log_error "Passwordless non-interactive sudo is required"
|
||||
exit "${ATLAS_EXIT_PREREQ}"
|
||||
}
|
||||
atlas_require_command apt-cache
|
||||
atlas_require_command apt-get
|
||||
atlas_require_command dpkg-query
|
||||
|
||||
ensure_backports_if_needed
|
||||
install_missing_sdks
|
||||
|
||||
if [[ "${ATLAS_DRY_RUN}" == "1" ]]; then
|
||||
atlas_log_info "Dry-run mode: skipping post-install dotnet verification"
|
||||
else
|
||||
verify_dotnet
|
||||
fi
|
||||
}
|
||||
|
||||
main
|
||||
@ -2,7 +2,7 @@
|
||||
|
||||
This directory is reserved for future ordered Atlas installation phases.
|
||||
|
||||
Phase 2A intentionally does not create speculative .NET, SQL Server, nginx, or Docker installer scripts. Future scripts should be added only when their implementation phase is approved.
|
||||
Phase 2A intentionally did not create speculative .NET, SQL Server, nginx, or Docker installer scripts. Phase 2 adds the .NET installer only.
|
||||
|
||||
## Naming Convention
|
||||
|
||||
@ -18,3 +18,11 @@ Use a two-digit phase number and lower-case hyphenated component name:
|
||||
|
||||
Each phase must source the shared framework under `install/lib/`, support dry-run behaviour where practical, and follow [../../SERVER-STANDARDS.md](../../SERVER-STANDARDS.md).
|
||||
|
||||
## Current Phases
|
||||
|
||||
- `10-dotnet.sh`: installs the required .NET 8 and .NET 10 SDKs from official Ubuntu package sources.
|
||||
|
||||
Installed SDKs after the current Phase 2 run:
|
||||
|
||||
- .NET 8 SDK `8.0.128`
|
||||
- .NET 10 SDK `10.0.109`
|
||||
|
||||
@ -5,4 +5,3 @@ This directory is reserved for development workflow helpers that do not belong t
|
||||
Do not store secrets, generated logs, package caches, or one-off experiments here.
|
||||
|
||||
Future structure is `TODO: Confirm during the relevant implementation phase.`
|
||||
|
||||
|
||||
@ -270,4 +270,3 @@ fi
|
||||
printf '\n'
|
||||
atlas_validation_summary
|
||||
atlas_validation_exit_code
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user