質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.49%
SQLite

SQLiteはリレーショナルデータベース管理システムの1つで、サーバーではなくライブラリとして使用されている。

Ruby on Rails

Ruby on Railsは、オープンソースのWebアプリケーションフレームワークです。「同じことを繰り返さない」というRailsの基本理念のもと、他のフレームワークより少ないコードで簡単に開発できるよう設計されています。

Q&A

解決済

1回答

8334閲覧

画像をデータベースに保存する場合の更新方法を教えてください。

s.k

総合スコア423

SQLite

SQLiteはリレーショナルデータベース管理システムの1つで、サーバーではなくライブラリとして使用されている。

Ruby on Rails

Ruby on Railsは、オープンソースのWebアプリケーションフレームワークです。「同じことを繰り返さない」というRailsの基本理念のもと、他のフレームワークより少ないコードで簡単に開発できるよう設計されています。

0グッド

0クリップ

投稿2017/04/25 03:26

###前提・実現したいこと
画像をデータベースに保存する場合の更新方法を教えてください。

・画像はcreate時にバイナリデータでデータベースに保存します。
・更新はeditメソッドとupdateメソッドを使用します。

###発生している問題・エラーメッセージ

update時に大量のメッセージが表示されます。
以下の分は先頭のエラー内容です。

Could not log "sql.active_record" event. NoMethodError: undefined method `bytesize' for #<ActionDispatch::Http::UploadedFile:0x007f33e269f3a8> ["/usr/local/rvm…

###該当のソースコード

def edit @user = User.find(params[:id]) end def update name = user_params[:name] region = user_params[:region] profile = user_params[:profile] upload_image1 = user_params[:image1] upload_image2 = user_params[:image2] upload_image3 = user_params[:image3] upload_image4 = user_params[:image4] upload_image5 = user_params[:image5] upload_evo = user_params[:evolution] user = {} if upload_image1 != nil user[:image1] = upload_image1.read end if upload_image2 != nil user[:image2] = upload_image2.read end if upload_image3 != nil user[:image3] = upload_image3.read end if upload_image4 != nil user[:image4] = upload_image4.read end if upload_image5 != nil user[:image5] = upload_image5.read end if upload_evo != nil user[:evolution] = upload_evo.read end user[:name] = name user[:region] = region user[:profile] = profile ★★★ @user = User.find(params[:id]) @user[:image1] = upload_image1.read @user.update(user_params) ★★★ redirect_to pages_manage_path end

今回は試験的にimage1だけを実装しようとしています。
上のコードはあまり気にしないでください。。。

また★で囲まれている箇所を以下のようにすると更新ではなく新たにデータが追加されてしまいます。

@user = User.new(user) @user.update(user)

ご経験ある方、ご指摘お願いします!

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

ActionDispatch::Http::UploadedFile:0x007f33e269f3a8
はバイナリデータではありません。
.tempfile.read
でバイナリデータになると思います。

ところで

上のコードはあまり気にしないでください。。。

すごく気になります…。
きになる点は2つ
1つ目は
サムネイルならともかく、画像をバイナリデータでデータベースに保存することにメリットはないということ
2つ目は
画像を5つ別々のcolomnに持たせる設計であること しかもUser.modelに!!
です。
特に2つ目は狂気の沙汰としか思えません

理由を説明しますと

1つ目に関しては

  • 画像のバイナリデータの内部を検索することはないので、DBに入れる意味は薄い
  • OSのファイル管理自体が、かなり効率のいいファイルDBになっておりfilepathだけ格納しても遅延はそこまで発生しない。
  • DBをバックアップするときに、画像データのバイナリをいちいち保存しなくてはいけないのでバックアップファイルが巨大になりかつ時間もかかる。
  • バイナリデータは拡張子を保存しないので、拡張子を別に保存するか、画像に変換時に、推定しなくてはいけない。

などです。

2つ目は

  • 画像の差し替え、更新、取得に際して、active_recordだけでは不可能で、ハードコーディング(SQLを直打ち)する必要がある。
  • そもそも、active_recordは構造上モデルのDataBaseのfieldを一旦、全て取得するので毎回、取得時にそれをメモリ上に展開して、処理を行うと、userに関わる全てのactive_recordでとんでもない遅延が発生する。

ですかね
特に最後は重要です。

投稿2017/04/25 05:36

編集2017/04/25 07:16
moke

総合スコア2241

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

s.k

2017/04/25 06:37 編集

mokeさん ありがとうございます! 先に上のコードから説明します。 自治体向けに会話ボットのAIを個人で開発してみようかなと考えてます。 画像は感情表現に利用します。ユーザーが単語を入力した時にその単語の感情値が+されます。 感情値の合計が-1になった時に、不機嫌1の画像に切り替わります。他も同様に一定の値になったら画像が切り替わります。 画像は多くとも6枚で済むので、データベースに保存する方が実装が容易であると考えました。 プロトタイプなので、1つの自治体が利用できれば良いという風に設計をしました。 おそらく、mokeさんの言いたいことに対応する説明にはなっていないと思うのですが、 とりあえずこんな感じです! 理由を知りたいです!
moke

2017/04/25 06:53 編集

面白い試みです 秋田県だと田沢湖→なまはげにみたいな感じで切り替わったり 数多いるゆるキャラで感情を表現したり、夢が広がりますね。 宮城だとむすび丸が「宮城?ああ、仙台ね」と言われると、てる政宗になったりとかw で、個人的に、話したり罵ったりすると目まぐるしく変化するみたいな 楽しそうですね。 勝手な妄想ですが もしこういった、運用だったらやはり画像の自由度を出すために 分離したほうがいい気もします
s.k

2017/04/25 07:03

ゆるキャラだけで考えていたのですが、それ以外でも色々面白そうなのありますね!! 分離できるように設計し直してみます! ありがとうございます!
s.k

2017/04/25 09:14 編集

返信が遅くなりました! なるほど、、、デメリットが多そうですね… 無知ですみません。質問があるのですが、今回の案件での最適な保存場所とそれを達成するためにGemを使った方がいいんでしょうか? それとも、プラグインを使わずにpublicに保存していくべきでしょうか?
moke

2017/04/25 13:31

どちらでもいいのですが、ユーザーがアップロードしたファイルを適切に加工して、云々というなら、careawaveみたいなアップロードのgemを使うものありだと思います。
s.k

2017/04/25 13:53

ありがとうございます! 大変勉強になりました! うまく言ったら報告します笑
moke

2017/04/25 14:22

頑張ってください。 例えばですが、ソフトバンクのペッパーくんの感情システムを参考にして見ると 方針がたつかも
s.k

2017/04/27 03:18

おおおお、そうですよね。 考えてませんでした。。。 見てみます!
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.49%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問