- 開発
週刊Railsウォッチ(20190624-1/2前編)6.1でActionView::Componentが入る、RuboCopのRuby/Railsスタイルガイドサイト、RailsガイドProプラン/Teamプランほか
こんにちは、hachi8833です。先週金曜日夜は銀座Rails#10でのmorimorihogeさんの発表を写真撮影しておりました。
TechRachoさん! #ginzarails pic.twitter.com/93N337l1tm
— シロ (@shiroemons) June 21, 2019
- 各記事冒頭には⚓でパーマリンクを置いてあります: 社内やTwitterでの議論などにどうぞ
- 「つっつきボイス」はRailsウォッチ公開前ドラフトを(鍋のように)社内有志でつっついたときの会話の再構成です👄
- 毎月第一木曜日に「公開つっつき会」を開催しています: お気軽にご応募ください
⚓お知らせ: 第12回公開つっつき会(無料)
開始以来ついに1年目を迎える第12回目公開つっつき会は、7月4日(木)19:30〜にBPS会議スペースにて開催されます。皆さまのお気軽なご参加をお待ちしております🙇。
⚓Rails: 先週の改修(Rails公式ニュースより)
主に公式情報から見繕いました。
⚓6.1にActionView::Component
がやってくる
- 元記事: Introduce support for ActionView::Component by joelhawksley · Pull Request #36388 · rails/rails
# actionview/lib/action_view/helpers/rendering_helper.rb#L27
def render(options = {}, locals = {}, &block)
case options
when Hash
in_rendering_context(options) do |renderer|
if block_given?
view_renderer.render_partial(self, options.merge(partial: options[:layout]), &block)
else
view_renderer.render(self, options)
end
end
else
- view_renderer.render_partial(self, partial: options, locals: locals, &block)
+ if options.respond_to?(:render_in)
+ options.render_in(self, &block)
+ else
+ view_renderer.render_partial(self, partial: options, locals: locals, &block)
+ end
end
end
なぜか公式の更新情報には入ってませんでしたが、プルリクのスレを見るとみんな超大喜び&大盛り上がりしているようです。実装はまだ始まったばかりのようですが、PRメッセージにがっつり構想が書かれています。Rails 6.1の真打ちの予感です(6はさすがに間に合わないそうです😅)。
プルリクの主はGitHubの中の人の@joelhawksleyさんです。
参考: Joel Hawksley | Boulder, Colorado
つっつきボイス:「今日社内Slackで盛り上がったActionView::Component
、やっぱり6.1からだそうです」「やはり😆まだ遠いかな〜」
「RailsConf 2019の以下の発表が先行していたようですが、このスライドは喋りの演出に最適化されてて単独だと読みづらかったのでウォッチではスキップしてました😆」
「Reactのコンポーネントみたいなものを目指してるのかな?」「お〜、こんな感じに書けるようになるっぽい↓😋」
「どうやらまたRails Wayに寄せてきた感あるかも😆」「フロントエンジニアに何言われるかと思うと🤣」「Reactとかの方もそれはそれで将来もっと書きやすくなるかもしれないし🤔」「ここはとりあえず見守っておこう🤣」「🤣」
ActionView::Component
は「新奇なアイデア」からは程遠いものである。Rubyにも以下のようなビューコンポーネントの有名な実装はあるが、この他にもある。
同PRより
- リポジトリ: trailblazer/cells: View components for Ruby and Rails.
- リポジトリ: dry-rb/dry-view: Complete, standalone view rendering system that gives you everything you need to write well-factored view code.
- リポジトリ: komposable/komponent: An opinionated way of organizing front-end code in Ruby on Rails, based on components
- リポジトリ: activeadmin/arbre: An Object Oriented DOM Tree in Ruby
「上のgemたちがActionView::Component
と同類ということみたいです」「コンポーネントっぽくしたいならこのあたりに似てくるでしょうね☺️」
「PRのスレを見てると、コンポーネント内のファイル配置↓をどれにしようかな〜ってみんなキャッキャウフフしてますね❤️」「遠足の前の日ですか😆」「Railsだけでコンポーネントやれるというのはいいかも😋」「採用するかどうかは、まプロジェクト次第ということで😆」
app/views/components/
- my_component/
- component.js
- component.css
- component.rb
- template.html.erb
- template.html+mobile.erb
app/views/components/
- my_component/
- component.rb
- template.html.erb
- template.html+mobile.erb
app/views/components/
- my_component.rb
- my_component.html.erb
- my_component.html+mobile.erb
「前回のウォッチで話したMicro Frontend(ウォッチ20190618)にも通じるんでしょうか?」「まそんな感じですね☺️」
「そういえば、モノは違うけどRails 1.2にこんなのあったよね↓とPRに書いてる人がいました」「あ〜なるほど、Webフレームワークってこういうコンポーネントみたいなものって昔からあって、自分もPHPのSymfonyでそういうの使いましたよ」「そうでしたか!」
- Rails 1.2のComponents: rails/components.rb at 1-2-stable · rails/rails
⚓Symfony 1.xのコンポーネント
「ただSymfonyのコンポーネントは、たしかレイアウトがあって、その中にコンポーネントを配置できて、コンポーネントの中にはさらにスロットを配置するという、いわゆるビューに階層を作れるアーキテクチャでしたね🧐」「お〜」「たとえばSideMenuコンポーネントの中にRankingスロットみたいなのをいろいろ配置できるヤツで、自分が見たSymfonyのコンポーネントはそういう趣き: 今はどうなってるか知りませんが😆」「😆」
「軽くググってみるとSymfony 1.x系みたいだから今はなさそうかな」「どうもそんな感じですね」「あの頃Symfony 1系の中のコードまで読んでたな〜」
「そうそう、Symfony 1.xのスロットはこんな感じだった↓: 全体テンプレート、ここではHeadlines SidebarというHeadlines部分テンプレート(partial)、さらにスロットを置けるようなつくりになってます」「う、ややこしい...😅」
「Rails 6.1に入るActionView::Component
は、これらよりはフロントエンドに寄せた感じというか、Web Componentsレイヤーのコンポーネント的な位置づけなんでしょうね☺️」「RailsでWeb Componentsすることになるんだろうか😆」
⚓ダイレクトアップロードでmirrorサポート
- mirrorサービスでダイレクトアップロードをサポート。
新しいファイルはprimaryサービスに直接アップロードされる。ダイレクトアップロードされたファイルはレコードにアタッチされ、バックグラウンドジョブがキューに入って各セカンダリサービスにコピーする。
ジョブをミラーリングする処理で使われるキューはconfig.active_storage.queues.mirror
で設定する。デフォルトは:active_storage_mirror
。
同Changelogより
# activestorage/lib/active_storage/engine.rb#L19
module ActiveStorage
class Engine < Rails::Engine # :nodoc:
isolate_namespace ActiveStorage
config.active_storage = ActiveSupport::OrderedOptions.new
config.active_storage.previewers = [ ActiveStorage::Previewer::PopplerPDFPreviewer, ActiveStorage::Previewer::MuPDFPreviewer, ActiveStorage::Previewer::VideoPreviewer ]
config.active_storage.analyzers = [ ActiveStorage::Analyzer::ImageAnalyzer, ActiveStorage::Analyzer::VideoAnalyzer ]
config.active_storage.paths = ActiveSupport::OrderedOptions.new
config.active_storage.queues = ActiveSupport::OrderedOptions.new
config.active_storage.queues = ActiveSupport::InheritableOptions.new(mirror: :active_storage_mirror)
つっつきボイス:「なるほど、そっちの意味のmirrorね☺️: ストレージサービスを複数(GoogleドライブとS3とか)使って、どちらにでもアップロードできるようにするということのようだ」「たしかにこれは欲しいヤツ😋」「マルチリージョンでアップロードできるようになったらうれしい😍」
⚓ActiveRecord::Relation
のプリロードを修正
# activerecord/lib/active_record/associations/preloader/association.rb#L29
def records_by_owner
- @records_by_owner ||= preloaded_records.each_with_object({}) do |record, result|
+ # owners can be duplicated when a relation has a collection association join
+ # #compare_by_identity makes such owners different hash keys
+ @records_by_owner ||= preloaded_records.each_with_object({}.compare_by_identity) do |record, result|
owners_by_key[convert_key(record[association_key_name])].each do |owner|
(result[owner] ||= []) << record
end
end
end
つっつきボイス:「❤️が山盛りなのは『Rubyエライ!』ということかしら😆」「compare_by_identity
?」「お〜、Hashインターフェイスにcompare_by_identity
というのがあるのか!」
参考: instance method Hash#compare_by_identity
(Ruby 2.6.0)
ハッシュのキーの一致判定をオブジェクトの同一性で判定するように変更します。
デフォルトでは、キーのオブジェクトによっては内容が同じならキーが一致しているとみなされますが、より厳密に Object#object_idが一致しているかどうかを条件とするようにselfを変更します。
selfが変化する破壊的メソッドです。
docs.ruby-lang.orgより
「ドキュメントにあるように、ハッシュのキーの一致判定をオブジェクトの同一性で判定するように変更するメソッドなのね」「おぉ?」「普通だとハッシュのキーはvalueで判定されるんですが、compare_by_identity
を呼ぶとハッシュのステータスが変わって、オブジェクトが同一でないと一致しないようになるという」「compare_by_identity
っていう名前だから同一性で比較するメソッドかと思ったら、同一性比較のためにハッシュを改変するってちょっとコワい😅」
「このプルリクは元々#36396↑の修正のためということで...なるほど、関連付けがプリロードされると同じレコードがインメモリでコピーされて重複することがあったから、それを扱えるようにcompare_by_identity
を使ったということらしい🧐」「おぉ」「レコードが複製された場合は違うものとみなされないと困るからでしょうね」「先週もマルチDB絡みで似たような話があった気がするので、その流れなのかも?」「よくぞ見つけた感👍」
⚓Active Recordのスキーマキャッシュのdeduplicate
# activerecord/lib/active_record/connection_adapters/deduplicable.rb#L3
+module ActiveRecord
+ module ConnectionAdapters # :nodoc:
+ module Deduplicable
+ extend ActiveSupport::Concern
+
+ module ClassMethods
+ def registry
+ @registry ||= {}
+ end
+
+ def new(*)
+ super.deduplicate
+ end
+ end
+
+ def deduplicate
+ self.class.registry[self] ||= deduplicated
+ end
+ alias :-@ :deduplicate
+
+ private
+ def deduplicated
+ freeze
+ end
+ end
+ end
+end
つっつきボイス:「これももしかするとマルチDB絡み?」「どちらかというとメモリ削減のリファクタリングっぽい: まあこれまでシングルトンだったのがマルチになってくるといろいろやらないといけないでしょうけど」
「Deduplicable
っていうモジュールが増えてますね」「レオナルド・デュカプリオみたい😆」「早口言葉😆」「dereference
とかも😆」
⚓小品: エラー画面をレスポンシブに
つっつきボイス:「あは、なるほど😆」「こういう修正はやっぱりいいっすね~😍」「地味だけどうれしい修正」「意外に今までやってなかったんですね☺️」「しかも修正はviewport
入れてCSSをちょいちょいっと直しただけ😆」「それでやれる修正ですし☺️」「グッジョブ!👍」「誰かがやってくれるとみんなが喜ぶヤツ😂」
# actionpack/lib/action_dispatch/middleware/templates/rescues/layout.erb#L2
<html lang="en">
<head>
<meta charset="utf-8" />
+ <meta name="viewport" content="width=device-width, initial-scale=1">
<title>Action Controller: Exception caught</title>
<style>
body {
⚓Rails
⚓RubyスタイルガイドのリニューアルとRailsスタイルガイド(Ruby Weeklyより)
- サイト: The Ruby Style Guide
つっつきボイス:「RuboCopの人たちがRubyとRailsのスタイルガイドサイトを立ち上げたそうです」「へぇ〜」「しかも私全然気が付かなかったんですが、どちらもしっかり日本語化されてます🇯🇵」「こういうのはコントリビュートしやすい分野ですよね☺️」
「以前TechRachoで出していたRubyスタイルガイドの翻訳プラスアルファ記事↑があってPV稼いでくれてますけど、今後は上のサイトがメインになるのかな...😢」「上のサイトの方が新しい?」「まだちゃんと見てませんが何だか編成も変わってるみたいで、RuboCopのLayout部署とかその辺も最近変わってるからかも」
「日本語版の『ヴァリデーション・ファイル』って表記珍しい😆」「私はこの中黒・
使わないスタイルでやってるので割と気になります😆」「『ユーザー・フレンドリー』とかも😆」「まあ統一されていればいいんですけど、点があったりなかったりしたらちょっと😅」「英単語が切れてたらそこが中黒になるんでしょうけど☺️」「その割には『ヘルパーメソッド』に点がないし😆」
「ともあれ、日本語じゃないと読みたくない人たちにはありがたいと思いますね☺️」「あと困ったときに『とりあえずここ読め』という一次情報があるのもありがたいです😂」
「私も翻訳で常日頃悩んでるんですが、今後原文の差分を訳文でどう追いかけるのかなと😆」「ほんにそれ😆」「『とりあえず原文で読め』と🤣」「それが結局コスト一番低いし🤣」「翻訳版で地雷踏んだことがあるとだいたいそうなる🤣」「ちゃんとメンテされているとわかっている日本語ドキュメントならさらっと読むのに使ったりするけど、訳が間違ってるとか古いとかでいろいろハマった身としては、ね☺️」
⚓Bounded Queueでアプリを短時間で復帰(Hacklinesより)
つっつきボイス:「Bounded Queues?」「お、これは中で詰まってるパターン↓ですね: キューがあふれてタイムアウト🕙」
Starting…
[0] 200 - 4.13 seconds elapsed
[1] 200 - 9.13 seconds elapsed
[2] 200 - 14.13 seconds elapsed
[3] 200 - 19.13 seconds elapsed
[4] 200 - 24.14 seconds elapsed
[5] 200 - 29.14 seconds elapsed
[6] 504 - 29.70 seconds elapsed
[7] 504 - 29.80 seconds elapsed
[8] 504 - 29.90 seconds elapsed
[9] 504 - 30 seconds elapsed
Took 30.0102 total, avg of 21.9242 in thread time, max 30, min 4.13
「こういうふうに時系列をちゃんと書いてくれているのはエライ↓👍」「たしかに〜」「教科書みたい」「できれば図にして欲しいけどっ😆」「TCPバッファリングの話もある」
00:00 — [A] Client sends request A to Server
00:01 — [A] NGINX buffers the HTTP request into memory and sends it to Puma
00:01 — [A] Puma accepts the connection, reads the request into memory and queues it
00:03 — [B] Client times out, sends request B to Server
00:04 — [B] NGINX buffers the HTTP request into memory and sends it to Puma
00:04 — [B] Puma accepts the connection, reads the request into memory and queues it
00:05 — [A] Puma starts processing the request, and responds with it to NGINX
00:06 — [A] NGINX throws the response away since the client closed the connection for A
00:06 — [B] Puma starts processing the request, responds with it to NGINX
00:07 — [B] Client receives the response for B
「NGINXをフロントにしてPumaを挟むとNGINXの方でいい感じにしてくれるという話」「ふむふむ」「Pumaでフロー制御までやるのは大変なので、NGINXのフロー制御周りの機能を使って、アプリケーションストリームだけPumaの方に流すとかそんな感じ☺️」
「そしてmax_conns=3
にかかったら即座にエラーを返すようにしたということみたい」「なるほど!」「スレッドプールがフルになってたらどうせさばけないので😆」「諦めが肝心😆」「おそらくNGINXでPumaのスレッドの残数とかを参照して、フロントのNGINXがPumaのステータスに応じて空気を読むことで、Pumaがあふれていたら手前のNGINXのところでリクエストを止めようという話でしょうね」「Pumaの顔色がやばかったら助けてあげる感じですか🤢」
Starting…
[0] 200 - 4.13
[1] 200 - 9.14
[2] 200 - 14.14
[3] 502 - 0.01
[4] 502 - 0
[5] 502 - 0
[6] 502 - 0
[7] 502 - 0
[8] 502 - 0
[9] 502 - 0
Took 14.14 total, avg of 2.74 in thread time, max 14.14, min 0
参考: Module ngx_http_upstream_module
「ステータス502って何だったかな: Bad Gatewayか↓」「502でいいのかというのはあるけど😆、クリティカルなものでなければこれでやれるでしょうね☺️」「案件によっては実際こうしないとキューが無限にたまり続けちゃいますけど、こうしておけば、さばくべきものはちゃんとさばけるようになりますし」「さばけないものはさばけないなりに早めに諦めると😆」
参考: 502 Bad Gateway - HTTP | MDN
⚓Railsガイド「Proプラン」「Teamプラン」
#Railsガイド から『Teamプラン』をリリースしました!! 🆕🚀✨ https://t.co/PxLnzoXLql
マネーフォワード様にβ版をご利用して頂きながら開発できたので、チームで使いやすい形に仕上げられました 🤝💖
本サービスを使った研修内容も公開したので、こちらも合わせてぜひ! 📜 https://t.co/KHPeGwkVHZ pic.twitter.com/z6jsyAMTPd
— 安川要平/Yohei Yasukawa (@yasulab) June 10, 2019
つっつきボイス:「お、安川さんだ!」「私も翻訳で関わっているRailsガイドのProプラン(個人向け)とTeamプラン(法人向けアカウント管理機能と決済一元化など)で、通常のガイドはもちろん誰でも見られるんですが、有料だとこうやって例のAlgolia検索やショートカットキーが使えます😋」「お〜なるほど!」
「こういうのはいいですね〜❤️」「私も少し試す機会がありましたが、ありがたいです🙏」「自分はそんなに頻繁には使わないかもですけど😆、BPS社内のWebチームでみんなが使いたいということであれば試しに契約してもよさそうだし😋」「今度Webチームミーティングで軽く聞いてみましょう😀」
「今の自分はRailsを長く使っていて検索キーワードがだいたい身体に沁み込んでるので、どちらかというと今は高速なAPI検索が欲しいかも😋」「APIdockの記事↓にも書きましたけど確かに欲しいですね😋」「その意味では、RailsガイドのProプラン/TeamプランはRails始めて日が浅い人とか久しぶりにやる人に特に向いている感じですね👍」
「APIのメソッドってときどき別のクラスやモジュールに引っ越したりしますけど、それを追うのって大変ですよね😢」「となると今だとそれを追えるのはAPIdockかな〜」
なお、本日以下の記事も公開されていますね。
参考: 🚀Railsガイド『Teamプラン』をリリース - YassLab 株式会社
⚓truemail: メールアドレスのバリデータgem(RubyFlowより)
# 同リポジトリより
require 'truemail'
Truemail.configure do |config|
config.verifier_email = 'verifier@example.com'
config.whitelisted_domains = ['white-domain.com', 'somedomain.com']
config.blacklisted_domains = ['black-domain.com', 'somedomain.com']
config.validation_type_for = { 'somedomain.com' => :mx }
end
つっつきボイス:「メールアドレスをバリデーションしてくれるgemだそうです」「お〜なるほど!」「自分で書かない方がよさそうなヤツですよね😆」
「どうやらtruemailはメール送信時にも使えるようだ」「あ、そうみたい」「実際に到達可能なメールアドレスかどうかをMXとかに問い合わせてやってくれそう😋」「MXバリデーションってありますね」「メールが届きません疑惑ってよくあるから😆、そういうときに使えるかも」
⚓その他Rails
- 元記事: Anonymous web authentication with Stellar blockchain — Martian Chronicles, Evil Martians’ team blog
つっつきボイス:「Stellerっていう認証方法をこれで初めて知りました」「名前はどこかで聞いたことあるかな🤔」「使ったことないけど😆」「ブロックチェーンでanonymousに認証するみたい」「それが真のanonymousかどうかだけど😆、ブロックチェーンでやる以上はノードが分散している限りはやれるということなんでしょうね☺️」
参考: StellarAuth - Authenticate using your Stellar account - Galactic Talk
参考: ブロックチェーン - Wikipedia
④まで一気にやったあと②がデプロイされるまでの間NOT NULL制約によって新規レコード作成がコケるのですぐさま②をデプロイするぜ!みたいなコードをよく見るけど、レースコンディションあるでって言ってもなぜかレースコンディション起きないように直してはくれない。急いでるんやろなと思てるけど。
— Ryuta Kamizono (@kamipo) June 19, 2019
つっつきボイス:「@kamipoさんのこの話、まさによくあるヤツ☺️」「これはマイグレーションの手順の問題: めちゃデカいテーブルのマイグレーションって一瞬では終わらないので、ALTER TABLEでロックされないようにこういう手順にしたりしますね」「ふむふむ」「でも②を先にやっておかないとコケることがあるよという話」
「まず、①で足すカラムはNULL許容でなければいけません」「それから②の新規レコードをデフォルト値fillで先にデプロイして、その後で③をやらないといけない: でないとデフォルト値fillしている最中にまた新規レコードが作られるとNULLカラムが残っちゃう、すると④のときにコケる😇」
「レースコンディション(競合状態)を発生させないためには、③の前に②をやっておくことが重要: ③の後に②をやることも可能は可能なんですが、それならもう一回③をやってから④をやらないといけない」
参考: 競合状態 - Wikipedia
「まあ例えるなら、昔のLinuxシステムの電源を落とす前にsync
コマンドを3回入力するみたいなものです🤣」「あ〜あの習慣ですか🤣」「自分もsync
コマンド3回的に念のためもう一度やっておくことありますし: 何しろマイグレーションでコケると結構ショックでかいので😇」
参考: sync; sync; sync; haltの伝承 - Qiita
⚓Ruby
⚓injectable: Ruby向けDIライブラリ(RubyFlowより)
# 同リポジトリより
class MyClass
include Injectable
dependency :collaborator
def call
collaborator.submit!
end
end
# 同リポジトリより
class PdfGenerator
include Injectable
dependency :wicked_pdf
argument :html
argument :render_footer, default: false
def call
wicked_pdf.pdf_from_string(html, options)
end
private
def options
return {} unless render_footer
{
footer: {
left: footer,
}
}
end
def footer
"Copyright ® #{Time.current.year}"
end
end
# でこんなふうに使ったり
PdfGenerator.call(html: '<some html here>')
# wicked_pdf依存をオーバーライドしたり
PdfGenerator.new(wicked_pdf: wicked_pdf_replacement).call(html: '<some html>')
つっつきボイス:「以前も似たようなDI gemを見たことある気がするけど?🤔」「これは初めてでしたが、似たようなのいっぱいありそうではありますね😅」「dependency :collaborator
とかするといい感じにやってくれると」「gemでやるほどのものだろうかという気はしますけどっ😆」「initialize
メソッドとか生やしてくれるんなら、まあとても使いたい人が使えばいいのかなと☺️」
「以下もbehavesも趣旨が近いのかなと思ったんですが」「これはまた別のものっぽいですね😆」「やっぱり😅」
# 同リポジトリより
class Predator
extend Behaves
implements :hunt
end
class Prey
extend Behaves
implements :run, :hide
end
class Shark
extend Behaves
# Sharkは`Predator`でもあり`Prey`でもある
behaves_like Predator
behaves_like Prey
end
「implements
とかあるあたりにJavaの匂いを感じる😆」「injectもできるところは上と似ていなくもないけど」「これを使って効果的に読みやすくなるかどうかはまた別かな〜: 既にこれでいっぱい書かれていて後の人はコピペすればできる、ぐらいになってればいいけど、新たにこれを入れようとはあまり思わないし😆」
⚓Rubyのパイプライン演算子
- Q&A: Ruby2.7のpipeline operatorで+や-等の演算子をはじいたのはなぜなんでしょうか? - Quora
- Feature #15799: pipeline operator - Ruby trunk - Ruby Issue Tracking System -- たぶんこれかなと
pipeline operator の第一印象は「いや冗談でしょ」なんだけど、実際に入ってみると「意外とアリなのか……? いや、でも……」みたいなシーソーゲームを繰り返して結論が出ない。
こんなものをいきなり投入判断できる matz のセンスと胆力は健在で、Ruby は生きているな。
— Yusuke Endoh (@mametter) June 14, 2019
こういうのも動きましたhttps://t.co/Fop1eQXHfP pic.twitter.com/dvmAGgC5nU
— 𝓜𝓲𝔂𝓪𝓰𝓲 (@hanachin_) June 14, 2019
つっつきボイス:「演算子、はじかれたっぽい😆」「話があちこちで進んでるっぽくて、今どうなってるのか時系列を追うのつらいです😭」「Matzの『積極的に読みにくさに貢献してますね』というコメント🤣」「『必要性が高くない』も🤣」「まあパイプライン演算子が入ったところで使う人は少なそうですけど☺️」
「パイプライン演算子は順番通りに書き下しっぽく書けるから、たとえばコマンドラインなんかでマルチラインで入力して、最後にCtrl-Dと入力すると実行されるみたいな使い方のときにいいかも」「あ〜それあるかも」「手元でスクリプトのRubyをcat -
とかで開いて、そこにコピペして最後にCtrl-Dとか、そういうふうにできるんだったらあってもいいかも😋」「pryとかで使ったりとか」「まぁ使うかというと使わないかな〜😆」
「そしてmametterさんのパイプライン演算子の歴史、日英両方で書かれてましたね」「偉大な仕事!」
参考: パイプライン演算子の歴史 - まめめも
参考: A Brief History of Pipeline Operator - mamememo
「パイプライン演算子だとこういうふうに実行順どおりに書けますからね↓」「うんうん」「エディタでなら普通に書きますけど、シェルだとReturn押したら戻ってこれないし🤣」「そうそう🤣」「だからパイプラインでこうやってシェルで入力できるなら意外にいいかも?」「まあドット.
で書いてもできますけどっ😆」「😆」
# 同記事より
astonishing_argument_x
|> fantastic_process_f
|> marvelous_process_g
|> wonderful_process_h
「外してるかもしれませんが、yield_self
ことthen
にこの|>
記号当てたらだめかなって」「パイプライン演算子はメソッドをチェーンしたいという目的があるからyield_self
だとまた違うかな🤔」「やはり〜😅」「左から右に処理を書けるのはいいかも」
⚓OmniAuth::Apple(Ruby Weeklyより)
つっつきボイス:「さっそくAppleの匿名認証に乗っかってきた😆」
参考: アップル「匿名認証機能」がもたらす巨大衝撃 | スマホ・ガジェット | 東洋経済オンライン | 経済ニュースの新基準
⚓その他Ruby
# 同回答より
class C
private
def private_method
end
end
こういう質問への一次回答を読めてとてもうれしいです😂。
つっつきボイス:「endがないのはアクセス修飾子だから?、と思ったらC++に似せたのか!」「インデントも浅くて済むし」「そういえば先週private
の後のインデントってどうよって話になりましたけど(ウォッチ20190617)、Matzの回答に沿うならprivate
の後の行はインデントを変えないのが正当?😆」「Matzはインデントしてない、やったね😋」「じゃこれで行きましょう😆」
⚓Ruby trunkより
⚓0.nonzero?
はnil
を返す(Ruby Weeklyより)
つっつきボイス:「上のissueはRuboCop作者の以下の記事で知ったんですが、下の方が読みやすいです」「0.nonzero?がnil
を返す😆」「1.nonzero?
は1
を返す🤣」
# 同記事より
0.zero?
# => true
0.nonzero?
#=> nil
1.zero?
#=> false
1.nonzero?
#=> 1
「たぶんif
文の中でif a = 1.nonzero?
みたいに代入する形にするヤツで、1.nonzero?
があれば自分自身を返して、なければnil
を返すみたいな、Railsで言うpresence
的な使い方なのかな、たぶんね😆」「実際Rubyのbooleanとして使う分には問題ないし☺️」「Rubyではnil
とfalse
以外はtrue
でしたね」
参考: Object.presence
参考: Railsのpresence
メソッドが便利
前編は以上です。
おたより発掘
#週刊Railsウォッチ で #Railsガイド の新サービス『Proプラン』『Teamプラン』をご紹介していただきました...!! ありがとうございます!! 😻✨ #YassLabhttps://t.co/16s6fkn3Pi https://t.co/X9ud2ar6qI pic.twitter.com/H715kyJRTb
— 安川要平/Yohei Yasukawa (@yasulab) June 25, 2019
rails 6.1 で入る ActionView::Component を良さそうって眺めてた。
Symfony 1.x系の項目を見て、微妙なお気持ちになってる(この感想には個人的な体験が影響してます)https://t.co/RDbILlPklW— EREFY (@EREFY) June 25, 2019
バックナンバー(2019年度第2四半期)
週刊Railsウォッチ(20190618-2/2後編)決済の分散トランザクション、フロントエンドのMicro Frontendアーキテクチャ、GitHubのコードジャンプほか
- 20190617-1/2前編 マルチプルデータベースガイドが追加、mmcと「Ruby 3の型解析に向けた計画」、Ruby 2.6のCSVライブラリはいいほか
- 20190611-2/2後編 Dockerfileベストプラクティス、DBの冗長化、jQueryとの付き合い方ほか
- 20190610-1/2前編 RailsConf 2019のスライドを追う、Railsのファイル添付gem、Railsの技術的負債を返す、RuboCop 1.0間近ほか
- 20190604-2/2後編 Cloudflare Workers KVの可能性、PostgreSQL 12 Beta 1、Bootstrap 5でjQuery廃止ほか
- 20190603-1/2前編 Ruby 2.7.0-preview1リリース、RailsConf 2019を追う、pluckとincludesの組み合わせに注意、deep_transform_keys追加ほか
- 20190521-2/2後編 サーバーレスクラウドのベンチマーク比較サイト、VueJSパフォーマンス向上、GraalVM 19.0ほか
- 20190520-1/2前編 Evil Martians愛用の便利gemたち、render_asyncでRails表示を高速化、split gemでA/Bテストほか
- 20190514-2/2後編 Webpackerを現場で使う、Dockerfileベストプラクティス、SONYのユニークID生成ツールsonyflakeほか
- 20190513-1/2前編 6.0の地味に嬉しい機能、ActiveModelエラーの扱いが変更、Railsのリクエスト/レスポンスをビジュアル表示ほか
- 20190508-2/2後編 サロゲートキーのコスト、Cloud RunとLambdaの違い、miniredis、CSS Subgridほか
- 20190507-1/2前編 Rails 6.0.0rc1が4/24にリリース、Rails 6の新メソッド群、RubyリポジトリがCgitに移行ほか
- 20190416-2/2後編 最近のRDBMS市場、Flutterがデスクトップにも向かう、書籍『失敗から学ぶRDBの正しい歩き方』ほか
- 20190415-1/2前編 Railsバージョンアップに便利なstill_life gem、Zeitwerkの改修進む、named_capture追加ほか
- 20190409-2/2後編 Ruby 2.3系サポート終了、Thoughtbotのコーディング指南書、PostgreSQLのgenerated column、Chromebrewほか
- 20190408-1/2前編 RubyKaigiの予習資料、Rails「今年ベストのプルリク」、numbered parametersの議論ほか
- 20190402-2/2後編 Apache Arrowとは何か、prop drillingはアンチパターン、Node-REDほか
- 20190401-1/2前編 Rails 5.2.3/5.1.7がリリース、Railsdmの「Railsの正体」、Ruby 2.7のnumbered parameter、新元号「令和」ほか
今週の主なニュースソース
ソースの表記されていない項目は独自ルート(TwitterやはてブやRSSなど)です。