scottwinkler / terraform-provider-shell

Terraform provider for executing shell commands and saving output to state file
Mozilla Public License 2.0
279 stars 60 forks source link

Terraform refresh stage dumping {} o unique lines for each shell resource #66

Closed Zordrak closed 3 years ago

Zordrak commented 4 years ago

Not sure if this is intended, but not seen any docs related to it.

Using 1.7.2 from the registry, each shell_script resource is being refreshed and below it is printed "{}" in non-bold (the other refresh output is emboldened.

e.g.:

module.bs_gr.shell_script.securityhub_invite_accepter[2]: Refreshing state... [id=bqc46gujtk81e0bh2ur0]
module.bs_gr.shell_script.securityhub_invite_accepter[1]: Refreshing state... [id=bqc46gujtk81e0bh2urg]
module.bs_gr.shell_script.securityhub_invite_accepter[0]: Refreshing state... [id=bqc46h6jtk81e0bh2us0]
{}
{}
{}
scottwinkler commented 4 years ago

not sure what is causing this. i cannot replicate it on my end. sometimes Terraform output gets messed up for unknown reasons. is it repeatable? if so, could you share your config with me?

Zordrak commented 4 years ago

Sure. This issue only occurred when changing from a custom binary I build around January time from master, to using 1.7.2 from the Hashicorp registry.

shell_script_securityhub_invite.tf

resource "shell_script" "securityhub_invite" {
  count = var.securityhub_master ? 0 : length(local.multiball_multiball_multiball)

  lifecycle_commands {
    create = "${path.module}/files/securityhub_invite.sh create"
    read   = "${path.module}/files/securityhub_invite.sh read"
    update = "${path.module}/files/securityhub_invite.sh update"
    delete = "${path.module}/files/securityhub_invite.sh delete"
  }

  working_directory = path.module

  environment = {
    AWSCLI_BIN_PATH   = "${path.module}/../../lib/awscli/bin"
    CSI               = local.csi
    EXTERNAL_ID       = var.org_xacct_external_id
    MASTER_ACCOUNT_ID = var.org_security_account_id
    MEMBER_ACCOUNT_ID = var.aws_account_id
    REGION            = local.multiball_multiball_multiball[count.index]
    ROLE_NAME         = var.org_xacct_role_name
  }

  depends_on = [ shell_script.securityhub_member ]
}

files/securityhub_invite.sh

#!/usr/bin/env bash

set -xo pipefail

declare script_name="$(basename ${0})";

declare awscli_bin_path="${AWSCLI_BIN_PATH-""}";
if [ "${awscli_bin_path}" != "" ]; then
  export PATH="${awscli_bin_path}:${PATH}";

  # Just in case
  export AWS_PAGER="";
fi;

echo -n "AWS CLI Version: ";
aws --version;

declare csi="${CSI}";
declare external_id="${EXTERNAL_ID}";
declare master_account_id="${MASTER_ACCOUNT_ID}";
declare member_account_id="${MEMBER_ACCOUNT_ID}";
declare region="${REGION:-eu-west-1}";
declare role_name="${ROLE_NAME}";

function aws_run_as() {

  local account="${1}";

  declare -a session_tokens;

  session_tokens=($(aws sts assume-role \
    --role-arn "arn:aws:iam::${account}:role/${role_name}" \
    --role-session-name "${csi}-${script_name}" \
    --external-id "${external_id}" \
    --duration-seconds 900 \
    --query Credentials \
    --output text; ));

  export AWS_ACCESS_KEY_ID="${session_tokens[0]}";
  export AWS_SECRET_ACCESS_KEY="${session_tokens[2]}";
  export AWS_SESSION_TOKEN="${session_tokens[3]}";
  export AWS_SESSION_EXPIRY="${session_tokens[1]}";

  aws "${@:2}";
}
export -f aws_run_as

function create {
  local state_stdin="$(cat)";
  echo "stdin: ${state_stdin}";

  aws_run_as "${master_account_id}" securityhub invite-members --account-ids "${member_account_id}" --region "${region}" || return 1
  return 0;
}

function read {
  local state_stdin="$(cat)";
  echo "stdin: ${state_stdin}";

  echo "${state_stdin}" >&3;
  return 0;
}

function update {
  local state_stdin="$(cat)";
  echo "stdin: ${state_stdin}";

  # Stop messing about
  return 0;
}

function delete {
  local state_stdin="$(cat)";
  echo "stdin: ${state_stdin}";

  aws_run_as "${master_account_id}" securityhub delete-invitations --account-ids "${member_account_id}" --region "${region}" || return 1
  return 0;
}

case "${1}" in
  'create'|'read'|'update'|'delete')
    "${1}"; # || exit "${?}"; Seems the provider is a bit shonky at handling errors, so we're better off returning success than hanging forever
    ;;
  *)
    echo "Invalid command: ${1}"
    exit 5;
    ;;
esac;

exit 0;
scottwinkler commented 3 years ago

was not able to replicate and have not had anyone else report this problem with latest version. if this is still an issue, please open a new ticket.