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

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

新規登録して質問してみよう
ただいま回答率
85.48%
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

解決済

2回答

1731閲覧

PHPのプルダウンメニューが反映されない

gsuisk

総合スコア72

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クリップ

投稿2017/09/20 14:04

PHPの勉強で、ページリンクを作成したのですが機能しません。

MySQLに番号(id)、性別(sex)、名前(name)の3つのカラムを持つレコードをいくつか格納しました。

そこで性別を選択し、名前を入力し検索すると、一致するレコードを取り出して表示させました。
(性別選択は必須で、名前が未入力であれば選択された性別のレコードを全部抽出)

入力画面は以下です。input.html

HTML

1 <form action="search.php" method="post"> 2 3 性別: 4 <select name="sex" required> 5 <option value="男">男</option> 6 <option value="女">女</option> 7 </select> 8 9 名前: 10 <input type="text", name="name"> 11 12 <input type="submit" value="検索"> 13 14 </form>

抽出してきたレコードをは1ページあたり3レコードになるよう分割しました。search.php

PHP

1<?php 2 3 if(isset($_POST["sex"])){ 4 $sex=$_POST["sex"]; 5 }else { 6 $sex="男"; 7 } 8 9 10if(isset($_POST["name"])){ 11 $name=$_POST["name"]; 12}else { 13 $name=""; 14} 15 16 $pdo = new PDO($dsn, $user, $password); 17 $pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, false); 18 19//1ページあたり3つ表示させる 20if(isset($_GET['page'])){ 21 $page=(int)$_GET['page']; 22}else { 23 $page=1; 24} 25 26if ($page > 1) { 27 $start = ($page * 3) - 3; 28} else { 29 $start = 0; 30} 31 32 $sql = "SELECT * FROM table WHERE 1 "; 33 34 $data=[]; 35 if(!is_null($sex)){ 36 $sql.="and sex=? "; 37 $data[]=$sex; 38 } 39 if(!is_null($name)){ 40 $sql.="and ( 0 "; 41 $sql.="or name like concat('%',?,'%') "; 42 $data[]=$name; 43 $sql.="or ? like concat('%',name,'%') "; 44 $data[]=$name; 45 $sql.=") "; 46 } 47 $sql.="LIMIT {$start}, 3"; 48 49 $stm = $pdo->prepare($sql); 50 $stm->execute($data); 51 $result=$stm->fetchAll(PDO::FETCH_ASSOC); 52 53 foreach ($result as $row) { 54 echo $row['name']; 55 } 56 57 58 59// テーブルのデータ件数を取得する 60 61$sql = "SELECT * FROM table WHERE 1 "; 62$data=[]; 63if(!is_null($sex)){ 64 $sql.="and sex=? "; 65 $data[]=$sex; 66} 67if(!is_null($name)){ 68 $sql.="and ( 0 "; 69 $sql.="or name like concat('%',?,'%') "; 70 $data[]=$name; 71 $sql.="or ? like concat('%',name,'%') "; 72 $data[]=$name; 73 $sql.=") "; 74} 75 76$stm = $pdo->prepare($sql); 77$stm->execute($data); 78 79//抽出したレコード数 80$records=$stm->rowCount(); 81 82//トータルページ数 83$totalPage = ceil($records / 3); 84 85?> 86 87<?php for ($i=1; $i<= $totalPage ; $i++):?> 88 89<a href="?page=<?php echo $i ?>"><?php echo $i; ?></a> 90 91<?php endfor; ?> 92

input.htmlで「男」を選択すれば問題なく機能します。

しかし「女」を選択して検索すると、確かに「女」で登録された3レコードが表示されますが、下のページリンク(1 2 3...)をクリックすると、「男」のレコードが表示されてしまいます。1をクリックすると、「男」のレコードが上から3つ分表示さます。

つまり、input.htmlのプルダウンメニューの選択が反映されません。

原因が全く分からずに困っています。皆様のお力を貸していただきたいです。

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

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

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

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

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

guest

回答2

0

ベストアンサー

下のページリンク(1 2 3...)をクリックすると、「男」のレコードが表示されてしまいます

ページングにsexをパラメータで渡す処理がかかれていませんね
そもそもデータ受け渡しをpostでしているので、get経由では処理ができません

考え方としては

  • データ渡しをgetにして、ページングの際にもパラメータを渡すか
  • postで渡したデータをセッションにいれて継続性をだす

が妥当だと思います

sample

PHP

1<form method="post"> 2性別: 3<select name="sex" required> 4<option value=""></option> 5<option value=""></option> 6</select> 7<input type="submit" value="検索"> 8</form> 9<?PHP 10$sex=filter_input(INPUT_POST,"sex")?:filter_input(INPUT_GET,"sex"); 11if(!is_null($sex)){ 12print "<a href=\"?sex=".urlencode($sex)."\">".htmlspecialchars($sex)."</a>"; 13} 14?> 15

追記

sexの他にnameとpageを保持する

PHP

1<form method="post" action="<?PHP print $_SERVER["SCRIPT_NAME"];?>"> 2性別: 3<select name="sex" required> 4<option value=""></option> 5<option value=""></option> 6</select> 7<input type="text" name="name"> 8<input type="submit" value="検索"> 9</form> 10<?PHP 11$param=[]; 12$sex=filter_input(INPUT_POST,"sex")?:filter_input(INPUT_GET,"sex"); 13if(!is_null($sex)) $param=array_merge($param,["sex"=>$sex]); 14$name=filter_input(INPUT_POST,"name")?:filter_input(INPUT_GET,"name"); 15if(!is_null($name)) $param=array_merge($param,["name"=>$name]); 16$page=filter_input(INPUT_GET,"page",FILTER_DEFAULT,["options"=>["default"=>0]]); 17$prev_search=$page>0?("?".http_build_query(array_merge($param,["page"=>$page-1]))):""; 18$next_search="?".http_build_query(array_merge($param,["page"=>$page+1])); 19 20if(!is_null($page)){ 21 if($page>0) print "<a href=\"{$prev_search}\">&lt; 前へ </a>"; 22 print "<a href=\"{$next_search}\">後ろへ &gt;</a>"; 23} 24?>

投稿2017/09/21 00:27

編集2017/09/22 00:44
yambejp

総合スコア114839

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

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

gsuisk

2017/09/21 05:56

この場合はセッションを使うのが良いですかね?getだと性別と名前の2つ渡さないといけませんよね。 POSTされた段階でまず性別と名前をSESSIONに入れ、SQL文での$sexと$nameを $_SESSION['sex']、$_SESSION['name']にしたんですが、結果は同じくページング番号をクリックしたら男のデータになってしまいました。 <a href="?page=<?php echo $i ?>"><?php echo $i; ?></a> セッションはどの$iページでも継続されているのではないのですか?
gsuisk

2017/09/21 14:05

<form>を method="get" として、ページ遷移の際には名前と性別も一緒に<a>で送るのが良いですかね?つまりpostは使わずにgetで統一するということです。
yambejp

2017/09/22 00:40

前回はちょっと端折りすぎてかえって混乱させてしまったみたいで失礼しました 基本はGETバージョンです。追記しておきました
gsuisk

2017/09/22 16:24

丁寧にコードまで書いていただきありがとうございます。 $sexも$nameもフォームからGETで送ろうと思います。 $page=filter_input(INPUT_GET,"page",FILTER_DEFAULT,["options"=>["default"=>0]]); これは $page = intval(filter_input(INPUT_GET, 'page')); このように書いても問題ないでしょうか?
gsuisk

2017/09/22 16:26

また、filter_inputを使うのと以下ではどちらが良いですか? if( (isset($_GET['page'])) && (preg_match('/^[1-9][0-9]*$/',$_GET['page'])) ){ $page=(int)$_GET['page']; }else { $page=1; }
guest

0

SUBITはformのaction先に一度だけ送信します。
GET送信はURLのクエリストリングから取得するので動作しますが、
POST送信は一度しか送信しないため、ページングのリンクで遷移した際には
input.htmlから送信した内容は保持されていません。
そのため、性別部分は!isset($_POST["sex"]となり、elseで設定している
$sex="男";となっています(そのほかの送信内容も同様)

ページングリンクにGETで検索項目を追加で送信して受け取るようにするか、
セッションを利用してPOST送信内容を保持するようにしてください。

その他:
input.htmlの名前入力のinputに「, 」入ってますが転記ミスですか?
そうでないのであれば、タグ内に関係のない文字が入ると正しく動作しない原因となりかねないので注意してください。

投稿2017/09/20 22:05

m.ts10806

総合スコア80850

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

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

gsuisk

2017/09/21 14:01

input.htmlの「,」はミスでした...ご指摘ありがとうございます。 ページ遷移の時のinput.htmlからのPOSTデータが渡されていないので、ページ遷移するとPOSTデータが初期化されることが原因なのですね。 ことような場合は、input.htmlの<form>もgetにして、ページ遷移の際に名前と性別のパラメータを<a>で渡してあげるのが一般的なのでしょうか?
m.ts10806

2017/09/21 23:18

要件次第ですね。どれが正しいとかっていうのはないと思います。 検索条件をブックマークしてもらいたいのであれば全てGETでしょうし。そうでなければセッション保持でしょうし。 いずれにしてもSQLインジェクションなどの対策は講じなければなりません。
gsuisk

2017/09/22 15:58

どちらの方が安全とかいうことでもないですよね。 検索結果などはできるGETがよいのかなと思いました。 ありがとうございました。
m.ts10806

2017/09/30 21:27 編集

いずれにしても出力時のXSS対策などはしなければならないので、 GETかセッションかはあくまで条件保持の手段にすぎません。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問