#4 SinatraでActiveRecordを使わずに掲示板アプリを作ってみた

[前回](https://qiita.com/divclass123/items/9a9e2f9ccfba2286a901#comment-2aa5a3d01881ceaf6cc4)の続き

前回コードを見ていったので、いよいよアプリを実行して実際の挙動を見ていきたいと思います！
んで、どんな感じでデータベース作成すればええねん。と思ったが、
setup.shを実行すれば良いと、課題の作者の谷道さんから教えていただきました。ありがとうございます。。。！(2ちゃん風に言うとサンガツ、知らんけど)

# 下準備

.shの拡張子がついているファイルすら初めて見たので、、、。
まぁ要するにlinuxコマンドをファイルに書いといて
```
$ sh setup.sh
```
とかで一斉に実行できる感じ。

# setup.sh

```
mysql -u root < ./database/create_database.sql
mysql -u root 0ch < ./database/create_topics.sql
mysql -u root 0ch < ./database/create_posts.sql
mysql -u root 0ch < ./database/seeds.sql
```

なんとなくはわかるけど、
mysql -u root だけでMySQLにログインできる気がしないから、多分

```
$ sh setup.sh
```

これを実行しても上手くいかない気がする。
あと、< 何？

https://loumo.jp/archives/4905
ここら辺に色々書いてあった。

> hoge < file	標準入力を file から読み込む

んー、意味がよく分からない。。。。

標準出入力の解説は
https://products.sint.co.jp/topsic/blog/standard-input-output
が分かりやすい。

> プログラムが実行されるとき、必要な情報が流れ込む口があると思ってください。この口を標準入力といいます。特に何もしなければ、その口にはキーボードからの入力が接続されています。よって、一般的な標準入力＝キーボード入力と考えても問題ありません。


https://qiita.com/blueskyarea/items/6372f25647b48274e000

```
command < file
```

こうやって書いてあった。

https://www.kenschool.jp/blog/?p=1143

>コマンドはfileの内容を標準入力として受け取る

>Linuxでは基本的に標準出力や標準入力、標準エラー出力その「向かう先を変更する」ことをリダイレクトという。

ファイルの中身をコマンドの標準入力とする。
ってことなので、要するに

```
mysql -u root < ./database/create_database.sql
```

これの場合、CREATE DATABASE IF NOT EXISTS 0ch;
をmysql -u root に渡す的な感じ？

んーーー、なんかいまいち腑に落ちない。ってか、linux疎かにしすぎやろ。俺。あかんわ。

```ruby
puts < "hoge"
```

ってやったら、hogeが出力されるってことでいいんすかね。
rubyでlinuxコマンドは使えないと思うけど、イメージこんな感じかな

ただ、mysql -u rootにCREATE DATABASE IF NOT EXISTS 0ch;
を標準入力してるのが、よく分からない。何が分からないのかが分からない。

何はともあれ実行してみよう。

Enter password: 
ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2)
ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2)
setup.sh: line 3: ./database/create_posts.sql: No such file or directory
ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2)

実行結果がこうなった。まぁ予想通り。

**setup.sh**

```
sudo touch /tmp/mysql.sock
sudo mysql.server restart
mysql -u root -p $MYSQL_ROOT_PASSWORD < ./database/create_database.sql
mysql -u root 0ch -p $MYSQL_ROOT_PASSWORD < ./database/create_topics.sql
mysql -u root 0ch -p $MYSQL_ROOT_PASSWORD < ./database/create_posts.sql
mysql -u root 0ch -p $MYSQL_ROOT_PASSWORD < ./database/seeds.sql

```

こんな感じに編集した。
 -p $MYSQL_ROOT_PASSWORD が機能しておらず、毎回パスワードを打つことになってめんどくさい。
そこも標準入力をなんとかかんとかすれば、パスワードも自動入力してくれそうだが、、、。

が、とりあえず、0chデータベースが作られた！やったね！！

# アプリを起動

https://qiita.com/k-ta-yamada/items/9e35c5f8b31862267e01
sinatraのアプリの起動の仕方はこの記事が参考になりました。

```
bundle exec ruby app.rb
```

でアプリを起動したら、Mysql2::Error::ConnectionError at /
Access denied for user 'root'@'localhost' (using password: NO)

となりました。

 @client ||= Mysql2::Client.new(host: 'localhost', username: 'root', database: '0ch')

ここでエラー起きとるらしい。
パスワードを設定してないから、そりゃそうだ。

**db.rb**

```rb
  def self.client
    @client ||= Mysql2::Client.new(host: 'localhost', username: 'root', password: ENV['MYSQL_ROOT_PASSWORD'],database: '0ch')
  end
```

と変更した！！！！

したら上手くいった。
ENV['MYSQL_ROOT_PASSWORD']は環境変数を呼び出してる感じ。
あと、ビューに表示するためのインスタンス変数は、app.rbに定義してる感じなんすねー。
app.rbがroutes.rbとcontrollerの役割を果たしている的な。
データベースと直接やり取りするメソッドはモデルに定義する慣習がある。ってのは聞いたことあった気がする。。。。

**post.rb**

の

  def validate
    unless @body.size >= MIN_SIZE && @body.size <= MAX_SIZE
      raise Invalid, "本文は#{MIN_SIZE}文字以上、#{MAX_SIZE}文字以下で指定してください"
    end
  end

を実際に実行してみると、

エラー画面に
本文は#{MIN_SIZE}文字以上、#{MAX_SIZE}文字以下で指定してください

が出るようになっていた。例外処理をこっから自分なりに実装できていけば面白い。

あと、form_withも使わないで

**show.slim**

```slim
form action="/topics/#{@topic.id}/posts" method="post"
```

と書いてるところも注目！


自分で試行錯誤せず、ただコード読んでいっただけでしたが、
それだけでもだいぶ普段railsがどう言った挙動をしてるのかをなんとなくですが
把握できたり、それ以外の知識もついたように思えます。
この後はsinatraをもう少しいじりたいですが、Vue.jsとRailsで色々やりたいのもあるので、
一旦そっちをやることにしますう。
後、これをやった後にrailsをいじってみることで気づくことも色々ありそう。
@ttanimichi さん、課題を出してくださりありがとうございました！！！☺️