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

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

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

HTML5 (Hyper Text Markup Language、バージョン 5)は、マークアップ言語であるHTMLの第5版です。

MySQL

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

PHP

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

Q&A

解決済

4回答

1096閲覧

checkboxでDB情報を任意の数削除したい

Sushi

総合スコア4

HTML5

HTML5 (Hyper Text Markup Language、バージョン 5)は、マークアップ言語であるHTMLの第5版です。

MySQL

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

PHP

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

0グッド

0クリップ

投稿2022/02/14 16:30

編集2022/02/15 14:17

実現したいこと

メモアプリを作成しています。チェックボックスにチェックが入っているものだけをDBから消去したい

PHP

1<?php 2session_start(); 3 4//DB接続// 5try{ 6 $pdo=new PDO('mysql:host=********; 7 dbname=********=utf8', 8 '********', 9 '********'); 10}catch(PDOException $e){ 11echo '接続できませんでした。'; 12} 13?> 14 15<?php 16//ログイン中のIDと書き込み内容をDBに登録// 17if(isset($_SESSION['user']) && isset($_POST['add']) && !empty($_POST['contents'])){ 18$sql = $pdo->prepare('insert into text(login_id,contents) values(?,?)'); 19$sql -> bindvalue(1,$_POST['login_id']); 20$sql -> bindvalue(2,$_POST['contents']); 21$sql -> execute(); 22} 23 24//ユーザーIDによって違う内容を表示// 25if(isset($_SESSION['user']['id'])){ 26$sql=$pdo->prepare('select * from text where login_id = "'.$_SESSION['user']['id'].'"'); 27$sql->execute(); 28foreach($sql as $row){ 29echo '<form method="post">'; 30echo $row['contents']; 31echo '<input type="checkbox" name="check">'; 32echo '</form>'; 33 } 34} 35 36 37//任意のものだけ消去したい 38if(isset($_POST['delete'])){ 39 $sql=$pdo->prepare('delete from text where login_id = "'.$_SESSION['user']['id'].'" and //何か条件を追加すれば良いと思う'); 40 $sql -> execute(); 41} 42 43 44 45 46//PHP空白判定// 47$add = filter_input(INPUT_POST,'add'); 48$contents = filter_input(INPUT_POST,'contents',); 49if(isset($add)){ 50 if(empty($contents)) 51 echo '内容を入力してください'; 52} 53?> 54 55 56<!DOCTYPE html> 57<html lang="en"> 58<head> 59 <meta charset="UTF-8"> 60 <meta http-equiv="X-UA-Compatible" content="IE=edge"> 61 <meta name="viewport" content="width=device-width, initial-scale=1.0"> 62 <meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1, maximum-scale=1, user-scalable=no"> 63 <link rel="stylesheet" href="../css/style2.css"> 64 <title>Document</title> 65</head> 66<body> 67<?php 68require('../header/header.php'); 69?> 70<hr> 71<h1>リスト</h1> 72<?php 73//セッションが入っている場合 74if(isset($_SESSION['user'])){ 75echo 'ユーザーID:<input type="text" name="login_id" value="'.$_SESSION['user']['id'].'" readonly>','<br>'; 76} 77echo '<form method="post">'; 78echo '<input type="text" name="contents" value="">'; 79echo '<button type="submit" name="add">追加</button>'; 80echo '<button type="submit" name="delete">消去</button>'; 81echo '</form>'; 82?> 83 84</body> 85</html> 86

環境

  • VSCode
  • MySQL

試したこと

$sql -> excute($_POST['check']);にした場合できるかなと思いましたが無理でした。
postにcheckの値が入っていれば送信して任意のものを消去できる,もしくはDBにもチェックボックスみたいな感じの役割のものを追記すればできると思いましたがわかりませんでした。有識者さんアドバイスお願いいたします。


更新後のコード

PHP

1<?php 2session_start(); 3 4//DB接続// 5try{ 6 $pdo=new PDO('mysql:host=mysql154.phy.lolipop.lan; 7 dbname=LAA1290628-upup;charset=utf8', 8 'LAA1290628', 9 'Shion0724'); 10}catch(PDOException $e){ 11echo '接続できませんでした。'; 12} 13?> 14 15 16<!DOCTYPE html> 17<html lang="en"> 18<head> 19 <meta charset="UTF-8"> 20 <meta http-equiv="X-UA-Compatible" content="IE=edge"> 21 <meta name="viewport" content="width=device-width, initial-scale=1.0"> 22 <meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1, maximum-scale=1, user-scalable=no"> 23 <link rel="stylesheet" href="../css/style2.css"> 24 <title>Document</title> 25</head> 26<body> 27<?php 28require('../header/header2.php'); 29?> 30 <hr> 31<h1>リスト</h1> 32<?php 33echo '<form method="post">'; 34//セッションが入っている場合 35if(isset($_SESSION['user'])){ 36echo 'ユーザーID:<input type="text" name="login_id" value="'.$_SESSION['user']['id'].'" readonly>','<br>'; 37} 38 39//内容追加 40echo '<label for="name">内容:</label><input type="text" name="contents" id="name" value="">'; 41echo '<button type="submit" name="add">追加</button>'; 42echo '</form>'; 43 44//内容消去 45echo '<form id="check" method="post">'; 46echo '<button type="submit" name="delete">消去</button>'; 47if(isset($_POST['check'])){ 48 $check = $_POST['check']; 49 foreach($check as $name){ 50 //チェックボックスに内容が入っている 51 //echo $name; 52 } 53} 54echo '</form>'; 55?> 56 57<?php 58//ログイン中のIDと書き込み内容をDBに登録// 59if(isset($_SESSION['user']) && isset($_POST['add']) && !empty($_POST['contents'])){ 60$sql = $pdo->prepare('insert into text(login_id,contents) values(?,?)'); 61$sql -> bindvalue(1,$_POST['login_id']); 62$sql -> bindvalue(2,$_POST['contents']); 63$sql -> execute(); 64} 65 66//内容を消去// 67if(isset($_POST['delete'])){ 68 $sql=$pdo->prepare('delete from text where login_id = "'.$_SESSION['user']['id'].'" and contents="'.$name.'"'); 69 $sql -> bindvalue(1,$name); 70 $sql -> execute(); 71} 72 73//ユーザーIDによって違う内容を表示// 74if(isset($_SESSION['user']['id'])){ 75$sql=$pdo->prepare('select * from text where login_id = "'.$_SESSION['user']['id'].'"'); 76$sql->execute(); 77foreach($sql as $row){ 78// echo '<form method="post">'; 79echo $row['contents']; 80echo '<input type="checkbox" name="check[]" form="check" value="'.$row['contents'].'" >'; 81echo '<br>'; 82// echo '</form>'; 83 } 84} 85 86 87 88//PHP空白判定// 89$add = filter_input(INPUT_POST,'add'); 90$delete = filter_input(INPUT_POST,'delete'); 91$contents = filter_input(INPUT_POST,'contents',); 92$check = filter_input(INPUT_POST,'check',); 93if(isset($add)){ 94 if(empty($contents)) 95 echo '内容を入力してください'; 96} 97if(isset($delete)){ 98 if(empty($check)) 99 echo 'チェックを入れてください'; 100} 101?> 102 103 104</body> 105</html> 106

現状ですと1つずつしか消去できない感じです。
delete文のところに問題があると思いますが躓いています。

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

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

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

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

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

guest

回答4

0

PHP

1<?PHP 2$ch=filter_input(INPUT_POST,"ch",FILTER_DEFAULT,FILTER_REQUIRE_ARRAY); 3if(!is_null($ch)){ 4 $sql="delete from tbl where id in("; 5 $sql.=implode(",",array_fill(0,count($ch),"?")); 6 $sql.=")"; 7 //$stmt = $pdo->prepare($sql); 8 //$stmt->execute($ch); 9 print $sql; 10} 11?> 12<form method="post"> 13<label><input type="checkbox" name="ch[]" value="1">1</label> 14<label><input type="checkbox" name="ch[]" value="2">2</label> 15<label><input type="checkbox" name="ch[]" value="3">3</label> 16<input type="submit" value="send"> 17</form>

投稿2022/02/15 01:36

yambejp

総合スコア114784

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

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

0

ベストアンサー

postにcheckの値が入っていれば送信して任意のものを消去できる,もしくはDBにもチェックボックスみたいな感じの役割のものを追記すれば

フレームワークを利用しているわけでもなく、手組でやる以上はそういった便利なものはありません。
1つ1つ情報を受け渡し、受け取り、処理を書いてあげるしかありません。

チェックボックスに限りませんが、同じnameで複数値送る場合はリクエストを配列で送る必要があります。
なのでname属性の属性値に[]をつけて「この要素は配列である」ことを明示してあげる必要があります。

PHP

1echo '<input type="checkbox" name="check[]">';

そして、nameがキーとなって取得されるのはその要素のvalue属性の属性値なので、nameだけではいけません。

PHP

1echo '<input type="checkbox" name="check[]" value="'.$row[/*IDなど一意となるカラム*/].'">';

そしてチェックボックスは「チェックされたもの」のみ送信されます。
例えばこうなっていたとしたら

html

1<input type="checkbox" name="check[]" value="1" checked> 2<input type="checkbox" name="check[]" value="2"> 3<input type="checkbox" name="check[]" value="3" checked>

こうすることで$_POST["check"]には[1,3]と値が配列が入ってきます。

あと今現在「消去」ボタンが所属しているのは追加ボタンと同じフォーム内ですし、チェックボックスがあるのも遥か彼方です。
一覧表示の場所の問題もあるでしょうし、可能ならbody内に適宜配置してもらって、
「消去」ボタンもform内に置いたほうが良いでしょう。
※formタグにIDをつけてボタンにform属性を指定して属性値をIDと同じにするとform内に入れる必要はないですが。

ここまでが「前準備」です。
ようやくデータを送信する準備ができたという段階です。

削除処理とかは置いといて「ちゃんとチェックしたチェックボックスのvalueが送られているか」を確認してみてください。


次にやるべきは「削除SQLの完成」でしょう。
まずは既存データの削除をPHPからではなく直接SQL実行してやってみては如何でしょうか。
質問を見た限りだと「条件はWhereで指定する」「カラム=値で指定する」「複数ある場合はANDで繋ぐ」ということは理解しているようですから、その組み合わせで行います。
全削除でない限り特定のデータを削除するのでしょうから、「何を以て特定のデータとするか」ですが、これはアプリケーションの仕様なので決めるしかありません(本来は設計時に決まっていることです)


ここまで出来てようやく「削除SQLをPHPから実行する」です。
先に書いたように「送りかた」と「送った時の内容」が分かったと思いますし、チェックした内容が来ていることも確認できていると思います。

リクエストは配列で来ているのですから単純にするならその配列の個数分だけSQLを実行すればチェック入れた分だけで削除できます。つまり、$_POST["check"]をループ。

SQL1回で「同じカラムを参照するが複数の値どれかに一致するデータを抽出する」ことができるのと同様、同じ条件で特定の幾つかの行をSQL1回で削除することも出来ますが、それはまず意図した行が意図通りに削除できるようになった次の段階です。


ただ、SQLインジェクションの脆弱性もあるので、insert と同じようにプリペアドステートメントから値をバインドされたほうが良いです(それがセッション参照であっても、実装にブレがでますし)し、

今のコード進行だと削除より取得が先に書かれているので、「画面に削除したデータが出てしまっている」「再アクセスすると消える」という現象が起きえます。
処理の優先順も考えた方が良いです。

投稿2022/02/14 22:49

m.ts10806

総合スコア80850

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

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

Sushi

2022/02/15 14:17

コードを更新しました。 一応前準備まではできてると思います。 checkboxを使ってDBに登録している内容を1つずつ消去することはできました。 「何を以て特定のデータとするか」について今回は'contents'でいこうと思います。(重複している場合、両方消去) 現状は複数選択をした場合、最後に選択した内容だけ消去という形になってしまっています。 <input type="checkbox" name="check[]" value="1" checked> <input type="checkbox" name="check[]" value="2" checked> ('delete from text where login_id = "'.$_SESSION['user']['id'].'" and contents="'.$name.'"'); おそらく$nameのなかに12は入っていると思いますが、2の内容だけが消去されるという形です。
m.ts10806

2022/02/15 21:14

テーブル定義次第なのですけど、insertからすると、login_idだけでデータ特定できるのでは?
Sushi

2022/02/16 02:28

login_idはユーザーごとに異なるページを表示するためにinsertしています。 contents 内容1 login_id 2 contents 内容2 login_id 1 contents 内容3 login_id 2 という感じにしており、現状ですとlogin_idを指定した場合、2の内容がすべて消去されてしまいますのでandの部分の追記を考えています。
Sushi

2022/02/16 02:33

login_id 2でログイン中の場合です。
m.ts10806

2022/02/16 02:53

でしたらログインIDの他にもう1つキーを準備してください。 自由入力の内容を削除条件にするのは設計としてかなり無理があります。
Sushi

2022/02/16 03:04

わかりましたやってみます。
m.ts10806

2022/02/16 03:06

カラムを追加、しかもキーとなるので(not null)データも1回全部消してやり直す必要があります。
Sushi

2022/02/16 07:42

質問内容解決できました。これから作成していく上で基本的なDB操作やmysqlについて学び直しながら作成していこうと思います。アドバイスありがとうございました。頑張ります。
m.ts10806

2022/02/16 07:51

そうですね。 なにか作るときに情報整理は必須です。
guest

0

php

1 and //何か条件を追加すれば良いと思う

↑そこが一番重要でしょう。そこでどんな条件を試しましたか?

まずはPHPを介さずに直接DBのテーブルにアクセスして実際にレコードを削除してみれば、どんなクエリを投げればいいかが分かると思います。
phpMyAdminなどを使えば、簡単に出来ますよ。

投稿2022/02/14 21:00

teratail_begin

総合スコア72

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

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

m.ts10806

2022/02/14 22:37

ほぼ「質問への追記修正依頼」に書くような内容と思います。
Sushi

2022/02/16 02:31

おっしゃる通りです。login_idなどを試しましたが内容が全部消えてしまいます。 DBのほうで操作しながらandの追記などを考えていきます。 現状ではcontentsで一意に指定できたらなと思います。
teratail_begin

2022/02/16 06:29 編集

想像ですけど、テーブル設計の時点で適切な主キーが設定されてないような気がします。 「書き込み1件ごとに1つの主キーが付く」という状態になっていれば、いろいろ解決しやすくなるかと思います。それ自体は特に意味を持たない、単なるユニークな数字を主キーにすれば、たぶんあなたの抱えている悩みは解決します。「主キー」という言葉にピンとこなければ、「書き込みID」と言ってもいいかもしれません。 詳しくは「主キー」とか「プライマリキー」とかでググってみてください。 MySQLではオートインクリメントでユニークな主キーを自動生成できますので、その辺もググってみてください。 要件によっては「正規化」もググったほうがいいかもしれません。
Sushi

2022/02/16 06:43

textテーブルには login_id contents check_id(新しく追加) オートインクリメント という感じにしています。表示の場合はlogin_idとcontentsの組み合わせ 消去の場合はcheck_idとcontentsの組み合わせで試していますが1つずつの消去しかできない感じです。
teratail_begin

2022/02/16 06:51

私の書き込みをもう一度よく読んでください。 「書き込みを特定できる適切な主キーが設定されていますか?」 「主キーなどの用語についてググってください」 私はこのように書きました。 それを実行してくれましたか? ググりましたか? あなたのご返信は、私のアドバイスとは噛み合っていないように思えます。 check_idというのが私が言っている一意の主キーの役割を果たしているようでしたら、check_idをwhere条件に入れて削除すればあなたの望み通りの結果になるはずですが? 「check_idとcontentsを組み合わせる」という意味がわかりません。check_idが主キーになっているならば、それのみで書き込みを特定して削除可能です。 一回のクエリで複数のcheck_idを指定したい、というのならば、「mysql where 演算子」でググってください。
Sushi

2022/02/16 06:54

訂正します。現状は 表示の場合、login_id=ログイン中のidで表示 消去の場合、login_id=ログイン中のid and check_id = //配列の最後尾しか入らない ので1つずつ消去という感じになってしまっています。
Sushi

2022/02/16 06:54

もう一度読んでから以降の書き込みをします
Sushi

2022/02/16 07:39

主キーについてググってきました。 上記とは別ですが、チェックボックスにチェックしている項目だけ消去できました。 delete文の記載場所のせいか配列に値が1つしか入ってなかったです。記載場所をforeachの下にした場合、ちゃんとチェックした値が配列に入っていました。 delete文としては(delete from text where check_id = //チェックした項目)でできました。 一応質問内容じたいは解決しましたが、他の記載方法やmySQLやDBの基本について学び直しながらメモアプリを作成していきたいと思います。アドバイス等ありがとうございました。
teratail_begin

2022/02/16 08:47

RDBMSの基礎やSQLについて少し勉強しておくと、PHPでいろいろこねくり回すよりも簡単かつ確実に目的のDB操作ができたりします。 私も初心者レベルですが、一緒にぜひ頑張りましょう。
guest

0

回答とは直接関係ありませんが、
「投稿2022/02/15 01:30 編集2022/02/15 15:00」
という表示になっていますね。

編集日時が未来の日付です(今日の15時にはまだなっていない)。
teratailのバグかな??

イメージ説明

投稿2022/02/14 21:05

teratail_begin

総合スコア72

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

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

m.ts10806

2022/02/14 21:57 編集

質問者がどうともできることではなく、質問の回答でもない事項をわざわざ回答として投稿するのは如何なものかと。 当該現象は下記スレッドにて当初から既に報告されています。 https://teratail.com/questions/36leqkyeq9nzih
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問