20200531のRailsに関する記事は16件です。

Rails 単数リソース resourceによるルーティング

単数リソース

resourcesメソッドは7つの基本アクションに対するルーティングを一括して設定するメソッドです。
うんそれはわかってる。でもresourceってなんだ..."s"付け忘れてない?
となったので、本日は単数リソースresourceについてまとめてみます。

見た目ではsがついてるかついていないかですが、働きは結構違います。

あるシステムについて考える

管理ユーザーと一般ユーザーのいるシステムを考えます。
一般ユーザーはログイン後、自分のアカウントのみを閲覧、管理することができます。
この場合resourcesでrouteを設定すると以下のように設定が行われます。

resources :users
HTTP パス コントローラ#アクション
GET /users users#index
GET /users/new users#new
POST /users users#create
GET /users/:id users#show
GET /users/:id/edit users#edit
PATCH/PUT /uses/:id users#update
DELETE /users/:id users#destroy

考えるべきこと

先ほども言った通りユーザーは自分のアカウントしか閲覧、管理することができません。
自分のアカウントしか見れないのであればユーザーを一覧表示する、indexアクションは不要であることがわかります。

じゃあどうする?

まず初めに出てくるのはonly, exceptでindexだけ外せばいいじゃん。
その通りです。それで全てオッケーでしょうか?
もう一度routeを確認しましょう。

HTTP パス コントローラ#アクション
GET /users/:id users#show
GET /users/:id/edit users#edit
PATCH/PUT /uses/:id users#update
DELETE /users/:id users#destroy

ここで考えるべきはパスの:idです。
ユーザーが自分のアカウントを閲覧、管理できるのはログインしている時です。
ログインをしているということはユーザーのid属性はユーザーのセッションオブジェクトから取得できる。
⇨ URLのパスにidパラメータを入れる必要はない!!
ということがわかります。

つまり目指すべきパスは上の表から:idをなくしたものです。

ここで満を時してresourceが登場します

単数リソースのためのルーティング

ここで単数リソースを使うことで以上のようなニーズに対応したルーティングを実現!!

resource :user
HTTP パス コントローラ#アクション
GET /user/new users#new
POST /user users#create
GET /user users#show
GET /user/edit users#edit
PATCH/PUT /user users#update
DELETE /user users#destroy

以上のように:idとindexアクションのないルーティングをresourceメソッドを使って
設定することができるんですね。
また一つ学ぶことができました。

本日の記事はおしまい。

100日後に一人前になるエンジニアの連載11日目でした。

1人前のエンジニアになるまであと89日

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【マークアップ 】デザインボタン

概要

ボタンに少しデザインを付けることで、サイトがカッコ良くなる〜:laughing:
と思い実装しました!

今回紹介するのは、立体的に見えて押し込み式のボタンとなります:bulb:

実装

views/index.html.haml
.btn
  .new__dispaly--commit
  = f.submit "Submit", class:"commit-btn"
index.scss
  .btn {
    input.commit-btn {
      display: inline-block;
      position: relative;
      padding: 0.5em 1.4em;
      text-decoration: none;
      background: #1d4d8b;/*ボタン色*/
      color: $white;
      border-bottom: solid 5px #123158;/*ボタンの下 色*/
      border-right: solid 5px #5375bd;/*ボタンの右 色*/
    }
    input.commit-btn:before {
      content: " ";
      position: absolute;
      bottom: -5px;
      left: -1px;
      width: 0;
      height: 0;
      border-width: 0 6px 6px 0px;
      border-style: solid;
      border-color: transparent;
      border-bottom-color: $white;
      }
    input.commit-btn:after {
      content: " ";
      position: absolute;
      top: -1px;
      right: -5px;
      width: 0;
      height: 0;
      border-width: 0px 6px 6px 0px;
      border-style: solid;
      border-color: white;
      border-bottom-color: transparent;
    }
    input.commit-btn:active {
      /*ボタンを押したとき*/
      border:none;
      -webkit-transform: translate(6px,6px);
      transform: translate(6px,6px);
    }
    input.commit-btn:active:after, input.commit-btnt:active:before {
      content: none;/*ボタンを押すと線が消える*/
    }
  }

実装結果

ボタン:静止画像

スクリーンショット 2020-05-31 20.57.38.png

ボタン:動画 

※Gyazoで撮影していますので、タイミングによっては見れないかもしれません:cry:

https://gyazo.com/d5c37521452af8a951b69bf658ac2f53

感想

HamlとScssで簡単実装できました!
皆様もぜひ活用してください:laughing:

参考

https://saruwakakun.com/html-css/reference/buttons

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

プログラミング未経験化学系大学院生がWeb系企業に新卒で内定をもらうまでの記録

はじめに

はじめまして!
就職活動の結果、全くの未経験の状態からWeb系自社開発企業に内定をいただくことができたので、記録を残しておきます。
中途ではなく、新卒のエンジニア職での採用になります。他業種からエンジニアに転職されている方の記事は多く見かけましたが、新卒についての情報は少ないと感じたので記事化しようと思いました。もちろん転職活動に取り組んでいる方にも参考になる内容だと思います。

学習を始める前の状況

  • 某私立大の大学院生、化学系の研究をしている
  • 研究室では完全なポンコツで、業績としては国内の小さな学会で1回発表しただけ
  • 月~土は10時から23時くらいまで研究漬け(いわゆるブラック研究室)
  • 2020年5月現在で大学院修士2年生、就活的には”21卒"と呼ばれる世代
  • 研究でも学部時代もプログラミングには一切触れていない
  • SIerとかWeb系といった言葉自体を知らない本当に0の状態からスタート

読んでほしい人

  • 現在、Web系エンジニアを目指し就職活動に取り組んでいる人
  • これからWeb系エンジニアになりたい人
  • なんとなくIT業界に行きたいと思ってる人
  • 研究室で苦しんでいる大学(院)生

伝えたいこと

相性の合わない研究室に入ってしまい、挫折して絶望していた自分が、新しいステージでやり直すという思いでプログラミングを勉強し、エンジニアとして再スタートすることができました。
この記事を通して、色々な状況で苦しい思いをしている人に、分野を変えるのはいつからでも遅くはないと伝えたいです。

就職活動を始めてから内定をもらうまで

基本情報技術者試験を受ける(2019年10月)

2019年の夏ごろ、自分の研究分野への才能の無さを痛感し、一念発起してIT業界に就職しようと考え始めました。完全な未経験だったので、とりあえず勉強しとこうと思い、7月くらいに基本情報技術者の試験に申し込みました。
この学習方法についてはまた他の記事で書こうと思いますが、3ヶ月半ほどの学習で合格しました。

資格の有無が内定に直結したとは思わないですが、ここで広く浅く学んでおいたのは後の学習に活きましたし、面接で話すネタにもなりました。

研究のかたわら情報収集(2019年11月~12月)

基本情報の試験が終わってから年末くらいまでは研究が忙しくなり、平日は研究、休日は合同説明会などで情報収集をしてました。

他にも勝又健太さん(@poly_soft)のYouTubeを観たりしてました。
このあたりでSIerとWeb系の違いを知り、Web系の企業に行きたいなと思いつつもプログラミングをしたことがないので無理かな、、、と思ってました。

初めてプログラミングに触れる(2020年1月)

年末年始で時間があったのでふと思い立ってProgateやドットインストールを始めました。
- Progate HTML/CSS
- ドットインストール Bootstrap
- Progate JavaScript
- Progate jQuery
- YouTube動画を見ながら模写コーディング×2
  - https://youtu.be/9cKsq14Kfsw
  - https://youtu.be/V_lAhqLXT9A

以上を1ヶ月ぐらいでやりました。ここまでで、時間はかかるもののWebサイトの見た目については1人でコードを書いて実装できるようになっていたと思います。

ポートフォリオを作成(2020年2月)

2月の頭に1社面接を受けました。ポートフォリオ無しで特攻した結果、門前払いを受けたため、すぐにポートフォリオ作成にとりかかりました。
- Progate Ruby
- Progate Rails
以上を2週間ほどで集中的にこなしました。

さらに2週間ほどでSNS系のWebアプリを作成し、herokuにデプロイしました。(2020年2月)
GoogleMapsAPIを使ってみたりはしましたが、機能として目立ったところは特に無く、"Progateに毛が生えた程度"のポートフォリオでした。

ちなみにこの時の経験をQiitaに投稿したりもしました。

これ以降はポートフォリオは触っていません。

説明会、面接ラッシュ、そして内定へ(2020年3月~5月)

3月に入り、説明会や面接が本格的に始まりました。3月中はエントリーシート、自己分析、企業調べといった就活っぽいことをしてました。SIerやSES企業は避けるようにし、Web系企業で入れそうなところにエントリーしていました。

4月中は面接ラッシュでした。コロナウイルスが直撃しましたが、さすがWeb系企業という感じで、すぐにオンライン面接に切り替わり、問題なく選考を受けていました。

最終的に5月に入ったくらいで内定の連絡をいただきました。

就活についてはよく分かりませんが、技術力が不足している分、中高の部活や大学、研究などこれまでの経験で得たことをどう活かして事業に貢献できるか、という視点が大切なのかなと感じました。

振り返り・反省点

学習時間

学習にかけた時間をざっと計算してみると
- 1月は研究と並行していたこともあり、月~土は2時間、日曜は1日中勉強していたので、週で20時間くらい。なので月で80時間くらい。
- 2月は研究は下火になり、月~土は5時間、日曜は1日中という感じで、週で40時間くらい。なので月で160時間くらい。

以上から、プログラミングを始めてポートフォリオを完成させるまでにだいたい250時間前後かかったかと思います。

また、基本情報技術者の資格のために3ヶ月半の間、たまにサボりつつ1日1時間くらいずつ勉強していたので、それを含めると300時間~350時間
くらいになると思います。

良かった点

ポートフォリオを作成したこと

転職市場ではポートフォリオがないと話にならないという状況のようですが、新卒ではポートフォリオがあるというだけで評価していただける企業もありました。Progateに毛が生えた程度のしょぼいものでも、とりあえず作成して公開しているという事実はかなり重要だったと思います。

基礎学習に時間をかけ過ぎなかったこと

これは様々な方が見飽きるほど言及していることですが、Progateを何週もするような学習は無駄です。 私自身、Progateは各1回だけやって、すぐにポートフォリオの作成に取り組みました。その中で忘れていることがあればその都度スライドを見直して確認する、という形で勉強していました。
結果として、プログラミングを始めてから2ヶ月でポートフォリオを作成できました。

新卒でWeb系をあきらめてSIer、SES企業にいかなかったこと

非情報系、プログラミング未経験ということで、就活を始める直前までは新卒ではとりあえずSIerに入って、そこからWeb系に転職しようかなと思っていました。ただ、新卒カードをSIer系企業で使ってしまうことが得策ではない理由のような動画を観ているうちに、新卒でSIerに行くのはもったいないと考えるようになりました。
結果的にWeb系の企業に挑戦し、内定をいただくことができました。受ける前からあきらめず、ダメもとでも挑戦して本当に良かったと思います。

必要以上に費用をかけなかった

プログラミングの学習にあたってかかった費用はProgateとドットインストールの会費くらいで、合計5000円くらいです。数万円もするようなプログラミングスクールには通っていません。
スクールについては賛否両論あるかと思いますが、プログラミング未経験者がエンジニアになるにあたって、個人的には必ずしもスクールに通う必要はないと思いました。
運が良かった部分もありますが、私自身はスクールに通わずWeb系企業に内定をいただけたので、「未経験からエンジニアになるには数万~数十万という費用をかけてスクールに通わないといけない」と思い込み、あきらめてしまうのはもったいないと思います。

悪かった点

もっとポートフォリオに力を入れておくべきだった

エントリーシートや面接対策を言い訳に、herokuにデプロイした時点でポートフォリオの作成をストップしてしまいました。他の応募者と差別化するために、AWSやDockerといった技術をポートフォリオに組み込むところまで取り組むべきでした。

ポートフォリオの題材

ポートフォリオ作成では、どんな技術を使うかも重要ですが、何のために作るのかも重要だと個人的に思いました。面接では、ポートフォリオを作った理由を聞かれることが多かったです。自分はポートフォリオの題材を深く考えずに決めてしまったため、志望理由と成果物の間の矛盾を指摘されることが何度かありました。
単にプログラミングの練習のために作る、というよりも、自分の志望理由や経歴に沿うような題材を選ぶと面接の際に話がしやすいと感じました。
例)前職で医療系の仕事をしていた→ヘルスケア系のアプリ、など

長期インターンをやっておけばよかった

学部時代にアルバイトの代わりとして、どこかしらのベンチャー企業とかの長期インターンをやっておけばよかったと思います。多くの人がスクールなどでお金を払ってでも体験したいチーム開発を、給料をもらいながら経験できるのはかなりお得です。
学生であれば未経験でも採用してくれるところはけっこうあるイメージです。就活を意識し始めた学部3年生の方とかは、まだ全然間に合うのでぜひ参加することをおすすめします。

受ける企業を絞ってしまった

「未経験可」や「技術力は不問」といった注意書きのある企業を優先的に受けていましたが、自分の可能性を狭めているだけで無駄でした。特に新卒については技術力以外の部分を評価してもらえる企業が多いと思うので、勝手に自分で制限を設けず、もっと多くの企業にエントリーすべきでした。

最後に

QiitaやYouTube等で多くのエンジニアに関する情報に触れ、なんとかエンジニアとして就職することができました。このような有益な情報を発信をされている方々や面接をしていただいた企業の方々、ポートフォリオ作成や面接対策の際に相談に乗っていただいた先輩方に感謝の気持ちを伝えたいです。

この記事の通りにすれば絶対上手くいくとかではなく、あくまでもサンプルの1つとして参考にしていただければと思います。
新たにエンジニアとして働きたいという方の励みになれば幸いです。

参考にした記事など

自分がエンジニアを目指すきっかけとなった、未経験からWeb系エンジニアに転職された方の記事
- 未経験から4ヶ月でWeb系エンジニアに転職するためにやったこと
- 化学系研究者が完全未経験からWeb系自社開発企業に転職するまで

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Ruby】paizaで頻出メソッドまとめてみた

参考文献

入力メソッド

//入力値:文字列 改行:あり
input = gets

//入力値:文字列 改行:なし
input = gets.chomp

//入力値:数値   改行:あり
input = gets.to_i

//入力値:数値  改行:なし
input = gets.chomp.to_i

配列メソッド

//入力値を配列に格納 ※数値 
input = gets.split.map(&:to_i)

//分割して配列に格納
a,b,c = gets.split(" ").map &:to_i

//入力値を順番に格納
a = readlines.map &:to_i


//複数行 && 複数要素の格納  ※文字列
lines = []
while line = gets
    lines << line.chomp.split(' ')
end


//複数行 && 複数要素の格納  ※数値
lines = []
while line = gets
    lines << line.chomp.split(' ').map(&:to_i)
end

timesメソッド + 配列

//繰り返し回数
n = 5
//配列の設定
sample = []

//繰り返し回数分、配列に格納
n.times do
  sample.push(gets.chomp.split(" ").map &:to_i)
end

eachメソッド + 配列

//入力値取得
sample = readlines.map &:to_i

//変数宣言
n = 5

//eachメソッド
sample.each do |i|
 if n < 10
    n += 1
 else
    puts "sample"
 end
end

その他

//絶対値取得
n = 5
sample = n.abs


//単数形→複数形
sample = "post".pluralize
puts sample
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

rails6でデータベースを変更した話

これまではMySQLを使用していましたが、本番環境を考えてPostgreSQLに変更しました。

ググって、SQLite→MySQL or PostgreSQLの変更方法は出てくるのですが、
MySQL→PostgreSQLの変更方法は、ネットになかなか落ちていませんでした。

そんなとき、webpack周りで躓いた際に参考にした記事を思い出しました。
Ruby on Rails 6の主要な新機能・機能追加・変更点

どうやらrails6では簡単に変更出来るらしい

ターミナル
bin/rails db:system:change

上記で行けるみたい。
rails6からはRDBMSを変更するdb:system:changeタスクが追加されたとのこと。

ちなみにMySQLとSQLiteへの変更の仕方は以下の通り
Rails6「SQLite ⇆ MySQL ⇆ PostgreSQL」データベースを移行(変更)する方法

ターミナル

#MySQLに変更
rails db:system:change --to=mysql

ターミナル

#SQLiteに変更
rails db:system:change --to=sqlite3

実際にやってみる

ターミナル
#--to=*********で変更したいDBを指定する
bin/rails db:system:change --to=postgresql

ターミナル

Overwrite /Users/environment/アプリ名/config/database.yml? (enter "h" for help) [Ynaqdhm]

上記で、「上書きしますか?」と出るので、yを記入

ターミナル
Overwrite /Users/environment/アプリ名/config/database.yml? 
 (enter "h" for help) [Ynaqdhm] y
       force  config/database.yml
        gsub  Gemfile
        gsub  Gemfile

これで変更完了。
SQLite→MySQLに変更した際は、bin/rails db:system:changeを知らなかったので
database.ymlを自身で書き換えたりと少々めんどくさかった。

基本DBは変更しないほうがいいと思いますが、
rails6になってDBは簡単に変更出来るようになったよって、
話でした。

ではでは。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

AWSへのRailsアプリのデプロイ その1

はじめに

チームで開発したアプリを自分で建てたEC2に移行させたため記事に残しておきます。

EC2インスタンスを作る

まず、アプリの移行先のインスタンスを作りましょう。

スクリーンショット 2020-05-30 22.34.15.png
ここは各個人で違うと思いますが、今回は「Amazon Linux AMI」を選択。
スクリーンショット 2020-05-30 22.36.53.png

EC2インスタンスを起動させるとキーペアの作成画面が表示されます。
ここでは新しいキーペアの作成を選択し、キーペア名を入力した後、キーペアのダウンロードをしておきましょう。(キーは厳重に保管してください)
スクリーンショット 2020-05-30 22.48.48.png

Elastic IPの紐付け

インスタンスにElastic IPを紐付けます。
スクリーンショット 2020-05-30 22.56.28.png

「AmazonのIPv4アドレスプール」を選択肢て「割り当て」を押下。
これでElastic IPが割り当てられます。
スクリーンショット 2020-05-30 22.59.19.png

続いて、IPアドレスとEC2インスタンスを関連づけます。
EC2のインスタンスIDが分からないと関連付けできないので、確認しておきましょう
スクリーンショット 2020-05-30 23.05.32.png
Elastic IPの関連付けを選択します。
スクリーンショット 2020-05-30 23.09.22.png
インスタンスに、先ほど確認したインスタンスIDを入力して「関連付ける」を押下します。
スクリーンショット 2020-05-30 23.11.20.png

ポートを開く

現状のままだと、HTTPでの通信ができないため、ポートを開きます。
下記の画像の赤枠の部分をクリックしてください。
スクリーンショット 2020-05-30 23.15.22.png

インバウンドルールの編集を行います。
スクリーンショット 2020-05-31 14.47.19.png

HTTPのルールを追加して保存します。
スクリーンショット 2020-05-31 14.52.28.png

ターミナルからEC2インスタンスへログインする。

先ほどダウンロードした秘密鍵を~/.sshフォルダに移動させます。

mv 秘密鍵のパス ~/.ssh

秘密鍵のパーミッションをいじってルートユーザーのみ読み書き可能にします。

chmod 600 ダウンロードした鍵の名前.pem
ssh -i 秘密鍵のパス ec2-user@EC2インスタンスと紐付けたElastic IP

成功したらターミナルにデカデカとEC2と表示されます。

       __|  __|_  )
       _|  (     /   Amazon Linux AMI
      ___|\___|___|

EC2の設定

EC2上で以下のコマンドを実行して、パッケージをアップデートしましょう。

sudo yum -y update

続いて、必要なパッケージをインストールします。

sudo yum -y install git make gcc-c++ patch libyaml-devel libffi-devel libicu-devel zlib-devel readline-devel libxml2-devel libxslt-devel ImageMagick ImageMagick-devel openssl-devel libcurl libcurl-devel curl

上記のパッケージをインストールしたらNode.jsをインストールしましょう。

sudo curl -sL https://rpm.nodesource.com/setup_14.x | sudo bash -
sudo yum -y install nodejs

これでnode.jsのインストール完了です。ですが、まだまだインストールするものがあります。
続いてRuby関係のインストールです。まずコマンドでgitからrbenvをクローンしましょう。

git clone https://github.com/sstephenson/rbenv.git ~/.rbenv

以下の2つのコマンドでパスを通します。パスを通すことで、どのディレクトリにいてもアプリを呼び出せます。

echo 'export PATH="$HOME/.rbenv/bin:$PATH"' >> ~/.bash_profile
echo 'eval "$(rbenv init -)"' >> ~/.bash_profile

~/.bash_profileの編集内容はログインし直さないと反映されないので、sourceコマンドで即時反映させます。

source .bash_profile

gitからruby-buildをクローンします。

git clone https://github.com/sstephenson/ruby-build.git ~/.rbenv/plugins/ruby-build

rehashでgemのコマンドを使えるようにします。

rbenv rehash

ここからはRubyのインストールです。
使用しているRubyのバージョンを確認し、コマンドを各々で読み替えてください。

rbenv install x.x.x(バージョン)

EC2インスタンス内で使用するRubyのバージョンを決めます

rbenv global x.x.x(バージョン)

rehashしてRubyのインストールは終了です。

rbenv rehash

今回はここまで

長くなったので今回はここまでです。次の記事で完成予定。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Rails5.2以降のCredentialsについてわかりやすく

ポイントとなるのはconfig/master.key

 production環境でアプリを利用する場合、production環境で使われる秘密情報(暗号化されているもの)を元データに復元するために利用する鍵が必要(元データに復元することを復号といったりします!)

この鍵は、Rails5.2以降はconfig/master.keyファイルとして管理されている(自分でrails newした場合)

production環境用の秘密情報の管理

  • Rails5.1までは秘密情報を環境変数でアプリに伝える方法がとられていたが、
  • Rails5.2からはCredentialsという新しい機能になった

Credentialsとはなにか

  • 特定の方式で管理されるproduction環境用の秘密情報そのものその管理の仕組みという2つの意味があります。

  • Credentialsは、秘密情報が構造化して記述され(credentials.yml.enc)、リポジトリで管理されるが、リポジトリに入る内容は暗号化される。

  • 暗号化する暗号化されたものを復元するために鍵(config/master.key)をつかいます。

  • そしてこの鍵はリポジトリの外で管理する。つまりローカルのconfig/master.keyファイルのみで保存される。GitHubなどには保存しない!というか初期設定ではGitHubに保存されないようになっている。

秘密情報の暗号化とその復元

 暗号化された秘密情報(Credentials)は, config/credentials.yml.encに記述される。
このファイルの内容を編集するには、Railsの用意している専用のコマンドをつかう。(下で説明します)

config/credentials.yml.enc(Credentials)の初期状態の確認

 ファイル自体はrails newしたときに作成されていて、次のコマンドを打つとつらつらと初期状態の長い暗号文があらわれます。

$ cat config/credentials.yml.enc
=> 0mX2hE/8qS1bsCY1D9e9zIl+qH3UnwZ8JbLN7LqwXXttCAb7KpbiKQRlmcchkbsQHq5CVF0p4OutHW4Z1n0EOK5+eeKc9LYieWkBBt1FvP4dtgeWLUvg987HbNiH1XollAgJ+yH1mhIeQ5DGswGIf3yDAqRxYoJdhijaf7wuVDysWTSypJNdhUiFNde87LzjDVAL7M2fvNYE2Uk8F0awpM2k5r9zJ1HDzDB2ApIam95nDAZjIChBcbgQKQP3eCSqhuomRAt4U1PS52hOSgT+DAhXd+SqRhHoUQkzCmnuVttl7Cq9hxQgAcsKeGnWyrG3eYDoyEtZAArsRczb9wvxunX6xtZubm8uolxz+PishTW4oUxwE4mEdThnUz1AEnVpzm/DH67G+Z5HrdOiUBt1aS9cD4B/gT+RoKkE--WUeSWKvOQJj65J0A--A2Uif217M8ZadNsqs75r5Q==

上のように暗号化されているためセキュリティ上は安心だが、開発者は何を書かれているのか把握できないため、復元された内容を下記コマンドで閲覧することができる

$ bin/rails credentials:show

config/credentials.yml.enc(Credentials)の編集

config/credentials.yml.encの内容の編集

 下記コマンドで編集できる!
 EDITORという環境変数で、エディタを設定しておくと、その環境変数で指定されたエディタで、Credentialsを編集できるようになる。

$ bin/rails credentials:edit

アプリケーションからCredentialsを参照する

  • Railsアプリから秘密情報にアクセスできる。
$ bin/rails credentials:edit
  New credentials encrypted and saved
$ bin/rails c
[1] pry(main)> Rails.application.credentials.aws   
=> {:access_key_id=>123, :secret_access_key=>345}

鍵(config/master.key)の扱いに気をつける

  • このキーを紛失してしまうと、秘密情報を2度と復号できない

  • なくしたらconfig/credentials.yml.encを削除

    • 再度bin/rails credentials:editで新しくつくりなおす。
  • config/master.keyファイルをCredentialsと同じリポジトリに保存しないこと。このため「.gitignore」ファイルには「config/master.key」がはじめから記述されている。

参考

現場で使える Ruby on Rails 5速習実践ガイド

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

[Rails]graphql-rubyでpolymorphicを表現する

はじめに

最近、graphql-rubyでAPIを実装しています。
Railsでは、モデルの関連付けにポリモーフィックという便利な機能があります。
これをUnionTypeを使ってgraphqlでも表現する方法について説明します。

やりたいこと

UserテーブルとPetShopテーブルがDogテーブルのownerableでポリモーフィックな場合を考えます。graphqlでdogを取得するときに、その所有者であるownerable(user or pet_shop)のカラムも一緒にとってこれるようにする。

ポリモーフィックではない場合

まず復習をかねて、通常の関連付け(belongs_toとかhas_manyとか)の場合を考えてみます。
以下のようにUserとDogが1対多だとします。

user.rb
Class User < ApplicationRecord
  has_many: dogs
end
dog.rb
Class Dog < ApplicationRecord
  belongs_to: user
end

ObjectType

モデルで定義した関連付けをgraphql-rubyで表現するには、ObjectTypeを以下のように書きます。

user_type.rb
Class UserType < Types::BaseObject
  field :id, ID, null: false
end
dog_type.rb
Class DogType < Type::BaseObject
  field :name, String, null: false
  field :user, ObjectTypes::UserType, null: false # userとの関連付け
end

上記のようにObjectTypeを定義すると、dogオブジェクトを返す際に一緒に関連付けられたuserオブジェクトも取得してくれます。

ポリモーフィックの場合

続いて、ポリモーフィックで関連づけられた場合を考えてみます。
userの他にpetShopもdogを所有しています。

モデルの関連付け

ポリモーフィックの場合、Rialsモデルの関連付けは以下のようにかけます。

user.rb
Class User < ApplicationRecord
  has_many :dogs, as: :ownerable
end
pet_shop.rb
Class PetShop < ApplicationRecord
  has_many :dogs, as: :ownerable
end
dog.rb
Class Dog < ApplicationRecord
  belongs_to :ownerable, polymorphic: true
end

ObjectType

続いて、Objectタイプを定義します。
petShopオブジェクトが追加されたのと、dogTypeのfieldがuserではなく、ポリモーフィックな関連付けを示すownerableに変更されています。

user_type.rb
Class UserType < Types::BaseObject
  field :id, ID, null: false
end
pet_shop_type.rb
Class PetShopType < Types::BaseObject
  field :id, ID, null: false
end
dog_type.rb
Class DogType < Type::BaseObject
  field :name, String, null: false
  field :ownerable, UnionTypes::OwnerableType, null: false # ownerableとの関連付け
end

注意点はownerableのtypeがObjectTypesではなく、UnioTypesになっている点です。
UnionTypeはこれから定義していきます。

UnioneType

UnioTypeは、本記事の肝となる箇所です。dogTypeに定義したownerableをUnionTypeとして定義して、userTypeかpetShopTypeかを振り分けてくれます。

ownerable_type.rb
module UnionTypes
  class OwnerableType < Types::BaseUnion
    # possible_typesで関連付けられうるタイプを宣言する
    possible_types ObjectTypes::UserType, ObjectTypes::PetShopType

   # 分岐処理を記述
    def self.resolve_type(object, _context)
      if object.is_a?(User)
        ObjectTypes::PostType
      elsif object.is_a?(PetShop)
        ObjectTypes::ReplyType
      end
    end
  end
end

上記のように書くことで、resolverで返す型を判断して、UserかPetShopを選んでくれます。(rubyっぽくはない感じはしますが...)

Query

UnionTypeを使った場合は、queryも少し特殊な書き方をします。

query{
  dog(id: [dog_id]){
    id
    ownerable {
      __typename #型を指定する
      ... on User {
        id
      }
      __typename
      ... on PetShop {
        id
      }
    }
  }
}

上記のようにtypenameを指定することによってほしいownerを選択することができます。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

[Rails]都道府県プルダウンリスト

前置き

検索フォームの都道府県プルダウンリスト実装を備忘録として残します。

前提条件

ransack導入済

1.導入

gem 'active_hash'

まずGemfileに上記のように記述し、bundle install。
再起動も忘れずに。

2.prefectureモデルを作成

こちら手動です。

models/prefecture.rb
class Prefecture < ActiveHash::Base
  self.data = [
      {id: 1, name: '北海道'}, {id: 2, name: '青森県'}, {id: 3, name: '岩手県'},
      {id: 4, name: '宮城県'}, {id: 5, name: '秋田県'}, {id: 6, name: '山形県'},
      {id: 7, name: '福島県'}, {id: 8, name: '茨城県'}, {id: 9, name: '栃木県'},
      {id: 10, name: '群馬県'}, {id: 11, name: '埼玉県'}, {id: 12, name: '千葉県'},
      {id: 13, name: '東京都'}, {id: 14, name: '神奈川県'}, {id: 15, name: '新潟県'},
      {id: 16, name: '富山県'}, {id: 17, name: '石川県'}, {id: 18, name: '福井県'},
      {id: 19, name: '山梨県'}, {id: 20, name: '長野県'}, {id: 21, name: '岐阜県'},
      {id: 22, name: '静岡県'}, {id: 23, name: '愛知県'}, {id: 24, name: '三重県'},
      {id: 25, name: '滋賀県'}, {id: 26, name: '京都府'}, {id: 27, name: '大阪府'},
      {id: 28, name: '兵庫県'}, {id: 29, name: '奈良県'}, {id: 30, name: '和歌山県'},
      {id: 31, name: '鳥取県'}, {id: 32, name: '島根県'}, {id: 33, name: '岡山県'},
      {id: 34, name: '広島県'}, {id: 35, name: '山口県'}, {id: 36, name: '徳島県'},
      {id: 37, name: '香川県'}, {id: 38, name: '愛媛県'}, {id: 39, name: '高知県'},
      {id: 40, name: '福岡県'}, {id: 41, name: '佐賀県'}, {id: 42, name: '長崎県'},
      {id: 43, name: '熊本県'}, {id: 44, name: '大分県'}, {id: 45, name: '宮崎県'},
      {id: 46, name: '鹿児島県'}, {id: 47, name: '沖縄県'}
  ]
end

app/models配下にprefecture.rbを作成し上記のように編集。
Prefecture < ActiveHash::BaseでActiveHash::BaseをPrefectureに継承。

3.検索フォーム作成(ransack導入済)

_search_form.html.haml
.search_form
  = search_form_for @q do |f|
    = f.collection_select :place_cont, Prefecture.all, :name, :name
    = f.submit "検索", class: "search_submit"

完了。
以下解説。

:place_contについて、placeはカラム名です。_contは〜を含むというransackのマッチャーというものです。
※詳しくはこちらransack

Prefecture.allは、上記のPrefectureモデル全て持ってきてってことですね〜。
Prefecture < ActiveHash::BaseでActiveHash::BaseをPrefectureに継承したからActive Recordメソッドが使えるってことです。
Active Recordメソッドとは、
・all:テーブルの全てのデータを取得する
・find:テーブルレコードの一つのデータを取得する
・new:クラスのインスタンスの生成
・save:クラスのインスタンスの保存
などのことです。

普段rails g modelで作成しているモデルもActiveHash::Baseを継承していますね。

application_record.rb
class ApplicationRecord < ActiveRecord::Base
  self.abstract_class = true
end
post.rb
class Post < ApplicationRecord
end

最後の方は「:name, :name」にしています。
他の記事では「:id, :name」でしたが、これだと検索出来なかったので変えました。

htmlを確認してみると下記のようになっていました。

# 「:id, :name」の場合
<option value="1">北海道</option>

# 「:name, :name」の場合
<option value="北海道">北海道</option>

ありがとうございました!

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

RailsアプリをCircleCI(2.1)を使ってHerokuにデプロイするときの設定

はじめに

Railsアプリの開発効率を上げるため、
GitHubにpushしたら静的コード解析(rubocop)と自動テスト(rspec)を実行し、
stagingブランチにマージしたらSTG環境に、masterブランチにマージをしたら本番環境に自動デプロイするように設定した。

前提

  • Railsのアプリケーションを作成済み
  • Rubocop, Rspec設定済み
  • Herokuの登録&設定済み
  • CircleCIのユーザおよびプロジェクト登録済み&GitHubと連携済み

環境

  • Ruby 2.5.0
  • Rails 5.2.2
  • CircleCI 2.1
  • SQLite(Rspec実行時)

手順

  • CircleCIに環境変数を設定する
  • .circleci/config.ymlを記述し、GitHubにpushする

CircleCIに環境変数を設定

Project Settings > Environment Variables にAdd Variableで以下を設定する。

  • HEROKU_API_KEY(HerokuのAccount Settings > Account > API Keyの内容を記載)
  • HEROKU_APP_NAME_PRD(本番環境のHerokuアプリ名)
  • HEROKU_APP_NAME_STG(STG環境のHerokuアプリ名)

設定ファイルの記述

以下のファイルを作成する。
masterブランチの時のみ本番環境のHerokuアプリにデプロイされ、
stagingブランチの時のみSTG環境のHerokuアプリにデプロイされる。

circleci/config.yml
version: 2.1
orbs:
  ruby-orbs: sue445/ruby-orbs@1.6.0
  heroku: circleci/heroku@1.0.1

workflows:
  build_test_and_deploy:
    jobs:
      - build
      - rubocop:
          requires: 
            - build
      - rspec:
          requires:
            - build
            - rubocop
      - deploy_prd:
          requires:
            - build
            - rspec
          filters:
            branches:
              only:
                - master
      - deploy_stg:
          requires:
            - build
            - rspec
          filters:
            branches:
              only:
                - staging

executors:
  default:
    working_directory: ~/repo
    docker:
      - image: ruby:2.5.0-stretch
        environment:
          BUNDLE_PATH: vendor/bundle
          RAILS_ENV: test

jobs:
  build:
    executor: default
    steps:
      - checkout
      - bundle-install
  rubocop:
    executor: default
    steps:
      - preparate
      - run:
          name: Rubocop
          command: bundle exec rubocop
  rspec:
    executor: default
    steps:
      - preparate
      - run: bundle exec rails db:create
      - run: bundle exec rails db:schema:load
      - run:
          name: Rspec
          command: bundle exec rspec
  deploy_prd:
    executor: heroku/default
    parameters:
      app-name: 
        default: $HEROKU_APP_NAME_PRD
        type: string
      post-deploy:
        default:
          - run:
              command: heroku run rails db:migrate --app $HEROKU_APP_NAME_PRD
        type: steps
    steps:
      - checkout
      - heroku/install
      - heroku/deploy-via-git:
          app-name: << parameters.app-name >>
      - steps: << parameters.post-deploy >>
  deploy_stg:
    executor: heroku/default
    parameters:
      app-name: 
        default: $HEROKU_APP_NAME_STG
        type: string
      post-deploy:
        default:
          - run:
              command: heroku run rails db:migrate --app $HEROKU_APP_NAME_STG
        type: steps
      force:
        default: true
        type: boolean
    steps:
      - checkout
      - heroku/install
      - heroku/deploy-via-git:
          app-name: << parameters.app-name >>
      - steps: << parameters.post-deploy >>

commands:
  bundle-install:
    steps:
      - ruby-orbs/bundle-install:
          bundle_clean: true
          bundle_extra_args: ''
          bundle_gemfile: Gemfile
          bundle_jobs: 4
          bundle_path: vendor/bundle
          bundle_retry: 3
          cache_key_prefix: v1-bundle-dependencies
          restore_bundled_with: true
  preparate:
    steps:
      - checkout
      - bundle-install

Rubocop, Rspecもorbを使ったほうがよかったかもしれないです。

注意

3rdパーティ製のorb(sue445/ruby-orbs@1.6.0)を利用する場合は、Orb Security Settingsを有効にしておく必要がある。

Organization Settings > Security > Orb Security Settings
Allow Uncertified OrbsをYesにする。

参考

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Rails】Font Awesomeの導入方法

開発環境

・Ruby: 2.5.7
・Rails: 5.2.4
・Vagrant: 2.2.7
・VirtualBox: 6.1
・OS: macOS Catalina

アカウント作成

1.下記リンクにアクセスする。
Font Awesome Start画面

2.メールアドレスを入力し、「Send Kit Code」をクリックする。
1.png

3.確認メールが届くので「Click to Confirm Your Email Address + Set Things Up」というリンクにアクセスする。

4.下記画面に遷移するので、パスワードを入力して「Set Password & Continue」をクリックする。
image.png

5.プロフィール情報入力画面に遷移するが、今は特に設定する必要も無いので、
何も入力せずに「All set.Let's Go!」をクリックする。
image.png

6.下記画面に遷移するので、「Copy Kit Code」をクリックして、コードをコピーする。
image.png

Rails側の操作

1. 「application.html.slim」を編集

先ほどコピーしたコードを貼り付けて、Slim形式に変換する。

application.html.slim
doctype html
html
  head
    title
      | Font Awesomeテスト
    = csrf_meta_tags
    = csp_meta_tag
    = stylesheet_link_tag    'application', media: 'all', 'data-turbolinks-track': 'reload'
    = javascript_include_tag 'application', 'data-turbolinks-track': 'reload'
    / 追記
    script src='https://kit.fontawesome.com/c51513dd6c.js' crossorigin='anonymous'

2. アイコンを表示

①下記サイトにアクセスし、使用したいアイコンをクリックする。
Font Awesome Icon一覧

②下記の様な画面に遷移するので、クラス名をコピーする。
image.png

③下記の様にHTMLに記述するとアイコンが表示されます。

~html.slim
i.far.fa-heart
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Ruby on RailsへのjQueryの導入準備

環境・前提条件

macOS Catalina バージョン10.15.4
ruby 2.5.1p57 (2018-03-29 revision 63029)
Rails 5.2.4.3

jQuery導入準備

Gemfileを確認し、

gem "jquery-rails"

と記載する。

application.jsに、 

//= require jquery 

と記載する。※注意点として、"//= require_tree ."より上に記載する。

//= require jquery

//= require_tree .

実際にjQueryが使えるのか、確認する。
任意の名前のjsファイルを作成する。(同名のcoffeeファイルがあれば削除すること。)

$(function(){
 console.log('OK');
});

これでページを更新し、コンソールに'OK'と表示されれば準備OK!

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

[JQuery] ファイルからフォーム選択プレビュー表示

はじめに

ファイルから画像を選択するし、submitする前に自分の選択した画像を表示できるようにする。

イメージとしては以下のようなものです。
画面収録 2020-05-31 13.21.05.mov.gif

前提として

・jQueryを設定できるようにしてある。
・Railsのバージョン5.2を使用
・Hamlを使用

ビューファイルを設定しよう

edit.html.haml
.editmain_right
  .editmain_right_form
    .editmain_right_form_sub
      %span.icon
      %span.icontext  プロフィール画像をアップロード
    .editmain_right_form_main
      .editmain_right_form_main_ajax
      .editmain_right_form_main_file
        = f.file_field :image, class: "image_form"
       %span.texpic  
       写真アップロード

jQueryを設定

edit.js
$(document).on('turbolinks:load', function() {
$(function(){
  //画像ファイルプレビュー表示のイベント追加 fileを選択時に発火するイベントを登録
  $('form').on('change', 'input[type="file"]', function(e) {
    var file = e.target.files[0],
        reader = new FileReader(),
        $subsubimageboxs = $(".editmain_right_form_sub");
        t = this;

    // 画像ファイル以外の場合は何もしない
    if(file.type.indexOf("image") < 0){
      return false;
    }

    // ファイル読み込みが完了した際のイベント登録
    reader.onload = (function(file) {
      return function(e) {
        //既存のプレビューを削除
        $subsubimageboxs.empty();
        // .prevewの領域の中にロードした画像を表示するimageタグを追加
        $subsubimageboxs.append($('<img>').attr({
                  src: e.target.result,
                  width: "150px",
                  class: "editmain_right_form_sub",
                  title: file.name
              }));
      };
    })(file);

    reader.readAsDataURL(file);
  });
});
});
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

初心者向けRailsでブログを作ってみるチュートリアルその0

これはなに?

Webプログラマを目指す人で、ある程度プログラミングができるようになったけど自分でインターネット上にサービスを公開する方法はわからない...という方向けにRailsでブログを作り、インターネット上からアクセスできるようにクラウドサービス(今回はherokuを利用します1)上で公開する方法を書いていきます。
下の対象者に該当するレベル感の方がこのチュートリアルを全部終わる頃には、最低限一人で一応Webサービスを作れるようになっている予定です

これの対象者

以下のような方々が対象です

  • 前提として、Rubyをある程度さわれるようになっている人(今回は文法の説明は含みません)
  • Railsがなんなのかはある程度わかっていて、コードを書くお題が欲しい人
  • コードを書く以外のWeb開発のいろいろな要素を体験してみたい人
  • Github上でPull Requestを出して機能単位でコードを開発するやり方をやってみたい人

イメージ的にはこちらのチュートリアルを少しボリュームを削って、すでに触ったことある方向けにシンプルにしたものを書く予定です。 https://railstutorial.jp/chapters/beginning 

今後作っていくお題

ブログを作ってみる、ということでざっくりワイヤーフレームっぽいものを作ってみました。
他の画面や、サイトマップについては次の更新でお見せします(まだ作ってない)

rails_blog_wireframe-List.png


  1. おまけとしてGoogle Cloud Platform上で動かすバージョンも書く予定 

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Railsで404エラーページを設定するとrefileで投稿した画像が表示されなくなる場合の対処法

概要

Railsで404のエラーページを作成した場合のみ、refileで投稿した画像が表示されなくなる。
エラーページのコードをコメントアウトすると画像は表示される。

404エラーページのためのコードは下記の通り。

application_controller.rb
  unless Rails.env.development?
    rescue_from Exception,                      with: :render_500 
    rescue_from ActiveRecord::RecordNotFound,   with: :render_404
    rescue_from ActionController::RoutingError, with: :render_404
  end

# viewsでerrorディレクトリを作りそこに404.html.erb/505.html.erbを作成する
  def render_404
    render 'error/404', status: :not_found
  end

  def render_500
    render 'error/500', status: :internal_server_error
  end
config/routes.rb
Rails.application.routes.draw do

# 上から順に評価されるので、一番下に書く
get '*path', to: 'application#render_404'

end

原因

ターミナルでrails routesして確認すると、

GET /*path(.:format)
refile_app /attachments

の順になっていた。
routesは上から評価されるので、config/routes.rbに何も設定していないrefileのURLである/attachmentsが評価される前にconfig/routes.rbget '*path', to: 'application#render_404'が評価されてしまっていた。

対処

refile_app /attachmentsGET /*path(.:format)より先に評価するようにすれば大丈夫です。

まず、initializers/refile.rbに下記を追加。
refile.rbが無い場合は新たに作成してください。

config/initializers/refile.rb
Refile.automount = false
config/routes.rb
Rails.application.routes.draw do

mount Refile.app, at: Refile.mount_point, as: :refile_app #追加
get '*path', to: 'application#render_404' # 一番下に書く

end

ターミナルでrails routesして確認すると、

refile_app /attachments
GET /*path(.:format)

の順になっていると思います。

これで/attachmentsが先に評価されて、画像が表示されるようになると思います。

https://github.com/refile/refile#mounting
にも書いてますが、refileの自動マウントをオフにして自分でルートを設定する必要がありました。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【rails】デプロイ時のUglifier::Error: Unexpected token: について

はじめに

デプロイ時にでたエラー
Uglifier::Error: Unexpected token:

の解決方法を記載しておきます

解決方法

config/environments/production.rb
config.assets.js_compressor = :uglifier

上記の記述を下記の記述に編集します⬇︎

config/environments/production.rb
config.assets.js_compressor = Uglifier.new(harmony: true)

編集したらコミットプッシュを忘れずに!

以上で解決できました。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む