파일에 에코를 적용할 수 있지만 쉘 스크립트 소스에서는 들여쓰기를 사용할 수 있습니까? [복사]

파일에 에코를 적용할 수 있지만 쉘 스크립트 소스에서는 들여쓰기를 사용할 수 있습니까? [복사]

여러 줄의 문자열을 파일에 반영하는 중첩되고 들여쓰기된 문이 있는 경우 원래 셸(내 경우에는 bash)의 들여쓰기가 대상 파일로 전송됩니다.

이를 방지하기 위해 에코된 출력에서 ​​들여쓰기를 제거했지만 소스 코드에서 들여쓰기된 코드 형식이 손실됩니다. 예:

#! /bin/bash

function configure_default_vhost() {

    case "$2" in
        [--production])
              echo "<VirtualHost *:80>
# These lines are "breaking" out of the preffered indenting
redirect 404 /
ErrorDocument 404
</VirtualHost>
" > /etc/apache/sites-availabe/000-default.conf
    esac
}

내 목표는 가능한 한 다음과 비슷한 것을 얻는 것입니다.

#! /bin/bash

function configure_default_vhost() {

    case "$2" in
        [--production])
              echo "<VirtualHost *:80>
                    # These lines are aligned with the preffered indenting
                    redirect 404 /
                    ErrorDocument 404
                    </VirtualHost>
                    " > /etc/apache/sites-availabe/000-default.conf
    esac
}

(참고: 이 질문은 HEREDOC 관련 질문과 중복될 가능성이 있는 것으로 나열되었습니다. 이 질문에 답변해야 할 올바른 위치가 어디인지 확신할 수 없으므로 지금 여기에 입력하겠습니다(그렇지 않은 경우 알려주세요). 내 질문은 코드 블록 들여쓰기에 관한 것입니다. heredoc은 이를 수행하는 여러 방법 중 하나일 뿐이며 실제로 heredoc는 제가 원하는 솔루션이 아닙니다.

답변1

수정자와 함께 "here-document"를 사용할 수 있습니다 -. 탭을 사용하여 들여쓰기할 수 있습니다. echo에서 으로 전환해야 합니다 cat.

cat <<-EOF > /etc/apache/sites-availabe/000-default.conf
        <VirtualHost *:80>
        redirect 404 /
        ErrorDocument 404     
        </VirtualHost>
EOF

또는 결과에서 탭을 유지하려면 HERE 문서를 전처리하고 sed4개의 공백으로 들여쓰기할 수 있습니다.

sed 's/^    //' <<EOF
....{
....(------)func () {
....(------)return
....(------)}
....}
EOF

스크립트 형식을 지정하는 방법을 보여주기 위해 .공백과 탭 대신 공백과 탭을 사용했습니다 .(------)

답변2

여러 가지 방법:

  • printf '%s\n' > "$conf_file" \
      '<VirtualHost *:80>' \
      '  redirect 404 /' \
      '  ErrorDocument 404' \
      '</VirtualHost>'
    

    이스케이프 시퀀스를 확장하려면 %s다음으로 바꾸십시오 %b.

    printf '%b\n' > "$conf_file" \
      '<VirtualHost *:80>' \
      '\tredirect 404 /' \
      '\tErrorDocument 404' \
      '</VirtualHost>'
    
  • @choroba의 cat <<- EOF접근 방식, 그러나 들여쓰기는 탭 문자로만 이루어져야 하며 모두 제거됩니다.

  • ...
      indent='
      '; cut -b "${#indent}-" << EOF > "$conf_file"
      <VirtualHost *:80>
        redirect 404 /
        ErrorDocument 404     
      </VirtualHost>
    EOF
    

    $indent( 트림할 들여쓰기 문자 수를 저장 하는 것이 요령입니다 (이번에는 들여쓰기에는 탭 문자가 아닌 공백 문자를 사용해야 합니다).

  • ...
      cut -d'|' -f2- << EOF > "$conf_file"
      |echo "<VirtualHost *:80>
      |  redirect 404 /
      |  ErrorDocument 404     
      |</VirtualHost>
    EOF
    

    이스케이프 시퀀스는 확장되지 않지만 변수 및 명령 대체는 확장됩니다. EOF이를 방지하기 위해 따옴표를 사용합니다 ( cut... << 'EOF'예:).

  • 첫 번째 줄의 들여쓰기를 기준으로 자를 수도 있습니다.

    show() {
      expand | awk 'NR == 1 {match($0, /^ */); l = RLENGTH + 1}
                    {print substr($0, l)}'
    }
    ...
      show << EOF > "$conf_file"
        <VirtualHost *:80>
          redirect 404 /
          ErrorDocument 404     
        </VirtualHost>
    EOF
    

답변3

echo스위치와 함께 사용 -e(백슬래시 이스케이프 해석 가능):

#!/bin/bash

function configure_default_vhost() {
    conf_file="/etc/apache/sites-availabe/000-default.conf"
    case "$2" in
        [--production])
            # The ">" overwrites; the ">>" appends. 
            {
                echo -e "<VirtualHost *:80>"
                echo -e "\tredirect 404 /"
                echo -e "\tErrorDocument 404"
                echo -e "</VirtualHost>"
            } > "$conf_file"
    esac
}

관련 정보