Bash 배열 액세스가 예상대로 작동하지 않습니다.

Bash 배열 액세스가 예상대로 작동하지 않습니다.

최신 시스템을 사용하기 위해 코드를 다시 작성하고 있습니다. 원본 코드를 작성하진 않았지만 예전 코드를 템플릿으로 사용해 보았습니다. 혼자서 명령을 실행하면 잘 작동합니다. 셸에서 스크립트나 함수의 일부로 실행하려고 하면 실행되지 않습니다.

#!/bin/bash
function find_user() {
    local txt
    local user_list
    local username
    local displayName

    echo "Find User"
    echo "---------"

    echo -n "Enter search text (e.g: lib): "
    read txt

    if [ -z "$txt" ] || ! validate_fullname "$txt"; then
        echo "Search cancelled."
    else
        echo
        user_list="$(samba-tool user list | grep -i ${txt} | sort)"
        (
            echo "Username Full_Name"
            echo "-------- ---------"
            # Dev Note: Get the username, then displayName parameter, replacing
            # the spaces in displayName with an underscore. Do not need to look
            # for a dollar sign anymore, as computers are not listed as "user"
            # class objects in AD.
            for a in "${user_list[@]}"; do
                username=$a
                displayName="$(
                    samba-tool user show ${a} | grep 'displayName:' | \
                        awk -F: '{gsub(/^[ \t]+/,"""",$2); gsub(/ ./,""_"",$3); print $2}' | \
                        tr ' ' '_')"
                echo "${username} ${displayName}"
            done
        )| column -t
     fi
}

실행하고 find_user함수를 입력하려고 하면 검색 텍스트를 입력하라는 메시지가 표시되고(예: 입력할 수 있음 js) Enter 키를 누릅니다.

내 질문은 그 부분과 관련이 있습니다 $displayName=. 스크립트 내에서 실행될 때 빈 문자열을 생성하는 것 같습니다. 터미널에서 명령을 수동으로 실행하면(즉, jsmith대체 항목 입력 ${a}) 전체 이름이 올바르게 출력됩니다.

내 시스템이 bash를 실행 중입니다.

어떻게 되어가나요? 이 문제를 어떻게 해결할 수 있나요?

답변1

문제는 user_list배열로 액세스하는 것입니다.

for a in "${user_list[@]}"

그러나 문자열로 설정:

user_list="$(samba-tool user list | grep -i ${txt} | sort)"

대신에 당신은 필요합니다

IFS=$'\n'     # split on newline characters
set -o noglob # disable globbing

# assign the users to the array using the split+glob operator
# (implicitly invoked in bash when you leave a command substitution
# unquoted in list context):
user_list=( $(samba-tool user list | grep -ie "${txt}" | sort) )

또는 더 나은 방법은 다음과 같습니다( bash구체적이긴 하지만).

readarray -t user_list < <(samba-tool user list)

(빈 줄을 버리는 Split+glob 방법과 달리 입력의 각 빈 줄에 대해 빈 요소가 생성된다는 점에 유의하세요.)

관련 정보