"key: value" 문의 값을 바꾸지만, 파일에서 키가 처음 나타나는 경우에만 해당됩니다.

"key: value" 문의 값을 바꾸지만, 파일에서 키가 처음 나타나는 경우에만 해당됩니다.

yml 파일이 있습니다

spring:
  datasource:
    url: url
    username:test
    password: testpwd
api:
  security:
    username:foo
    password: foopwd

다음과 같이 Linux 시스템에서 명령줄을 사용하여 처음 나타나는 사용자 이름과 비밀번호만 업데이트하고 싶습니다.

spring:
  datasource:
    url: url
    username:toto
    password: totopsw
api:
  security:
    username:foo
    password: foopwd

내가 시도할 때:

sed -i -e 's!^\(\s*username:\)[^"]*!\1toto!' test.yml

그는 사용자 이름을 모두 바꿨습니다

답변1

또 다른 sed옵션:

sed '1,/username/{/username/ s/:.*/:toto/};
     1,/password/{/password/ s/:.*/:totopsw/}' infile

1,/regex/첫 번째 줄부터 시작하여 주어진 내용과 일치하는 첫 번째 줄까지regex(여기서는 문자열 username) "사용자 이름"을 변경하고 "비밀번호" 부분에도 동일한 작업을 수행합니다.

답변2

파일이 더 긴 경우 awk한 줄씩 처리하는 기반 솔루션은 다음과 같습니다.

awk '/^[[:space:]]+username/ && !u_chng{sub(/:.+$/,": toto"); u_chng=1}
     /^[[:space:]]+password/ && !p_chng{sub(/:.+$/,": totospw"); p_chng=1} 1' input.yml 

username각 줄이 또는 개별적으로 시작하는지 확인합니다 password. 그렇다면 관련 플래그가 u_chng아직 p_chng설정되지 않은 경우 다음 값을 원하는 새 값으로 설정 :하고 해당 키워드가 더 이상 발생하지 않도록 해당 플래그를 설정합니다.

결과:

spring:
  datasource:
    url: url
    username: toto
    password: totospw
api:
  security:
    username:foo
    password: foopwd

문자 클래스( ) awk를 이해하지 못하는 구현을 사용하는 경우 다음을 변경하십시오.[[:space:]]

/^[[:space:]]+username/

도착하다

/^[ \t]+username/

답변3

파일이 메모리에 들어갈 만큼 작은 경우 전체 파일을 단일 레코드로 읽어 볼 수 있습니다. 이렇게 하면 sed패턴이 "행"(레코드)에 처음 표시될 때만 교체가 발생합니다.

$ sed -Ez 's/(username:)[^\n]*/\1toto/; s/(password:)[^\n]*/\1totopsw/' file.yaml 
spring:
  datasource:
    url: url
    username:toto
    password:totopsw
api:
  security:
    username:foo
    password: foopwd

원본 파일을 변경하려면 다음을 추가하세요 -i.

sed -i -Ez 's/(username:)[^\n]*/\1toto/; s/(password:)[^\n]*/\1totopsw/' file.yaml 

답변4

스크립트가 작동 하면 bash다음 sed quit 명령을 사용할 수 있습니다.

#!/bin/bash

sed -E '
    # If we find an username
    /username/ {

        # make the sobstitution of the username
        s/^([[:space:]]*username:)/\1toto/g

        n # Take the next line with the password

        # Sobstitute the password
        s/^([[:space:]]*password:).*$/\1totopw/g

        q1 # Quit after the first match
    }
' test.yml > new_test.yml

# How many line we have taken
len_line=$(sed -n '$=' new_test.yml)

# write the other line
sed "1,${len_line}d" test.yml >> new_test.yml

# rename all the file
rm -f test.yml
mv new_test.yml test.yml

관련 정보