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

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

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

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

PHP

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

Q&A

解決済

2回答

578閲覧

MySQLのデータをPHPで更新したい

kazumasa118

総合スコア6

MySQL

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

PHP

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

0グッド

0クリップ

投稿2020/02/04 18:11

編集2020/02/04 23:29

前提・実現したいこと

MySQL 5.7.26
PHP 7.3

テーブル名:syohin_data
id name tanka
1 りんご 300
2 ばなな 400

上記テーブルをPHPで更新したいのですが、実行時にエラーが出てしまいます。
SQL Server 2014で実行した場合,問題なく更新されるのですが、MySQLで実行するとエラーになってしまいます。update文を1つにした場合は問題なく更新されたので、2つある場合にエラーになるのは確認しました。MySQLではこのような形で更新するのは不可能なのでしょうか?
ご教授お願いいたします。

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

Fatal error: Uncaught PDOException: SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'UPDATE SYOHIN_DATA1 SET TANKA1 = 600 WHERE ID = 2' at line 1 in

該当のソースコード

<?php $sql = 'UPDATE SYOHIN_DATA1 SET TANKA1 = 500 WHERE ID = 1;UPDATE SYOHIN_DATA1 SET TANKA1 = 600 WHERE ID = 2'; // DB接続情報 $user = 'ユーザー名'; $pass = 'パスワード'; $dbnm = 'DB名'; $host = 'ホスト名'; // 接続先DBリンク $dsn = "mysql:host={$host};dbname={$dbnm}"; // DB接続 try { $conn = new PDO($dsn, $user, $pass, array(PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES utf8')); $conn->setAttribute(PDO::ATTR_EMULATE_PREPARES, false); $conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); } catch (Exception $e) { echo "<p>DB接続エラー</p>"; echo $e->getMessage(); exit(); } //実行 $result = $conn->query($sql); if( $result === false ) { echo mysql_errno($result) . ": " . mysql_error($result). "\n"; } //接続クローズ $result =null; $conn = null; ?>

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

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

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

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

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

m.ts10806

2020/02/04 20:16

コードはマークダウンのcode機能を利用してご提示ください
Orlofsky

2020/02/04 22:31

[PDO]タグを追記されては?
guest

回答2

0

ベストアンサー

MySQLではこのような形で更新するのは不可能なのでしょうか?

MySQLで、というよりPHPからの実行が不可能だと思います。
1つのSQLにつき1の結果を返します。
手元にSQLServerないので試してませんが。

設定次第で可能とのことです。

MySQL 関数 (PDO_MYSQL)

PDO::MYSQL_ATTR_MULTI_STATEMENTS (integer)
FALSE にすると、PDO::prepare() や PDO::query() でのマルチクエリの実行を無効にします。

つまり、trueを指定すると複数実行できるということになります。
trueにするリスクはあります。
いずれにしても後述のようにSQLインジェクション対策は必須です。

蛇足:
他にもイカン実装が幾つかあります。

本来は値も固定ではなく可変になるのでそうなるとqueryでそのまま実行するとSQLインジェクションの脆弱性があります。

というかmysql*系はPHP7では削除された機能です。

投稿2020/02/04 20:38

編集2020/02/04 21:56
m.ts10806

総合スコア80850

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

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

m.ts10806

2020/02/04 21:52

なんと。 貴重な情報ありがとうございます。
maisumakun

2020/02/04 22:01

(以前に別件で複文にハマったことがありまして)
退会済みユーザー

退会済みユーザー

2020/02/04 23:37

記事だと標準で許可の模様?
m.ts10806

2020/02/04 23:50

んーどうなんでしょう。 現状動いてないなら明示的にtrueにするか、やはり本数分実行するのが良いですね。 私なら後者。本数分実行します。
退会済みユーザー

退会済みユーザー

2020/02/04 23:55

今回は PDO::ATTR_EMULATE_PREPARES, false なんで、複文が使えないかと。 参考: https://blog.tokumaru.org/2013/12/pdo-and-mysql-allow-multiple-statements.html 「PDO+MySQLで複文実行できる条件」のあたり > PHP5.2.0以下を使っている場合、、あるいは PDO::setAttribute(PDO::ATTR_EMULATE_PREPARES, false); を呼んでいる場合は、PDO::queryによるSQL呼び出しであっても下記のようにいったんprepareされます。 ちなみに俺はここもイヤ。 PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES utf8' 多分実害はないだろうけど。。。
m.ts10806

2020/02/04 23:59

te2jiさん フォローありがとうございます。勉強になります。 やはり謎の実装は多いですね。 SET NAMESは私も気にはなりましたが、他の実装の方がまずそうなので、私も実害なしと思い結局スルーしました。
kazumasa118

2020/02/05 00:04

ありがとうございます!!!解決しました!! 『PDO::ATTR_EMULATE_PREPARES, false』を消したらできるようになりました!
m.ts10806

2020/02/05 00:07

今回はそこよりもまずい実装がたんまりあるのでご認識を。
退会済みユーザー

退会済みユーザー

2020/03/27 07:02 編集

*複文を使用しないで、分割すべきかと。 初学者は、エミュレーションを off にした実装を心がけたほうが良いです。 以下の違いがわかるようになってから、on を検討してください。 https://qiita.com/mpyw/items/b00b72c5c95aac573b71#%E3%82%A8%E3%83%9F%E3%83%A5%E3%83%AC%E3%83%BC%E3%82%B7%E3%83%A7%E3%83%B3%E3%81%AB%E9%96%A2%E3%81%99%E3%82%8B%E3%81%BE%E3%81%A8%E3%82%81 参考 https://qiita.com/te2ji/items/56c194b6cb9898d10f7f https://teratail.com/questions/233051
kazumasa118

2020/02/05 00:17

ご指摘ありがとうございます! 大変勉強になりました!
m.ts10806

2020/02/05 00:19

PHPでデータベースに接続するときのまとめ 回答にも貼ってますが途中じゃなく、トップからリンク貼っておけばよかった。 この記事にはずっとお世話になってるなあ
guest

0

バッドノウハウ

更新(ちゃんとデータ件数文分けて投げたほうが早いです。)

UPDATE t SET a = CASE name WHEN 'a' THEN 2 WHEN 'b' THEN 3 ELSE a END WHERE name in ('a', 'b');

検証用データ作成

CREATE TABLE t ( name varchar(1) primary key, a int, b int, c int); insert into t values ( 'a', 1, 1, 1 ), ( 'b', 1, 1, 0 ), ( 'c', 1, 0, 1 ), ( 'd', 0, 1, 1 ), ( 'e', 0, 0, 1 ), ( 'f', 0, 1, 0 ), ( 'g', 1, 0, 0 ), ( 'h', 0, 0, 0 );

投稿2020/02/04 22:16

退会済みユーザー

退会済みユーザー

総合スコア0

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

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

kazumasa118

2020/02/04 23:34

ご指摘ありがとうございます。 勉強になりました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問