こんにちは、hachi8833です。
🔗Ruby
🔗 Ruby 3.2のYJITはproductionで使えるレベル(Ruby Weeklyより)
つっつきボイス:「Shopifyの記事で、YJIT開発の中心メンバーであるMaxime Chevalier-Boisvertさん↓の記事です」「ShopifyはRubyに多くの技術投資を行ってきていて、YJITもそのひとつとしてフィーチャーされていますよね」
以下は同記事で引用されていたツイートです↓
Ruby 3.2 + YJIT against Ruby 2.7 in @discourse
Categories Page => 32% faster
Home Page => 34% faster
Topic Page => 28% faster
Categories Page (admin) => 32% faster
Home Page (admin) => 33% faster
Topic Page (admin) = >24% fasterwhen using Unicorn (p75 numbers)
🚀
— Rafael Silva (@rafael_falco) December 26, 2022
「ところで、Ruby 3.2のYJITベンチマーク記事の中でNoah GibbsさんのMastdonでの発言が引用されていて、現在のYJITデフォルト設定はメソッドが30回呼ばれると最適化するので、単体テストではYJITをオフにしておく方がよさそうとのことです↓」「お、なるほど」
参考: Benchmarking Ruby 3.2 with YJIT - by Peter Solnica
@solnic @joeldrapper デフォルトではYJITは30回呼び出されたメソッドを最適化する(この値はコマンドラインのパラメータで変更可能)。しかしメソッドの利用頻度が高くない場合はYJITはあまり有効でないので、単体テストでのYJITの利用は原則としておすすめしない。
Noah Gibbs
「30回実行すると最適化が効くみたいな動作は、もしかすると状況によってはテストが不安定になるかもしれませんね: たとえばテストコード内でRailsのActive SupportのTime.current
を2回連続で実行したときに、YJITが無い場合は安定して少し進んだ時刻が返るけど、YJITが効いた場合には間の処理が早くなって同じ時刻が返るかもしれない、みたいなことはあり得るかも」「あ、そうか」「まあそもそもそういうテストコードはtravel
を使って適切に記述すべきという話でもありますが」
参考: Rails API current
-- Time
🔗 polars-ruby: 高速なカラム指向データライブラリPolarsのRubyラッパー
つっつきボイス:「これはruby-jp Slackで知りました: 以前も話題にしたApache Arrow(ウォッチ20190402)のカラム指向データストアのメモリモデルをRustで実装したPolarsというライブラリがあって、polars-rubyはそのラッパーだそうです」「よく見たらankaneさんが作ったgemだ」
「こういうのを高速に行えるということでしょうね: データサイエンス方面で標準的なApache Parquetのフォーマットも扱えるらしい↓」「なるほど」「こういう機能を単体で使えるgemがあると、AWS Lambdaみたいなところでちょっと動かしたりするときなんかに便利かもしれませんね」
# https://github.com/ankane/polars-rubyより
#From a CSV
Polars.read_csv("file.csv")
# or lazily with
Polars.scan_csv("file.csv")
# From Parquet
Polars.read_parquet("file.parquet")
# From Active Record
Polars.read_sql(User.all)
# or
Polars.read_sql("SELECT * FROM users")
# From a hash
Polars::DataFrame.new({
a: [1, 2, 3],
b: ["one", "two", "three"]
})
# From an array of hashes
Polars::DataFrame.new([
{a: 1, b: "one"},
{a: 2, b: "two"},
{a: 3, b: "three"}
])
# From an array of series
Polars::DataFrame.new([
Polars::Series.new("a", [1, 2, 3]),
Polars::Series.new("b", ["one", "two", "three"])
])
参考: Apache Arrow - PG-Strom Manual
参考: Parquet | Databricks
つっつき後に、Apache ArrowはApache Parquetを元に構築されたと教わりました↓
🔗 RubyのEnumerableのドキュメントは読んでおけ(Ruby Weeklyより)
つっつきボイス:「実際EnumerableはRubyに組み込まれた強力な機能なので、ドキュメントはマジで読んでおく価値があると思います」「Enumerableを使いこなすとこんなに短く書けるというコード例もありますね」
参考: module Enumerable
- Documentation for Ruby 3.3
参考: module Enumerable
(Ruby 3.2 リファレンスマニュアル)
# 同記事より
def longest_string(strings)
longest = ""
strings.each do |str|
longest = str if str.length > longest.length
end
longest
end
# Enumerable#max_byを使うとこう書ける
def longest_string(strings)
strings.max_by(&:length)
end
「ところでこの記事にもオチがあるんですが、末尾の▶をクリックしてみてください↓」「おや、この記事もChatGPTにこれを質問して書かれているのね」「このブログの"Blogging with AI"シリーズは別のレビュアーによるチェックを行ってから公開しているそうです」
▶Prompt for ChatGPT
One thing I feel would be really helpful for junior and even intermediate Rubyists is to become really familiar with the methods provided by Ruby's Enumerable module, which is included in Arrays, Hashes, and Sets among other things. How would you convince developers to read up on that, with a few examples of naive approaches to problems with each or map being replaced with more appropriate Enumerable methods?
同記事より
🔗 RubyGemsにgem exec
サブコマンド追加の提案
つっつきボイス:「まだドラフトですが、npm exec
的なgem exec
コマンドをRubyGems追加してはどうかというプルリクがrubygemsのリポジトリに上がっています」
「gem exec
が使えると便利になるんでしょうか?」「これが使えると嬉しいと思いますね: gemビルトインコマンドのバージョン指定実行もできるようになりますし、他にも、現在だと、あるコマンドを実行したいときに、それがgemからインストールされたものなのか、他のパッケージによってインストールされたのかがわかりにくくなることが割とあるんですよ: gem exec
が使えれば、gemによってインストールされたコマンドが実行されることが明確になる」
「これはbundle exec
だとできそうでできないんですよ: たとえばbundle exec ls
を実行するとシェルのパスにあるls
コマンドの方が実行されてしまいますが、gem exec
が使えれば、指定したgemによってインストールされた独自のls
コマンドを確実に実行できる」「そういうことなんですね」「使えるようになったら積極的に使いたい👍」
概要
RubyGemsに
gem exec
サブコマンドを追加して、rubygems.orgやユーザー独自のgemサーバーにあるgemを、そのgemが現在インストールされているかどうかとは無関係に(必要ならgemをインストールして)実行できるようにする。動機
npx
/npm exec
にインスパイアされた。これは既にgemxという別gemが存在するが、見つけにくいうえに、RubyGmes標準の組み込みコマンドではなく単独のgemとして依存することになる。ガイドレベルの解説
gem exec
コマンドは、gem install
を実行して、インストールされた実行可能ファイルを実行するショートカットと考えられる。
たとえば、gem exec rails new .
を実行するとrails new .
をカレントディレクトリで実行する。gem install rails
を手動で実行する必要はなく、rails new
を一度実行するだけで、それ以外のrails
コマンドは実行しない(rails new
ではGemfileが生成されるため)。もう少し完全な実行例:
$ gem exec --gem cocoapods -r '> 1' -r '< 1.3' -v -- pod install --no-color --help
これは、
cocoapods
gemのpod
実行ファイルを用いて、バージョン1〜1.3を指定してpod install --no-color --help
を実行する。
(中略)
リファレンスレベルの解説
gem
のexec
という新しいサブコマンドがRubyGemsに追加される。
gem exec
は、gemのインストールに独自のgemパスを利用する(必要な場合)。そして、既存のgemセットから要求されるバイナリのロードを試みる。
バイナリが見つからない場合は、そのgemをインストールし(デフォルトではバイナリと同じ名前になるが、コマンドラインオプションで変更可能)、そのライブラリを有効にして実行する。欠点
これは純粋に追加を提案するものなので、既存ユーザーには影響しないはず。
Bundler を使う場合やGemfileを使うユーザーが混乱する可能性がある。
まず、gem exec
を実行するときは、Gemfileを完全に無視することを計画している。これは、gemの取得元をGemfileでカスタマイズしようとしている場合に混乱する可能性がある。
さらに、gem exec
はbundle exec
コマンドと紛らわしく、両者の動作はそれぞれ異なる。
この混乱を改善できそうな方法は、gem exec
では要求された実行ファイルが現在のバンドルに存在するかどうかをチェックし、存在する場合はbundle exec
を使うようユーザーに促すというもの。Add RFC for gem exec command by segiddins · Pull Request #45 · rubygems/rfcsより
🔗 設計・セキュリティ
🔗 スライド: 和暦を正しく扱うための暦の話
つっつきボイス:「BPS Webチーム内ミーティングでも少し話題になった和暦の話ですね」「和暦がこんなにややこしいとは思わなかった」「うるう月を表すUndecimberって造語かと思ったらラテン語由来なんですね」「そういえば江戸時代の太陰暦にもうるう月があった」「スペルが微妙に違うUndecemberは"13月を表すユーモラスな語とされる"ですって」
「元号の話あたりはプログラミングをやっている人にも好きな人がいそう」「歴史学者がどうやって元号や年号を解決していたのか何となく気にはなっていました」「歴史の教科書でもそのあたりが書き換わったりしますよね」「そういえばCivilizationにも古典の技術にCalendar(暦)があった」「Civilizationは学びの多いゲーム」
参考: データ/テクノロジー/古典 - Civilization4(Civ4 シヴィライゼーション4) 攻略Wiki
「こういう世界があるという驚きを感じられるスライド👍」
🔗 Danger のコマンドインジェクション
つっつきボイス:「ruby-jp Slackのセキュリティチャンネルで知りました」「Dangerって何だっけと思ったらコードの自動レビューツールか」「CIでこういうツールを連携させたりしますね」
「"細工された名前のブランチで実行されると任意のコマンドを実行できる問題"、これはこの間のGitの脆弱性並に怖いヤツ」「git clone
すると任意のコマンド実行、怖すぎ...」
参考: 「Git」に3件の脆弱性 ~修正版のv2.39.1が公開 - 窓の杜
「シェルは便利なんだけど、コマンドラインの引数に渡した文字列を展開する文化はよくないとつくづく思う」「以前も話したRubyのShellwordsのような文字列エスケープを使って安全にやりたい(ウォッチ20200225)」「ですね」「でもRubyからのシェルコマンド実行はShellwordsで守ることはできますが、Rubyから実行するシェルスクリプト側での引数の処理が甘いと結局そこが脆弱になったりすることはあるんですよ」
参考: module Shellwords
(Ruby 3.2 リファレンスマニュアル)
参考: 【 eval 】コマンド――文字列を評価、連結して実行する:Linux基本コマンドTips(170) - @IT
🔗クラウド/コンテナ/インフラ/Serverless
🔗 AWSのsso login
つっつきボイス:「babaさんのSlack書き込みで知りました↑」「aws configure sso
コマンドでURLとリージョンを渡すとブラウザが開いて認証できるんですね↓」
# 同記事より
$ aws configure sso
SSO start URL [None]: https://my-sso-portal.awsapps.com/start
SSO region [None]:us-east-1
SSO authorization page has automatically been opened in your default browser.
Follow the instructions in the browser to complete this authorization request.
「AWSアカウントが複数ある場合はこんなふうに選択できる↓」
There are 2 AWS accounts available to you.
> DeveloperAccount, developer-account-admin@example.com (123456789011)
ProductionAccount, production-account-admin@example.com (123456789022)
「期限切れの一時認証を自動更新してくれる、これなら使ってみたい👍」「新しいAWS CLIはいろいろ便利になっていますね」「後から登場するツールはこうあって欲しい」
IAM Identity Center にサインインしていて、キャッシュされた認証情報が期限切れでない限り、AWS CLI は必要に応じて期限切れ AWS の一時認証情報を自動的に更新します。
AWS IAM Identity Center (successor to AWS Single Sign-On) を使用するための AWS CLI の設定 - AWS Command Line Interfaceより
🔗 Apache Airflow
- サイト: Apache Airflow
- ドキュメント: Running Airflow in Docker — Airflow Documentation
- 元記事: Airflow : Docker で検証環境を構築して画面と CLI と REST API で操作する - kakakakakku blog
つっつきボイス:「APIの死活監視にも使えそうなApache Airflowというオープンソースのワークフロー管理ソフトウェアを見つけました」
「触ったことはないけど、雰囲気としてはワークフローエディタで作ったデータを中間言語的な形でエクスポートして、サイトに書かれているさまざまなサービスとインテグレーションする感じかな」「ドキュメントを見るといろんなサービスとインテグレーションできるみたいですね」「Apacheのプロダクトだからそれなりに手堅く作られていそう」「データ収集もできるみたい」
「このあたりはGitLabのワークフローエディタを思わせますね↓: dependencyがあるとか、並列化可能かどうかを指定するみたいな部分はたいていのワークフローで共通していますね」
「JP1とかSenjuみたいなエンタープライズ向けの有償ワークフローをちょっと思い出した」「なつかしい名前ですね」
「Docker HubにもApache AirFlowがあって、ドキュメントにもDocker利用について書かれていました」「Apache AirFlowをローカルのDocker環境で使えるということですね: 機会があったら使ってみようかな」
- Docker Hub: apache/airflow - Docker Image | Docker Hub
後編は以上です。
バックナンバー(2023年度第1四半期)
週刊Railsウォッチ: Ruby 3.2のベンチマーク記事、dry-cliで高度なCLIを作るほか(20230201後編)
- 20230131前編 Evil Martiansが使っているgem、JavaScriptガイドが更新ほか
- 20230125前編 2022年のRails振り返り記事、RailsにDocker関連ファイルが追加ほか
ソースの表記されていない項目は独自ルート(TwitterやはてブやRSSやruby-jp SlackやRedditなど)です。
週刊Railsウォッチについて
TechRachoではRubyやRailsなどの最新情報記事を平日に公開しています。TechRacho記事をいち早くお読みになりたい方はTwitterにて@techrachoのフォローをお願いします。また、タグやカテゴリごとにRSSフィードを購読することもできます(例:週刊Railsウォッチタグ)