#!/bin/bash
# Copyright 2018 The Fuchsia Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

#### CATEGORY=Build
### re-use a previous build directory set up by `fx set`

## usage: fx use DIR
##    or: fx --dir DIR use
##    or: fx use
##
## Switches further `fx` commands to using a different build directory.
## This only works if `fx --dir DIR set ...` succeeded previously
## (and DIR has not been removed since).  The next `fx build` or other
## such command will now refer to DIR.  The previous build directory is
## left in place, so you can switch back again with `fx use` later.
##
## fx use without arguments will list the available build directories, naming
## the current active build directory (if any).
##
## fx use with `ffx.ui.mode = tui` set will prompt you to choose a build director.
## ffx.ui.mode can be set using `ffx config set ffx.ui.mode tui`
## The UI mode for just fx use can be set with e.g.
## `ffx config set ffx.ui.overrides.fx-use text`

source "$(cd "$(dirname "${BASH_SOURCE[0]}")" >/dev/null 2>&1 && pwd)"/lib/vars.sh || exit $?

function main {
  local build_dir="$1"

  case "${build_dir}" in
  -h | --help)
    fx-command-help
    return 0
    ;;
  esac

  if [[ -z "${build_dir}" ]]; then
    build_dir="${_FX_BUILD_DIR}"
  fi

  if [[ -z "${build_dir}" ]]; then

    fx-build-dir-if-present
    local possible_build_dirs=()
    local current="${FUCHSIA_BUILD_DIR##"${FUCHSIA_DIR}"/}"
    if [[ -n "${current}" ]]; then
      possible_build_dirs+=("${current} (current)")
    fi

    shopt -s nullglob
    for d in "${FUCHSIA_DIR}"/out/*; do
      local item_rel_path="${d##"${FUCHSIA_DIR}"/}"
      # Skip known invalid directories
      if [[ "${item_rel_path}" == */*.zircon ||
        "${item_rel_path}" == */*.device ||
        "${item_rel_path}" == "${current}" ||
        "${item_rel_path}" == */*crash.log ||
        "${item_rel_path}" == */*.json ||
        "${item_rel_path}" == out/_* ||
        "${item_rel_path}" == out/repro_*.instructions ||
        "${item_rel_path}" == out/.*build_lock ||
        "${item_rel_path}" == out/rust-analyzer ]]; then
        continue #skip
      fi
      possible_build_dirs+=("${item_rel_path}")
    done
    shopt -u nullglob

    use_tui=$(fx-get-ui-mode "fx-use")
    if [[ "$use_tui" == "tui" ]]; then
      # TUI picker
      # check if we have any possible build directories to choose from.
      if [ "${#possible_build_dirs[@]}" -eq 0 ]; then
        fx-error "There are no current build directories. Make sure you have run fx set."
        exit 1
      fi

      chosen_dir="$(fx-choose-tui "${possible_build_dirs[@]}" --select-if-one --header="Select a build dir:")"
      # strip off any trailing spaces and the '(current)' string
      local suffix=" (current)"
      if [[ "${chosen_dir}" == *"${suffix}" ]]; then
        build_dir="${chosen_dir%${suffix}}"
      else
        build_dir="${chosen_dir}"
      fi

      if [[ -z "${build_dir}" ]]; then
        # This can happen if users close out of the picker without selecting anything
        fx-error "No build directory picked. If you still want to change directories,\nrun this command again and select a directory."
        exit 1
      fi
    else
      # Non-TUI default
      fx-info "listing build directories:"
      for d in "${possible_build_dirs[@]}"; do
        echo "$d"
      done
      return 1
    fi
  fi

  # Remove trailing slash.
  # This can potentially lead to the file `out/foo/.device` being written to
  # when calling `fx set-device` instead `out/foo.device`.
  # shellcheck disable=SC2001
  build_dir="$(echo "$build_dir" | sed 's:/*$::')"

  if [[ "$build_dir" == /* ]]; then
    local -r full_build_dir="${build_dir}"
  else
    local -r full_build_dir="${FUCHSIA_DIR}/${build_dir}"
  fi

  if [[ ! -e "${full_build_dir}/args.gn" ]]; then
    fx-error "\"${build_dir}\" is not a valid build dir."
    echo >&2
    fx-command-help
    exit 1
  fi

  fx-change-build-dir "${build_dir}"

  # Refresh $FUCHSIA_NODENAME to ensure the below checks will report the correct
  # error message.
  if [[ -e "${FUCHSIA_BUILD_DIR}.device" ]]; then
    FUCHSIA_NODENAME="$(<"${FUCHSIA_BUILD_DIR}.device")"
  else
    FUCHSIA_NODENAME=""
  fi

  # Print the default target status message.
  # If it's already been printed before, do nothing.
  has_default_target_status_been_printed="false"
  function print-default-target-status-once {
    [[ $has_default_target_status_been_printed == "true" ]] && return
    out_dir="$(realpath -s --relative-to="$FUCHSIA_DIR" "$FUCHSIA_BUILD_DIR")"
    if [[ -n "${FUCHSIA_NODENAME}" ]]; then
      fx-info "The default device for ${out_dir} is \"${FUCHSIA_NODENAME}\"."
    else
      fx-info "The default device for ${out_dir} is not set."
    fi
    has_default_target_status_been_printed="true"
  }
  if [[ -n "${FUCHSIA_NODENAME}" ]]; then
    print-default-target-status-once
  fi

  # Check if the user has set a default target via environment variable(s)
  # which can override default targets set by `fx set-device`.
  function external-default-target-env-warning {
    print-default-target-status-once
    fx-warn "However, you've overridden this by setting ${ENV_VARS}."
    if [[ -n "${FUCHSIA_NODENAME}" ]]; then
      fx-warn "If you want to use \"${FUCHSIA_NODENAME}\", please unset the ${ENV_VAR_NAMES} environment variable."
    else
      fx-warn "If you want to use leave it unset, please unset the ${ENV_VAR_NAMES} environment variable."
    fi
  }
  fx-if-target-set-by-env external-default-target-env-warning
}

main "$@"
