2019/12/06

ziprubyapp: 実行可能なRubyスクリプトアーカイバ

妙なもの第2弾。

ziprubyapp: Make an executable ruby script bundle using zip archive

コンピュータとだけマルチリンガルな私としては、Python と Perl と Ruby と OCaml は同じくらいの頻度で話したり(実際の所、Perlはここ20年でぐっと減りました)するのですが、
PythonPerl でできるなら、Ruby でもやりたい、単一ファイル実行形式でお手軽自作ツール運用したいと思うのは自然な流れなので。

こちらも結果としては、単一ディレクトリに依存ファイル (*.rb だけですが) を置いて ziprubyapp で処理すると、サクッと1ファイルの実行スクリプトにまとめてそれらしく実行してくれます。


zipperlapp: 実行可能なPerlスクリプトアーカイバ

また妙なものを作っています。

zipperlapp: Make an executable perl script bundle using zip archive

Perlに限らずスクリプト言語で書いたコマンドラインツールは、標準的なインタプリタさえあれば、とりあえずコピーして $PATH に放り込めば動く、というポータブルな実行形式としてのお手軽さも魅力の一つだと思っているのです。
でも、今時のモジュールをちゃんと使ったプログラミングでファイルが複数になると、導入時の配置とか考えることが増えて、だんだんポータブルでもお手軽でもなくなっていくのが不満。
「実行ファイルは /home/???/bin の下に置くと、ライブラリは名前付けて /usr/local/lib/perl の下の全プログラム共有空間に置くか、あるいは /home/???/lib の下に個別に @INC 通すスクリプトを置いて、でもそうすると置き場所で毎回書き換えが...」と。
今時だと Ruby の gem とか Python の egg にして /home の下に入れるオプションでインストールして、... とやるのが正しいかもしれないですけど、それでも C 言語のコンパイル済みバイナリのように、ファイル一発コピーでおしまいとはいかず。

この辺りを解決するのが、このzipperlappの目的です。


2019/12/01

suid_sudo: sudo を使った setuid スクリプト用ライブラリ

並行して (?)、suid_sudo という「sudo を使った setuid」のヘルパーライブラリを公開しました。…「『いまさら』を2連発」なんて言わないで。

「一般ユーザ権限だけでは出来ないシステム操作を、ユーザごとにできることを制約して許可したい」という用途はUnixでは結構あり、全てがcapabilityのようなシステム提供の機能では制御できないため、Unix系OSではその多くがsetuidという仕組みを通じて実現されています。例えば、passwdコマンドでは「全員のパスワードが書かれたデータベースの内、自分のパスワードだけを変更できる」とか、そういう類のものです。

そして、もうかなりの昔語りですが、かつて Perl には suidperl という setuid をサポートする仕組みがありました。Unixのセキュリティ上の欠点を克服してスクリプトのsetuidをシミュレートする仕組みでしたが、なかなかkernelの支援なしに安全に作るのは難しく、2010年に削除されてしまいました。
Perlのマニュアルを見ると、

    Use of suidperl is highly discouraged.  If you  think you need it, try alternatives such as sudo first.

    「suidperl」の使用はお勧めしないよ。もし必要だと思ったら、sudoとか別のものを先に試してね!

と書いてあります……なんといい加減な。

というのは、sudo は実行できるコマンドは厳しく制限できるのですが、コマンドそのものは root 権限などでそのまま実行されるので、例えば上の passwd コマンドでいうと、「特定の人だけが全員のパスワードを変更できる」とか「AさんがAさんのパスワードを変更できる(それぞれ自分の、ではない)」のような制限しか出来ないのです。手元では suidperl script を置き換える段階で、この性質にかなり困りました。

というわけで、「じゃぁ sudo でちゃんとユーザ別の分岐処理できる環境を作るか」といって書き始めたところ、結構巨大なライブラリになってしまいました。

セキュリティ的には、実行可能なコマンドが「sudoの設定が許したコマンド」に限定されていて、「権限を落とすだけ」のライブラリなので、suidperlよりは随分楽で、確かに suidperl の better alternative にはなっていますが、それにしても結構複雑な処理が必要でした。

「自分で自分をsudoで呼ぶ」辺りは、できるだけユーザの使い勝手が悪くならないように工夫をしたところです。必要があったら参考にしてくれると良いなと思います。

ちなみに、技術的にこのヘルパーの内部実装で一番セキュリティ的に面倒なところは、「誰が起動したか」をきちんとsudoと連携して把握するところです。sudo は環境変数に「誰」の情報をセットしてくれるのですが、「本当にsudoがセットしたものなのか」がそう簡単にはわからない。その辺りをチェックするために、かなりシステムのいろいろな情報を調べています。それでも root だと色々微妙な判定しきれないケースを作れるので、その辺りは安全サイドに倒しています。(そのせいで、元からrootのときだけ使い勝手がちょっと悪い。)

python-httpauth-lib: Python向けHTTP認証ライブラリ(新しめ)公開

先日シンガポールでのIETFに行っている間に、Python向けのHTTP認証の実装を公開しました。……といっても、これだけだと今更感が大きく漂いますね。

これは、仕事でHTTP APIを使ったプロジェクトを進めている最中、最近のRFCでのDigest認証の更新に対応した実装が世の中に全然ないもので、割と必要にせまられて作ったものです。
一方で、HTTP認証の標準化に関わった人としては「自分で作るならちゃんと作るしかない」、また国際化の標準にもちょっと関わったからにはこちらも「ちゃんとしておきたい」ということで、
  • RFC 7235: 複数認証形式の同時提示への対応。
  • RFC 7617: Basic認証でのUTF-8サポート。
  • RFC 7616: Digest認証のさまざまな機能対応。
    • SHA-256 / SHA-256-sess アルゴリズム。
    • メッセージ認証内容 qop=auth / qop=auth-int の両対応。
    • HTTP応答の逆方向認証への完全な対応。
    • 多言語化対応ヘッダ (RFC 5987) に対応した UTF-8 サポート。
あたりを全部きちんと押さえてあります。

Python側のフレームワークとしては、標準添付のhttp.server, Flask, Eve (サーバ側), requests (クライアント側) 辺りを押さえてあります。共通ルーチン部分は、他のライブラリでも適用可能だと思います。
 どうもこの辺の規格化の仕事は余り実装が充実していないようなので、interopできたらいいなぁと思っているのですが、まずは MD5/SHA-1 以外に対応したDigest認証の実装ってものが殆ど無いので、その辺りの比較対象の the first one としてcontributeしておきたいという思いもあります。
とりあえず、Digest/SHA-256を使わなきゃいけなくなった人には使えるものになっていると思いますが、 試してみて頂ければ。

2018/12/12

ホームページデザイン更新

職場の組織が変わって、職場の方のホームページを更新しなければいけなくなったのが発端なのですが、同僚と会話していて、ぼそっと「なんか昔のホームページだよねー」と言われてしまったので、ホームページ作成のバックエンドを更新しました。

もともと割とブラウザを選ばないように、またレイアウトも画面サイズに柔軟に作っていたのですが、ここ5年位で急速にWebの古い環境が消え去っていったので、一気に HTML5 + CSS3  ベースに更新するとともに、モバイル環境に正式対応することにしました。
とはいえ、静的コンテンツしか置けないような環境もあるので、システムの基本の作りは変わっていません。

今回、自分の記録を兼ねて、過去のデータを調べなおしてみました。WayBack Machine をみると、(今となっては恥ずかしい)データがいろいろ残っています。

2018/11/26

make-password: パスワード生成ツール 公開

職場の方に、パスフレーズ生成ツールとライブラリ実働デモサイトを合わせて公開しました。

職場で色々な人と仕事の文書をやり取りする際、最近では暗号化は当然のことになっていますが、みんな作るパスワードがどうしても緩いものになりがちでした。さらに、パスワードを次のメールで送るという悪癖も、大変気になります。
とはいえ、100ビットとかの強いパスワードを手で作るのは結構大変で、それを会議の参加者で共有するのも大変面倒でした。会議室のWi-fiパスワードでも面倒くさいと思った人は多いはず。
というわけで、職場でこれを見直し、周りの関係者も巻き込んでいくには、色々工夫しないとダメだぞ、ということで、それにはリファレンスとなるツールをきちんと開発しないといけないね、と。

作ったツールですが、まずはデモサイトを見てもらうのが早いかもしれません。
ツールに世の中の単語の辞書をいくつか内蔵していて、
  •   ランダムな文字の組み合わせ
  •   ランダムに選んだ英単語の列
  •   ランダムに選んだ日本語の列
などを自由に選んで組み合わせられます。
これで、「打ちづらく間違えやすいけど、短いパスワード」と、「長いけど読みやすく間違えにくいパスフレーズ生成」の、好きな方を選ぶことができます。特に日本語の場合はローマ字だけでは読みづらいため、元の単語もヒントとして一緒に表示できます。また、パスワードの強度も数値で指定して、それに合わせた文字数・単語数を自動的に選びます。
PDFイメージ
さらに、生成したパスワードをカードに印刷(PDF)する機能を持っていて、共同プロジェクトや委員会などの初回にパスワード共有を face-to-face で済ませて、都度メールでパスワードを送らない運用を意図しています。メモは自席に戻ったら金庫に入れるなり、シュレッダーにかけるなりお好きにどうぞ。パスワード管理専門のソフトを使うのもおすすめです。

また、パスフレーズ生成部分は独立して使えるライブラリにしたので、応用して上手いワークフローを考えて貰えると嬉しいです。

最近の計算機が速くメモリが潤沢になっても、10万語クラスのテキストの読み込みは一瞬(0.5秒くらい)止まるので、その辺りはちょっと工夫してあります。
ちょっとずつ世の中の慣習が、良い方向に変えられるといいなぁ。

2018/11/23

hex-m17n: 多言語対応のダンプツール 公開

 hex-m17n: 多言語対応のダンプツール を公開しました。

 日本語のLinux環境はどうしても多種多様な文字コードが入り混じるものですが、日本語含むバイナリファイルを文字化けさせずに読むために、1996年頃にに大学の先輩の多賀さんが作られていた hex というツール が当時はすごく便利で、愛用していました。制御文字を単に 「.」 で表示するのではなくて、色分けしてそれなりに判りやすく表示してくれるのがすごくお気に入りでした。

 でも、その後すっかり UTF-8 が標準になって、自分のコンソールもUTF-8化して、他の文字コードや言語も色々と扱うようになったので、これは自分で欲しいものは自分で作ってしまおう、と思って2年前に一気に書き上げたものです。

 今時作るからには ISO 10646-1 / Unicode ベースで作ることになるのですが、
  • 「読みやすい od -c 相当の機能が欲しいよね」とか、
  • 「そもそも『文字化けしない cat』が欲しいだけなんだよね」、とか
  • 「今時日本語だけ対応のフリーソフトってどうなんだろう」とか、
  • 「2000年頃に自分がこだわっていた、ISO 2022 ベースの多言語化はきちんと対応させたいよね(ISO 2022 で多言語化した昔の文書ファイル、未だに結構持ってるんです)」とか、
結構やりたいことが出てきて、どんどん機能が膨れ上がっています。

作り上げてから自分で愛用しつつ2年くらい放置していたのですが、この際 github 周りを色々整理したので、いっそのこと公開することにしました。

説明のWebページはこれから作りますが、とりあえず github に README を上げておけばいいよねと、ずいぶん気楽な時代になったものです。