• 締切済み

同じname属性をまとめ未記入の項目を削除する方法

現在メールフォームを作成しており、アドバイスを受けながら一歩ずつ前進している者ですが今回も行き詰ってしまいました。度々の質問で心苦しいですが何卒宜しくお願いします。 言葉での説明が難しいので以下のアドレスに【ブラウザ入力画面】と【確認画面】のイメージを掲載しました。 http://homepage2.nifty.com/nippon/qe/qes.html htmlソースは以下の通りで同じ「msg」などname属性の物が存在します。 <h1>フォーム</h1> <FORM action="abc.cgi" method="POST"><INPUT type="hidden" name="location" value = "http://abc.com"> <INPUT type="hidden" name="subject" value="【フォームメール】"> <TABLE border="0" cellpadding="3"> <TBODY> <TR> <TD bgcolor="#ffeadf">メッセージ1:</TD> <TD><INPUT size="50" type="text" name="msg"></TD> </TR> <TR> <TD bgcolor="#ffeadf">メッセージ2:</TD> <TD><INPUT size="50" type="text" name="msg"></TD> </TR> <TR> <TD bgcolor="#ffeadf">質問:</TD> <TD><INPUT size="50" type="text" name="qes"></TD> </TR> <TR> <TD bgcolor="#ffeadf">名前:</TD> <TD><INPUT size="50" type="text" name="Name"></TD> </TR> <TR> <TD bgcolor="#ffeadf">メールアドレス:</TD> <TD><INPUT size="50" type="text" name="Email"></TD> </TR> </TBODY> </TABLE> <BR> <INPUT TYPE="submit" VALUE="確認"> <INPUT TYPE="reset" VALUE="リセット"><BR> </BODY> </HTML> name属性が同じ場合は改行ぜずに1つにまとめvalue属性の値をカンマで区切って1行で表示させたいと思っております。 また、ブラウザ側で入力が無かった項目は表示させないようにしたいと思っております。 いろいろとIF関数を試してみましたがうまく表示しません(;;) 現在以下のプログラムで全ての項目と値が1行づつ表示されています、どのように変更すれば良いでしょうか? $count = @DATA_N; foreach (0..$count-1) { if ($DATA_V[$_] =~ /\n/) { &jis("$DATA_N[$_] =\n$DATA_V[$_]\n"); print OUT "$msg\n"; } else { &jis("$DATA_N[$_] =$DATA_V[$_]"); print OUT "$msg\n"; } } push(@DATA_N,$name); push(@DATA_V,$value); なにとぞ宜しくお願いいたしますm(_ _)m

みんなの回答

  • okmotokun
  • ベストアンサー率59% (92/155)
回答No.1

対症療法的にその都度考えるのではなく、専門的なことは要りませんから、基本的な知識は得ておく必要はありそうです。 それと、ホームページでプログラムを使うときは、セキュリティのことも考えないと、とんでもないことが起きかねません。 CGIプログラムを触るのは初めての様子なので要点を説明しておきます。 ホームページのフォームに入力された内容は、「項目名=入力内容」という形で送信されてきます。 なお、送信方法(METHOD)が「GET」の場合と「POST」で送信形式(ENCTYPE)が「application/x-www-fprm-urlencode」の場合は、入力内容に、「英字」「数字」「ピリオド」「マイナス」「アンダーバー」以外の文字や記号が含まれている場合は「パーセントエンコード」されます。スペースは「プラス」に変換されます。 送信される項目が複数ある場合は、これが「&」で連結されて送信されてきます。 項目名=入力内容&項目名=入力内容&項目名=入力内容&項目名=入力内容&項目名=入力内容 という具合ですね。 ですから、受信したデータはファイルに保存したり、メールで送信したりするために、 (1) &ごとに分割し、 (2) さらにそれぞれを=で分割して、項目名の変数にその入力内容を代入して、 (3) パーセントエンコードされた部分を元に戻す ことが必要です。これを「ポストデータのパース」といいます。 以下、ポストデータをパースするプログラムの一例です。 #-------------------------------- # 送信方法が「POST」のデータ #-------------------------------- if($ENV{'CONTENT_LENGTH'}){  read(STDIN,$query,$ENV{'CONTENT_LENGTH'});  if($ENV{'CONTENT_TYPE'}=~/multipart\/form-data; boundary=(.+)/i){   $boundary=$1;   binmode(STDIN);   foreach(split(/\-+$boundary\-*\x0D*\x0A*/,$query)){    #------------------------------------------------    # 送信形式が multipart/form-data のパース    #------------------------------------------------    ($header,$val)=split(/\x0D\x0D|\x0A\x0A|\x0D\x0A\x0D\x0A/,$_,2);    $header=~s/^(\x0D\x0A|\x0D|\x0A)+//;    $val=~s/(\x0D\x0A|\x0D|\x0A)$//;    if($header=~/ name="(.+?)"/i&&$val){     $key=$1;     if($header=~/filename=".+[\\\/:]+([^\\\/:]+)"/){      #--------------------------------      # アップロードファイルの保存      #--------------------------------      $FORM{$key}=$filename=$1;      open(FILE,">$filename");      binmode FILE;      print FILE $val;      close FILE;     }else{      ($FORM{$key}=$val)=~s/(\x0D\x0A|\x0A|\x0D)/\n/sig;     }    }   }   $query="";  } } #-------------------------------- # 送信方法が「GET」のデータ #-------------------------------- if($ENV{'QUERY_STRING'}){  if($query){$query.='&'}  $query.=$ENV{'QUERY_STRING'}; } #----------------------------------------------------- # 送信方法が「GET」のデータと # 送信形式が application/x-www-form-urlencode のパース #----------------------------------------------------- if($query){  for(split(/&/,$query)){   ($key,$val)=split(/=/);   $val=~s/(%0D%0A|%0A|%0D)/\n/g;   $val=~s/<[^>]+>//sg;   $val=~s/\+/ /sg;   ($FORM{$key}=$val)=~s/%([A-F0-9][A-F0-9])/pack("C",hex($1))/ige;  } } これで、データは「項目名」をキーとして連想配列 %FORM にセットされます。 データをファイルに保存したり、メール文に引用する場合は、$FORM{項目名} で自由に加工できるわけです。 なお、上の例ではセキュリティ上、HTMLタグの入力をすべて無効にしています。 タグの入力が必要な場合は、確認画面などにタグをそのまま表示する場合はくれぐれも安全性を考えて対策してください。

kohkun2008
質問者

お礼

okmotokun 様 いつもありがとうございます。昨日から書いていただいたプログラムを理解しようとcgiの本を購入して解読していますがなかなか難しいですね(^^;A これから素早く基本だけでも分かるようにして書いていただいたプログラムを理解します。本当にありがとうございました。

すると、全ての回答が全文表示されます。

関連するQ&A