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

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

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

MySQL(マイエスキューエル)は、TCX DataKonsultAB社などが開発するRDBMS(リレーショナルデータベースの管理システム)です。世界で最も人気の高いシステムで、オープンソースで開発されています。MySQLデータベースサーバは、高速性と信頼性があり、Linux、UNIX、Windowsなどの複数のプラットフォームで動作することができます。

SQL

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

PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

Q&A

5回答

1097閲覧

新しく追加した列を条件に含めずに検索したい

metal777

総合スコア7

MySQL

MySQL(マイエスキューエル)は、TCX DataKonsultAB社などが開発するRDBMS(リレーショナルデータベースの管理システム)です。世界で最も人気の高いシステムで、オープンソースで開発されています。MySQLデータベースサーバは、高速性と信頼性があり、Linux、UNIX、Windowsなどの複数のプラットフォームで動作することができます。

SQL

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

PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

0グッド

0クリップ

投稿2020/06/01 07:38

MySQL(Aurora) + PHP7 で簡単なwebアプリを作っています。

商品テーブル item が存在するのですが、今回そこに削除フラグとして以下のように deleted という列を追加することになりました。

ALTER TABLE item ADD deleted TINYINT UNSIGNED DEFAULT 0 -- 0:有効, 1:削除済

ここまでは何の問題もないのですが、この商品テーブルを参照するSQLがソース内に既に500以上存在します。(ORMやビューは未使用です)

ほとんどのケースにおいて、削除済み商品については基本的に処理をさせたくないため、原則的には WHERE deleted = 0 をSQLに追加していけばよいのですが、現時点で item テーブルにアクセスするSQLが各ソース内に合計で500以上存在します。

流石にこれらのSQLに対して1つ1つ WHERE条件を追加していくのは無駄な気がしてならないのですが、95%以上のSQLで deleted = 0 のみのデータを対象とすることから、「WHERE句に何も指定していない場合は deleted = 0 として扱われ、明示的に削除済みの商品も扱いたい場合は deleted = 1 ないし deleted IN (0,1) のように指定することで扱える」ようにするために、何か良い方法はないでしょうか?

なお、現時点では削除済みの商品はないものの、今後削除済みになる可能性はあるという状態です。
また、単純なSELECTのみでなく、UPDATE/INSERTやJOIN、サブクエリ等にも使用しています。

書き換え漏れや再テストの手間を考えて、既存のSQLやPHPソースの書き換えを最小限にできればと考えています。
最初からビューにしておけばいくらか手間が減った気はするのですが、今からSQLの参照先を全てビューに変更するのもどうかと思っています。

こういうケースは結構ありそうな気がするのですが、自分で検索しても良い検索結果が得られなかったため、妙案があればアドバイスいただければ幸いです。

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

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

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

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

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

guest

回答5

0

WHERE句でdeleted列の判断が必要ならインデックスに追加することも検討した方が良いでしょう。

削除済みデータを参照する機会が少なければ、deleted列を追加するのではなく、削除済みデータを別テーブルに保存する方法も考えられます。

metal777さんが明日COVID-19を発症して亡くなっても後継者がシステムを維持できるように、きちんとシステムを管理しておくのがソフトウェア屋としてのモラルです。

商品テーブルを参照するSQLがソース内に既に500以上存在します。

であれば「簡単なwebアプリ」ではないです。

投稿2020/06/01 08:34

Orlofsky

総合スコア16417

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

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

m.ts10806

2020/06/01 08:55

>であれば「簡単なwebアプリ」ではないです。 同感です。 管理面もかなり複雑
guest

0

where句になにも指定しないで条件分岐するのはむしろ危険なので
きちんとdelete=0とするか、思い切って物理削除して、別テーブルに
保持するなど抜本的な対応が必要でしょう

投稿2020/06/01 07:50

yambejp

総合スコア116724

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

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

metal777

2020/06/01 08:03

別テーブルも考えたのですが、このためだけにトランザクション更新処理が必要になってしまうことが多発してしまうため、今のところ想定から外しました。 主旨としては「SQL標準では厳しいと思われるので、MySQL特有の機能(関数やユーザ変数など)で何とかして delete=0 を省略できないか」ということになります。 ストアドプロシージャにしていれば比較的簡単だったのですが、素のSQLが大量に書かれている状態でして・・
yambejp

2020/06/01 08:05

元テーブルで削除して、別テーブルに保存する場合、triggerでやれば一発ですね。
guest

0

こういうケースは結構ありそうな気がするのですが

あるかもしれませんが、「やってはいけない」パターンかと思います。

今からSQLの参照先を全てビューに変更するのもどうかと思っています。

PHP側でORMが挟まっていてそのレイヤでどうにかできるのでなければ、いちばん手間の少ない方法としてはこれでしょう。

投稿2020/06/01 07:47

maisumakun

総合スコア146018

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

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

0

whereの対象にdeletedを使わなければいいだけじゃない
そこに懸念があったり実装が出来ない理由があるならそこまで質問に書いてないと分からない

投稿2020/06/01 07:47

hentaiman

総合スコア6426

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

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

metal777

2020/06/01 07:58

deletedを指定しない場合、今後削除済みデータが発生した場合に不要なデータまで対象となってしまいます。 PHP側も直せばよいのは当然ですが、LIMITやORDER BY句も使用しているのでSQL内のみで完結させたいと考えています。
hentaiman

2020/06/01 08:09

orderbyはともかくLimitはどうしようもない。既に方法については様々検討されてると思うし本来取るべき手法も理解はされてると思うので、後は技術以外の面で検討するしかないですね レコード件数・修正箇所・そのシステムがどの程度生きるのか・今後拡張するのかを含めてコストに見合った方法を取るのがよろしいでしょうね
guest

0

案を挙げますが、これをするくらいならphpを直した方がマシ、
と考えて頂けたら良いと思います。
・現状のitemテーブルをitem2という名前に変更してdeletedを追加する
・item2をdeleted = 0の条件で参照するitemというビューを作る

作業時はシステム停止が必要
itemテーブルの更新処理の仕様次第では修正が必要
deleted = 0ではない条件で参照する機能も修正が必要
あとでわかりにくい
JOINとかもしているということなので実行計画が狂うかも
etc...

リスキーかつ美しくないと思います。

投稿2020/06/01 08:55

toyotaku

総合スコア103

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

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

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

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

ただいまの回答率
85.35%

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

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

質問する

関連した質問