표적
저는 사용자가 일부 템플릿 파일과 함께 사용되는 파일 whiptail
에 비밀번호를 삽입할 수 있도록 이 기능을 사용하고 있습니다.envsubst
whiptail
체크리스트
콘텐츠를 렌더링하려면 whiptail
다음을 사용합니다.
declare -A availableServices=(
[grafana]="Grafana Dashboard"
[influxdb]="InfluxDB v1.x TSDB"
[node-red]="Node-RED Flow UI"
[portainer]="Portainer Container Mgmt"
)
# Render TUI
function askGenerateCredential() {
local message="Set Password for particular Service\n
Press <SPACEBAR> to Select \n
Press <Enter> to Skip
"
local arglist=()
# Generate a String for Whiptail Checkboxes
# FORMAT: "<INDEX> <DESCRIPTION> <OFF>"
for index in "${!availableServices[@]}";
do
# Default all Services are NOT-Selected (OFF)
arglist+=("$index" "${availableServices[$index]}" "OFF")
done
SELECTED_SERVICES+=$($WHIPTAIL --title "Available Services within Populo" \
--notags --separate-output \
--ok-button Next \
--nocancel \
--checklist "$message" $LINES $COLUMNS $(( LINES - 12 )) \
-- "${arglist[@]}" \
3>&1 1>&2 2>&3)
}
SELECTED_SERVICES
다음과 같이 선언된 배열 입니다 .
declare -a SELECTED_SERVICES=()
렌더링은 제대로 작동하지만 if else
스크립트에 위 배열에서 선택한 서비스를 기반으로 특정 명령을 실행하지 못하게 하는 특정 조건이 있습니다.
askGenerateCredential
if [ -z "$SELECTED_SERVICES" ]; then
echo "No Services were selected. Exiting..."
exit 1
else
for service in "${SELECTED_SERVICES}";
do
if [ "$service" == "influxdb" ]; then
echo "Setting Credentials for InfluxDB"
setInfluxDBCredentials
elif [ "$service" == "grafana" ]; then
echo "Setting Credentials for Grafana"
setGrafanaCredentials
elif [ "$service" == "node-red" ]; then
echo "Setting Credentials for node-RED"
setNodeRedCredentials
elif [ "$service" == "portainer" ]; then
echo "Setting Credential for Portainer"
setPortainerCredentials
fi
done
fi
위 블록을 추가한 후 0
UI를 통해 여러 값을 선택하면 스크립트가 종료되고 코드가 표시됩니다 whiptail
. 대신 UI에서 값을 선택하면 해당 함수가 호출됩니다.
내가 여기서 뭘 잘못하고 있는 걸까? service
스크립트를 종료하지 않고 변수를 기반으로 해당 함수를 호출하고 싶습니다 .
암호
#!/bin/env bash
WHIPTAIL=$(which whiptail)
if [ -z $WHIPTAIL ]
then
echo "This script requires whiptail to render the TUI."
exit 1
fi
declare -a SELECTED_SERVICES=()
LINES=$(tput lines)
COLUMNS=$(tput cols)
declare -A availableServices=(
[grafana]="Grafana Dashboard"
[influxdb]="InfluxDB v1.x TSDB"
[node-red]="Node-RED Flow UI"
[portainer]="Portainer Container Mgmt"
)
function askGenerateCredential() {
local message="Set Password for particular Service\n
Press <SPACEBAR> to Select \n
Press <Enter> to Skip
"
local arglist=()
# Generate a String for Whiptail Checkboxes
# FORMAT: "<INDEX> <DESCRIPTION> <OFF>"
for index in "${!availableServices[@]}";
do
# Default all Services are NOT-Selected (OFF)
arglist+=("$index" "${availableServices[$index]}" "OFF")
done
SELECTED_SERVICES+=$($WHIPTAIL --title "Available Services within Populo" \
--notags --separate-output \
--ok-button Next \
--nocancel \
--checklist "$message" $LINES $COLUMNS $(( LINES - 12 )) \
-- "${arglist[@]}" \
3>&1 1>&2 2>&3)
}
function setInfluxDBCredential() {
echo "set admin password env var for influxdb"
}
function setGrafanaCredential() {
echo "set admin password env var for grafana"
}
function setNodeRedCredential() {
echo "set admin password env var for node-REd"
}
function setPortainerCredential() {
echo "set password file for portainer"
}
askGenerateCredential
if [ -z "$SELECTED_SERVICES" ]; then
echo "No Services were selected. Exiting..."
exit 1
else
for service in "${SELECTED_SERVICES}";
do
if [ "$service" == "influxdb" ]; then
echo "Setting Credentials for InfluxDB"
setInfluxDBCredentials
elif [ "$service" == "grafana" ]; then
echo "Setting Credentials for Grafana"
setGrafanaCredentials
elif [ "$service" == "node-red" ]; then
echo "Setting Credentials for node-RED"
setNodeRedCredentials
elif [ "$service" == "portainer" ]; then
echo "Setting Credential for Portainer"
setPortainerCredentials
fi
done
fi
편집하다
${SELECTED_SERVICES[@]}
echo "$service"
제안된 대로 for 루프 내에 배열을 반복할 수 있는 루프를 추가하려고 시도했지만 if
조건이 트리거되지 않았습니다.
답변1
나는 귀하의 기능의 논리가 askGenerateCredential()
귀하가 원하는 것을 수행하지 않는다고 생각합니다. 현재는hiptail 명령의 전체 출력이 배열에 단일 요소로 추가됩니다. 여러 요소를 줄바꿈으로 분할하려면 다음과 같이 변경해야 합니다.
askGenerateCredential() {
local message="Set Password for particular Service\n
Press <SPACEBAR> to Select \n
Press <Enter> to Skip
"
local arglist=()
# Generate a String for Whiptail Checkboxes
# FORMAT: "<INDEX> <DESCRIPTION> <OFF>"
for index in "${!availableServices[@]}";
do
# Default all Services are NOT-Selected (OFF)
arglist+=("$index" "${availableServices[$index]}" "OFF")
done
readarray -t SELECTED_SERVICES < <("$WHIPTAIL" --title "Available Services within Populo" \
--notags --separate-output \
--ok-button Next \
--nocancel \
--checklist "$message" "$LINES" "$COLUMNS" $(( LINES - 12 )) \
-- "${arglist[@]}" \
3>&1 1>&2 2>&3)
}
바라보다4.2 Bash 내장 명령
또한 SELECTED_SERVICES
배열이 아닌 변수로 호출합니다.
다음을 변경해야 합니다.
for service in "${SELECTED_SERVICES}"
도착하다:
for service in "${SELECTED_SERVICES[@]}"
있는 그대로 배열의 첫 번째 요소만 확장합니다. 그러나 코드를 작성하면 SELECTED_SERVICES
하나의 요소만 수신됩니다.
바라보다6.7 배열
또한 if/elif 구조보다 케이스를 사용하는 것이 더 나을 수도 있습니다. 그것은 다음과 같습니다:
case $service in
influxdb) echo "Setting Credentials for InfluxDB"; setInfluxDBCredentials;;
grafana) echo "Setting Credentials for Grafana"; setGrafanaCredentials;;
node-red) echo "Setting Credentials for node-RED"; setNodeRedCredentials;;
portainer) echo "Setting Credential for Portainer"; setPortainerCredentials;;
*) echo "Error; unknown option: $service" >&2;;
esac