【感想】「スッキリわかるSQL入門」を読んで
概要
SQLはバックエンドエンジニアに必須スキルであり、今回は知識の再確認のため、ミック本の次のステップとして有名な「スッキリわかるSQL入門」を読んだ感想です。
良かったところ
- 基礎知識が整理できた
- 一部知らないことを知れたこと
学んだこと
サブクエリをINSERT文で利用する
あまり使う機会はなさそうですが、サブクエリを用いてデータ追加する方法です。
# 平均所有ポイントより高いユーザーを高ポイントテーブルに追加 insert into high_point_users (id, name, point) select id, name, point from users where point > (select avg(point) from users);
他のテーブルに登場する行のみ抽出したい
これは頻繁に使うパターンです。
# 高ポイントテーブルに登場するユーザーのみ抽出 select name from users u where exists ( select * from high_points_users hpu where u.id = hpu.id );
truncate
はdelete
より高速
定番の知識ではありますが、テーブルの全件を削除したい時には、truncate
がdelete
より高速です。
今回はその理由をちゃんと理解することができました。
truncate
:記録を残さずに全行削除するため高速(しかし、ロールバックできない)delete
:行ごとにログ記録が行われるため、大量のデータを削除する際にはパフォーマンスが低下する
まとめ
SQLの基礎知識を改めて整理するために、「スッキリわかるSQL入門」を読んだ感想を簡単にまとめました。新しく知られた知識はほとんどなかったですが、知識の再確認ができたことにより、確実に身についているとわかり自信が持てました。今後も、新しい知識だけでなく、既に知っていることの再確認は定期的にやっていこうと思います!
RailsアプリをDocker化してみた
はじめに
この記事では、Dockerfile
、docker-compose.yml
を作成することで、既存のRailsアプリをDocker化する方法を紹介します。
前提条件
- Docker Desktopがインストールされていること
- 対象となる既存のRailsアプリが存在すること
- DBはPostgreSQLを使用すること
Dockerfileの作成
RailsアプリのルートディレクトリにDockerfile
を作成し、下記の内容を記述します。
FROM node:16 as build-stage FROM ruby:3.0.2 # Install Node.js and Yarn RUN mkdir -p /opt COPY --from=build-stage /opt/yarn-* /opt/yarn COPY --from=build-stage /usr/local/bin/node /usr/local/bin/ COPY --from=build-stage /usr/local/lib/node_modules/ /usr/local/lib/node_modules/ RUN ln -s /opt/yarn/bin/yarn /usr/local/bin/yarn \ && ln -s /opt/yarn/bin/yarn /usr/local/bin/yarnpkg \ && ln -s /usr/local/bin/node /usr/local/bin/nodejs \ && ln -s /usr/local/lib/node_modules/npm/bin/npm-cli.js /usr/local/bin/npm \ && ln -s /usr/local/lib/node_modules/npm/bin/npm-cli.js /usr/local/bin/npx # Setup Rails App RUN apt-get update -qq && apt-get install -y \ build-essential \ libpq-dev RUN mkdir /myapp WORKDIR /myapp COPY Gemfile /myapp/Gemfile COPY Gemfile.lock /myapp/Gemfile.lock RUN bundle install COPY . /myapp
イメージ軽量化のためマルチステージビルドしていますが、ここでは紹介しないので下記を参考にしてください。
docker-compose.ymlの作成
Railsアプリのルートディレクトリにdocker-compose.yml
ファイルを作成し、以下の内容を記述します。
version: "3" services: db: image: postgres:12 environment: POSTGRES_USER: postgres POSTGRES_PASSWORD: postgres POSTGRES_DB: postgres volumes: - db_data:/var/lib/postgresql/data web: build: . command: bundle exec rails s -p 3000 -b '0.0.0.0' volumes: - .:/myapp ports: - "3000:3000" depends_on: - db stdin_open: true tty: true environment: DB_HOST: db DB_NAME: myapp DB_USER: postgres DB_PASSWARD: postgres volumes: db_data:
config/database.ymlの編集
Railsアプリのconfig/database.yml
ファイルを編集して、PostgreSQLを使用するように設定します。
default: &default adapter: postgresql host: <%= ENV['DB_HOST'] %> database: <%= ENV['DB_NAME'] %> username: <%= ENV['DB_USER'] %> password: <%= ENV['DB_PASSWARD'] %> pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %> development: <<: *default database: myapp_dev test: <<: *default database: myapp_test production: <<: *default database: myapp_prd
動作確認
下記のコマンドで、Dockerコンテナを起動します。
docker-compose build docker-compose up
次に、データベースの作成です。
docker-compose run web rake db:create
コンテナ内でマイグレーションする。
docker-compose exec web bash > rails db:migrate
http://localhost:3000/
にアクセスして、アプリケーションが正常に動作していることを確認できれば完了です!
まとめ
この記事では、RailsアプリをDockerコンテナで実行するための基本的な設定を行いました。非DockerなものをDocker化するのは骨が折れると思いますが、Docker環境での開発のメリットは大きいので移行しておくいいかと思います!
P.S. 本番環境をEC2→ECSに移行するのは結構大変そう...
Rubyのoptparseを使ったコマンドライン引数の解析
はじめに
Rubyの標準ライブラリであるoptparseは、コマンドライン引数の解析を簡単かつ効率的に行うためのライブラリです。optparseの基本的な機能について説明し、使い方を紹介します。
基本的な使い方
使用するために、optparseを読み込みます。
require 'optparse'
on
メソッドでオプションを定義します。また、どのオプションが指定されたかを保持するためにハッシュを使用します。
opt = OptionParser.new option = {} opt.on('-f', '--file FILENAME', 'input file') { |v| option[:f] = v } opt.on('-m', '--month MONTH', 'input the month(1-12)') { |v| option[:m] = v } opt.parse(ARGV) puts "-f:#{option[:f]}, -m:#{option[:m]}"
上記のコードを実行するとコマンドライン引数を受け取れていることがわかります。
$ ruby optparse.rb -f input_file -m 1 -f:input_file, -m:1
定義されているオプションも簡単に出力できます
opt.on('-h', '--help', 'Show help message') { puts opt }
カレンダーを作る
Rubyでカレンダーを作成するのにoptparseを使ってオプション-m
を実装しました。
# オプションなし $ ruby calendar.rb 4月 2023 月 火 水 木 金 土 日 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 # オプションで1月を指定 $ ruby calendar.rb -m 1 1月 2023 月 火 水 木 金 土 日 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
なお、コードは下記になります。
require 'date' require 'optparse' def print_calendar(month = nil) year = Time.now.year # 現在の年 month ||= Time.now.month # nilなら現在の月 first_day = Date.new(year, month, 1) # 始まり last_day = Date.new(year, month, -1) # 終わり print_header(month, year) print_first_spaces(first_day.wday) (first_day..last_day).each do |date| print date.strftime('%e') print(date.sunday? || date == last_day ? "\n" : ' ') end end def print_header(month, year) puts " #{month}月 #{year}" puts '月 火 水 木 金 土 日' end def print_first_spaces(wday) if wday.zero? # 日 print ' ' elsif wday == 1 # 月 print '' else # 火〜土 print ' ' * (wday - 1) end end def valid_month(month) month && (month >= 1 && month <= 12) end # コマンドライン引数を取得 opt = OptionParser.new option = {} opt.on('-m MONTH', 'the month(1-12)') { |v| option[:m] = v } opt.parse(ARGV) target_month = option[:m]&.to_i # オプションのチェック if target_month && !valid_month(target_month) puts "#{target_month} is neither a month number (1..12) nor a name" return end # 出力 if target_month print_calendar(target_month) else print_calendar end
まとめ
optparseは、オプションの定義やヘルプメッセージの生成が容易に行えるため、コマンドラインツールやスクリプトを開発する際に非常に便利です。ぜひ使ってみてください。
【感想】「プロを目指す人のためのRuby入門」を読んで
概要
Rubyのキャッチアップをすることになり、Prodateで学習した後の入門書で有名な「プロを目指す人のためのRuby入門」を読んだ感想です。
良かったところ
さすが有名な著書ということもあり情報量が素晴らしく良かった。よく使われるテクニックが載っているので、たくさんあるRubyの文法から重要なもの掻い摘んで勉強できて良かった。
悪かったところ
特に悪いと思ったわけではないが、、、 入門書の割にボリュームが凄いので、Ruby初学者は全てマスターしようとせずに、こんな書き方があるんだーくらいで読み進めていくのが良さそうでした。
学んだこと
&.
ぼっち演算子
メソッドを呼び出されたオブジェクトがnilでない場合はその結果をnilだった場合はnilを返す。
str&.upcase # strがnilならばnil、nilでないならupcaseの結果となる
||=
nilガード
変数がnilまたはfalseであれば値を代入する。
sum ||= 10 # sumがnilまたはfalseならば10を代入する
これは、下記のように評価されるから
sum || sum = 10
!!
を使った真偽値の型変換
!!
を使うと、?
で定義したメソッドを短く書ける。
def user_exists? !!find_user end
難しかったこと
文法が多すぎるので、どの書き方がよく使用されるか見極めるのが難しかった。現場ではマニアックな文法に出くわす機会が多そうな言語なので、その都度調べて習得していく。
まとめ
Rubyの文法は多すぎて習得するのは難しいが、その中でも重要なものについては特筆されていたので学習しやすかった。頻繁に使われそうなものはこの機会に習得して今後のコーディングに役立てていきたい。
覚えておきたいvimとtmux操作
概要
VSCode
等を使用しているとvim
やtmux
については使用する機会は少ないが、vim
はサーバー内での設定ファイルの変更で、tmux
はサーバーのログ監視で活躍しそうなイメージがあるので、基本操作について整理しておく。
vim
たくさんあるvimのキーバインドやコマンドで絶対に覚えておきたいものをまとめてみました。
:set number
、:set list
は結構使っています。
visual block
モードは覚えてもすぐ使い方を忘れるので今回はリストから外しました。
キーバインドorコマンド | 説明 |
---|---|
esc | Normalモード |
i | Insertモード |
:wq | 保存して終了 |
:q! | 保存せず終了 |
dd | 1行削除 |
{数値}dd | {数値}行削除 |
yy | 1行コピー |
{数値}yy | {数値}行コピー |
P | ddやyyで保持した行をペースト |
:set number | 行番号を表示 |
:set list | 制御文字を表示 |
gg | ファイルの先頭に移動 |
G | ファイルの最後に移動 |
{数値}gg | {数値}行目に移動 |
gg | ファイルの先頭に移動 |
/{検索したい文字列} | 文字列を検索 |
n | 次の検索結果に移動 |
N | 前の検索結果に移動 |
tmux
tmuxは使い慣れていないので、これぐらいなら覚えられるだろうとまとめてみました。
コマンド | 説明 |
---|---|
tmux | tmuxを起動 |
tmux ls | セッション一覧を表示 |
tmux a -t {セッション名} | 指定のセッションにアタッチ |
Control + b d | デタッチ |
tmux kill-server | tmuxのシャットダウン |
Control + b % | 左右に分割 |
Control + b " | 上下に分割 |
exit | ペイン破棄 |
Control + b ↑↓←→ | ペインを移動 |
Control + b { | ペインの順序を前方向に入替 |
Control + b } | ペインの順序を前方向に入替 |
tmux
の使用例として2つのログ監視で使用するデモを行いました。ターミナル複数並べるより見やすいです!
下記がログ出力用のシェルスクリプトです。
#!/bin/bash logfile="test.log" while true; do random_number=$((RANDOM % 3 + 1)) case $random_number in 1) message="testlog A" ;; 2) message="testlog B" ;; 3) message="testlog C" ;; esac echo "$(date) - $message" >> $logfile sleep 2 done
まとめ
これぐらいは覚えておいた方がいいと思ったものをまとめてみました!
とは言っても使ってないと忘れるので、たまにはvim
でコーディングしてみるのもアリかなって思ってます(笑)