You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

345 lines
13 KiB

  1. #!/usr/bin/env bash
  2. set -o errexit
  3. set -o pipefail
  4. if [[ ${DEBUG:-false} == "true" ]]; then
  5. set -o xtrace
  6. fi
  7. checksums_file="$(git rev-parse --show-toplevel)/roles/kubespray-defaults/defaults/main/checksums.yml"
  8. downloads_folder=/tmp/kubespray_binaries
  9. default_file="$(git rev-parse --show-toplevel)/roles/kubespray-defaults/defaults/main/main.yml"
  10. kube_min_version="$(grep kube_version_min_required ${default_file} | sed -E 's|kube_version_min_required: v(.*)|\1|g')"
  11. function filter_version() {
  12. while read version; do
  13. if [[ "${version}" =~ ^v?[0-9]*\.[0-9]*\.[0-9]*$ ]]; then
  14. echo "${version}"
  15. fi
  16. done < /dev/stdin
  17. }
  18. function min_version() {
  19. local min_version="$1"
  20. local func_filter="${2:-filter_version}"
  21. while read version; do
  22. if _vercmp "${version#v}" '>=' "${min_version}"; then
  23. echo "${version}"
  24. fi
  25. done | "${func_filter}"
  26. }
  27. function limit_version() {
  28. local number_versions="${1:-7}"
  29. local func_filter="${2:-filter_version}"
  30. "${func_filter}" | head -n "${number_versions}"
  31. }
  32. function gvisor_version_filter() {
  33. while read version; do
  34. echo "${version}" | sed -E 's|^release-(.*)\..*$|\1|'
  35. done | head -n 8
  36. }
  37. function get_versions() {
  38. local type="$1"
  39. local name="$2"
  40. local version_func="${3:-limit_version}"
  41. if [ "$#" -ge 3 ]; then
  42. shift 3
  43. else
  44. shift 2
  45. fi
  46. local version=""
  47. local attempt_counter=0
  48. readonly max_attempts=5
  49. until [ "$version" ]; do
  50. version=$("_get_$type" "$name" "${version_func}" "$@")
  51. if _vercmp "${version#v}" '<' "${min_version}"; then
  52. continue
  53. elif [ "$version" ] ; then
  54. break
  55. elif [ ${attempt_counter} -eq ${max_attempts} ]; then
  56. echo "Max attempts reached" >&2
  57. exit 1
  58. fi
  59. attempt_counter=$((attempt_counter + 1))
  60. sleep $((attempt_counter * 2))
  61. done
  62. echo "${version}"
  63. }
  64. function _get_github_tags() {
  65. local repo="$1"
  66. local version_func="$2"
  67. shift 2
  68. # The number of results per page (max 50).
  69. tags="$(curl -s "https://api.github.com/repos/$repo/tags?per_page=50")"
  70. if [ "$tags" ]; then
  71. echo "$tags" | grep -Po '"name":.*?[^\\]",' | awk -F '"' '{print $4}' | "$version_func" "$@"
  72. fi
  73. }
  74. function _vercmp() {
  75. local v1=$1
  76. local op=$2
  77. local v2=$3
  78. local result
  79. # sort the two numbers with sort's "-V" argument. Based on if v2
  80. # swapped places with v1, we can determine ordering.
  81. result=$(echo -e "$v1\n$v2" | sort -V | head -1)
  82. case $op in
  83. "==")
  84. [ "$v1" = "$v2" ]
  85. return
  86. ;;
  87. ">")
  88. [ "$v1" != "$v2" ] && [ "$result" = "$v2" ]
  89. return
  90. ;;
  91. "<")
  92. [ "$v1" != "$v2" ] && [ "$result" = "$v1" ]
  93. return
  94. ;;
  95. ">=")
  96. [ "$result" = "$v2" ]
  97. return
  98. ;;
  99. "<=")
  100. [ "$result" = "$v1" ]
  101. return
  102. ;;
  103. *)
  104. echo "unrecognised op: $op"
  105. exit 1
  106. ;;
  107. esac
  108. }
  109. function get_checksums() {
  110. local binary="$1"
  111. local version_exceptions="cri_dockerd_archive nerdctl_archive containerd_archive youki"
  112. declare -A skip_archs=(
  113. ["crio_archive"]="arm"
  114. ["calicoctl_binary"]="arm"
  115. ["ciliumcli_binary"]="arm ppc64le"
  116. ["etcd_binary"]="arm"
  117. ["cri_dockerd_archive"]="arm ppc64le"
  118. ["runc"]="arm"
  119. ["crun"]="arm ppc64le"
  120. ["youki"]="arm arm64 ppc64le"
  121. ["kata_containers_binary"]="arm arm64 ppc64le"
  122. ["gvisor_runsc_binary"]="arm ppc64le"
  123. ["gvisor_containerd_shim_binary"]="arm ppc64le"
  124. ["containerd_archive"]="arm"
  125. ["skopeo_binary"]="arm"
  126. )
  127. echo "${binary}_checksums:" | tee --append "$checksums_file"
  128. for arch in arm arm64 amd64 ppc64le; do
  129. echo " $arch:" | tee --append "$checksums_file"
  130. for version in "${@:2}"; do
  131. checksum=0
  132. [[ "${skip_archs[$binary]}" == *"$arch"* ]] || checksum=$(_get_checksum "$binary" "$version" "$arch")
  133. [[ "$version_exceptions" != *"$binary"* ]] || version=${version#v}
  134. echo " $version: $checksum" | tee --append "$checksums_file"
  135. done
  136. done
  137. }
  138. function get_krew_archive_checksums() {
  139. declare -A archs=(
  140. ["linux"]="arm arm64 amd64"
  141. ["darwin"]="arm64 amd64"
  142. ["windows"]="amd64"
  143. )
  144. echo "krew_archive_checksums:" | tee --append "$checksums_file"
  145. for os in "${!archs[@]}"; do
  146. echo " $os:" | tee --append "$checksums_file"
  147. for arch in arm arm64 amd64 ppc64le; do
  148. echo " $arch:" | tee --append "$checksums_file"
  149. for version in "$@"; do
  150. checksum=0
  151. [[ " ${archs[$os]} " != *" $arch "* ]] || checksum=$(_get_checksum "krew_archive" "$version" "$arch" "$os")
  152. echo " $version: $checksum" | tee --append "$checksums_file"
  153. done
  154. done
  155. done
  156. }
  157. function get_calico_crds_archive_checksums() {
  158. echo "calico_crds_archive_checksums:" | tee --append "$checksums_file"
  159. for version in "$@"; do
  160. echo " $version: $(_get_checksum "calico_crds_archive" "$version")" | tee --append "$checksums_file"
  161. done
  162. }
  163. function get_containerd_archive_checksums() {
  164. declare -A support_version_history=(
  165. ["arm"]="2"
  166. ["arm64"]="1.6.0"
  167. ["amd64"]="1.5.5"
  168. ["ppc64le"]="1.6.7"
  169. )
  170. echo "containerd_archive_checksums:" | tee --append "$checksums_file"
  171. for arch in arm arm64 amd64 ppc64le; do
  172. echo " $arch:" | tee --append "$checksums_file"
  173. for version in "${@}"; do
  174. _vercmp "${version#v}" '>=' "${support_version_history[$arch]}" && checksum=$(_get_checksum "containerd_archive" "$version" "$arch") || checksum=0
  175. echo " ${version#v}: $checksum" | tee --append "$checksums_file"
  176. done
  177. done
  178. }
  179. function get_k8s_checksums() {
  180. local binary=$1
  181. echo "${binary}_checksums:" | tee --append "$checksums_file"
  182. echo " arm:" | tee --append "$checksums_file"
  183. for version in "${@:2}"; do
  184. _vercmp "${version#v}" '<' "1.27" && checksum=$(_get_checksum "$binary" "$version" "arm") || checksum=0
  185. echo " ${version}: $checksum" | tee --append "$checksums_file"
  186. done
  187. for arch in arm64 amd64 ppc64le; do
  188. echo " $arch:" | tee --append "$checksums_file"
  189. for version in "${@:2}"; do
  190. echo " ${version}: $(_get_checksum "$binary" "$version" "$arch")" | tee --append "$checksums_file"
  191. done
  192. done
  193. }
  194. function get_crictl_checksums() {
  195. local binary=$1
  196. echo "${binary}_checksums:" | tee --append "$checksums_file"
  197. echo " arm:" | tee --append "$checksums_file"
  198. for version in "${@:2}"; do
  199. _vercmp "${version#v}" '<' "1.29" && checksum=$(_get_checksum "$binary" "$version" "arm") || checksum=0
  200. echo " ${version}: $checksum" | tee --append "$checksums_file"
  201. done
  202. for arch in arm64 amd64 ppc64le; do
  203. echo " $arch:" | tee --append "$checksums_file"
  204. for version in "${@:2}"; do
  205. echo " ${version}: $(_get_checksum "$binary" "$version" "$arch")" | tee --append "$checksums_file"
  206. done
  207. done
  208. }
  209. # Note: kata changed their arch starting at version 3.2.0
  210. function get_arch_kata() {
  211. local version="${1}"
  212. local arch="${2}"
  213. if _vercmp "${version}" '<' '3.2.0'; then
  214. echo "${arch//amd64/x86_64}"
  215. else
  216. echo "${arch}"
  217. fi
  218. }
  219. function _get_checksum() {
  220. local binary="$1"
  221. local version="$2"
  222. local arch="${3:-amd64}"
  223. local os="${4:-linux}"
  224. local target="$downloads_folder/$binary/$version-$os-$arch"
  225. readonly github_url="https://github.com"
  226. readonly github_releases_url="$github_url/%s/releases/download/$version/%s"
  227. readonly github_archive_url="$github_url/%s/archive/%s"
  228. readonly google_url="https://storage.googleapis.com"
  229. readonly release_url="https://dl.k8s.io"
  230. readonly k8s_url="$release_url/release/$version/bin/$os/$arch/%s.sha256"
  231. # Download URLs
  232. declare -A urls=(
  233. ["crictl"]="$(printf "$github_releases_url" "kubernetes-sigs/cri-tools" "crictl-$version-$os-$arch.tar.gz.sha256")"
  234. ["crio_archive"]="$google_url/cri-o/artifacts/cri-o.$arch.$version.tar.gz.sha256sum"
  235. ["kubelet"]="$(printf "$k8s_url" "kubelet")"
  236. ["kubectl"]="$(printf "$k8s_url" "kubectl")"
  237. ["kubeadm"]="$(printf "$k8s_url" "kubeadm")"
  238. ["etcd_binary"]="$(printf "$github_releases_url" "etcd-io/etcd" "etcd-$version-$os-$arch.tar.gz")"
  239. ["cni_binary"]="$(printf "$github_releases_url" "containernetworking/plugins" "cni-plugins-$os-$arch-$version.tgz.sha256")"
  240. ["calicoctl_binary"]="$(printf "$github_releases_url" "projectcalico/calico" "calicoctl-$os-$arch")"
  241. ["ciliumcli_binary"]="$(printf "$github_releases_url" "cilium/cilium-cli" "cilium-$os-$arch.tar.gz.sha256sum")"
  242. ["calico_crds_archive"]="$(printf "$github_archive_url" "projectcalico/calico" "$version.tar.gz")"
  243. ["krew_archive"]="$(printf "$github_releases_url" "kubernetes-sigs/krew" "krew-${os}_$arch.tar.gz")"
  244. ["helm_archive"]="https://get.helm.sh/helm-$version-$os-$arch.tar.gz"
  245. ["cri_dockerd_archive"]="$(printf "$github_releases_url" "Mirantis/cri-dockerd" "cri-dockerd-${version#v}.$arch.tgz")"
  246. ["runc"]="$(printf "$github_releases_url" "opencontainers/runc" "runc.sha256sum")"
  247. ["crun"]="$(printf "$github_releases_url" "containers/crun" "crun-$version-$os-$arch")"
  248. ["youki"]="$(printf "$github_releases_url" "containers/youki" "youki_$([ $version == "v0.0.1" ] && echo "v0_0_1" || echo "${version#v}" | sed 's|\.|_|g')_$os.tar.gz")"
  249. ["kata_containers_binary"]="$(printf "$github_releases_url" "kata-containers/kata-containers" "kata-static-$version-$(get_arch_kata "${version}" "${arch}").tar.xz")"
  250. ["gvisor_runsc_binary"]="$(printf "$google_url/gvisor/releases/release/$version/%s/runsc" "$(echo "$arch" | sed -e 's/amd64/x86_64/' -e 's/arm64/aarch64/')")"
  251. ["gvisor_containerd_shim_binary"]="$(printf "$google_url/gvisor/releases/release/$version/%s/containerd-shim-runsc-v1" "$(echo "$arch" | sed -e 's/amd64/x86_64/' -e 's/arm64/aarch64/')")"
  252. ["nerdctl_archive"]="$(printf "$github_releases_url" "containerd/nerdctl" "nerdctl-${version#v}-$os-$([ "$arch" == "arm" ] && echo "arm-v7" || echo "$arch" ).tar.gz")"
  253. ["containerd_archive"]="$(printf "$github_releases_url" "containerd/containerd" "containerd-${version#v}-$os-$arch.tar.gz.sha256sum")"
  254. ["skopeo_binary"]="$(printf "$github_releases_url" "lework/skopeo-binary" "skopeo-$os-$arch.sha256")"
  255. ["yq"]="$(printf "$github_releases_url" "mikefarah/yq" "yq_${os}_$arch")"
  256. )
  257. mkdir -p "$(dirname $target)"
  258. [ -f "$target" ] || curl -LfSs -o "${target}" "${urls[$binary]}"
  259. if [ ! -f "$target" ]; then
  260. echo "$target can't be downloaded" >&2
  261. echo 0
  262. return
  263. fi
  264. if echo "${urls[$binary]}" | grep -qi sha256sum; then
  265. local hashes="$(cat "${target}")"
  266. if [ "$(echo "${hashes}" | wc -l)" -gt 1 ]; then
  267. hashes="$(echo "${hashes}" | grep -- "${arch}")"
  268. fi
  269. if [ "$(echo "${hashes}" | wc -l)" -gt 1 ]; then
  270. hashes="$(echo "${hashes}" | grep -- "${os}")"
  271. fi
  272. if [ "$(echo "${hashes}" | wc -l)" -gt 1 ]; then
  273. echo "more than 1 hash" >&2
  274. echo "${hashes}" >&2
  275. exit 1
  276. fi
  277. echo "${hashes}" | awk '{print $1}'
  278. elif echo "${urls[$binary]}" | grep -qi sha256; then
  279. cat "${target}" | awk '{print $1}'
  280. else
  281. sha256sum ${target} | awk '{print $1}'
  282. fi
  283. }
  284. mkdir -p "$(dirname "$checksums_file")"
  285. echo "---" | tee "$checksums_file"
  286. get_crictl_checksums crictl $(get_versions github_tags kubernetes-sigs/cri-tools min_version "${kube_min_version}")
  287. get_checksums crio_archive $(get_versions github_tags cri-o/cri-o min_version "${kube_min_version}")
  288. kubernetes_versions=$(get_versions github_tags kubernetes/kubernetes min_version "${kube_min_version}")
  289. echo "# Checksum" | tee --append "$checksums_file"
  290. echo "# Kubernetes versions above Kubespray's current target version are untested and should be used with caution." | tee --append "$checksums_file"
  291. get_k8s_checksums kubelet $kubernetes_versions
  292. get_checksums kubectl $kubernetes_versions
  293. get_k8s_checksums kubeadm $kubernetes_versions
  294. get_checksums etcd_binary $(get_versions github_tags etcd-io/etcd)
  295. get_checksums cni_binary $(get_versions github_tags containernetworking/plugins)
  296. calico_versions=$(get_versions github_tags projectcalico/calico limit_version 20)
  297. get_checksums calicoctl_binary $calico_versions
  298. get_checksums ciliumcli_binary $(get_versions github_tags cilium/cilium-cli limit_version 10)
  299. get_calico_crds_archive_checksums $calico_versions
  300. get_krew_archive_checksums $(get_versions github_tags kubernetes-sigs/krew limit_version 2)
  301. get_checksums helm_archive $(get_versions github_tags helm/helm)
  302. get_checksums cri_dockerd_archive $(get_versions github_tags Mirantis/cri-dockerd)
  303. get_checksums runc $(get_versions github_tags opencontainers/runc limit_version 5)
  304. get_checksums crun $(get_versions github_tags containers/crun)
  305. get_checksums youki $(get_versions github_tags containers/youki)
  306. get_checksums kata_containers_binary $(get_versions github_tags kata-containers/kata-containers)
  307. gvisor_versions=$(get_versions github_tags google/gvisor gvisor_version_filter)
  308. get_checksums gvisor_runsc_binary $gvisor_versions
  309. get_checksums gvisor_containerd_shim_binary $gvisor_versions
  310. get_checksums nerdctl_archive $(get_versions github_tags containerd/nerdctl)
  311. get_containerd_archive_checksums $(get_versions github_tags containerd/containerd limit_version 30)
  312. get_checksums skopeo_binary $(get_versions github_tags lework/skopeo-binary)
  313. get_checksums yq $(get_versions github_tags mikefarah/yq)