- 投稿日:2019-03-27T20:24:12+09:00
誰でもプログラムを書けるようになる方法が発見される!なんだこれは?
プログラムを書けるようになる方法を見つけた!なんだこれは?
眼鏡のフレーム端を耳の横に掛けたらなぜか書けるようになった。なんだこれは?
このやり方をやれば誰でもプログラムが書けるようになると思います。頭も良くなった!と思うプログラムを挫折した経験がある方一度お試しあれ!
このように耳の横にフレーム端を掛けてやる自己責任で
メガネのフレームを少し曲げる必要があります。破損しても自己責任で
個人差があると思います。人によってできない人もいると思います。
以上自己責任で試してみてください。用意するもの
必須
メガネ (耳の横にかけれるもの フレームの横幅が広いものがいいです)
紫外線防止コーティング (眼鏡屋さんで3千円くらいでやってもらえます)お好み
片方は非球体の方がいい (目が疲れない)
黒縁じゃないほうがいい。(縁が太いと視野が狭くなる)やり方
フレームの端を耳の横に掛ける
目をつぶり、頭の周りに衛星が回転するイメージをするメガネをかけていない時 20回ぐらいの回転が限度 疲れてしまう
メガネをかけている時 10回ぐらいの回転が限度 スムーズに回らない うまく回らない
メガネの端を耳の横にかけている時 スムーズに回る 無限に回ることを確認するメガネを耳の横にかけてイメージの衛星が無限に回ったら、プログラムが書けるようになっていると思います。
個人差があるため、できない人もいるかもしれません。またある程度この掛け方で生活していく必要があります。普段からイメージトレーニングをやってください。
プログラムが書けるようになったかを確かめてみる。
メガネのこの掛け方をしてプログラムの学習サイトで授業を受けてみましょう
初心者はJavaScriptをお勧めします。https://dotinstall.com/lessons
途中、掛け方を元に戻してみる。反応を比べてみる
プログラム書けるようになりましたか?理解できるようになりましたか?
プログラムが書けるようになっていた、理解できるようになっていたら、
あなたは今日からプログラマーです。おめでとう!
近眼じゃない人は?メガネがないとできないの?
近眼じゃなくてもできると思います。近眼になる必要はないです。
今はメガネは必須だと思いますが、近い将来メガネがなくてもできる発明品が出てくるかもしれません。眼鏡屋さんでメガネのフレームを買う。横幅の広いフレームを選ぶこと
最初についているプラスチックの度の入ってないレンズ
このレンズの上に紫外線防止コーティングを追加してもらう。
3千円くらいでやってもらえます。これでできると思いますが。個人差もあるので自己責任で
眼鏡を買う前に、眼鏡屋さんで耳の横に掛けて衛星が無限に回るイメージになるか試してみましょう。無限に回るイメージができたらプログラムは書けていると思います。
まずは安いメガネで試すとよいでしょう。初心者はどのプログラム言語から始めたらいいのか?
C# .NetCore WindowsFormをお勧めします。(画像参照)
GUIなのでわかりやすい。書籍もたくさん出ています。(Visual C# 2018逆引き大全 555の極意はお勧めです)C#は動画学習サイトUdemyで学習できます
https://www.udemy.com/jp/(iOSやアンドロイドをやりたい人はその言語を最初に初めてもいいと思います)
そのあと
ゲーム Unity C#
Web Asp.net MVC C#
機械学習 Tensorflow for C#
Iot Windows 10 IoT Core C#
iOS SwiftかObjective-C
Android KotlinかJava便利ツール
タスク管理ソフト
https://trello.com/jaオンラインチャット Slack
https://slack.com/intl/ja/
- 投稿日:2019-03-27T15:58:59+09:00
bcryptがインストールしてるのに出来てないと出るエラーと対策
概要
Railsチュートリアルを進行中に躓いたbcryptに関するエラーと対策を記載していきます。
内容
まずは、インストール手順を説明します。
Gemfileに追加したいライブラリとそのバージョンを追加する。
Gemfilesource 'https://rubygems.org' gem 'rails', '5.0.0.1' gem 'bcrypt', '3.1.11' #追加 . . .そしてコマンドを実行してインストール
$ bundle installここまでは、問題ない。rails test などのコマンドを実行すると
bcryptをインストールしたにも関わらず、インストールしてないと出てくる。You don't have bcrypt installed in your application. Please add it to your Gemfile and run bundle install ・ ・ ・チュートリアル進行中にこのエラーで嵌る人は結構いるみたいです。
対策
色んな方のQiitaを参考にして改善に試みてみましたが、全く原因も対策も分からず
次の日になってbundle installしてrails testを実行してみると正常に動作しました...。ただ、IDEはCloud9を使用していて、30分でサーバーが切れるので
サーバーの再起動などが関わっている可能性もあるので実行してみる価値はあると思います。Weblickの再起動などの対策方法もあるみたいなので調べてみてください。
参考URLに自分が実行していなかった方法が記載されていたので、是非試してみてください。参考URL
- 投稿日:2019-03-27T15:35:27+09:00
もそ、プログラミングを学ぶ【Ruby & Rails復習編】〜本引数と仮引数の違いってなに?〜
相変わらずエラー問題に苦戦中の もそ。
やさしい先輩たちから「この部分はRubyの復習をしてみるといいかも」というアドバイスをもらい早速Rubyを復習しています。すると早速、
「げっ、ここって意味がよくわからなくてスルーしたところじゃん...」
となっていたところが出てきました。
Railsを学んだのでなんとな〜く分からんでもないのですが、理解を深めるべくリベンジしました。今日はそんなRubyの本引数と仮引数について書いていきます。
引数について
まずは引数(ひきすう)についておさらいします。
引数は、プログラムでメソッドなどに渡すことのできる値です。
変数の値には使える範囲が決まっていて、これをスコープと呼びます。
たとえば、あるdef~end内で定義した変数は、ほかのメソッドでそのまま使うことはできません。引数を使うことでメソッドの外にある変数、つまりスコープ外にある変数をメソッドの中で使うことができます。
そして引数には、メソッドを呼び出す部分に記述する本引数とメソッドを定義している部分に記述する仮引数の2つがあります。
コードを実際に見てみましょう。① def multi(input)←()内は仮引数 puts input * input end ② puts "何か数字を入力してください" input = gets.to_i ③ multi(input)←()内は本引数こんな感じです。
コードが読み込まれて処理される順番は③→②→①となります。
③と②でスコープを定義して、引数を使うことで①に変数を渡しています。ひとつポイントなのが、仮引数の名前は本引数と違ってもいいということ。
先ほどのコードの流れは、
③のinputという本メソッド内に②gets.to_iという数値を入れて、①で結果を表示する
というものでした。
これは方程式と同じで、仮の名前に数値を代入しているので、「x=aとして x+1*10=aを解きなさい」という数学の問題と同じような感覚です。なので先ほどのコードは、
def multi(number) puts number * number return number * number end puts "何か数字を入力してください" value = gets.to_i multi(value)と表すことができます。
スコープの範囲に注意
次に、このようなコードで考えてみましょう。
① def rename(name) name = "もそと#{name}" end ② name = "ポチ" rename(name) puts nameこのコードを実行すると、出力結果は「ポチ」だけになります。
では、「もそとポチ」と出力するにはどうすればいいでしょうか?このコードのポイントは、何回も出てきている"name"の記述。
同じ名前が出てきているのですが、実は①と②で中身が違います。...意味分かんないですよね。私もわからないです。
というわけで、LINEでポチに泣きつきました。
「え、これ外側で名前変えてるだけだからでしょ(即答)」
ここでポチのいう外側は②の部分。
① def rename(name) name = "もそと#{name}" end ② name = "ポチ" rename(name) puts name②のコードでは、
「name=ポチとして、rename(ポチ)にします。ではnameを出してください」
と記述しています。
最初にname=ポチと言っているので、ここで指すnameの中身は「ポチ」になります。では①の部分はどうでしょうか。
「rename(name)を定義します。name=”もそとポチ”です」よくよく考えてみてください。
これ、②と①でnameで指示しているnameの中身が違いますよね。なので出力結果を「もそとポチ」にするには、
① def rename(name) name = "もそと#{name}" end ② name = "ポチ" name=rename(name) puts nameこのように記述すればよいのです!なるほど〜!
--
ふわふわしていた引数の考え方が、やっときちんと理解できた...気がします(理解したとは言っていません)
配列と本引数/仮引数はややこしいとポチも言っていたので、ここは焦らず少しずつ理解を深めていこうと思います。
果たして理解できる日は来るのか...もその修行は続く。
- 投稿日:2019-03-27T15:18:09+09:00
数分経ってもCloud9でherokuコマンドが使えるようにする
環境
Railsチュートリアルの推奨環境
Cloud9のIDE
heroku
原因
Cloud9のIDEは30分アクセスが無いとサーバーが落ちるようになっている。(恥ずかしながら全く知りませんでした。)
また、ターミナル毎に秘密鍵やherokuが設定されているため
サーバーを立ち上げ直したり、別ターミナルを開くと登録されていない状態に戻る$ heroku create bash: heroku: command not foundRailsチュートリアル 第1章 1.5.1 herokuのセットアップ で紹介されている通り
cloud9上でherokuをインストールする事が出来ますが、毎回無駄な処理が必要となる。source <(curl -sL https://cdn.learnenough.com/heroku_install)さらに詳しい原因については参考URLをご覧ください。
現在の自分の知識では、理解が追いつかなかったので説明が出来ません。
日々精進をして理解出来るようになりたいと思います。
対策
ターミナル起動時にPOSTが自動で設定されるようにする必要がある。$ vi ~/.bashrc # 以下をファイルの最後に追記 PATH=/usr/local/heroku/bin:$PATH # こちらの記載でも可 source $HOME/.profile > /dev/null参考URL
https://qiita.com/tathuhi10/items/281c0d8e03438e0e752c
https://railstutorial.jp/chapters/beginning?version=5.1#sec-heroku_setup
- 投稿日:2019-03-27T11:40:51+09:00
不足分をnilで埋めた配列を取得
String#splitなどで配列を作成する場合、指定した長さより実際の長さが短いことがある。長さ5の配列を作りたい"a,b,c,d,e,f,g".split(',', 5) #=> ["a", "b", "c", "d", "e,f,g"] "a,b,c,d".split(',', 5) #=> ["a", "b", "c", "d"] # 足りない…
#firstや#takeを使っても数を増やすことはできない。"a,b,c,d".split(',', 5).first(5) #=> ["a", "b", "c", "d"] "a,b,c,d".split(',', 5).take(5) #=> ["a", "b", "c", "d"]
Array#values_atなら増やせる。"a,b,c,d".split(',', 5).values_at(0...5) #=> ["a", "b", "c", "d", nil]
破壊的に拡張したいなら、
Array#[]=で範囲外に代入する手がある。"a,b,c".split(',', 5).tap { |a| a[5-1] = a[5-1] } #=> ["a", "b", "c", nil, nil]
nilでなくデフォルト値があるのなら、#zipでも良いかもしれない。[*"1".."5"].zip("a,b,c".split(',', 5)).map { |v0,v| v || v0 } #=> ["a", "b", "c", "4", "5"]※
||を使う場合は、偽の値(nilとfalse)が既に入っていても書き換えてしまうので注意。
- 投稿日:2019-03-27T10:18:53+09:00
[Ruby] 配列、eachメソッド
eachメソッド
今回は配列内に共通の処理を行うときに使うeachメソッドを説明していきたいと思います。
配列.rbexample = ["ゆーいち", 25, "エンジニア"]例えばこのような配列があったとします。配列内の一つの要素を取り出す場合はexample[0]のように番号を指定してあげるのでした。
もしここら辺がわからないという場合はこちらをご確認ください。今回は配列内全てに対して処理を行います。
eachメソッドの定義
それでは配列内の全ての要素を順番に取り出し表示するという処理を書いていきます。
配列.rbexample = ["ゆーいち", 25, "エンジニア"] example.each do |ex| puts ex end # =>ゆーいち #25 # エンジニアこれで配列内から要素を順番に取り出しそれぞれに対してputsという処理をする事ができました。
まず定義の仕方としては
配列名.each do |変数|
処理
end
このように定義します。
このとき変数名はなんでも構いません。
言い方を変えるとこの処理は、配列内の0番目の要素を取り出し変数にその要素が代入され処理をする。次に1番目の要素を...
この作業を配列内に要素がなくなるまで繰り返すと言ったほうがわかりやすいかもしれません。配列内に処理をする要素がなくなった時点で終了します。
上の例でいうと、まず0番目の要素である"ゆーいち"が変数exに代入されex = "ゆーいち"の関係になりputs exなので"ゆーいち"が表示されます。次に25が取り出され...と言った感じですね。
each_with_indexメソッド
少し発展的なものとしてeach_with_indexメソッドも紹介していきます。
eachメソッドと処理の仕方は変わりませんがこのメソッドは取り出した要素の番号をつける事ができます。
例えば上の例で
[0]ゆーいち
[1]25
[2]エンジニア
と出力したい場合配列.rbexample = ["ゆーいち", 25, "エンジニア"] example.each_with_index do |ex, index| puts "[#{index}]#{ex}" end # =>[0]ゆーいち #[1]25 # [2]エンジニアこれで出力できました。変わったところは変数が一つ増えていますね一つ目の変数には配列内の要素が、二つ目には0から始まる番号を定義しています。
最後に
今回はeachメソッドについて説明していきました。例では要素が3つしかなかったので簡単でしたが、多くの要素を持っている配列だと一つ一つ取り出して行くのは無理がありますね。そういったときにeachメソッドを使いましょう。
最後まで読んでいただきありがとうございました。
- 投稿日:2019-03-27T10:03:55+09:00
while文による繰り返し (Ruby)
はじめに
初学者のアウトプット記事です。
while文によるループ処理
プログラムを終了させず同じ処理をずっと繰り返すループ処理を行う方法はwhile文の条件式をtrueにしておくこと。これでwhileが繰り返すための条件が常に真となり、永遠にwhile内の処理が繰り返される。
while true do # 条件式がtrueになることでプログラムは終了せず繰り返し処理が行われる ## 処理 endしかしこれでは無限ループとなり、処理が終わることがない。ループの処理から抜けるためにはexitメソッドを呼び出す。
↓
↓while true do exit # ここのexitでプログラムが終わる puts "こんにちは" # これは呼ばれない endexitメソッドはプログラム自体を強制終了させるのでexitメソッド以降の処理は行われない。
while true do input = gets.chomp # ユーザーの入力をinputに代入 if input == "exit" # exitと入力されたら exit # exitメソッドによりプログラムを終了 end puts "ループ中" endこれはexitと入力するまでずっと処理を続けるプログラム。whileの条件式をtrueにすることでexitを呼ぶまで同じ処理を行い続ける。
1〜10まで順に足し合わせて出力するプログラム
number = 1 while number <= 10 do #numberが10以下なら繰り返す puts number #number 出力 number += 1 #出力後numberに+1して繰り返し end訂正修正ありましたらご指摘お願いします。
- 投稿日:2019-03-27T08:33:49+09:00
RSpecでRedmineのsudoモードをテストする
# spec/support/time_helpers.rb RSpec.configure do |config| # travel_toを使えるようにする # https://api.rubyonrails.org/classes/ActiveSupport/Testing/TimeHelpers.html#method-i-travel_to config.include ActiveSupport::Testing::TimeHelpers, type: :feature endRSpec.describe 'sudoモードが有効になっているとパスワードを入力しないと操作ができない', type: :feature do include ActiveSupport::Testing::TimeHelpers background do # sudoモードを有効にする allow(Redmine::SudoMode).to receive(:enabled?).and_return(true) end scenario '操作しようとしたらsudoモードの期限が切れていたのでパスワードを再入力して操作を完了する' do visit パスワードの再入力が求められるフォームがある_path fill_in 'パスワードの再入力が求められるフィールド', with: 'なにか' # Redmine::SudoMode.timeoutの値はデフォルトだと15分に設定されている。 # そのため20分後に操作をしてパスワードの再入力が求められることを確認する。 travel_to(20.minutes.from_now) do click_on '送信' expect(page).to have_content('この操作を続行するにはパスワードを入力してください') fill_in 'パスワード', with: 'password' click_on '送信' end expect(page).to have_content('操作が成功した際に表示されるであろう文言') end end参考
https://github.com/redmine/redmine/blob/f0d579adebfe3c5da93135fbaa3d9ec503d06855/test/integration/sudo_mode_test.rb#L9
https://github.com/redmine/redmine/blob/f0d579adebfe3c5da93135fbaa3d9ec503d06855/test/integration/sudo_mode_test.rb#L197-L200
- 投稿日:2019-03-27T08:29:34+09:00
大学データとログイン機能gem deviseを組み合わせる
ここ3週間の一区切りとして、今週は
scaffoldで作成した大学データと、gemのdevise、Bootstrap等を組み合わせる。前回までのdeviseを使ったサイトに、大学データを一部コピーして、作成する予定だったが、
Active Record等がエラーを起こしたため、今回はrails newから作成した。
やってることの多くは以前のと重複しているので、詰まった所、初めてな所を、今日は書く。やった事
- #Railsの命名規則(単数形と複数形)
- DBのカラム定義を後から変更
- render partial: 部分テンプレの参照
- validation
- Postgresqlにはunsined型は存在しない
使用環境
- ホストOS: Windows10 Home
- 仮想環境: Ubuntu Bento/Bionic
- Ruby:2.51
- Rails: 5.2.2
- gem 'devise' : ログイン等の機能用
- gem 'kaminari' : ページネーション
- DB: PostgreSQL
Railsの命名規則(単数形と複数形)
rails gコマンドで、controller名やmodel名を指定する際に、混乱した。
# rails generate scaffold model名の単数形 フィールド名の型と並び # rails g controller controller名の複数形 # カラムの追加 # rails generate migration AddカラムToモデル名の複数形 フィールド名と並び
- model名は単数形で、頭文字を大文字にする
- scaffoldの場合、modelが基準
- modelは設計書であり、(テーブル1つに付き)1つなため
- controller名は複数形で、頭文字を大文字にする。
- 1つのcontrollerに複数のactionが含まれるため
DBのカラム定義を後から変更
rails g scaffoldコマンド時に、ClubStudentの外部キーの定義をreferecesとミスタイプしていた。
修正方法:app/db/migrate下のファイルを修正
app/db/migrate/20190326030303_create_club_students.rbclass CreateClubStudents < ActiveRecord::Migration[5.2] def change create_table :club_students do |t| #スペリングミス #t.refereces :student #訂正分 t.references :student t.references :club, foreign_key: true t.timestamps end end endなお、ALTTER TABLEコマンドを使って、あとから修正する方法は
DB内のデータを書き換えるだけで、アプリ自体のファイル等は編集されない。mysql# ALTER TABLE テーブル名 MODIFY COLUMN カラム名 新しい定義 ALTER TABLE ClubStudent MODIFY COLUMN student referencesつまり、原因の根本的な部分を修正できないので、駄目
render partial: 部分テンプレの参照
render レンダリング(render) - railsドキュメント
全てのページのヘッダー(上部)に、ログアウトや他のstudentやclubs等のリンクを乗せる
共通して表示させるので、/app/views/layouts/application.html.erb を編集する。
なお、部分テンプレファイル名は『_』アンダーバー始まり/app/views/layouts/application.html.erb<body> # <%= render :partial => '部分テンプレ名' %> <%= render :partial => 'shared/header' %> </body>表示させたいリンクを書きこむ。
/app/views/shared/_header.html.erb<%= link_to 'Student list', students_path %> <%= link_to 'subjects list', subjects_path %> <%= link_to 'clubs list', clubs_path %> <%= link_to 'exam_result list', exam_results_path %> <%= link_to 'club_stdent list', club_students_path %> <%= link_to 'Log Out', destroy_student_session_path, method: :delete %>validation
参考リンク Active Record Validations
バリデーションは有効なデータだけをDBに保存するのを確実にするための最善策。validate条件
空でないこと
validates :name, presence: true # 因みに、空が条件ならば # validates :name, absence: true入力文字の長さ
文字の最大長は、データ型を要参照。varcharなら255文字まで
/app/models/club.rb# 2文字以上 validates :name, length:{minimum:2} # 255文字以上 validates :name, length:{maximum:255}exclusion含まない
授業ではしなかったが、クラブ名末尾に『部』を入れない、という条件を追加してみる
/app/models/club.rbvalidates :name, exclusion: { in: %w(部 サークル) } # 『含む』ならinclusion実装結果
空白や文字列長、『サークル』という語には、validatesが発動した
ただ、現状だと、『テニスサークル』の様に文字列と連結すると、validateが動かない
あとまわしClub was successfully updated. Name: サークル部type "unsigned" does not exist (※Postgresql)
validatesの実装していく最中に、エラーに気づいた
studentのeditページで更新すると、
ActiveRecord::StatementInvalid in StudentsController#show PG::UndefinedObject: ERROR: type "unsigned" does not exist LINE 1: ...id as subject_id, CAST(AVG(exam_results.score) as unsigned) ... ^ : SELECT subjects.id as subject_id, CAST(AVG(exam_results.score) as unsigned) as avg_score, MAX(exam_results.score) as max_score, MIN(exam_results.score) as min_score FROM "students" INNER JOIN "exam_results" ON "exam_results"."student_id" = "students"."id" INNER JOIN "subjects" ON "subjects"."id" = "exam_results"."subject_id" GROUP BY subjects.id ORDER BY subjects.idと、エラーを吐き、因みに、ブラウザの戻るボタンで戻ると、更新されている。
また、エラー原因であると思わる、StudentController#showはapp/controllers/students_controller.rb#showdef show @students = Student.joins(:subjects) .select('students.name, students.email, students.age, students.gender, students.opinion, subjects.id as subject_id') .select('exam_results.name as exam_result_name, subjects.name as subject_name, exam_results.score') .select('CAST((exam_results.score / subjects.max_score) * 100 as unsigned) as ratio') .where(id: params[:id]) avg_result = Student.joins(:subjects) .select('subjects.id as subject_id') .select('CAST(AVG(exam_results.score) as unsigned) as avg_score') .select('MAX(exam_results.score) as max_score') .select('MIN(exam_results.score) as min_score') .group('subjects.id') .order('subjects.id') (以下略)因みに、このcontrollerは、以前の大学データのcontrollerからコピーしてきたものだ。
つまり、MySQLで動くアプリのcontroller。unsigned (MySQL)
- MySQLにおいては正と負の整数を扱うことができる。
- unsignedを指定すると、正の数しか格納できなくなり、代わりに範囲が2倍になる。
- unsignedにした値が負になると、エラーを起こす
- UNSIGNEDは、マイナス値が入らないだけでなく、マイナスになる計算もできない。
- CASTで一時的に型を変える事で回避は可能。
Postgresqlにはunsined型は存在しない(最重要)対応策
まだ、試験結果のデータを入れてないので、功を奏すか分からないけれども
- unsignedをint等の型に置き換える
- 今回は試験点数を扱っていて、intで事足りると思われる。
- ただ、MySQLでint unsignedだと、範囲が正の方向に2倍になっている。
- 扱う数によっては、intより1つ上ののbigintに変える必要がある
- CAST as unsignedの部分を消す
- MySQLでCAST as unsingedは、一時的に型を指定している
前回の大学データに倣って、今回はcast as intに変更した
app/controllers/students_controller.rb# (該当部分だけ抜き出し) .select('CAST((exam_results.score / subjects.max_score) * 100 as int) as ratio') .select('CAST(AVG(exam_results.score) as int) as avg_score')正常に、studentデータのedit、updateが機能した。
- 投稿日:2019-03-27T08:29:34+09:00
Scaffoldで作成したサイトにgem devise等を組み合わせていく
今週からは、scaffoldで作成した大学データと、gemのdevise、Bootstrap等を組み合わせる。
やった事
- Railsの命名規則(単数形と複数形)
- DBのカラム定義を後から変更
- render partial: 部分テンプレの参照
- validation
- UNSIGNEDという型が存在しないPostgreSQL
使用環境
- ホストOS: Windows10 Home
- 仮想環境: Ubuntu Bento/Bionic
- Ruby:2.51
- Rails: 5.2.2
- gem 'devise' : ログイン等の機能用
- gem 'kaminari' : ページネーション
- DB: PostgreSQL
Railsの命名規則(単数形と複数形)
rails gコマンドで、controller名やmodel名を指定する際に、混乱した。
# rails generate scaffold model名の単数形 フィールド名の型と並び # rails g controller controller名の複数形 # カラムの追加 # rails generate migration AddカラムToモデル名の複数形 フィールド名と並び
- model名は単数形で、頭文字を大文字にする
- scaffoldの場合、modelが基準
- modelは設計書であり、(テーブル1つに付き)1つなため
- controller名は複数形で、頭文字を大文字にする。
- 1つのcontrollerに複数のactionが含まれるため
DBのカラム定義を後から変更
rails g scaffoldコマンド時に、ClubStudentの外部キーの定義をreferecesとミスタイプしていた。
修正方法:app/db/migrate下のファイルを修正
app/db/migrate/20190326030303_create_club_students.rbclass CreateClubStudents < ActiveRecord::Migration[5.2] def change create_table :club_students do |t| #スペリングミス #t.refereces :student #訂正分 t.references :student t.references :club, foreign_key: true t.timestamps end end endなお、ALTTER TABLEコマンドを使って、あとから修正する方法は
DB内のデータを書き換えるだけで、アプリ自体のファイル等は編集されない。mysql# ALTER TABLE テーブル名 MODIFY COLUMN カラム名 新しい定義 ALTER TABLE ClubStudent MODIFY COLUMN student referencesつまり、原因の根本的な部分を修正できないので、駄目
render partial: 部分テンプレの参照
render レンダリング(render) - railsドキュメント
全てのページのヘッダー(上部)に、ログアウトや他のstudentやclubs等のリンクを乗せる
共通して表示させるので、/app/views/layouts/application.html.erb を編集する。
なお、部分テンプレファイル名は『_』アンダーバー始まり/app/views/layouts/application.html.erb<body> # <%= render :partial => '部分テンプレ名' %> <%= render :partial => 'shared/header' %> </body>表示させたいリンクを書きこむ。
/app/views/shared/_header.html.erb<%= link_to 'Student list', students_path %> <%= link_to 'subjects list', subjects_path %> <%= link_to 'clubs list', clubs_path %> <%= link_to 'exam_result list', exam_results_path %> <%= link_to 'club_stdent list', club_students_path %> <%= link_to 'Log Out', destroy_student_session_path, method: :delete %>validation
参考リンク Active Record Validations
バリデーションは有効なデータだけをDBに保存するのを確実にするための最善策。validate条件
空でないこと
validates :name, presence: true # 因みに、空が条件ならば # validates :name, absence: true入力文字の長さ
文字の最大長は、データ型を要参照。varcharなら255文字まで
/app/models/club.rb# 2文字以上 validates :name, length:{minimum:2} # 255文字以上 validates :name, length:{maximum:255}exclusion含まない
授業ではしなかったが、クラブ名末尾に『部』を入れない、という条件を追加してみる
/app/models/club.rbvalidates :name, exclusion: { in: %w(部 サークル) } # 『含む』ならinclusion実装結果
空白や文字列長、『サークル』という語には、validatesが発動した
ただ、現状だと、『テニスサークル』の様に文字列と連結すると、validateが動かない
あとまわしClub was successfully updated. Name: サークル部type "unsigned" does not exist (※Postgresql)
validatesの実装していく最中に、エラーに気づいた
studentのeditページで更新すると、
ActiveRecord::StatementInvalid in StudentsController#show PG::UndefinedObject: ERROR: type "unsigned" does not exist LINE 1: ...id as subject_id, CAST(AVG(exam_results.score) as unsigned) ... ^ : SELECT subjects.id as subject_id, CAST(AVG(exam_results.score) as unsigned) as avg_score, MAX(exam_results.score) as max_score, MIN(exam_results.score) as min_score FROM "students" INNER JOIN "exam_results" ON "exam_results"."student_id" = "students"."id" INNER JOIN "subjects" ON "subjects"."id" = "exam_results"."subject_id" GROUP BY subjects.id ORDER BY subjects.idと、エラーを吐き、因みに、ブラウザの戻るボタンで戻ると、更新されている。
また、エラー原因であると思わる、StudentController#showはapp/controllers/students_controller.rb#showdef show @students = Student.joins(:subjects) .select('students.name, students.email, students.age, students.gender, students.opinion, subjects.id as subject_id') .select('exam_results.name as exam_result_name, subjects.name as subject_name, exam_results.score') .select('CAST((exam_results.score / subjects.max_score) * 100 as unsigned) as ratio') .where(id: params[:id]) avg_result = Student.joins(:subjects) .select('subjects.id as subject_id') .select('CAST(AVG(exam_results.score) as unsigned) as avg_score') .select('MAX(exam_results.score) as max_score') .select('MIN(exam_results.score) as min_score') .group('subjects.id') .order('subjects.id') (以下略)因みに、このcontrollerは、以前の大学データのcontrollerからコピーしてきたものだ。
つまり、MySQLで動くアプリのcontroller。unsigned (MySQL)
- MySQLにおいては正と負の整数を扱うことができる。
- unsignedを指定すると、正の数しか格納できなくなり、代わりに範囲が2倍になる。
- unsignedにした値が負になると、エラーを起こす
- UNSIGNEDは、マイナス値が入らないだけでなく、マイナスになる計算もできない。
- CASTで一時的に型を変える事で回避は可能。
Postgresqlにはunsined型は存在しない(最重要)対応策
まだ、試験結果のデータを入れてないので、功を奏すか分からないけれども
- unsignedをint等の型に置き換える
- 今回は試験点数を扱っていて、intで事足りると思われる。
- ただ、MySQLでint unsignedだと、範囲が正の方向に2倍になっている。
- 扱う数によっては、intより1つ上ののbigintに変える必要がある
- CAST as unsignedの部分を消す
- MySQLでCAST as unsingedは、一時的に型を指定している
前回の大学データに倣って、今回はcast as intに変更した
app/controllers/students_controller.rb# (該当部分だけ抜き出し) .select('CAST((exam_results.score / subjects.max_score) * 100 as int) as ratio') .select('CAST(AVG(exam_results.score) as int) as avg_score')正常に、studentデータのedit、updateが機能した。
- 投稿日:2019-03-27T07:25:27+09:00
Parallel 的ゾンビを殺した話
TL; DR
v1.16.0 から、 parallel の gem 使ってるときに timeout とか使って親を殺しても、ちゃんと子供達も kill されるようになりました。
詳細
parallel の gem は、便利なんだけれども、親スレッドを kill してもその子供達は普通に活動し続ける。 thread であろうとも process であろうとも。
例:
t = Thread.new do Parallel.map(0..1000, in_threads: 2) do |i| p i sleep 1 end end sleep 1 t.kill sleep # 0 # 1 # 3 # 2 # 5 # 4 # => kill しているにも関わらず 1000 まで出力される。たとえば、悪名高い timeout と組み合わせるとこうなる。
begin Timeout.timeout(1) do Parallel.map(0..1000, in_threads: 2) do |i| p i sleep 1 end end rescue Timeout::Error p :timeout end sleep # 0 # 1 # 2 # 3 # :timeout # 4 # 5 # 6 # 7 # 8 # => 1000 まで続くこれは、あんまりにもあれなので、 parallel 本家に以下の PR を出してマージしてもらった。
https://github.com/grosser/parallel/pull/248
これによって、 Timeout やら 親スレッドの kill やらが行われた時に、その子供のスレッドやプロセスについても正しく kill されるようになった。
begin Timeout.timeout(1) do Parallel.map(0..1000, in_threads: 2) do |i| p i sleep 1 end end rescue Timeout::Error p :timeout end sleep # 0 # 1 # 3 # :timeout # 2 # => ここでとまる
Concurrent Ruby を使えよ、という話は若干ある
- 投稿日:2019-03-27T02:50:00+09:00
Rails勉強ネタ resources で名前付きヘルパー変わること確認
普段何気なくroutes.rbにてresourcesメソッドを使用しているが、
色々確認する。usersのコントローラーを作成(定番の7つのメソッド)
$ rails g controller users index new show create edit update destroyusers_controller.rbclass UsersController < ApplicationController def index end def new end def show end def create end def edit end def update end def destroy end endRails.application.routes.draw do get 'users/index' get 'users/new' get 'users/show' get 'users/create' get 'users/edit' get 'users/update' get 'users/destroy' endこの状態で
rails routesを実行すると。$ rails routes Prefix Verb URI Pattern Controller#Action users_index GET /users/index(.:format) users#index users_new GET /users/new(.:format) users#new users_show GET /users/show(.:format) users#show users_create GET /users/create(.:format) users#create users_edit GET /users/edit(.:format) users#edit users_update GET /users/update(.:format) users#update users_destroy GET /users/destroy(.:format) users#destroy全部users_'アクション名'という名前付きヘルパーになって、メソッドは全部GETです。
(空気を読んでPOSTとかDELETEなどになるのかと思っていた・・・)resoureceメソッド使う
routes.rbRails.application.routes.draw do # get 'users/index' # get 'users/new' # get 'users/show' # get 'users/create' # get 'users/edit' # get 'users/update' # get 'users/destroy' resources :users endこの状態で
rails routes実行すると$ rails routes WARNING: Nokogiri was built against LibXML version 2.9.7, but has dynamically loaded 2.9.4 Prefix Verb URI Pattern Controller#Action users GET /users(.:format) users#index POST /users(.:format) users#create new_user GET /users/new(.:format) users#new edit_user GET /users/:id/edit(.:format) users#edit user GET /users/:id(.:format) users#show PATCH /users/:id(.:format) users#update PUT /users/:id(.:format) users#update DELETE /users/:id(.:format) users#destroyRestfulな形になった。
ニュアンス的にcreateが user_path のPOSTなイメージがあるが、
users_pathである事に注意(間違えそう)。
- 投稿日:2019-03-27T02:50:00+09:00
Rails勉強ネタ resources での名前付きヘルパー確認
普段何気なくroutes.rbにてresourcesメソッドを使用しているが、
色々確認する。usersのコントローラーを作成(定番の7つのメソッド)
$ rails g controller users index new show create edit update destroyusers_controller.rbclass UsersController < ApplicationController def index end def new end def show end def create end def edit end def update end def destroy end endroutes.rbRails.application.routes.draw do get 'users/index' get 'users/new' get 'users/show' get 'users/create' get 'users/edit' get 'users/update' get 'users/destroy' endこの状態で
rails routesを実行すると。$ rails routes Prefix Verb URI Pattern Controller#Action users_index GET /users/index(.:format) users#index users_new GET /users/new(.:format) users#new users_show GET /users/show(.:format) users#show users_create GET /users/create(.:format) users#create users_edit GET /users/edit(.:format) users#edit users_update GET /users/update(.:format) users#update users_destroy GET /users/destroy(.:format) users#destroy全部users_'アクション名'という名前付きヘルパーになって、メソッドは全部GETです。
(空気を読んでPOSTとかDELETEなどになるのかと思っていた・・・)resoureceメソッド使う
routes.rbRails.application.routes.draw do # get 'users/index' # get 'users/new' # get 'users/show' # get 'users/create' # get 'users/edit' # get 'users/update' # get 'users/destroy' resources :users endこの状態で
rails routes実行すると$ rails routes Prefix Verb URI Pattern Controller#Action users GET /users(.:format) users#index POST /users(.:format) users#create new_user GET /users/new(.:format) users#new edit_user GET /users/:id/edit(.:format) users#edit user GET /users/:id(.:format) users#show PATCH /users/:id(.:format) users#update PUT /users/:id(.:format) users#update DELETE /users/:id(.:format) users#destroyRestfulな形になった。
ニュアンス的にcreateが user_path のPOSTなイメージがあるが、
users_pathである事に注意(間違えそう)。
- 投稿日:2019-03-27T00:27:06+09:00
CentOS7にRubyをインストール
いつも忘れがちなので、自分用のメモも兼ねてインストール方法を投稿します。
前準備
CentOS7はMinimal ISOでインストール済みであること
必要なパッケージのインストール
$ sudo yum -y install git bzip2 gcc gcc-c++ openssl-devel readline-devel zlib-devel $ sudo yum -y install epel-release $ sudo yum -y install nodejsrbenvをダウンロード
$ sudo git clone https://github.com/rbenv/rbenv.git /usr/local/rbenv $ sudo git clone https://github.com/rbenv/ruby-build.git /usr/local/rbenv/plugins/ruby-buildrbenvの環境設定
/etc/profile.d/rbenv.shを作成し、以下の内容を追加します。
export RBENV_ROOT=/usr/local/rbenv export PATH=${RBENV_ROOT}/bin:$PATH eval "$(rbenv init --no-rehash -)"rootユーザで以下の実行が必要
# source /etc/profile.d/rbenv.shsudoでrbenvを実行するためにsudorderにRBENV_ROOTとsecure_pathの追記が必要
# visudo ... Defaults env_keep += "RBENV_ROOT" Defaults secure_path = /sbin:/bin:/usr/sbin:/usr/bin:/usr/local/rbenv/bin:/usr/local/rbenv/shims ...Rubyのインストール
バージョンをチェック
$ rbenv install -l ... 2.6.0-rc1 2.6.0-rc2 2.6.0 2.6.1 2.6.2 2.7.0-dev jruby-1.5.6 ...インストール実行
バージョン2.6.2をインストールしてみます。
$ sudo rbenv install 2.6.2使用するRubyのバージョンを設定します。
$ sudo rbenv global 2.6.2 $ sudo rbenv rehashこれでインストール完了です。
後処理
必要なgemをインストール
bundlerはRailsを動かすために最低限必要なのでインストールします。
$ sudo gem install bundler --no-doc






