[VAULT-2937] Verify the /sys/version-history in enos scenarios (#27947)

When verifying the Vault version, in addition to verifying the CLI
version we also check that the `/sys/version-history` contains the
expected version.

As part of this we also fix a bug where when doing an in-place upgrade
with a Debian or Redhat package we also remove the self-managed
`vault.service` systemd unit to ensure that correctly start up using the
new version of Vault.

Signed-off-by: Ryan Cragun <me@ryan.ec>
This commit is contained in:
Ryan Cragun 2024-08-02 13:26:39 -06:00 committed by GitHub
parent 37dbe7bf38
commit 720e942662
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
15 changed files with 313 additions and 192 deletions

View File

@ -180,7 +180,8 @@ globals {
EOF
verify_vault_version = <<-EOF
Verify that the Vault cluster has the correct embedded version metadata. This metadata includes
Verify that the Vault CLI has the correct embedded version metadata and that the Vault Cluster
verision history includes our expected version. The CLI metadata that is validated includes
the Vault version, edition, build date, and any special prerelease metadata.
EOF

View File

@ -250,6 +250,21 @@ quality "vault_api_sys_storage_raft_remove_peer_write_removes_peer" {
EOF
}
quality "vault_api_sys_version_history_keys" {
description = <<-EOF
The v1/sys/version-history Vault API returns the cluster version history and the 'keys' data
includes our target version
EOF
}
quality "vault_api_sys_version_history_key_info" {
description = <<-EOF
The v1/sys/version-history Vault API returns the cluster version history and the
'key_info["$expected_version]' data is present for the expected version and the 'build_date'
matches the expected build_date.
EOF
}
quality "vault_artifact_bundle" {
description = "The candidate binary packaged as a zip bundle is used for testing"
}

View File

@ -411,33 +411,6 @@ scenario "agent" {
}
}
step "verify_vault_version" {
description = global.description.verify_vault_version
module = module.vault_verify_version
depends_on = [step.wait_for_leader]
providers = {
enos = local.enos_provider[matrix.distro]
}
verifies = [
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,
]
variables {
hosts = step.create_vault_cluster_targets.hosts
vault_addr = step.create_vault_cluster.api_addr_localhost
vault_edition = matrix.edition
vault_install_dir = global.vault_install_dir[matrix.artifact_type]
vault_product_version = matrix.artifact_source == "local" ? step.get_local_metadata.version : var.vault_product_version
vault_revision = matrix.artifact_source == "local" ? step.get_local_metadata.revision : var.vault_revision
vault_build_date = matrix.artifact_source == "local" ? step.get_local_metadata.build_date : var.vault_build_date
vault_root_token = step.create_vault_cluster.root_token
}
}
step "verify_vault_unsealed" {
description = global.description.verify_vault_unsealed
module = module.vault_verify_unsealed
@ -460,13 +433,39 @@ scenario "agent" {
}
}
step "verify_vault_version" {
description = global.description.verify_vault_version
module = module.vault_verify_version
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
}
verifies = [
quality.vault_api_sys_version_history_keys,
quality.vault_api_sys_version_history_key_info,
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,
]
variables {
hosts = step.create_vault_cluster_targets.hosts
vault_addr = step.create_vault_cluster.api_addr_localhost
vault_edition = matrix.edition
vault_install_dir = global.vault_install_dir[matrix.artifact_type]
vault_product_version = matrix.artifact_source == "local" ? step.get_local_metadata.version : var.vault_product_version
vault_revision = matrix.artifact_source == "local" ? step.get_local_metadata.revision : var.vault_revision
vault_build_date = matrix.artifact_source == "local" ? step.get_local_metadata.build_date : var.vault_build_date
vault_root_token = step.create_vault_cluster.root_token
}
}
step "verify_write_test_data" {
description = global.description.verify_write_test_data
module = module.vault_verify_write_data
depends_on = [
step.create_vault_cluster,
step.get_vault_cluster_ips
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -492,10 +491,7 @@ scenario "agent" {
description = global.description.verify_raft_cluster_all_nodes_are_voters
skip_step = matrix.backend != "raft"
module = module.vault_verify_raft_auto_join_voter
depends_on = [
step.create_vault_cluster,
step.get_vault_cluster_ips
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -515,10 +511,7 @@ scenario "agent" {
step "verify_replication" {
description = global.description.verify_replication_status
module = module.vault_verify_replication
depends_on = [
step.create_vault_cluster,
step.get_vault_cluster_ips
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -561,7 +554,7 @@ scenario "agent" {
step "verify_ui" {
description = global.description.verify_ui
module = module.vault_verify_ui
depends_on = [step.create_vault_cluster]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]

View File

@ -685,6 +685,8 @@ scenario "autopilot" {
}
verifies = [
quality.vault_api_sys_version_history_keys,
quality.vault_api_sys_version_history_key_info,
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,

View File

@ -388,33 +388,6 @@ scenario "proxy" {
}
}
step "verify_vault_version" {
description = global.description.verify_vault_version
module = module.vault_verify_version
depends_on = [step.create_vault_cluster]
providers = {
enos = local.enos_provider[matrix.distro]
}
verifies = [
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,
]
variables {
hosts = step.create_vault_cluster_targets.hosts
vault_addr = step.create_vault_cluster.api_addr_localhost
vault_edition = matrix.edition
vault_install_dir = global.vault_install_dir[matrix.artifact_type]
vault_product_version = matrix.artifact_source == "local" ? step.get_local_metadata.version : var.vault_product_version
vault_revision = matrix.artifact_source == "local" ? step.get_local_metadata.revision : var.vault_revision
vault_build_date = matrix.artifact_source == "local" ? step.get_local_metadata.build_date : var.vault_build_date
vault_root_token = step.create_vault_cluster.root_token
}
}
step "verify_vault_unsealed" {
description = global.description.verify_vault_unsealed
module = module.vault_verify_unsealed
@ -437,13 +410,39 @@ scenario "proxy" {
}
}
step "verify_vault_version" {
description = global.description.verify_vault_version
module = module.vault_verify_version
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
}
verifies = [
quality.vault_api_sys_version_history_keys,
quality.vault_api_sys_version_history_key_info,
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,
]
variables {
hosts = step.create_vault_cluster_targets.hosts
vault_addr = step.create_vault_cluster.api_addr_localhost
vault_edition = matrix.edition
vault_install_dir = global.vault_install_dir[matrix.artifact_type]
vault_product_version = matrix.artifact_source == "local" ? step.get_local_metadata.version : var.vault_product_version
vault_revision = matrix.artifact_source == "local" ? step.get_local_metadata.revision : var.vault_revision
vault_build_date = matrix.artifact_source == "local" ? step.get_local_metadata.build_date : var.vault_build_date
vault_root_token = step.create_vault_cluster.root_token
}
}
step "verify_write_test_data" {
description = global.description.verify_write_test_data
module = module.vault_verify_write_data
depends_on = [
step.create_vault_cluster,
step.get_vault_cluster_ips
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -469,7 +468,7 @@ scenario "proxy" {
description = global.description.verify_raft_cluster_all_nodes_are_voters
skip_step = matrix.backend != "raft"
module = module.vault_verify_raft_auto_join_voter
depends_on = [step.create_vault_cluster]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -489,7 +488,7 @@ scenario "proxy" {
step "verify_replication" {
description = global.description.verify_replication_status
module = module.vault_verify_replication
depends_on = [step.create_vault_cluster]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -532,7 +531,7 @@ scenario "proxy" {
step "verify_ui" {
description = global.description.verify_ui
module = module.vault_verify_ui
depends_on = [step.create_vault_cluster]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]

View File

@ -603,6 +603,8 @@ scenario "replication" {
}
verifies = [
quality.vault_api_sys_version_history_keys,
quality.vault_api_sys_version_history_key_info,
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,

View File

@ -700,6 +700,8 @@ scenario "seal_ha" {
}
verifies = [
quality.vault_api_sys_version_history_keys,
quality.vault_api_sys_version_history_key_info,
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,

View File

@ -430,33 +430,6 @@ scenario "smoke" {
}
}
step "verify_vault_version" {
description = global.description.verify_vault_version
module = module.vault_verify_version
depends_on = [step.create_vault_cluster]
providers = {
enos = local.enos_provider[matrix.distro]
}
verifies = [
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,
]
variables {
hosts = step.create_vault_cluster_targets.hosts
vault_addr = step.create_vault_cluster.api_addr_localhost
vault_edition = matrix.edition
vault_install_dir = global.vault_install_dir[matrix.artifact_type]
vault_product_version = matrix.artifact_source == "local" ? step.get_local_metadata.version : var.vault_product_version
vault_revision = matrix.artifact_source == "local" ? step.get_local_metadata.revision : var.vault_revision
vault_build_date = matrix.artifact_source == "local" ? step.get_local_metadata.build_date : var.vault_build_date
vault_root_token = step.create_vault_cluster.root_token
}
}
step "verify_vault_unsealed" {
description = global.description.verify_vault_unsealed
module = module.vault_verify_unsealed
@ -479,13 +452,39 @@ scenario "smoke" {
}
}
step "verify_vault_version" {
description = global.description.verify_vault_version
module = module.vault_verify_version
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
}
verifies = [
quality.vault_api_sys_version_history_keys,
quality.vault_api_sys_version_history_key_info,
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,
]
variables {
hosts = step.create_vault_cluster_targets.hosts
vault_addr = step.create_vault_cluster.api_addr_localhost
vault_edition = matrix.edition
vault_install_dir = global.vault_install_dir[matrix.artifact_type]
vault_product_version = matrix.artifact_source == "local" ? step.get_local_metadata.version : var.vault_product_version
vault_revision = matrix.artifact_source == "local" ? step.get_local_metadata.revision : var.vault_revision
vault_build_date = matrix.artifact_source == "local" ? step.get_local_metadata.build_date : var.vault_build_date
vault_root_token = step.create_vault_cluster.root_token
}
}
step "verify_write_test_data" {
description = global.description.verify_write_test_data
module = module.vault_verify_write_data
depends_on = [
step.create_vault_cluster,
step.get_vault_cluster_ips
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -511,10 +510,7 @@ scenario "smoke" {
description = global.description.verify_raft_cluster_all_nodes_are_voters
skip_step = matrix.backend != "raft"
module = module.vault_verify_raft_auto_join_voter
depends_on = [
step.create_vault_cluster,
step.get_vault_cluster_ips
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -534,10 +530,7 @@ scenario "smoke" {
step "verify_replication" {
description = global.description.verify_replication_status
module = module.vault_verify_replication
depends_on = [
step.create_vault_cluster,
step.get_vault_cluster_ips
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -580,10 +573,7 @@ scenario "smoke" {
step "verify_ui" {
description = global.description.verify_ui
module = module.vault_verify_ui
depends_on = [
step.create_vault_cluster,
step.get_vault_cluster_ips
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]

View File

@ -576,35 +576,6 @@ scenario "upgrade" {
}
}
step "verify_vault_version" {
description = global.description.verify_vault_version
module = module.vault_verify_version
depends_on = [
step.get_updated_vault_cluster_ips,
]
providers = {
enos = local.enos_provider[matrix.distro]
}
verifies = [
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,
]
variables {
hosts = step.create_vault_cluster_targets.hosts
vault_addr = step.create_vault_cluster.api_addr_localhost
vault_edition = matrix.edition
vault_install_dir = global.vault_install_dir[matrix.artifact_type]
vault_product_version = matrix.artifact_source == "local" ? step.get_local_metadata.version : var.vault_product_version
vault_revision = matrix.artifact_source == "local" ? step.get_local_metadata.revision : var.vault_revision
vault_build_date = matrix.artifact_source == "local" ? step.get_local_metadata.build_date : var.vault_build_date
vault_root_token = step.create_vault_cluster.root_token
}
}
step "verify_vault_unsealed" {
description = global.description.verify_vault_unsealed
module = module.vault_verify_unsealed
@ -629,11 +600,39 @@ scenario "upgrade" {
}
}
step "verify_vault_version" {
description = global.description.verify_vault_version
module = module.vault_verify_version
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
}
verifies = [
quality.vault_api_sys_version_history_keys,
quality.vault_api_sys_version_history_key_info,
quality.vault_version_build_date,
quality.vault_version_edition,
quality.vault_version_release,
]
variables {
hosts = step.create_vault_cluster_targets.hosts
vault_addr = step.create_vault_cluster.api_addr_localhost
vault_edition = matrix.edition
vault_install_dir = global.vault_install_dir[matrix.artifact_type]
vault_product_version = matrix.artifact_source == "local" ? step.get_local_metadata.version : var.vault_product_version
vault_revision = matrix.artifact_source == "local" ? step.get_local_metadata.revision : var.vault_revision
vault_build_date = matrix.artifact_source == "local" ? step.get_local_metadata.build_date : var.vault_build_date
vault_root_token = step.create_vault_cluster.root_token
}
}
step "verify_read_test_data" {
description = global.description.verify_write_test_data
module = module.vault_verify_read_data
depends_on = [
step.get_updated_vault_cluster_ips,
step.verify_write_test_data,
step.verify_vault_unsealed
]
@ -660,9 +659,7 @@ scenario "upgrade" {
description = global.description.verify_raft_cluster_all_nodes_are_voters
skip_step = matrix.backend != "raft"
module = module.vault_verify_raft_auto_join_voter
depends_on = [
step.get_updated_vault_cluster_ips,
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -682,9 +679,7 @@ scenario "upgrade" {
step "verify_replication" {
description = global.description.verify_replication_status
module = module.vault_verify_replication
depends_on = [
step.get_updated_vault_cluster_ips,
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]
@ -706,9 +701,7 @@ scenario "upgrade" {
step "verify_ui" {
description = global.description.verify_ui
module = module.vault_verify_ui
depends_on = [
step.get_updated_vault_cluster_ips,
]
depends_on = [step.verify_vault_unsealed]
providers = {
enos = local.enos_provider[matrix.distro]

View File

@ -7,7 +7,8 @@ terraform {
source = "hashicorp/aws"
}
enos = {
source = "registry.terraform.io/hashicorp-forge/enos"
source = "registry.terraform.io/hashicorp-forge/enos"
version = ">= 0.5.4"
}
}
}
@ -79,6 +80,10 @@ locals {
vault_bin_path = "${var.vault_install_dir}/vault"
}
// Upgrade the Vault artifact in-place. With zip bundles we must use the same path of the original
// installation so that we can re-use the systemd unit that enos_vault_start created at
// /etc/systemd/system/vault.service. The path does not matter for package types as the systemd
// unit for the bianry is included and will be installed.
resource "enos_bundle_install" "upgrade_vault_binary" {
for_each = var.hosts
@ -93,10 +98,32 @@ resource "enos_bundle_install" "upgrade_vault_binary" {
}
}
// We assume that our original Vault cluster used a zip bundle from releases.hashicorp.com and as
// such enos_vault_start will have created a systemd unit for it at /etc/systemd/systemd/vault.service.
// If we're upgrading to a package that contains its own systemd unit we'll need to remove the
// old unit file so that when we restart vault we pick up the new unit that points to the updated
// binary.
resource "enos_remote_exec" "maybe_remove_old_unit_file" {
for_each = var.hosts
depends_on = [enos_bundle_install.upgrade_vault_binary]
environment = {
ARTIFACT_NAME = enos_bundle_install.upgrade_vault_binary[each.key].name
}
scripts = [abspath("${path.module}/scripts/maybe-remove-old-unit-file.sh")]
transport = {
ssh = {
host = each.value.public_ip
}
}
}
module "get_ip_addresses" {
source = "../vault_get_cluster_ips"
depends_on = [enos_bundle_install.upgrade_vault_binary]
depends_on = [enos_remote_exec.maybe_remove_old_unit_file]
hosts = var.hosts
ip_version = var.ip_version

View File

@ -0,0 +1,37 @@
#!/bin/bash
# Copyright (c) HashiCorp, Inc.
# SPDX-License-Identifier: BUSL-1.1
set -e
fail() {
echo "$1" 1>&2
exit 1
}
[[ -z "$ARTIFACT_NAME" ]] && fail "ARTIFACT_NAME env variable has not been set"
if [ "${ARTIFACT_NAME##*.}" == "zip" ]; then
echo "Skipped removing unit file because new artifact is a zip bundle"
exit 0
fi
# Get the unit file for the vault.service that is running. If it's not in /etc/systemd then it
# should be a package provided unit file so we don't need to delete anything.
if ! unit_path=$(systemctl show -P FragmentPath vault 2>&1); then
echo "Skipped removing unit file because and existing path could not be found: $unit_path"
exit 0
fi
if [[ "$unit_path" == *"/etc/systemd"* ]]; then
if [ -f "$unit_path" ]; then
echo "Removing old systemd unit file: $unit_path"
if ! out=$(sudo rm "$unit_path" 2>&1); then
fail "Failed to remove old unit file: $unit_path: $out"
fi
else
echo "Skipped removing old systemd unit file because it no longer exists: $unit_path"
fi
else
echo "Skipped removing old systemd unit file because it was not created in /etc/systemd/: $unit_path"
fi

View File

@ -12,11 +12,15 @@ binpath=${VAULT_INSTALL_DIR}/vault
test -x "$binpath" || fail "unable to locate vault binary at $binpath"
if ! out=$(sudo systemctl stop vault 2>&1); then
echo "failed to stop vault: $out: $(sudo systemctl status vault)" 1>&2
fail "failed to stop vault: $out: $(sudo systemctl status vault)"
fi
if ! out=$(sudo systemctl daemon-reload 2>&1); then
fail "failed to daemon-reload systemd: $out" 1>&2
fi
if ! out=$(sudo systemctl start vault 2>&1); then
echo "failed to start vault: $out: $(sudo systemctl status vault)" 1>&2
fail "failed to start vault: $out: $(sudo systemctl status vault)"
fi
count=0

View File

@ -58,7 +58,7 @@ variable "vault_root_token" {
default = null
}
resource "enos_remote_exec" "verify_all_nodes_have_updated_version" {
resource "enos_remote_exec" "verify_cli_version" {
for_each = var.hosts
environment = {
@ -71,6 +71,25 @@ resource "enos_remote_exec" "verify_all_nodes_have_updated_version" {
VAULT_VERSION = var.vault_product_version,
}
scripts = [abspath("${path.module}/scripts/verify-cli-version.sh")]
transport = {
ssh = {
host = each.value.public_ip
}
}
}
resource "enos_remote_exec" "verify_cluster_version" {
for_each = var.hosts
environment = {
VAULT_ADDR = var.vault_addr,
VAULT_BUILD_DATE = var.vault_build_date,
VAULT_TOKEN = var.vault_root_token,
VAULT_VERSION = var.vault_product_version,
}
scripts = [abspath("${path.module}/scripts/verify-cluster-version.sh")]
transport = {

View File

@ -0,0 +1,47 @@
#!/usr/bin/env bash
# Copyright (c) HashiCorp, Inc.
# SPDX-License-Identifier: BUSL-1.1
# Verify the Vault "version" includes the correct base version, build date,
# revision SHA, and edition metadata.
set -e
fail() {
echo "$1" 1>&2
exit 1
}
[[ -z "$VAULT_ADDR" ]] && fail "VAULT_ADDR env variable has not been set"
[[ -z "$VAULT_BUILD_DATE" ]] && fail "VAULT_BUILD_DATE env variable has not been set"
[[ -z "$VAULT_EDITION" ]] && fail "VAULT_EDITION env variable has not been set"
[[ -z "$VAULT_INSTALL_DIR" ]] && fail "VAULT_INSTALL_DIR env variable has not been set"
[[ -z "$VAULT_REVISION" ]] && fail "VAULT_REVISION env variable has not been set"
[[ -z "$VAULT_TOKEN" ]] && fail "VAULT_TOKEN env variable has not been set"
[[ -z "$VAULT_VERSION" ]] && fail "VAULT_VERSION env variable has not been set"
binpath=${VAULT_INSTALL_DIR}/vault
edition=${VAULT_EDITION}
version=${VAULT_VERSION}
sha=${VAULT_REVISION}
build_date=${VAULT_BUILD_DATE}
test -x "$binpath" || fail "unable to locate vault binary at $binpath"
version_expected="Vault v$version ($sha), built $build_date"
case "$edition" in
*ce) ;;
*ent) ;;
*ent.hsm) version_expected="$version_expected (cgo)";;
*ent.fips1402) version_expected="$version_expected (cgo)" ;;
*ent.hsm.fips1402) version_expected="$version_expected (cgo)" ;;
*) fail "Unknown Vault edition: ($edition)" ;;
esac
version_expected_nosha=$(echo "$version_expected" | awk '!($3="")' | sed 's/ / /' | sed -e 's/[[:space:]]*$//')
version_output=$("$binpath" version)
if [[ "$version_output" == "$version_expected_nosha" ]] || [[ "$version_output" == "$version_expected" ]]; then
echo "Version verification succeeded!"
else
fail "expected Version=$version_expected or $version_expected_nosha, got: $version_output"
fi

View File

@ -12,36 +12,26 @@ fail() {
}
[[ -z "$VAULT_ADDR" ]] && fail "VAULT_ADDR env variable has not been set"
[[ -z "$VAULT_BUILD_DATE" ]] && fail "VAULT_TOKEN env variable has not been set"
[[ -z "$VAULT_EDITION" ]] && fail "VAULT_TOKEN env variable has not been set"
[[ -z "$VAULT_INSTALL_DIR" ]] && fail "VAULT_TOKEN env variable has not been set"
[[ -z "$VAULT_REVISION" ]] && fail "VAULT_TOKEN env variable has not been set"
[[ -z "$VAULT_BUILD_DATE" ]] && fail "VAULT_BUILD_DATE env variable has not been set"
[[ -z "$VAULT_TOKEN" ]] && fail "VAULT_TOKEN env variable has not been set"
[[ -z "$VAULT_VERSION" ]] && fail "VAULT_TOKEN env variable has not been set"
[[ -z "$VAULT_VERSION" ]] && fail "VAULT_VERSION env variable has not been set"
binpath=${VAULT_INSTALL_DIR}/vault
edition=${VAULT_EDITION}
version=${VAULT_VERSION}
sha=${VAULT_REVISION}
build_date=${VAULT_BUILD_DATE}
test -x "$binpath" || fail "unable to locate vault binary at $binpath"
version_expected="Vault v$version ($sha), built $build_date"
case "$edition" in
*ce) ;;
*ent) ;;
*ent.hsm) version_expected="$version_expected (cgo)";;
*ent.fips1402) version_expected="$version_expected (cgo)" ;;
*ent.hsm.fips1402) version_expected="$version_expected (cgo)" ;;
*) fail "Unknown Vault edition: ($edition)" ;;
esac
version_expected_nosha=$(echo "$version_expected" | awk '!($3="")' | sed 's/ / /' | sed -e 's/[[:space:]]*$//')
version_output=$("$binpath" version)
if [[ "$version_output" == "$version_expected_nosha" ]] || [[ "$version_output" == "$version_expected" ]]; then
echo "Version verification succeeded!"
else
fail "expected Version=$version_expected or $version_expected_nosha, got: $version_output"
# The sys/version-history endpoint only includes major.minor.patch, any other semver fields need to
# be stripped out.
if ! version=$(cut -d + -f1 <<< "$VAULT_VERSION" | cut -d - -f1); then
fail "failed to parse the expected version: $version"
fi
if ! vh=$(curl -s -X LIST -H "X-Vault-Token: $VAULT_TOKEN" http://127.0.0.1:8200/v1/sys/version-history | jq -eMc '.data'); then
fail "failed to Vault cluster version history: $vh"
fi
if ! out=$(jq -eMc --arg version "$version" '.keys | contains([$version])' <<< "$vh"); then
fail "cluster version history does not include our expected version: expected: $version, versions: $(jq -eMc '.keys' <<< "$vh"): output: $out"
fi
if ! out=$(jq -eMc --arg version "$version" --arg bd "$VAULT_BUILD_DATE" '.key_info[$version].build_date == $bd' <<< "$vh"); then
fail "cluster version history build date is not the expected date: expected: $VAULT_BUILD_DATE, output: $out"
fi
printf "Cluster version information is valid!: %s\n" "$vh"