|
| 1 | +#!/bin/bash |
| 2 | + |
| 3 | +set -eu |
| 4 | + |
| 5 | +MARKER=/etc/opt/oxide/NO_INSTALL |
| 6 | +if [[ -f "$MARKER" ]]; then |
| 7 | + echo "This system has the marker file $MARKER, aborting." >&2 |
| 8 | + exit 1 |
| 9 | +fi |
| 10 | + |
| 11 | +# Set the CWD to Omicron's source. |
| 12 | +SOURCE_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )" |
| 13 | +cd "${SOURCE_DIR}/.." |
| 14 | + |
| 15 | +function on_exit |
| 16 | +{ |
| 17 | + echo "Something went wrong, but this script is idempotent - If you can fix the issue, try re-running" |
| 18 | +} |
| 19 | + |
| 20 | +trap on_exit ERR |
| 21 | + |
| 22 | +# Parse command line options: |
| 23 | +# |
| 24 | +# -y Assume "yes" intead of showing confirmation prompts. |
| 25 | +# -p Skip checking paths |
| 26 | +ASSUME_YES="false" |
| 27 | +SKIP_PATH_CHECK="false" |
| 28 | +while getopts yp flag |
| 29 | +do |
| 30 | + case "${flag}" in |
| 31 | + y) ASSUME_YES="true" ;; |
| 32 | + p) SKIP_PATH_CHECK="true" ;; |
| 33 | + esac |
| 34 | +done |
| 35 | + |
| 36 | +# Offers a confirmation prompt, unless we were passed `-y`. |
| 37 | +# |
| 38 | +# Args: |
| 39 | +# $1: Text to be displayed |
| 40 | +function confirm |
| 41 | +{ |
| 42 | + if [[ "${ASSUME_YES}" == "true" ]]; then |
| 43 | + response=y |
| 44 | + else |
| 45 | + read -r -p "$1 (y/n): " response |
| 46 | + fi |
| 47 | + case $response in |
| 48 | + [yY]) |
| 49 | + true |
| 50 | + ;; |
| 51 | + *) |
| 52 | + false |
| 53 | + ;; |
| 54 | + esac |
| 55 | +} |
| 56 | + |
| 57 | +# Packages to be installed on all OSes: |
| 58 | +# |
| 59 | +# - libpq, the PostgreSQL client lib. |
| 60 | +# We use Diesel's PostgreSQL support to connect to CockroachDB (which is |
| 61 | +# wire-compatible with PostgreSQL). Diesel uses the native libpq to do this. |
| 62 | +# `pg_config` is a utility which may be used to query for the installed |
| 63 | +# PostgreSQL libraries, and is expected by the Omicron build to exist in |
| 64 | +# the developer's PATH variable. |
| 65 | +# - pkg-config, a tool for querying installed libraries. |
| 66 | +# |
| 67 | +# Packages to be installed on Helios only: |
| 68 | +# |
| 69 | +# - pkg, the IPS client (though likely it will just be updated) |
| 70 | +# - build-essential: Common development tools |
| 71 | +# - brand/omicron1/tools: Oxide's omicron1-brand Zone |
| 72 | + |
| 73 | +HOST_OS=$(uname -s) |
| 74 | +if [[ "${HOST_OS}" == "Linux" ]]; then |
| 75 | + packages=( |
| 76 | + 'libpq-dev' |
| 77 | + 'pkg-config' |
| 78 | + 'xmlsec1' |
| 79 | + 'libxmlsec1-dev' |
| 80 | + 'libxmlsec1-openssl' |
| 81 | + 'libclang-dev' |
| 82 | + 'libsqlite3-dev' |
| 83 | + ) |
| 84 | + sudo apt-get update |
| 85 | + if [[ "${ASSUME_YES}" == "true" ]]; then |
| 86 | + sudo apt-get install -y ${packages[@]} |
| 87 | + else |
| 88 | + confirm "Install (or update) [${packages[*]}]?" && sudo apt-get install ${packages[@]} |
| 89 | + fi |
| 90 | +elif [[ "${HOST_OS}" == "SunOS" ]]; then |
| 91 | + packages=( |
| 92 | + 'pkg:/package/pkg' |
| 93 | + 'build-essential' |
| 94 | + 'library/postgresql-13' |
| 95 | + 'pkg-config' |
| 96 | + 'library/libxmlsec1' |
| 97 | + # "bindgen leverages libclang to preprocess, parse, and type check C and C++ header files." |
| 98 | + 'pkg:/ooce/developer/clang-120' |
| 99 | + ) |
| 100 | + |
| 101 | + # Install/update the set of packages. |
| 102 | + # Explicitly manage the return code using "rc" to observe the result of this |
| 103 | + # command without exiting the script entirely (due to bash's "errexit"). |
| 104 | + rc=0 |
| 105 | + confirm "Install (or update) [${packages[*]}]?" && { pfexec pkg install -v "${packages[@]}" || rc=$?; } |
| 106 | + # Return codes: |
| 107 | + # 0: Normal Success |
| 108 | + # 4: Failure because we're already up-to-date. Also acceptable. |
| 109 | + if [[ "$rc" -ne 4 ]] && [[ "$rc" -ne 0 ]]; then |
| 110 | + exit "$rc" |
| 111 | + fi |
| 112 | + |
| 113 | + pkg list -v "${packages[@]}" |
| 114 | +elif [[ "${HOST_OS}" == "Darwin" ]]; then |
| 115 | + packages=( |
| 116 | + 'postgresql' |
| 117 | + 'pkg-config' |
| 118 | + 'libxmlsec1' |
| 119 | + ) |
| 120 | + confirm "Install (or update) [${packages[*]}]?" && brew install ${packages[@]} |
| 121 | +else |
| 122 | + echo "Unsupported OS: ${HOST_OS}" |
| 123 | + exit -1 |
| 124 | +fi |
| 125 | + |
| 126 | +# CockroachDB and Clickhouse are used by Omicron for storage of |
| 127 | +# control plane metadata and metrics. |
| 128 | +# |
| 129 | +# They are used in a couple of spots within Omicron: |
| 130 | +# |
| 131 | +# - Test Suite: The test suite, regardless of host OS, builds temporary |
| 132 | +# databases for testing, and expects `cockroach` and `clickhouse` to |
| 133 | +# exist as a part of the PATH. |
| 134 | +# - Packaging: When constructing packages on Helios, these utilities |
| 135 | +# are packaged into zones which may be launched by the sled agent. |
| 136 | + |
| 137 | +./tools/ci_download_cockroachdb |
| 138 | +./tools/ci_download_clickhouse |
| 139 | + |
| 140 | +# Install static console assets. These are used when packaging Nexus. |
| 141 | +./tools/ci_download_console |
| 142 | + |
| 143 | +# Download the OpenAPI spec for maghemite. This is required to build the |
| 144 | +# ddm-admin-api crate. |
| 145 | +./tools/ci_download_maghemite_openapi |
| 146 | + |
| 147 | +# Validate the PATH: |
| 148 | +expected_in_path=( |
| 149 | + 'pg_config' |
| 150 | + 'pkg-config' |
| 151 | + 'cockroach' |
| 152 | + 'clickhouse' |
| 153 | +) |
| 154 | + |
| 155 | +function show_hint |
| 156 | +{ |
| 157 | + case "$1" in |
| 158 | + "pg_config") |
| 159 | + if [[ "${HOST_OS}" == "SunOS" ]]; then |
| 160 | + echo "On illumos, $1 is typically found in '/opt/ooce/bin'" |
| 161 | + fi |
| 162 | + ;; |
| 163 | + "pkg-config") |
| 164 | + if [[ "${HOST_OS}" == "SunOS" ]]; then |
| 165 | + echo "On illumos, $1 is typically found in '/usr/bin'" |
| 166 | + fi |
| 167 | + ;; |
| 168 | + "cockroach") |
| 169 | + echo "$1 should have been installed to '$PWD/out/cockroachdb/bin'" |
| 170 | + ;; |
| 171 | + "clickhouse") |
| 172 | + echo "$1 should have been installed to '$PWD/out/clickhouse'" |
| 173 | + ;; |
| 174 | + *) |
| 175 | + ;; |
| 176 | + esac |
| 177 | +} |
| 178 | + |
| 179 | +# Check all paths before returning an error, unless we were told not too. |
| 180 | +if [[ "$SKIP_PATH_CHECK" == "true" ]]; then |
| 181 | + echo "All prerequisites installed successfully" |
| 182 | + exit 0 |
| 183 | +fi |
| 184 | + |
| 185 | +ANY_PATH_ERROR="false" |
| 186 | +for command in "${expected_in_path[@]}"; do |
| 187 | + rc=0 |
| 188 | + which "$command" &> /dev/null || rc=$? |
| 189 | + if [[ "$rc" -ne 0 ]]; then |
| 190 | + echo "ERROR: $command seems installed, but was not found in PATH. Please add it." |
| 191 | + show_hint "$command" |
| 192 | + ANY_PATH_ERROR="true" |
| 193 | + fi |
| 194 | +done |
| 195 | + |
| 196 | +if [[ "$ANY_PATH_ERROR" == "true" ]]; then |
| 197 | + exit -1 |
| 198 | +fi |
| 199 | + |
| 200 | +echo "All builder prerequisites installed successfully, and PATH looks valid" |
0 commit comments