クライアントシステムを複製し、ファイル内の特定の行を変更するスクリプトを作成しています。
次の行を含むソースファイルがあります。
$DB_HOST = "LegitDbHost";
ターゲットファイルには次の行があります。
$DB_HOST = "testDbHost";
したがって、ターゲットラインをソースラインに置き換える必要があり、次の内容を印刷したいと思います。
Replacing line 12: '$DB_HOST = "testDbHost";' ==with==> '$DB_HOST = "LegitDbHost";'(y/n):
これまで私はこれを得ました:
toReplace='$DB_HOST';
sourceLine=$(cat ./sourceFile.php | grep -m 1 "$toReplace[[:space:],=]");
destLineNr=$(cat ./destFile.php | grep -n -m 1 "$toReplace[[:space:],=]" | grep -Eo '^[^:]+');
destLine=$(cat ./destFile.php | grep -m 1 "$toReplace[[:space:],=]");
read -p "Replacing line $destLineNr: $destLine ==with==> $sourceLine.(y/n): ";
しかし、私の出力は次のようになります。
==with==> $DB_HOST ST = "testDbHost";.(y/n):
;
これは、sourceLineが内部を持っていてCommand側に解釈されるからだと思います。この問題を解決する方法がわかりません。
これが理解できることを願っています。
編集する:
提案したようにecho -n
toReplace='$DB_HOST';
sourceLine=$(cat ./sourceFile.php | grep -m 1 "$toReplace[[:space:],=]");
destLineNr=$(cat ./destFile.php | grep -n -m 1 "$toReplace[[:space:],=]" | grep -Eo '^[^:]+');
destLine=$(cat ./destFile.php | grep -m 1 "$toReplace[[:space:],=]");
echo -n "Replacing line $destLineNr: "
echo -n $destLine
echo -n " ===with===> "
echo -n $sourceLine
これは次のように印刷されます。
===with===> $DB_HOST = "testDbHost";OS";
答え1
努力する:
#! /bin/zsh -
die() {
print -ru2 -- "$@"
exit 1
}
srcFile=./sourceFile.php
dstFile=./destFile.php
toReplace='$DB_HOST'
sourceLine=$(<"$srcFile" grep -Pm1 "\Q$toReplace\E[\s,=]") ||
die "Can't find $toReplace in $srcFile"
<"$dstFile" grep -nPm 1 "\Q$toReplace\W[\s,=]" |
IFS=: read -r destLineNr destLine ||
die "Can't find $toReplace in $dstFile"
if
read -q "?Replacing line $destLineNr: ${(q+)destLine} ==with==> ${(q+)sourceLine}? (y/n): "
then
(
export destLineNr destLine
perl -lpi -e '$_ = $ENV{destLine} if $. == $ENV{destLineNr}' -- "$dstFile"
)
fi
zsh パラメーター拡張を使用すると、${(q+)line}
その変数の CR 文字 (入力ファイルに Unix LF 区切り記号の代わりに MSDOS CRLF 区切り文字があるように見えるため) が端末にC-M
あるまま転送されるのではなくレンダリングされます (ターミナルの場合、CR 文字はカーソルを行の先頭に戻します(テレタイプマシンのキャリッジリターン)。