PATH와 유사한 위치 목록에서 리소스 파일을 검색하는 방법은 무엇입니까?

PATH와 유사한 위치 목록에서 리소스 파일을 검색하는 방법은 무엇입니까?

PATH나는 posix 쉘이 명령 이름을 기반으로 바이너리를 검색하는 방법과 유사한 의미를 사용하여 특정 파일에 대해 가능한 자산 파일 위치 목록을 쉽게 검색 할 수 있기를 원합니다 .

예를 들어, 다음과 같은 디렉토리 구조가 있다고 가정해 보겠습니다.

/usr/foo/assets
+- sounds
|  +- ding.ogg
|  +- dong.ogg
+- images
   +- foo.png

/usr/local/foo/assets
+- sounds
|  +- ding.flac      # better ding
+- images
   +- bar.png

나는 이와 같은 일종의 검색 경로를 정의하고 사용자 자신의 경로도 포함하고 .local내 자산 폴더 다음에 freedesktop 기본 사운드로 돌아갈 수 있기를 원합니다.

FOO_SOUNDS_PATH=$HOME/.local/foo/assets/sounds:/usr/local/foo/assets/sounds:/usr/foo/assets/sounds:/usr/share/sounds/freedesktop/stereo

최종 결과는 전체 경로를 직접 결정하는 대신 기본 이름만 사용하여 파일을 참조할 수 있기를 원한다는 것입니다. 이를 통해 다음과 유사한 내용을 작성할 수 있습니다.

#!/bin/bash

play_sound(){
  paplay $(find_on_path --ext="ogg,wav,mp3,flac" --path="$FOO_SOUNDS_PATH" "$1")
}

play_sound ding         # play /usr/local/foo/assets/sounds/ding.flac
play_sound dong         # play /usr/foo/assets/sounds/dong.ogg
# fallback to freedesktop system 'complete' sound:
play_sound complete     # play /usr/share/sounds/freedesktop/stereo/complete.ogg

편리한 예이기 때문에 사운드 파일을 사용하고 있지만 시스템 사운드를 재생하는 방법에 대해서는 특별히 관심이 없으며 보다 일반적인 기술에 관심이 있습니다.

다른 유형의 리소스에 대해 이러한 동일한 의미를 쉽게 재사용할 수 있는 방법이 있습니까 $PATH? 그렇다면 어떻게 해야 합니까? 그렇지 않다면 어떻게 해야 합니까?

답변1

음, 여기에 이러한 아이디어를 bash 스크립트나 함수로 래핑할 수 있는 한 가지 접근 방식이 있습니다.

$ FOO_SOUNDS_PATH=$HOME/.local/foo/assets/sounds:/usr/local/foo/assets/sounds:/usr/foo/assets/sounds:/usr/share/sounds/freedesktop/stereo
$ IFS=':' read -r -a array <<< "$FOO_SOUNDS_PATH" # IFS splits path into array var by ':'
$ echo "${array[@]}"
$ /home/sparrow/.local/foo/assets/sounds /usr/local/foo/assets/sounds /usr/foo/assets/sounds /usr/share/sounds/freedesktop/stereo

이는 다음을 추론할 수 있음을 의미합니다.

$ for i in "${array[@]}"; do find $i -type f -name *.ogg -or -name *.wav -or -name *.mp3 -or -name *.flac -printf "%f\n"; done

그러면 관련 사운드 파일이 모두 제공됩니다. 명령에 따라 재생할 수 있도록 파일을 변수로 저장하도록 나머지 파일을 스크립트해야 합니다. 적어도 올바른 방향을 알려줬으면 좋겠습니다!

답변2

몇 가지 변형을 시도해 보세요.

$ cat tst.sh
#!/bin/env bash

assPath='/foo:/bar/whatever:/somewhere/else'

assFind() {
    local tgt="$1" dir assArr
    IFS=':' read -r -a assArr <<< "$assPath"
    for dir in "${assArr[@]}"; do
        printf 'Searching "%s"\n' "$dir" >&2
        if [[ -e "${dir}/${tgt}" ]]; then
            printf '%s/%s\n' "$dir" "$tgt"
            return 0
        fi
    done
    return 1
}

assFind 'ding.ogg'

$ ./tst.sh
Searching "/foo"
Searching "/bar/whatever"
Searching "/somewhere/else"

분명히 이러한 디렉터리나 파일은 내 시스템에 존재하지 않으므로 실행할 때 표준 출력이 없습니다.

관련 정보