人力検索はてな
モバイル版を表示しています。PC版はこちら
i-mobile

PHPについて質問です。

フォームから受け取った後の処理として下記のような
スクリプトを書いてみたのですが、いかにも冗長です。
これをスマートに書き直してください。

$tokyo = htmlspecialchars($_GET['tokyo']);
$oosaka = htmlspecialchars($_GET['oosaka']);
$nagoya = htmlspecialchars($_GET['nagoya']);
$hukuoka = htmlspecialchars($_GET['hukuoka']);

●質問者: taroemon
●カテゴリ:コンピュータ
✍キーワード:PHP Tokyo スクリプト スマート
○ 状態 :終了
└ 回答数 : 3/3件

▽最新の回答へ

1 ● litt
●23ポイント

こんな感じでいかがでしょう?

$cities = array('tokyo','oosaka','nagoya','hukuoka');

foreach ($cities as $city) {

eval("\$$city = ".htmlspecialchars($_GET[$city]).";");

}

◎質問者からの返答

ご回答ありがとうございます。


ご回答いただいた物をそのまま使ってみたのですが、下記のようなエラーが出ます。

Parse error: syntax error, unexpected T_STRING in C:\xampp\(略)(9) : eval()'d code on line 1


もちろんこのエラーを回避できないのは私がいたらないせいだとは思うのですが、

リファレンス本を参照したところ、

「eval関数は負荷が大きいので、本当に必要な場合にのみ使うように」とありました。


他の方法をお待ちしています。


2 ● tobeoscontinue
●35ポイント

近いものとしてP_BLOG Projectのソース(include/fnc_base.inc.php)の中にagainst_xss()というものがあります。

ただ使う場合はライセンスがGPLですので注意が必要です。

私はformで使う名前を配列に入れてhtmlの生成と値を受け取る場合の両方で使うようにしています。

function array_htmlspecialchars($vars) {
 $sanitized = array();
 foreach ($vars as $value) {
 $sanitized[] = is_array($value)
 ? array_htmlspecialchars($value)
 : htmlspecialchars($value);
 }
 return $sanitized;
}

受け取る値が配列になることがないなら必要ないです。

配列($vars)に対してhtmlspecialchars()を再帰的に適用して配列で返します。

function sanitize($vars, $names) {
 $sanitized = array();
 foreach ($names as $key) {
 if (isset($vars["$key"])) {
 $sanitized["$key"] = is_array($vars["$key"])
 ? array_htmlspecialchars($vars["$key"])
 : htmlspecialchars($vars["$key"]);
 } }
 return $sanitized;
}

連想配列($vars:実態は$_GETや$_POST)の内$namesで指定される名前のものだけについてhtmlspecialchars()を適用して連想配列を返します。

$varsの内容が配列とならないなら

$sanitized["$key"] = htmlspecialchars($vars["$key"]);

だけでokです。

$_GET['tokyo'] = "<to&kyo>";
$_GET['oosaka'] = "<oo&saka>";
$_GET['nagoya'] = "<nago&ya>";
$_GET['hukuoka']= "<huku&oka city=\"\">";
$_GET['aomori'] = "<aomori>";
// テスト用に値を設定

extract(sanitize($_GET, array('tokyo','oosaka','nagoya','hukuoka')));
// 処理部分

echo "tokyo($tokyo)\n";
echo "oosaka($oosaka)\n";
echo "nagoya($nagoya)\n";
echo "hukupka($hukuoka)\n";
// 確認用に出力

sanitize($_GET, array())

$_GETについてarray()で指定される名前のものだけについてhtmlspecialchars()を適用した連想配列が返ります。array()で指定する利点は$_GETの中にあってもarray()で指定していなければ処理をしないということです。仮に攻撃で$_GETにある名前で変な値が設定されたとしても指定された名前のものしか処理しないので影響を受けません。

extract()は連想配列を変数にしますので$tokyo、$oosaka、$nagoya、$hukuokaが作成されます。

◎質問者からの返答

ご回答ありがとうございます。

たくさん答えていただいてありがとうございます。

大変参考になりました。


3 ● Lu-such
●22ポイント

こんな感じでいかがでしょう?

$_GET['tokyo'] = '東京';

$_GET['oosaka'] = '大阪';

$_GET['nagoya'] = '名古屋';

$_GET['hukuoka']= '福岡';

foreach($_GET as $key => $val) {

$val=htmlspecialchars($val);

$array[$key]=$val;

}

extract($array);

echo $tokyo,$oosaka,$nagoya,$hukuoka;

◎質問者からの返答

ご回答ありがとうございます。

参考になりました。

関連質問


●質問をもっと探す●



0.人力検索はてなトップ
8.このページを友達に紹介
9.このページの先頭へ
対応機種一覧
お問い合わせ
ヘルプ/お知らせ
ログイン
無料ユーザー登録
はてなトップ