プログラミング -> Ruby on Rails

Rails で datetime型 にテキストをそのまま入れる形で find_or_initialize_by でレコード操作したらタイムゾーンが異なっていたためすべて新規レコードになってしまった

前提 find_or_initialize_by にこだわるのは本質的ではなく、find_by や where などでも同じです。本質はタイムゾーンの違いです。 結論 具体例を見たほうが早いと思いますので、載せます。 NG な例 user = User.find_or_initialize_by( name: 'hoge', submi…

Activerecord-Import で大量のデータをバルクインポートしようとすると PostgreSQL が落ちる

Activerecord-Import とは github.com 結論(どうするか) インポート時に batch_size オプションを指定してやる。 具体例 User.import!(users, batch_size: 10000) PostgreSQL が落ちたときのエラーメッセージ PQconsumeInput() SSL SYSCALL error: EOF det…

.dot ファイル (Graphviz) を PDF に変換する方法

結論 Graphviz (CLI) はインストール済みであるとします。 $ dot -Tpdf /path/to/hoge.dot -o /path/to/fuga.pdf 具体例 Rails ERD では dot で出力が可能なところ、その dot を PDF に変換するために有用です。 「Rails ERD で最初から PDF に出力すると Gi…

Rails でテスト環境の migration が更新されない場合は schema.rb がそのままの可能性が高い

結論 標題通りです。 マイグレーションのコードをテストと同時に書いていた際にハマりました。直接コマンドで db:migrate(:reset) すると schema.rb を見に行き、schema.rb の更新作業が走っていない場合には例えば UNIQUE制約 などが変更されません。 DBが…

Ruby で Google::Apis::DriveV3 を用いて Google Drive のファイルを操作する方法

前提条件 サービスアカウントを用いて認証を行うとします 使う gem google-api-client google-apis-sheets_v4 でもいいですが、名前が適切な方が誰からも分かりやすいので google-api-client がよいと思います 注意事項 当該ドライブ(フォルダ等)に、サー…

Rails ERD で継続的に diff を取って pdf をコミットする方法

結論 dot フォーマットの diff を取り、差分があった場合に PDF を更新(生成)する PDFファイル のバイナリは、同じスキーマの場合でも生成のたびに異なるバイナリファイルになり、diff が出てしまうから dot フォーマットならば、同じスキーマに対して常に…

macOS で Bundler で pg gem をインストールしようとする際に Can't find the 'libpq-fe.h' header というエラーが出る場合の対処方法の一つ

前提 Intel Mac pg のバージョンは 1.4.6 Ruby のバージョンは 3.2.2 PostgreSQL のバージョンは 15 結論 bundler の config にて、build.pg に対して --with-opt-dir="/usr/local/opt/libpq" を設定する。 具体的な設定方法 設定方法は 2つ あります。 1. b…

Rails で特定のディレクトリ配下にある Rakeタスク ファイル内のタスクを全て実行する

状況 以下の3つの Rakeタスクファイル があるとします。 lib/tasks/foo/a.rake lib/tasks/foo/b.rake lib/tasks/foo/c.rake それぞれのファイル内には以下の名前のタスクが定義されているものとします。 a b c この 3つ のタスクを抽象的なコード*1で実行し…

Rails で routes.rb にデータベースのデータを使うロジックを書くと CI で落ちる(ことがある)

結論 表題通り。 ハマった 落ちるときのエラーは次のような感じ。 rails aborted! ActiveRecord::NoDatabaseError: We could not find your database: hogehoge_test. Which can be found in the database configuration file located at config/database.ym…

Capybara で現在のトップの URL を取得する方法

結論 Capybara.current_session.server.base_url 実例 Capybara が走っているところで適当に binding.irb して、確認できます。 [10] irb> Capybara.current_session.server.base_url => "http://127.0.0.1:37539"

Capybara + Headless Chrome で JavaScript を実行する方法

結論 page.execute_script を用いる*1。 具体例 page.execute_script("document.getElementById('foobar')") 補足 これを利用すればページスクロールをしたり、ページスクロールをした上でスクリーンショットを撮影したりできると思います 引数が「スクリプ…

Rails の jbuilder でハッシュが完成された形で収められているインスタンス変数を愚直にそのまま返す書き方

前提 以下のように定義されていて、そのまま返したいだけの場合です。 @hello = { foo: [ { a: "b"}, { c: "d"}, ], (以下省略) 結論 json.merge! @hello

"establish_connection :outer_database" の記述により CI で データベース接続エラーが出て 6時間 溶かした

状況 Rails にて外部データベース(複数データベース)を用いている状況で CI*1 で RSpec を回そうとしました。すると、データベース接続エラーがどうやっても解消できず、6時間溶かしました*2。 結論(解決方法) モデルのファイル中に establish_connectio…

Letter Opener を WSL2 で用いると、ローカルファイルが開かれる時にファイルが見つからない(当然)

Letter Opener github.com ローカルファイルが開かれる 例えば、tmp/letter_opener/1648090024_918493_6bde588/rich.html のようなファイルが開かれるとします。 その時、WebブラウザがリクエストするURLは file://home/USERNAME/.ghq/github.com/FOO/BAR/tm…

Capybara で複数回の同じ send_keys を送るときのスマートな書き方

結論 find('#search').send_keys(*([:backspace] * 8)) 参考 2、3回ぐらいならば以下で良いと思います。 find('#search').send_keys(:backspace, :backspace, :backspace)

Capybara で要素が「存在する」「存在しない」をテストする方法

結論 have_selector マッチャを用いる。 例 expect(page).to have_selector "#submit" expect(page).not_to have_selector "#cancel" 補足 非表示要素を取り扱う際などは *options で様々な設定が可能です。 chaika.hatenablog.com

rails console をするときだけ "You must use Bundler 2 or greater with this lockfile." エラーが出るときの解決方法

gyazo.com 結論 $ spring stop 参考(答え) github.com

Ruby にてハッシュの「キーだけ」を加工したい場合には transform_keys メソッドを用いる

結論 たとえば、{ foo: 'bar', hoge: 'fuga' } というハッシュがあったとします。このハッシュの foo および hoge のそれぞれを大文字に変更したい場合には次のようにします。 { foo: 'bar', hoge: 'fuga' }.transform_keys { |key| key.upcase } 上記の戻り…

Capybara (RSpec) の System Spec にて Selenium + Chrome を使っている際に Cookies の内容をチェックする方法の一つ

結論 page.driver.browser.manage.all_cookies 注意点 page.driver.browser.manage.all_cookies は Array オブジェクトであり、各要素は以下のような key-value を含むハッシュです {:name=>"foo", :value=>"bar", :path=>"/", :domain=>"127.0.0.1", :expir…

Capybara でテストの対象を特定のセレクタ範囲だけに絞りたいとき

結論 within を用います。 例 例えば、以下のような HTML があったとします。 (省略) <div data-testid="target_area"> <p>foobar</p> <p>fugafuga</p> </div> <div data-testid="not_target_area"> <p>barbar</p> <p>hogehoge</p> </div> このとき <div data-testid="target_area"> ~ </div> の範囲内だけをテストの対象にしたい場合には次のように書きます。 within find('[data-testid="tar…

Capybara で CSSフレームワーク を用いた SPA をテストするのがつらい(レンダリング確定のためにウィンドウサイズ変更したり)

理由 「たまに落ちる」が発生する sleep や rspec-retry を使わないとうまくいかないことがある sleep や rspec-retry は極力使うべきではない*1と思うので、超苦肉の策 マイナーなメソッドを探さないといけないことがある 経験上、検索してもなかなかたどり…

Rails で URL に付与されているパラメータ(クエリ)をハッシュに変換する

結論 おそらくこれが一番スマートだと思います。 sample_url = 'https://example.com/?foo=bar&hoge=fuga&this=that&here=there' query = URI.parse(sample_url).query #=> "foo=bar&hoge=fuga&this=that&here=there" query_by_hash = Rack::Utils.parse_que…

rails_same_site_cookie を使っていると localhost で Firefox にて cookie が保存されなくなった

結論 文字通りです。 gyazo.com どうするか Issue では以下の方法が推奨されています。 github.com また、ngrok などを使って https で開発するのも一つの方法だと思います*1。 補足 2022年3月9日(水)現在の挙動です 起きたバージョンは v99 です Chrome …

Rakeタスク で引数を取る時にクォートで囲まないと zsh ではエラーが出る

実例 クォートで囲まないと NG。 $ bundle exec rails foo_task:barbar[hoge,fuga] zsh: no matches found: foo_task:barbar[hoge,fuga] クォートで囲むと OK。 $ bundle exec rails "foo_task:barbar[hoge,fuga]" (正常処理)

Rails で i18n が反映されないときに試すこと

結論 Rails サーバを再起動する

Rails で Active Elastic Job のバージョンを上げると Sprockets::Rails::Helper::AssetNotPrecompiled エラーが出ることがある

Active Elastic Job とは github.com バージョンアップすると Sprockets::Rails::Helper::AssetNotPrecompiled になることがある Dependabot でバージョンアップのプルリクエストが作られることがあります。その際にタグの単位ではなくコミットハッシュの単…

Rails を Docker 環境で動かす際にローカル環境と共存させるとエラーが出る

結論 表題のとおりです。 .bundle とか tmp/ とか vendor/ とかがローカル環境と混ざるとエラーが起き得ます*1。Docker 環境で使うディレクトリは Docker 環境だけで使いましょう。ローカル環境で使いたい場合には別途ディレクトリを作りましょう。 *1:gem …

RSpec (Capybara) でアラートモーダルを操作する方法

アラートモーダルとは こういうやつです*1。 gyazo.com 結論 「はい」の選択肢を選ぶとき page.accept_confirm 「いいえ」の選択肢を選ぶとき page.dismiss_confirm ドキュメント www.rubydoc.info *1:「アラートモーダル」はおそらく正しい呼び方ではないで…

Rails で CI 中の db:create 時に LoadError: cannot load such file -- rexml/document が出る場合

結論 rexml gem を追加します。 具体例 Gemfile の group :test に以下のように追加すればよいでしょう。 group :test do (省略) gem 'rexml' (省略) end 参考 stackoverflow.com

Rails のコードの中で突然現れる reset_password_email というメソッドはどこで定義されているのか

結論 Sorcery が定義しています*1。 Sorcery とは 公式ドキュメント *1:Sorcery を使っている場合。使っていない場合にこのメソッド名を使うと将来的に衝突する可能性はあります

Powered by はてなブログ