質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
sh

shは、UNIX系OSのシェル操作の1つであり、最も基本的なシェルのことです。

Q&A

解決済

3回答

857閲覧

shellスクリプトで.bash_profileの一部PATHを削除したい

hirooze

総合スコア7

sh

shは、UNIX系OSのシェル操作の1つであり、最も基本的なシェルのことです。

0グッド

0クリップ

投稿2018/02/08 15:52

編集2018/02/08 15:59

前提・実現したいこと

前提

Shellスクリプト で Uninstall.sh を作成しています。
インストールで入力したPATHを削除したいと考えています。
PATHは、「.bash_profile」の最下部に入力されています。
下記がインストール時のコマンドです。

bash

1$ echo 'export PATH=$PATH:$HOME/.origin/bin' >> ~/.bash_profile`

実現したいこと

「.bash_profile」に、特定の文字を含む行があった場合、
その文字列を含む行を削除するコードを書きたいと思っております。
そのため、現在下記コードを書いてみました。

bash

1path=`grep origin $HOME/.bash_profile` 2if [[ `grep origin $HOME/.bash_profile` ]] ; then 3 sed -i "s/$path//g" 4 source ~/.bash_profile 5else 6: 7fi

発生している問題・エラーメッセージ

発生したエラーメッセージは、下記の通りです。

bash

1sed: -e expression #1, char 37: unknown option to `s'

恐らく、sed の条件式の中に半角スペースが混じってしまい、
エラーが出てしまっているのかと思っています。
ただ、PATHを外から消したいのですが、他の手段が思い付きません。

試したこと

  • if [-z 〜〜]と変更してみましたが、ファイル名を対象としてしまったため、条件に引っ掻からず。
  • sed -i "s/$path//g"のsオプションを消したりしましたが、できませんでした。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答3

0

あくまで個人的な意見ですが・・・

.bash_profileを自動変更するというならパターンマッチは極力「ガチガチ」に書いた方がよい気がします。質問者さんのコードですと、ユーザーが"origin"という文字列を含むような行を.bash_profileに書いていた場合それを消してしまうため、場合によって致命的な結果を招くのではないかと思います。

せめてインストール時に追加した行に完全に一致するもののみを削除した方が多少なりとも安心できる気がします。もしsedで削除するなら以下のように行全体のパターンを指定することになります。

sed -i.bak '/^export PATH=$PATH:$HOME/.origin/bin$/d' ~/.bashrc

grepした結果だとどんなパターンになるか不明なのでどうやって特定の文字をエスケープするかについて考えないといけませんが、固定パターンであればかえって指定は容易になりますね。


ちなみに、インストール時に自動追加した部分は1文字でも変更されると困るので
# 自動生成スクリプト: 以下の行は編集しないでください
風のコメントも追加したい気もします。それをやってしまうと連続した複数行のパターンマッチをしなくてはなりませんが・・・

投稿2018/02/08 22:45

KSwordOfHaste

総合スコア18394

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

hirooze

2018/02/15 07:45 編集

ご意見ありがとうございます。 確かに他のシステムに影響ないようにするためには「ガチガチ」にすべきだと思います。 ガチガチにするためのコーディングが思いつかない、また試したがエラーに突き当たってしまい、 動けず仕舞でした。 頂いたアドバイスをもとに、下記のように書き直しました。 if [[ `grep origin $HOME/.bash_profile` ]] ; then sed -i.bak '/^export PATH=$PATH:$HOME/.origin/bin/d' $HOME/.bash_profile source $HOME/.bash_profile else : fi if のカッコのみ書き換えで上手く動きました。 他$HOMEなどは、ちょっと冗長かも知れませんが、一応自分が分かり易い書いております。
guest

0

ベストアンサー

「.bash_profile」に、特定の文字を含む行があった場合、その文字列を含む行を削除するコードを書きたいと思っております。

あとのシェルスクリプトをみるに、要するにoriginという文字列が含まれる行を行単位で消したいということでよろしいのでしょうか?
であれば、こんなややこしいことをしなくても以下で十分です。

sed -i.bak '/origin/d' .bashrc

投稿2018/02/08 17:09

KojiDoi

総合スコア13671

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

hirooze

2018/02/08 19:26

迅速な回答ありがとうございます。 当コードを参考に、sedの部分を書き直したところ、解決しました。 ありがとうございました。
guest

0

質問タイトルや変数名にPATHとあるのでパス文字列の入った行を消したいのだと思いますが、パス文字列には普通“/”が含まれるので、単純に"s/$path//g"とすると問題が起きそうです。たとえば$pathに「/bin」が入っていると、これは"s//bin//g"と書かれているのと同じになります。

sedのsコマンドの区切り文字は“/”じゃなくてもいいので、$pathに入ってなさそうな“|”あたりを使って"s|$path||g"とかすると、sedのエラーは回避できそうです。

投稿2018/02/08 16:39

emasaka

総合スコア524

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

hirooze

2018/02/08 19:24

迅速な回答ありがとうございます。 同じようにやってみましたが、sedでエラーがまた出てしまったため、断念しました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問