파일이 있습니다:
$cat file1.txt
1234|W
1345|S
8427|D
2132|C
3243|V
내 SQL 파일은 다음과 같습니다
$cat select.sql
SELECT *
FROM CUSTOMERS
WHERE ID IN (FLAG);
다음 지침이 포함된 쉘이 있습니다.
$cat replace.ksh
!#/bin/ksh
S_ids=`awk -F"|" '{print "\47" $1 "\47" ","}' file1.txt |sed '$s/,$//'`
sed -i "s/FLAG/${S_ids}/g" select.sql
FLAG라는 단어의 파일 입력 에 변수 "S_ids"의 값을 넣어야 합니다. select.sql
결과는 다음과 같아야 합니다.
$cat select.sql
SELECT *
FROM CUSTOMERS
WHERE ID IN ('1234',
'1345',
'8427',
'2132',
'3243');
나는 이것을 시도했지만 sed -i "s/FLAG/${S_ids}/g" select.sql
예상한 결과를 얻지 못했습니다.
답변1
이것이 작동하지 않는 이유는 (제공을 생략한) 오류 메시지에서 추론할 수 있습니다.
sed: -e expression #1, char 14: unterminated `s' command
이 sed
명령은 여러 줄 값을 허용하지 않습니다. 여러 행을 하나로 축소해야 합니다. 다음과 같은 스크립트를 사용하여 이 작업을 수행할 수 있습니다.
#!/bin/ksh
S_ids="'$(cut -d'|' -f1 file1.txt | tr '\n' ' ' | sed -e 's/ *$//' -e "s/ /','/g")'"
sed -i "s/FLAG/${S_ids}/g" select.sql
S_ids
생성 방법을 보려면 파이프라인의 각 부분을 가져오면 됩니다.
cut -d'|' -f1 file.txt # Extract first column
tr '\n' ' ' # Convert newlines to spaces
sed -e 's/ *$//' # Strip the trailing space
sed -e "s/ /','/g" # Replace each remaining space with the three characters ','
답변2
#! /bin/ksh
inputfile='file1.txt'
sqlfile='select.sql'
S_ids=$(awk -F"|" '{gsub(/^|$/,"\\'\''",$1) ; print $1","}' "$inputfile" |
xargs |
sed -e 's/,$//')
sed -i "s/FLAG/${S_ids}/g" "$sqlfile"
산출:
$ cat select.sql
SELECT *
FROM CUSTOMERS
WHERE ID IN ('1234', '1345', '8427', '2132', '3243');
이는 awk
각 행의 시작과 끝 부분에 첫 번째 필드를 추가하는 함수를 사용합니다 gsub()
. 단순히 추가하는 것이 아니라 작은 따옴표를 파이프에 유지합니다.\'
\',
\'
'
xargs
'\''
작은 따옴표 스크립트에 작은 따옴표를 삽입하는 방법에 유의하세요 awk
. "end-single-quote, escaped-single-quote, start-single-quote-again"으로 읽어보세요.
xargs
xargs echo
기본적으로 모든 출력 라인(file1.txt의 작은따옴표로 묶인 첫 번째 필드)이 공백으로 구분된 한 라인에 배치되도록 실행할 명령이 없습니다 . 이는 file1.txt
최대 쉘 라인 길이(보통 128KB 이상)를 초과하기에 충분한 수만 개의 라인이 있지 않는 한 작동합니다 .
마지막으로 xargs
출력을 파이프로 연결하여 라인에서 제거합니다 sed
.,
의 각 ID 뒤에 줄바꿈을 추가하려면 select.sql
스크립트의 마지막 줄을 다음과 같이 변경하세요.
sed -i "s/FLAG/${S_ids}/g; s/, /\n/g" "$sqlfile"
출력은 다음과 같습니다:
SELECT *
FROM CUSTOMERS
WHERE ID IN ('1234',
'1345',
'8427',
'2132',
'3243');
답변3
$ FLAG=$(awk -F\| '{printf("%s, ", $1)}' file1.txt)
$ echo $FLAG
1234, 1345, 8427, 2132, 3243,
$ sed "s/FLAG/${FLAG%%, }/" select.sql
SELECT *
FROM CUSTOMERS
WHERE ID IN (1234, 1345, 8427, 2132, 3243);
플래그 목록이 명령줄에 들어갈 만큼 작은지 여부에 따라 다릅니다. 그렇지 않은 경우 다음을 사용할 수 있습니다.줄을 서다awk에서 file1.txt를 처리하고, BEGIN
패턴에서 대체 문자열을 수집한 후, select.sql을 처리합니다.