🎄teratailクリスマスプレゼントキャンペーン2024🎄』開催中!

\teratail特別グッズやAmazonギフトカード最大2,000円分が当たる!/

詳細はこちら
SQL

SQL(Structured Query Language)は、リレーショナルデータベース管理システム (RDBMS)のデータベース言語です。大きく分けて、データ定義言語(DDL)、データ操作言語(DML)、データ制御言語(DCL)の3つで構成されており、プログラム上でSQL文を生成して、RDBMSに命令を出し、RDBに必要なデータを格納できます。また、格納したデータを引き出すことも可能です。

Ruby on Rails

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

Active Record

Active Recordは、一つのオブジェクトに対しドメインのロジックとストレージの抽象性を結合するデザインパターンです。

Q&A

解決済

3回答

1065閲覧

ActiveRecord joinメソッドで、SQL文を追加するとシンタックスエラーになる

orori

総合スコア42

SQL

SQL(Structured Query Language)は、リレーショナルデータベース管理システム (RDBMS)のデータベース言語です。大きく分けて、データ定義言語(DDL)、データ操作言語(DML)、データ制御言語(DCL)の3つで構成されており、プログラム上でSQL文を生成して、RDBMSに命令を出し、RDBに必要なデータを格納できます。また、格納したデータを引き出すことも可能です。

Ruby on Rails

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

Active Record

Active Recordは、一つのオブジェクトに対しドメインのロジックとストレージの抽象性を結合するデザインパターンです。

0グッド

0クリップ

投稿2019/09/28 00:59

編集2019/09/28 01:43

以下のようなSQLの内容を、railsのモデルで行いたいと考えています。

reservationsテーブルで、cartsテーブルをそれぞれのcart_idとidとでleft joinで結合し、
cartsのレコードが作成されてから5分間経過したものは、結合先の内容をnullにする、という条件を加えます。

SQL

1SELECT * 2FROM reservations AS r 3LEFT OUTER JOIN carts AS c 4ON r.cart_id = c.id AND c.create_date >= SUBTIME(NOW(), '00:05:00') 5WHERE r.id = 20

rails の Reservation モデルでは以下のように記述しました。

rb

1scope :getReservationStates, lambda { 2 select('*') 3 .joins('LEFT OUTER JOIN carts AS c ON lock_id = c.id AND c.create_date >= SUBTIME(NOW(), '00:05:00')') 4 .where('id = 20') 5 }

すると以下のエラーが出ます。

syntax error, unexpected tINTEGER, expecting ')'
...eate_date >= SUBTIME(NOW(), '00:05:00')')
... ^~ ^~

以下のように、SUBTIME(NOW(), '00:05:00')の部分をNOW()に変えるとうまくいきます。

rb

1scope :getReservationStates, lambda { 2 select('*') 3 .joins('LEFT OUTER JOIN carts AS c ON lock_id = c.id AND c.create_date >= NOW()') 4 .where('id = 20') 5 }

そもそもjoinメソッド内にこのような記述ができないのか、括弧が多すぎるのか、
それとも全くこの方法付では間違いなのか、お教えいただけますと幸いです。

よろしくお願いいたします。

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

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

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

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

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

guest

回答3

0

ベストアンサー

SQL中のシングルクォートはシングルクォートを2つ書く、ってのがあるので

SQL

1 .joins('LEFT OUTER JOIN carts AS c ON lock_id = c.id AND c.create_date >= SUBTIME(NOW(), '00:05:00')') 23 .joins('LEFT OUTER JOIN carts AS c ON lock_id = c.id AND c.create_date >= SUBTIME(NOW(), ''00:05:00'')') 4

かも?

投稿2019/09/28 02:02

Orlofsky

総合スコア16417

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

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

orori

2019/09/28 02:13 編集

すごいです。昨日から検索しまくっていたんですが解決しました、ご指摘のとおりです。 どうしたらこういうことに引っかからなくなるのでしょう。経験つんで基礎力をあげていくしかないのでしょうね・・・ 本当に助かりました。
Orlofsky

2019/09/28 03:37

お使いのデータベースについてSQL入門レベルの勉強をしっかりやっておくこと。 同じSQLでもデータベースやそのバージョンによって方言が大きいですから、どのデータベースを使うのかを質問のタグで明示したり、バージョンも明記した方が適切なコメントが付き易いです。
orori

2019/09/28 03:48 編集

ありがとうございます、おっしゃるとおりですね。今後気をつけます。MySQL5.7だったのですが勉強精進します!
guest

0

表記法の問題です。一重引用符の中に一重引用符を書いたので、そこで文字列が終わると認識されてしまっています。

エスケープするか、外側を二重引用符にしましょう。

ruby

1.joins("LEFT OUTER JOIN carts AS c ON lock_id = c.id AND c.create_date >= SUBTIME(NOW(), '00:05:00')")

投稿2022/01/13 05:56

maisumakun

総合スコア145967

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

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

0

()の始まりと終わりの数があっていないように思います。

select('*') .joins('LEFT OUTER JOIN carts AS c ON lock_id = c.id AND c.create_date >= SUBTIME(NOW(), '00:05:00'))') .where('id = 20')

select('*') .joins('LEFT OUTER JOIN carts AS c ON lock_id = c.id AND c.create_date >= SUBTIME(NOW(), '00:05:00')') .where('id = 20')

投稿2019/09/28 01:32

退会済みユーザー

退会済みユーザー

総合スコア0

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

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

orori

2019/09/28 01:44 編集

すみません!本文のほうはコピーする際に間違ったようですが、ご指摘のように直してもエラーは発生するのです。本文のほうも訂正しておきます。大変申し訳ありません、エラーの内容も変更しました。 syntax error, unexpected tINTEGER, expecting ')' ...eate_date >= SUBTIME(NOW(), '00:05:00')') ... ^~
退会済みユーザー

退会済みユーザー

2019/09/28 02:20 編集

解決できず、すみません。自分のローカルで少し試してみたのですが、subtimeの部分がうまく動かないですね。。。 少し煩雑になりますが、 時間計算部分を外でやるというのはどうでしょうか? time = Time.now - (5 * 60) select('*') .joins('LEFT OUTER JOIN carts AS c ON lock_id = c.id AND c.create_date >= ?', time) .where('id = 20') また、最適解ではありませんが、ActiveRecordで生SQLを使う方法 参考:https://qiita.com/yut_h1979/items/4cb3d9a3b3fc87ca0435
orori

2019/09/28 02:29 編集

ありがとうございます!今回Zendframework1のアプリをRailsに移植しているのですが、上のような記述が数多く存在し、ご指摘の方法は、もとの記述の形式から異なってしまい、それをすべて適用するのは大変になってしまうのです。しかし、他の方法も模索しているところでした。大変助かりました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.36%

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

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

質問する

関連した質問