csh 系のシェルを使ってた
FreeBSDにログインする機会があり、文字コードで詰まった。
文字コードの環境変数をセットするには setenv を使うらしい。
setenv LANG ja_JP.UTF-8
これで日本語が正しくなった。
pv はプロセスパイプを通過したバイト数をみて、進捗を見ることが出来るのですが。
pv の output は stderr に書かれるのだけれど、それをキャプチャリングしたいなと思ったら。。。結構面倒くさいのです。
pv は プロセスの起動をアレコレしているっぽくて、ターミナルのFdに直接書いてるわけではなさそうなのです. たぶん tty とかに直接かいてるんじゃないかな。
-f
オプションを使う。オプションを使うことでstderr に書き出す事ができる。
pv -f hdd.img | lzop ... 2> out.log
r,w= IO.pipe cmd = 'pv -f IMG_3200.MOV | cat - > /dev/null' puts cmd pid = Process.fork do r.close STDERR.reopen w Process.exec cmd end s = '' w.close while s = r.read(100) do puts s end Process.waitpid pid
こうすれば、進捗を変数に取り出すことが出来た。あーこれはハマるわ。。。 ffmpeg の進捗をもっと簡単に取る方法ないのかな。。。。
http://takuya-1st.hatenablog.jp/entry/2017/03/06/172644
文字コードがグチャグチャーって化けるのでした。辛い。
conv_file_name.sh -v -n path/to/*.pdf conv_file_name.sh -v path/to/*.pdf
nkf があれば何とか出来るんだけけれど結構面倒くさいのでファイル名を変化するシェルコマンド書いた。
あれこれ冗長なのと細かいエラー処理をしてないのであらゆる場面に対応できるかと言われれば多分出来ないけど。
とりあえず、これでいいや
#!/usr/bin/env bash function mv_conv(){ src=$1 dst="$( echo -n $src | nkf -w )" if [[ "$src" == "$dst" ]] ; then return fi if [[ $3 == 1 ]] ; then echo "'$src'" "'$dst'" fi if [[ $2 != 1 ]] ; then mv "$src" "$dst" fi } declare FILES; declare VERBOSE; declare DRY_RUN; for arg ; do case $arg in '-n') DRY_RUN=1 ;; '-v') VERBOSE=1 ;; *) FILES+=("$arg") esac done for i in "${!FILES[@]}"; do file=${FILES[$i]} mv_conv "$file" "$DRY_RUN" "$VERBOSE" done
Seleniumで画像をだけを取り出して保存したり、ファイルを取り出すのは不便だよね。
だけど、直接Curlで叩くのもCookieの問題でもっと不便だよね。
そこでSeleniumのCookieをCurlで使える形式やNetscape形式で保存したり、RubyやPythonなどの http cookieクラスに変換して保存したら楽だと思ったので作ってみた。
保存する形式は次の通り。
imid=HeNFSXsHS82I7KZB9xiYkQ; expires=Thu, 06-Jun-2019 17:43:13 GMT; domain=.im-apps.net; path=/;
def save_cookie_to_cookie_jar(driver) s = driver.manage.all_cookies.map{|e| [ "#{e[:name]}=#{e[:value]}" , "#{e[:secure] ? 'secure; ':'' }", (e[:expires]||Time.now).strftime('%a, %d-%b-%Y %T GMT'), "domain=#{e[:domain]}" , "path=#{e[:path]}" , ].reject{|e| e == '' }.join("; ") }.join("\n") tmp = Dir::Tmpname.make_tmpname( 'a', '.cookie_jar.txt' ) tmp = File.expand_path(tmp, Dir.pwd) open(tmp, 'w'){|f| f.puts s} return tmp end
## 取り出したファオルの形式は次の通り。( タブ区切り ) example.com FALSE / TRUE 0 XSRF-TOKEN ePG7sHRafqxj
def save_cookie_for_curl(driver) s= driver.manage.all_cookies.map{|e| [ e[:domain], ((e[:domain]=~/^\./)==0).to_s.upcase, (e[:expires]||Time.now).to_time.to_i , e[:path], e[:secure].to_s.upcase, e[:name], e[:value] ].join("\t") }.join("\n") tmp = Dir::Tmpname.make_tmpname( 'a', '.cookie_jar.txt' ) tmp = File.expand_path(tmp, Dir.pwd) open(tmp, 'w'){|f| f.puts s} return tmp end
スクレイピングでHTMLからデータを抜くのに、並行処理だとか、分散処理が出来て一気に楽になる。
サーバーの負荷はたしかに気になるけど、ドメインを dig って CDN 経由ならもう気にしないことにしてる。
CDNはそう簡単に落ちないし、強い。
wkhtmltopdf
と組合せたり、 chrome --print-pdf
と組合せたり、curl と組合せたり、Mechanizeと組合せたり、Cookieさえなんとかすれば結構楽しい世界が広がる。
SeleniumからChromedriverが起動したときに、プロファイルがちゃんと渡されて起動したかどうか
それを調べるにはどうすれば良いのか。少し考えてみたら chrome://version/
を見るしか無いと思われる
version に行くとわかる。
executeScript("window.open('chrome://version')")
を実行して タブで開いて、タブへアクセスして version のページからプロファイルを取得することが出来る。
chrome --headless
で起動している場合には、version のページが全く空っぽになるのでここから取ることはできなかった。
別の方法を考えたけどやっぱり無理で。 headlessに関わるアレコレ(widthやnew tab )に苦しめられるので linux ならxvfb ( X virtual frame buffer) を使うほうが、ずっと楽な気がします。
新規タブを開かれると、element not clickable で、currently visibleで、 displayed がfalse になる。
なんで、クリックできないエラーになるのか頭をひねったら、width だった。
driver.execute_script("var tab = window.open('about:blank','_blank');"); driver.switch_to.window(driver.window_handles.last) driver.execute_script('return {"w":window.innerWidth, "h":window.innerHeight};') # => {"w"=>0, "h"=>0}
お疲れ様でした。Width=0,Height=0です。これではクリックできない。そうなります
chrome headless はdriver.manage.window.resize も通らないのでこれは詰んだと思う。phantomJSだとたしか出来たような。。
新規タブを開かせないように window.open を 乗っ取るしか無いのかもしれない
Selenium側の問題かもしれないと思って Chrome の Dev tool で ポートにアクセスして、実際に window.open して、リモートデバッグで見てきたが、駄目だった.remote debug 経由でタブを開くと問題ないなけど。window.open
が呼ばれるとどうも駄目みたい。chrome 側のバグっぽい。
chrome の headlessは 新規タブが開いてフォーカスが動かないのもちょっと面倒だし。 xvfb の方が楽ですね。それかseleniumすてて chrome の debugging protocol を使う方が良いかもしれない。
Chrome DevTools Protocol Viewer
戻る禁止の銀行WEBは戻る禁止 の制限があるので、新規タブを開きまくる。戻る禁止はCRSFやセッションハイジャック対策だとおもうけど、そんなことはPOSTを使うページだけに限定したらいい話だし。戻る対策としては戻る禁止はtoo bad だし、全ページをPOSTにするから戻るができないので新規タブを開きまくる。なのでwebappとして間違ってると思う。iframeに埋め込まれることを防ぐならHTTPヘッダでやるべきだと思うし。クリックジャッキングやはCSPでなんとかなるだろうし、もう戻る禁止と新規タブはやめてほしいわ
スマートダッシュ・スマート引用符で自動変換されていた件。
Evernoteに適当にメモしたコード断片をIPython や Pryに貼り付けたら動かなくて、なんだこれ? とおもってよく調べてみたら、引用符が引用符じゃなくなっていた。
お前は何を言ってるんだ?
よく調べてみたら、ダブルクォートじゃなくて、別の引用符に変換されていました。
いつ起きたのかと調べてみたら、どうやらスマート引用符という機能のようです。
スマート引用符が有効になった状態で、ダブルクォートを入れると、自動的に「引用符」をキレイにしてくれる例です。
同じように、スマートダッシュについても見てみました。ハイフンが変換されていました。
自動変換機能をオフにするのが一番です。
小さめのフォント(10px前後)を使っていると見逃すので注意が必要です。
クラスに所属するStaticなメソッドを呼び出したときに、クラス名を直接指定するのは不便だよね。
class A def self.do puts :do end def say A.do # クラス名が・・・ end end a = A.new a.say
self.class で参照すると楽ですね。
self.class.do
Object.send でメソッド名を sym か str で指定できるので、そっちを使っても便利かもしれない。
class A def self.do puts :do end def say self.class.send(:do) end end a = A.new a.say
これで、むやみにインスタンスメソッドを生やさなくて済む。インスタンスメソッドは「インスタンス」を扱うようにしたいよねやっぱり。インスタンスが無くても動くような処理はクラス・メソッドに登録しておくと使い方を変えられるので意図が明確になる気がする。
module で定義した、メソッドやローカル変数を、クラスの特異メソッドに取り込む
次のようにすると実現できる。
module S1 def sample puts :sample end end class A class << self include S1 end end
共通処理をクラスに書いてしまうとクラスのStaticな部分とインスタンスな部分がごちゃ混ぜになってしまうので、分けて書けるのはMix-inが強いなと思いました まる。
ただ、include や モジュールでほしいのは関数定義 def だけだったりするので、名前空間が独特でruby 分かりづらいよねともおもったり。クラスの継承をしなくて良いのは楽よね。
履歴から入力してて、イライラしてるときに、truncate コマンドを本番環境に実行してしまった。もう詰んだ。死にたい。
automysqlbackup
というパッケージを導入することにしました、
apt install automysqlbackup
以前入れていたと思ったら、入って無くて本当に詰んだ。
Twitterの認証連携をして、AuthorizeApp したあとにメールアドレスの確認が必要になる。ほとんどの「JPサービス」はこの形態を取る。
認証を丸投げしてるんだからメールアドレスを必須にされても手間が増えて困るだけなんですよ。
かといってFacebookで認証連携なんてフレンドリストやメールアドレスを抜かれて困る。
選ぶんだけどメアドが必須にされるのはナゼ?
わたしには理解できないです。そのそも設計がオカシイんじゃないのか。
それとも法律で「メールアドレス」を回収するように求められるのかな?公衆無線LANのように??
-c 生成済みの md5sum の一覧とファイルを比較して改ざんを検出する。
事前にファイルのmd5sum の値の一覧を作成しておき、いまのファイルがそのファイルのハッシュ値と一致するかを調べておく。すると簡単に改竄検出や不正検出を見つけることが出来る。
最初に、md5sum の一覧を計算してファイルに書き出しておきます。
md5sum sample.txt > out.md5
次に、この出力結果を使ってファイルが一致するかチェックします
md5sum -c out.md5
out.md5の中身は次のようになっています。 md5値 ファイルPATH
が列挙されています。
c3cec535915d86f2ce51c668f6919696 sample.ext
チェック-c
の場合は、右側のファイルパスのファイルを探して、md5値を導出し事前に計算していた左側に一致するかを調べてくれます。
1ファイルだと何の役に立つかわかりにくいのですが、フォルダの中のまとめてチェックすると強いです。
find コマンドや xargs と組合せる。 フォルダのすべてのファイルについて、md5を計算する
sudo find /etc/ -mindepth 1 -type f -exec md5sum {} \; > etc.md5
結果を使って、フォルダの中のすべてのファイルについて、ファイルの改竄検出を行う。
sudo md5sum -c etc.md5
bash の if 文でつかときは --status
オプションが便利です。
このオプションを付けると、表示をしない代わりに、チェック結果をコマンドの実行結果で返してくれます。
if ( md5sum -c --status etc.md5 ) ; do echo "改竄チェックOK" else echo "改竄チェックNG" fi
これで有るフォルダの中が書き換わってないかを手軽に調べることが出来ます。
sudo md5sum -c out.md5 | grep -i failed
のようにしたら見つけることが出来ました。
もっと簡単にするには、
sudo md5sum --quiet -c out.md5
--quiet don't print OK for each successfully verified file
このオプションをつけるのもいいでしょうね。
もし、ハッシュ値保存したファイルを改ざんされると怖いので、ハッシュ値を保存したファイルのハッシュ値を取ってそれをブロックごととに保存していくといいです。このブロックが・・・
ブロックチェーン技術などで盛んにファイルの記録をハッシュ値で云々と叫ばれてます。 基本的にはハッシュ値を計算してファイルに保存してそのファイルのハッシュ値を計算してーってことです。似たようなものです。
フォルダの中のファイルつまり、あるエントリの内部のハッシュ値をすべて見るには、md5sum である程度十分です。便利だし。
衝突の可能性も有るでしょうがローカルファイルで衝突は可能性が低いしね。
How to access all your cloud files in one place in Windows 10 | TechRadar
nkf には -mB
と -MB
のペアがあるのでBase64のエンコードとデコードが出来る。
echo -n こんにちは | nkf -MB
echo 44GT44KT44Gr44Gh44Gv| nkf -mBW こんにちは
入力の文字コードを -W : utf8 で指定してる。
文字列だとうまくいく。nkf は「文字コード」を変えるコマンドなので、バイナリも文字として扱ってしまうのでデータは壊れる。アレコレすればいいだろうけど、そこまでやる必要は特になくbase64
コマンドを使ったほうが良いので。
とある文字列を処理していて、CP932(Shift_JIS ) がそのまま、URLエンコードされた文字に出会って、ちょっと面倒な自体になった 。 node の decodeURI/decodeURIComponent だとUTF-8を期待されて動かない。ruby/pythonだと内部文字コード*1から変換が面倒くさい。nkf で文字コードを変換を調べてたら、 nkf だけで行けることがわかった。
$ echo %E3%81%93%E3%82%93%E3%81%AB%E3%81%A1%E3%81%AF%EF%BC%81 | nkf --url-input こんにちは!
--url-input
オプションを使えば、デコード出来る
デコード結果をさらに utf8にするには -W
オプションをつけておけばいい。nkf --url-input -W
takuya@:~$ echo こんにちは! | nkf -MQ | sed s/=/%/g %E3%81%93%E3%82%93%E3%81%AB%E3%81%A1%E3%81%AF%EF%BC%81
-MQ
オプションはQuoted stream に変換するので、 =
を使ってる。それを%に変換すればいい
組合せて使います。
echo %82%B1%82%F1%82%C9%82%BF%82%CD | nkf -w --url-input こんにちは
NKFは枯れた技術だし安心して使えるわ。Windowsの文字コードがutf8にならねーかなぁ
文字コード変換コマンドの nkfの使い方と実例をまとめました。 - それマグで!
開くダイアログのフォルダ選択のときに、隠しファイルやフォルダを開きたいときがよくある。
ドットファイルやドットのフォルダ( .rbenv / . pyenv など)を開きたい。
たとえば、atom/visual studio code/intelli J のIDEでドットファイルを見たいときが結構ある。
私の場合 RubyMineやPycharm で rubygems や pythonのpip ファイルを見たいときが頻発した。毎回コマンドで指定するのも面倒くさいので、なんか方法がないか調べたらあった。
保存・開くダイアログで上記のショートカットを入力すると、ダイアログが開いて、フルパスで指定できるようになる。
残念ながら、補完は効かないようで・・・
フルパスを取得するには、いったんターミナルなどでフルパスを作ってクリップボードに入れておく必要がありますね。
Windows(田)のNTFSみたいに、フォルダ・ファイルごとに可視・不可視を切り替えらればいいのにね。APFSで導入されないかなー
jetbranins の rubymine の nvm / rbenv と webstorm で .npm / nvm など、ドットファイル (dotfile) になったフォルダから インタプリタで実行バイナリを選ぶときにこの方法が活躍する
rubymine などで実行環境SDKで .rbenv が出てこない時があってそのとき、この方法によって Shift+Cmd+G を押してフルパスを入力しフォルダを移動して解決する。
Windowsのホームディレクトリに出てくる、dotfiles を非表示にする。 - それマグで!
intellij で困ったので追記した。