2016-06-20

zsh: 現在のディレクトリ中のファイル名の「特定部分A」を「特定部分B」に変えるスクリプト


zsh: 現在のディレクトリ中のファイル名の「特定部分A」を「特定部分B」に変えるスクリプト
zsh: Script to change the "specific part-A" to "specific part-B" of file-names in a current directory


概要


私は、Firefoxの外部CSS(Profile/chrome/userContent.css)をスクリプト経由で操作したくなりました。他方、細かなCSSの操作はStylishでしています。これらの為に、ファイル名を一括して変更するスクリプトが必要になりました。「old2new」がその答えで、具体例とソース・コードを以下に示します。


具体例

Figure 1: Demonstration of "old2new"




ソース・コード(old2new)



#!/bin/zsh 

# USAGE: old2new OLD NEW↩

# FUNCTION:
#   1) 変えたいファイルがあるディレクトリに移動
#   2) ファイルの「変ええたい一部」を$1(OLD)に入れる
#   3) 「その変更後の値」を$2(NEW)に入れる
#     NEWは何もなし("")でも可。
#   4) *${OLD}* --> *${NEW}*

# 2016-06-19-21:52

###############################################################################
# list current dir: % old2new ↩
if [[ ( $1 == "" ) && ( $2 == "") ]] ; then
  echo " • list of current dir"
 ls -dlG *
 exit
fi


###############################################################################
# for: % old2new OLD NEW↩

old="$1" # specific part-A
new="$2" # specific part-B


myls=( ${(f)"$(ls -d *)"} )
j=$((0))
for file in $myls ; do
 [[ -d "$file" ]] && continue
 [[ -f "$file" ]] || continue
 
 new_file=$( echo "$file" | grep "$old" | sed "s%$old%$new%" )
 [[ "$new_file" == "" ]] && continue
 j=$((j+1))
 echo -n "  • $j " 
 mv -fv "$file"  "$new_file"
done

if [[ $j -eq 0 ]]; then
 echo " •• old file: *${old}* not detected"
else
 echo " •• ---------------------------------------------------------------------- "
 ls -dlG *"${new}"*
fi


感想


時々、このようなスクリプトを作ろうかと思ったが、面倒くさいのでサボっていた。もう少し頑張れば、連番の付与もできそうだ...。


この記事の履歴

  1. 開始2016-06-20-01:16




2016-05-30

zsh: JavaScripを使って「Terminal.appのカラムや行」を設定する

zsh: JavaScripを使って「Terminal.appのカラムや行」を設定する
zsh: To sett columns and raws of Terminal.app by using JavaScript

経緯


JavaScriptを練習するのに、スクリプト・エディタを使っています。さらにTerminalに於いてjscを使っています。
  • /System/Library/Frameworks/JavaScriptCore.framework/Versions/A/Resources/jsc
  • OS: Yosemite  10.10.5 (14F1808)
その練習課題として、Terminal.appの設定を作ってみようと考えました。検索すると最適なスクリプトがありました;

これを基にして、"Script Editr"の”Window nenu -> Library”からTerminal.appを見ながら、完全設定をしようと思いましたが、なんと肝心んな16色のカラー設定やフォントの文字間隔、行 間隔の設定の項目が無くて、頓挫しました。

次の総括的な解説中の「コマンド・ライン引数の使用」を参考して、zshのスクリプト(txy)を作りました。

このスクリプトは、terminal作業の処理を次々にスクリーン・ショットに保存していくときに、意外と便利なので紹介します。



動作例


図1はターミナルが呼ばれた直後です。最後の設定(幅77x行10)となっています。
Figure 1 Just opened Terminal which preserve precious columns & raws.

そこで「% txy 80↩️」とすると幅だけが80に変わり、図2のように(幅80x行10)となります。
Figure 2. "txy 80" re-sized only columns to 80.

さらに 「% txy 82 22↩️」とすると幅と行が同時に変わり、図3のように(幅82x行22)となります。
Figure 3. "txy 82 22" re-sized columns & raws to (82x22)

最後に「% txy↩️」とすると規定値(幅80x行40)となります、図4.
Figure 4. "txy" re-sized to dafaut value (80x40).





スクリプト: txy


#!/bin/zsh 

# txy: default terminal resized to x*y
#           X: Number of columns for default Terminal.app
#           Y: Number of rows for default Terminal.app
# USAGE:
#         txy↩  -----> (80*40)     : defaut  ----------------------> Fig. 4
#         txy X↩   --> (X*Y0)      : Y0='previous value'  ---------> Fig. 2
#         txy X Y↩  -> (X*Y)       : set both of columns*raws  ----> Fig. 3. 
#         terminal opens with previous columns*raws:  ------------- > Fig. 1
    # 2016-05-07(土) 12:36:43  by mNeji
    # 2016-05-12(木) 11:55:07 set_JS, get_JS


###############################################################################
set_JS() {
# Execute $JS as Javascript. Throw unwanted output away to /dev/null
    osascript -l JavaScript -e "$1" > /dev/null
}

###############################################################################
get_JS() {
# Execute $JS as Javascript. The output is printed on standard output(screen)
    osascript -l JavaScript -e "$1"
}


########################### main ##############################################
# Reading current setting (X0•Y0) & display:
    td="Application('Terminal').defaultSettings"
    X0=$(get_JS "$td.numberOfColumns()")
    Y0=$(get_JS "$td.numberOfRows()")
    echo -n "terminal current: (${X0}x$Y0)  -->"

# Setting: (X, Y)
    case $# in
        0) X=80; Y=40;;
        1) X=$1; Y=$Y0;;
        2) X=$1; Y=$2;;
        *) X=$1; Y=$2;;
    esac

# Prepare JavaScript block for default Terminal Setting: ($X, $Y) 
    XYdataBlock="
    trmd =     Application('Terminal').defaultSettings
        trmd.numberOfColumns = $X
        trmd.numberOfRows = $Y
    "
    set_JS "$XYdataBlock"
    echo " resized: (${X}x${Y})\a"



zshで「osascript -l JavaScript -e JavaScript-commands」を使えば、JavaScript-commandsが実行できます。問題は、JavaScript- commandsは設定値を常時標準出力に出すことです。このような場合には「set_JS」関数を呼び出して、不要な出力を/dev/nullに捨てて います。
  • 例1)
    • set_JS "$XYdataBlock"

逆に、設定を読み取りたいコマンドの場合は、「get_JS」関数により出力させて、それを変数に代入させています。
  • 例2)
    • X0=$(get_JS "$td.numberOfColumns()")


感想


自力でアプリケーションのPreferencesを操れてうれしい。JavaScriptをshellの一つとして「#!/bin/javascript」とか「#!/bin/jsc」とか出来ないか? それとも「#!/bin/swift」の方が早かったり?


この記事の履歴
  1. 開始 2016-05-30(月) 23:18:39


2016-05-27

/Volumes内のドライブのUUIDをリストするスクリプト

5日ほど前に、Yosemiteで 「Update 2016-003」を実施しました。その後3日ほどしてから、DiskUtilで見ると、システム・ドライブの表示順序が不規則に入れ替わるようになりま した。「Apple サポート・コミュニティ: Mac OS X Technologies(Japan)」でこの現象を質問中です。
少なくとも「/etc/fstab」に「ドライブ毎に、UUID、種類、名前」をリストする必要があるようです。そこで、/Volumesの中にあるドライブのUUIDをリストするスクリプト、uuidsを作ったのでご紹介します。


terminalでの動作結果
Figure uuids action at terminal



スクリプト: uuids

#!/bin/zsh 
#
# uuids: list UUIDs in /Volumes/*
#
# USAGE: uuids↩
#_
# 2016-05-27(金) 18:11:14 
#
 
get_uuid(){
 #diskutil info "$1" | grep "Disk / Partition UUID:" | sed 's%[^0-9A-Z-]%%g' 
 diskutil info "$f" |grep 'Disk / Partition UUID:' |\
  sed 's%Disk / Partition UUID:    %%' | tr -d ' '  
}
 
 
mylc=( ${(f)"$(ls  /Volumes )"} )

echo "  #  UUIDs in /Volumes                      Drive Names"
echo " --  ------------------------------------  -----------------------------"
 
j=$((0))
for f in ${(O)mylc} ; do
 j=$((j+1))
  
 myu=$(get_uuid "$f")
 
  printf " %2d  %s  %s\n" $j $myu $f
done


この記事の履歴
  1. 開始2016-05-27(金) 23:18:54

2016-04-16

ウェブ安全色によるzshのプロンプト設定

少し前に、アップル・サポート・コミュニティでの論議、
で参考になる論議をいただいています。現在大雑把な方向を理解できたので、ターミナルからの色付き出力を;Web colors の説明にある
に従って、系統的に操作するユーティリティを検討中です。

するとターミナルのプロンプトの色もウェブ安全色にしたくなりました。幾つかのサイトに解説がありましたが、何れも正常に動作しませんでした。そこで、日本語のzsh解説書、「zshの本: Book on zsf、p103, 表4.3 文字表示属性を変えるエスケープシーケンス」を参考に、トライ&エラーしました。汚いですが雰囲気が判ると思うので、その表の部分を引用させていただきます。

Table 4.3, Escape sequences controlling attributes of character display.
from  p103, "Book on zsh"(Japanese edit.), Auther: HIROSE Yuuji,
2009-07-25, ISBN978-4-7741-3864-0.  


ウェブ安全色を「X=5」の拡張として書き出したところ、上手くいったので以下に紹介します。設定は「.zshrc」の中で行いました。コメント・アウトされた2行(PROMPT, RPROMPT)が実際の設定です。

##---- Step 4/4) Prompt: -------------------------------------------------------
#    %n=UserName, %m=MachineName, "%4~"='compact dir display'
#-------------------------------------------------------------------------------
# 2014-11-08(土) 11:12:35 : Bash & Zsh
#------------------------
#    export PROMPT='%B%F{cyan}%K{blue}%n@%m[%4~]%#%k%f%b '
#    export RPROMPT='%B%F{cyan}%K{blue}%D{%H:%M:%S}%k%f%b'
#-------------------------------------------------------------------------------
# Web safety color: 2016-04-12(火) 20:44:58 Web Safty Colors
#------------------------------------------------------------------------------
#                                              ~cyan 51,                     ~Blue
    export PROMPT=$'%{\e[1;38;5;51m%}%{\e[48;5;21m%}%n@%m[%4~]%#%{\e[0m%} '
   export RPROMPT=$'%{\e[1;38;5;51m%}%{\e[48;5;21m%}%D{%H:%M:%S}%{\e[0m%} '
#
 上記のプロンプト設定と、ターミナル16色の設定とを、ターミナルでのユーティリティwscInfoで示した結果を図1に示します;
 Figure 1. Terminal 16-colors, Cursor colors, Prompt colors.

上記の色はすべてウェブ安全色ですが、重複がないようにしています。気になるのは、#15
の白いバックグラウンドが白い文字の「231」よりも若干灰色になっているところです。「OS X」の不可思議な振る舞いの一つかも知れません。
環境:
  • OS X Yosemite Version 10.10.5
  • Terminal.app 2.5.3
  • zsh 5.0.5 (x86_64-apple-darwin14.0)


なお、wscInfoは一番初めにお話ししたサイトの「2016/04/12 0:16 」の記事(2.2 wscInfoのリスト)で公開しています。


この記事の履歴
  1. スタート2016-04-16(土) 18:21:25 

2016-03-24

zsh: 文字パラメータの置換を「zsh特有な方法」で行う

zsh: 文字パラメータの置換を「zsh特有な方法」で行う
zsh: Substitutions  for a character parameter are carried out  by using the  unique commands of zsh within a function

あらすじ


最近になって、図1でハイライトした部分で、パラメータの置換操作を知りました。


Figure 1. "Modifiers on arguments", Zsh Reference Card.pdf, p6.
上記の技法でサンプル・スクリプトを作りました。文字操作処理は関数にしていた方が保守性を示す。そこで以前の記事に沿って、関数スタイルのスクリプトにしてみました。;
参考までに以下に紹介します。


スクリプトの流れ


スクリプト名(test_Substitution)のターミナルでの動作結果を図2に示します。なお、スクリプトについては、別途を説明します。

Figure 2.  Output  of test_Substitution at Terminal.app.


これと比較しつつ、以下の説明をご覧ください。
  • (1)  mainで文字列パラメータ$scaが作られて;
    • (1.2)  sca='>>>>>  • fruits:  i) red apple,  ii) green apple. <<<<<'
    • (1.3)  $scaのアドレス(sca)として関数のargumentが与えられる。
  • (2)  pointer_called_functionに読み込まれて、
    • (2.1)  読み込み時に使ったパラメータ情報を表示。読み込んだ文字パラメータは$pv1に格納された。
    • (2.2)  pv1='>>>>>  • fruits:  i) red apple,  ii) green apple. <<<<<'
    • (2.3)  簡単な複数置換をし、最後に大文字(Upper case)に変換した。
    • (2.4)  pv1='»»»»»  •ANIMALS:  I) BLACK CAT,  II) WHITE CAT. «««««'
    • (2.5)  zshでは、手動でメインの変数に$pv1の値を上書き(override)が必須.。
      • だから「擬似ポインタ!」と呼ばれる理由だと思う。
      • この上書きが必要ないなら、(2.5)は不要になる。
  • (3)  mainに戻ると、$scaは正しく(2.4)を反映している!
    • (3.1)  sca='»»»»»  •ANIMALS:  I) BLACK CAT,  II) WHITE CAT. «««««'


スクリプト


#!/bin/zsh 

#!/bin/zsh 

# Usage:test_Substitution↩

# Purpose: To memorize;
#  1) Example of substitutiones by using "Modifiers on arguments",
#  2) Example of function of address call with overwrite to main,
#  3) Sumarize information of parameters usen in above function.

#
#####################################################################
 stringReplacement(){
#------------------ argument $1:pointer address --------------------#
 local pt1=$1            # pt1: pointer address of $1
 local pv1=${(P)pt1}     # pv1: pointed value addressed by pt1
#
#------------------ engine of function for parameter $pv1 ----------#
 echo "•••••••••••••••••••••••••••••••••••••••••••••••••••••••• (2) $0 •"
 echo "(2.1) Information on pt1=\$1       # \$pt1: pointer in \$1"
 echo "    (2.1.a)   \${1}'s type: ${(t)1}"
 echo "    (2.1.b) \${pt1}'s type: ${(t)pt1}"
 echo "            \${pt1}'s value: '${pt1}'"
 echo "    (2.1.c) \${pv1}'s type: ${(t)pv1}"
 echo "(2.2) Value of \$pv1=\${(P)pt1}    # same value to (1.2)"
 echo -n '    '
 bold_Rbw_echo ${(qq)pv1}
 echo "(2.3) Substitutions & Uppercase modification for \$pv1"
 echo "     • fruits → animals, apple → cat, green → white,… etc."
 # replace to new value by step by step change on $pv1 
 pv1=${pv1:s% fruits%animals%}  # :s%s1%s2%  
                                #  ↑ Substitute s1 with s2.
 pv1=${pv1:gs%apple%cat%}       # :gs%s1%s2%  
                                #  ↑ Globally Substitute s1 ← s2.
                                   # [:sg%...] ==> error.
                                   #   ↑ in sed: 's%s1%s2%g'
 pv1=${pv1:s%green%white%}
 pv1=${pv1:s%red%black%}
 pv1=${pv1:gs%>%»%}
 pv1=${pv1:gs%<%«%}
 pv1=${pv1:u}                  # (U) convert to Upper case.
 echo "(2.4) Value of \$pv1 replaced by (2.3)"
 echo -n '    '
 bold_Rbw_echo ${(qq)pv1}
 echo  "(2.5) \$pv1 ---> \$pt1: overwrite by (eqn.1a) or (eqn.1b )"
#
#------------------ overwrite $pv1 to original value $pt1 in main ------------#
 echo  "(2.6) overwritten by using (eqn.1b)"
 #eval "$pt1='$pv1'"    #--------------------------- ok ---------- (eqn.1a)
 eval "$pt1=${(qq)pv1}" #-------------------------- ok ---------- (eqn.1b)
   # both of (eqn.1a or eqn.1b) work well,
   # as '$pv1' <==> ${(qq)pv1}, (eqn.1a) <==> (eqn.1b)
 }

#####################################################################
 bold_echo(){echo "\e[38;1m${@}\e[m"}
 bold_mag_echo(){echo "\e[1;7;35m${@}\e[0m"}
 bold_Rbw_echo(){echo "\e[1;7;38m${@}\e[0m"}


#####################################################################
# -------------------------- main --------------------------------- #
#####################################################################

 echo "•••••••••••••••••••••••••••••••••••••••••••••••••••••••••• (1) main •"

 local sca='>>>>>  • fruits:  i) red apple,  ii) green apple. <<<<<'

 echo "(1.1) Type of \$sca: ${(t)sca}"
 echo "(1.2) Value of \$sca:"
 echo -n '    '
 bold_mag_echo ${(qq)sca}

 echo "(1.3) Call \"stringReplacement sca\""  
 echo "                            # ↑ Notice: 'not \$sca',"
 echo "                            #   because it is address."
 echo 
 stringReplacement sca
 echo
 echo "•••••••••••••••••••••••••••••••••••••••••••••••••• (3) back to main •"
 echo "(3.1) Value of \$sca: it's to the value of (2.3)"
  echo -n '    '
  bold_mag_echo ${(qq)sca}
 echo


  • 動作環境 
    •   OS Yosemite 10.10.5 
    •  Terminal Version 2.5.3 (343.7)
    •   zsh 5.0.5 (x86_64-apple-darwin14.0)

まとめ

  •  図1でのパラメータ置換では正規表現(regex)を使えない!
    • 日常的なデータ整理には使える。
    • 正規表現(regex)が必要なら、従来のgrep,shed,awkは適宜に使う必要がある。
  • Pointerの関係で、XcodeでC言語を動かしていた、
    •  意外と使えた!
      • 当面は、現在のzshの環境の中で、CとSwiftとを練習したい。
      • その後、C++とかにトライしたい。
    • 最近は、Swiftでも正規表現の環境が整いだしているらしい。

コメント

  • 配列への直接操作ができると便利そう。
 この記事の履歴
  1. 開始 2016-03-24(木) 15:44

2016-03-12

zsh: グロッビング・パターンを含むパラメータを持つコマンドを「eval」で実行する

zsh: グロッビング・パターンが含まれたパラメータの有るコマンドを「eval」で実行するには  ««« 日本語
zsh: To execute "eval" on a command with globbing pattern. ««« English

はじめに



zshの関数に配列をパラメータとして渡す方法をトライしたが、失敗した。次善の策として「eval」に興味を持ったので調べてみた。初めには、参考資料1のp298に示されている「パラメータ展開フラグ;: ${(e)cmd}」を触ってみたが上手くいかなかった。


Google 検索で参考資料2を拝見すると,凄い記述、Figure  2、に衝突した。「${=cmd}」という簡潔で「eval」を体験できたのです。

Figure 1.

  • 参考資料2: zshとbashでは変数の単語の分割ルールが違う。http://qiita.com/mollifier/items/7fdbf15765ccf37f4881
    • zshとbashでは変数の単語の分割ルールが違う
      • zshでbashと同じようにスペースで区切る → 方法2: % ${=Cmd}

常用している参考資料3のPDFで「${=cmd}」を検索すると、如何にもな「${~cmd}」があった,Figure 2,ので試行錯誤した。

Figure 2.


 何はともかく試行錯誤したら上手くできたので、具体例をご紹介します。


結果



テストディレクトリには3つのファイル:aaa, bb, ccbaa:があります。
% ls
aaa    bb    ccbaa

次のコマンドを投入すると;
% cmd="ls -dF"
% prm="*a*"  
% ${=cmd} ${~prm}
aaa    ccbaa


確かに、目的が実行できました;



検討


結果で使った$cmdでグロッビング・パターン(*a*)を入れた場合を示します;
% cmd="ls -dF *a*"
% ${=cmd}
ls: *a*: No such file or directory

  • グロッビング・パターン(*a*)が解釈されずにファイル「*a*」としてパラメータに追加されたようです。


ところが、この$cmdにevalを作用させると、上手くいきます。
% eval $cmd
aaa    ccba

しかし、zsh製作者さん達が${~val}を製作した以上、evalのzsh版を探しました;
% ${=${~cmd}}
aaa    ccba
  • 最初に、${~cmd}でグロッビング・パターン(*a*)が解釈し、
  • ${=...}で、 全体を分割してshellに渡して、
  • Shellがそれを実行。
要するに、,zsh製作者さん達の真意は下記だったのでしょうか;
  • 「eval $cmd」=「${=${~cmd}}」
    • 此処まで来ると、evalの方がシンプルか。
    • 私が製作者なら、 「${=~cmd}」を許すかな。


参照資料

  • Reference 1: From Bash to Z Shell,  Oliver Kiddle et. al., Apress, ISBN-13:978-1-59059-379-9.
    • p298, ${(e)cmd}: Perform shell expansions on the value.
      • cmd="ls" works well! but unfortunately cmd="ls -l" not work.
  • Reference 2: "The variable splitting rules to words" differs between zsh and bash. 
    • http://qiita.com/mollifier/items/7fdbf15765ccf37f4881
      • To get same result of "Word splitting by space" in bash, a elegant way in zsh is :  % ${=cmd}.
  • Reference 3: "Zsh Referrence Card.pdf"
    • http://www.bash2zsh.com/zsh_refcard/refcard.pdf
      • Search "${=" in pdf.


この記事の履歴
  • 開始 2016-03-12(土) 01:33
  • 追加 2016-03-13(日) 23:21 検討
  • 追加 2016-03-14(月) 15:17 検討: ${=${~cmd}}

注目の投稿

Terminalでの、なんちゃってViモドキ

近頃、ようやくKarabiner-Elementsに慣れてきたので、 Terminalで動作する「擬似Vi-Mode」を作って見たので、ご紹介します。 『概要』 「擬似Vi-Mode」の所以は、方向キー「←↓↑→」を通常の「hjkl」ではなくて「jkil」としました。これ...