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

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

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

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

Q&A

解決済

1回答

919閲覧

PHPで検索抽出後のページネーション

sj3600

総合スコア13

PHP

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

0グッド

0クリップ

投稿2019/01/15 11:46

お世話になります。
レシピサイトを作成しているのですが一覧表示でページネーションがうまくできなくて困っています。
2頁目をクリックすると「Forbidden access」になります。

前後の関係から少し長く記載していますが 対象部分は最下部の30行くらいだと思います。
検索からデータ抽出は120件ほどできています。

ご多忙のところ大変恐縮ですが、ご指導くださいませ。

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

2頁目のリンクは
http://www.****.com/cook_ichiran.php?n=20&where= where meat_kbn=1 and ( meat_bui=1 or meat_bui=2)
となっていまして「Forbidden access」になります。

該当のソースコード

<?PHP require("../../inc/scp.php"); require("../../inc/config.php"); $db = pg_connect(DB_CONN) or die("接続失敗\n"); $err = ""; $n = (isset($_REQUEST["n"])) ? $_REQUEST["n"] : 0; $n2 = $n + 20; $where = ""; $where = (isset($_REQUEST["where"])) ? $_REQUEST["where"] : ""; if(strlen($_POST["search"]) > 0){ if(count($_POST["gyu"]) > 0){ $gyudata=""; for($i=0;$i<count($_POST["gyu"]);$i++){ if($i== 0){ $gyudata .= " meat_bui=".$_POST["gyu"][$i]; }else{ $gyudata .= " or meat_bui=".$_POST["gyu"][$i]; } } $where .= " where meat_kbn=1 and (".$gyudata.")"; } if(count($_POST["buta"]) > 0){ $butadata=""; for($i=0;$i<count($_POST["buta"]);$i++){ if($i==0){ $butadata .= "meat_bui=".$_POST["buta"][$i]; }else{ $butadata .= " or meat_bui=".$_POST["buta"][$i]; } } if(strlen($where) > 0){ $where .= " or meat_kbn=2 and (".$butadata.")"; }else{ $where .= " where meat_kbn=2 and (".$butadata.")"; } } }elseif(strlen($_POST["search2"]) > 0){ if(strlen($_POST['Zairyo_1']) > 0){ $recipe_cd = Nmae_val ('dbo_ht_recipezairyo_table','recipe_cd',' where zairyo_cd='.$_POST['Zairyo_1']); if(strlen($where) > 0){$where .= ' '.$_POST['WHEREVAL'].' recipe_cd='.$recipe_cd;}else{$where .= ' where recipe_cd='.$recipe_cd;} } if(strlen($_POST['Zairyo_2']) > 0){ $recipe_cd = Nmae_val ('dbo_ht_recipezairyo_table','recipe_cd',' where zairyo_cd='.$_POST['Zairyo_2']); if(strlen($where) > 0){$where .= ' '.$_POST['WHEREVAL'].' recipe_cd='.$recipe_cd;}else{$where .= ' where recipe_cd='.$recipe_cd;} } if(strlen($_POST['Zairyo_3']) > 0){ $recipe_cd = Nmae_val ('dbo_ht_recipezairyo_table','recipe_cd',' where zairyo_cd='.$_POST['Zairyo_3']); if(strlen($where) > 0){$where .= ' '.$_POST['WHEREVAL'].' recipe_cd='.$recipe_cd;}else{$where .= ' where recipe_cd='.$recipe_cd;} } if(strlen($_POST['zkw']) > 0){ $rstZ = pg_query($db,"select zairyo_cd from dbo_hm_zairyo_table where zairyo_name LIKE '%".$_POST['zkw']."%'"); if($rstZ){ while($colZ = pg_fetch_array($rstZ)){ $recipe_cd = Nmae_val ('dbo_ht_recipezairyo_table','recipe_cd',' where zairyo_cd='.$colZ[0]); if(strlen($where) > 0){$where .= ' '.$_POST['WHEREVAL'].' recipe_cd='.$recipe_cd;}else{$where .= ' where recipe_cd='.$recipe_cd;} } } } if(count($_POST['season_val']) > 0){ $seasondata=''; for($i=0;$i<count($_POST['season_val']);$i++){ if($i==0){ $seasondata .= 'season='.$_POST['season_val'][$i]; }else{ $seasondata .= ' or season='.$_POST['season_val'][$i]; } } if(strlen($where) > 0){ $where .= ' and ('.$seasondata.')'; }else{ $where .= ' where '.$seasondata; } } if(strlen($_POST['cook_time']) > 0){ if(strlen($where) > 0){ $where .= ' and cook_time <='.$_POST['cook_time']; }else{ $where .= ' where cook_time <='.$_POST['cook_time']; } } if(strlen($_POST['cook_class']) > 0){ if(strlen($where) > 0){ $where .= ' and cook_class <='.$_POST['cook_class']; }else{ $where .= ' where cook_class <='.$_POST['cook_class']; } } } //print $where."<br>"; $sql = "select * from dbo_ht_recipe_table ".$where." order by meat_kbn,meat_bui"; //print $sql; $rst = pg_query($db,$sql); if($rst){ while($col = pg_fetch_array($rst)){ $data[] = array($col[0],$col[1],$col[2],$col[31],$col[3],$col[4]); } } $cnt = count($data); if($cnt > ($n+20)){ $NEXTLINK .= "<a href='cook_ichiran.php?n=".($n+20)."&where=".$where."'>次20件 &raquo;</a>"; }else{ $NEXTLINK = ""; } if($n != 0){ $FRONTLINK .= "<a href='cook_ichiran.php?n=".($n-20)."&where=".$where."'>&laquo; 前20件</a>"; }else{ $FRONTLINK = ""; } $totalpage = ceil($cnt / 20); $page_main = $n2 / 20; for($i=1;$i<$totalpage+1;$i++){ if($page_main <> $i ) { $PLINK .= "<a href='cook_ichiran.php?n=".(($i-1)*20)."&where=".$where."'>".$i."</a>&nbsp;"; }else{ $PLINK .= $i."&nbsp;"; } } if($cnt >= $n2){$n3=$n2;}else{$n3=$cnt;} $buiarray = array("","牛","豚","鶏","その他"); ?>

<!-- 頁移動ボタンの表示 HTML 部分 -->

<div> <?=$FRONTLINK ?> <?=$PLINK ?> <?=$NEXTLINK ?> </div>

試したこと

20&where= where meat_kbn=1 and ( meat_bui=1 or meat_bui=2) のところを色々と変更してみました。

補足情報(FW/ツールのバージョンなど)

PostgreSQL8.4 php5.6 です。 phpPgAdminで操作しています。

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

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

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

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

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

退会済みユーザー

退会済みユーザー

2019/01/15 12:00

where句をそのままURLに詰めるのはいろいろイカン気がするのだが。
m.ts10806

2019/01/15 12:26

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

回答1

0

ベストアンサー

where句に詰めるのに使われる$_REQUEST['where']は、
SQLインジェクションで攻撃される恐れがあるため、
やってはいけないことです。

where句を構成するのに多少冗長になっても、
(そのままSQL文に織り込まない)数字や文字列など単純なデータにするべきです。
そして、受信した$_POST$_GETに望まない不正なデータが含まれていないか検証する必要もあります。
(その検証をラクにする一つの手段として、filter_input()などがあります。)

URLに織り込むパラメータについては、
まず?より後ろの文字列を、&を区切り文字として分解し、
区切ったあとの文字列ごとに最初に出現する=でパラメータ名とデータを分離しているはず。
where句に使っている、「なんとかイコールなんとかの」のイコールも分離用に使われてしまうので、
せめてurlencode()でエンコードしますよ普通は。
&=?などurlに直接書いちゃいけない文字を置き換えてくれます。

それと、$_POST['~']とか$_REQUEST['~']とか
参照するデータが存在しない場合はちょっとしたエラーメッセージが
Notice: Undefined index: なんとか in 行番号
などとログに残るので、
filter_input()filter_input_array()にしなさいって言われるぞ。

さらに、
いちいちif (strlen($where) > 0) {をつけると無駄にソースコードが長くなるので、
私は配列に$where_terms[] = 'a = 1';みたいなのを積み上げておいて、
最後に$where = 'WHERE ' . implode(' AND ', $where_terms);みたいなことをするよ。

投稿2019/01/15 12:11

編集2019/01/16 00:38
退会済みユーザー

退会済みユーザー

総合スコア0

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

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

sj3600

2019/01/17 00:51

皆様、ご指導ありがとうございます。 時間をかけて初歩的なところから見直して参りたいと存じます。 取り急ぎで恐縮ですが御礼申し上げます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問