• ベストアンサー

フォーム入力後の確認画面表示について

こんにちは。tyabudaiと申します。 よろしくお願いします。 現在、私のサイトでCGIを使って投稿するフォームを作成しています。 流れは以下のようなものです。 1.フォームに内容を入力、送信ボタンでCGI起動。 (以下CGI) 2.入力内容をサーバのファイルに書込む。 3.送信完了のメッセージを表示 そして今、1と2の間に確認画面を表示する処理を 追加したいのですが、どのような処理にするのでしょうか? ソースについては勉強しますので、大まかな流れを教えて いただけないでしょうか?

質問者が選んだベストアンサー

  • ベストアンサー
  • ron3
  • ベストアンサー率35% (7/20)
回答No.4

CGIの基本の考えの問題を勘違いされているのではないかと思うのですが。 CGIは、ブラウザで一度表示するとそれで、プログラムとしては、終わります。 (説明下手ですね。) つまり、もう一度、同じURLを指定して、実行したとしても、 最初から実行し直しとなります。 値を保持するわけではありません。 解答としては、yuizuianのおっしゃる通りです。 下のサンプルを修正すると、 #!C:\Perl\bin\perl ~ここ省略~ if ($form{'mode'}='kakunin'){ # 連想配列から値だけを取り出し、区切り文字を追加 $data = "名前:$form{'name'}\nメール:$form{'mail'}\nタイトル:$form{'title'}\n記事:$form{'topic'}\n\n=========================\n\n"; &kakunin; exit; } elseif($form{'mode'}='touroku'){&write;} else{&error_print;} # 確認画面の表示サブルーチン sub kakunin { print "Content-type:text/html\n\n"; print << "END_OF_KAKUNIN"; <HTML> <HEAD> <TITLE>投稿内容確認</TITLE> </HEAD> <BODY> 以下の内容で投稿します <BR> <BR> 名前は $form{'name'}<BR> メールアドレスは $form{'mail'}<BR> アドレスの掲載は $form{'mail_up'}<BR> 映画のタイトルは $form{'title'}<BR> 投稿記事の内容は $form{'topic'}<BR> <form method="POST" action="test.cgi"> <INPUT TYPE="hidden" VALUE=$data name='data'> 名前が無くちゃダメ  (><)」 ~~~~~~~~~~~~ <INPUT TYPE="hidden" VALUE="touroku" name="mode"> <INPUT TYPE="submit" VALUE="この内容で投稿する"> <INPUT TYPE=button VALUE='戻 る' onClick=' history.go(-1)'> </FONT> </BODY> </HTML> END_OF_KAKUNIN } ~~~以下省略~~~ といった感じでしょうか。 もちろん、登録確認前の入力画面のHTMLのFORMタグの中に、 <INPUT TYPE="hidden" VALUE="kakunin" name="mode"> といった感じの物を書く必要がありますが。 ちなみに、ファイルロック、まともに考えると難しいですよね~。 いろいろ方法があるんですけど、考えるの面倒なんで、DB使ってます。 でも、イントラでしか使えませ~ん。

tyabudai
質問者

お礼

ありがとうございました。 皆様のアドバイスのおかげで、ようやく完成しました。 まだまだ機能的に追加していくものもありますが、 とりあえずは一段落つきました。 全く理解不足でしたが、大変勉強になりました。 本当にありがとうございました。 ながくなりますが、私みたいな人のために(いないか??) ソースを掲載します。 また、さらにソースに問題点があった場合のことを考え、 しばらくは締め切らないままにします。 -----------test.cgi-------------------------- #!C:Perl\bin\perl # ライブラリの読み込み require 'cgi-lib.pl'; # デコードサブルーチンの呼び出し &ReadParse(*form); # ライブラリ require 'jcode.pl'; # 文字コード変換サブルーチン &jcode'convert(*form,'sjis'); # 連想配列から値だけを取り出し、区切り文字を追加 $data = "名前:$form{'name'}\nメール:$form{'mail'}\nタイトル:$form{'title'}\n記事:$form{'topic'}\n\n=========================\n\n"; if ($form{'mode'} eq 'kakunin') {&kakunin;} elsif ($form{'mode'} eq 'touroku') {&write;} else {&error_print;} # ----確認画面の表示サブルーチン----------- sub kakunin { print "Content-type:text/html\n\n"; print << "END_OF_KAKUNIN"; <HTML> <HEAD> <TITLE>投稿内容確認</TITLE> </HEAD> <BODY> 以下の内容で投稿します <BR><BR> 名前は $form{'name'} <BR> メールアドレスは $form{'mail'} <BR> 映画のタイトルは $form{'title'} <BR> 投稿記事の内容は <BR> $form{'topic'} <BR> <form method="POST" action="test.cgi"> <input type="hidden" name="name" Value="$form{'name'}"> <input type="hidden" name="mail" Value="$form{'mail'}"> <input type="hidden" name="title" Value="$form{'title'}"> <input type="hidden" name="topic" Value="$form{'topic'}"> <INPUT TYPE="hidden" VALUE="touroku" name="mode"> <INPUT TYPE="submit" VALUE="この内容で投稿する"> <INPUT TYPE="button" VALUE="戻 る" OnClick=" history.go(-1)"> </FONT> </BODY> </HTML> END_OF_KAKUNIN } # ---------書込みサブルーチン---------- sub write { # 追加書き込みモード open(ENQ, ">>test.log") || die "File が開けません。"; #flock(ENQ, 2); print ENQ $data; #flock(ENQ, 8); close(ENQ); &write_ok; #書込み完了メッセージ } # --------- 書込み完了時のサブルーチン---- sub write_ok { print "Content-type:text/html\n\n"; print << "END_OF_OK"; (略) END_OF_OK } # ----------- エラー表示サブルーチン --------- sub error_print { print "Content-type:text/html\n\n"; print << "END_OF_ERROR_PRINT"; (略) END_OF_ERROR_PRINT } -----------------ここまで--------------------

その他の回答 (3)

noname#32059
noname#32059
回答No.3

書き込みサブルーチンのデータを書き込んだあとに ----見本---- Print "Content-type:text/html\n\n"; Print<<EndOfSubRou; <html> てきと~にめっせーじ </html> EndOfSubRou ---見本終わり--- ってなかんじでHTMLを出力するスクリプトを追加するとかはどうでしょう。

tyabudai
質問者

補足

アドバイスありがとうございます。 上記の内容は 'sub write' の最後にある '&write_ok' のサブルーチンのこととはまた違う処理でしょうか? 記述は省略してしましましたが、'sub write_ok' では 書込み完了メッセージを表示しています。

  • yuizuian
  • ベストアンサー率42% (103/245)
回答No.2

こんにちは。 ソースを拝見させていただきましたが、 その方法では何度ボタンを押しても確認画面に飛んでしまうと思います。 test.cgiの中で、「区切り文字の追加」をした後に Kakuninサブルーチンに飛んで、その後exitしているからです。 私はこういった場合、フォームの中にmode、act等という名前を付けたデータを hiddenで隠し持たせています。 例:)<INPUT TYPE=hidden NAME=mode VALUE=kakunin> こうするとその値によってジャンプするサブルーチンを変えることができますよね? 確認画面の表示の仕方は、今のままで問題ないと思いますよ。 頑張ってください。

tyabudai
質問者

お礼

ありがとうございました。 皆様のアドバイスのおかげで、ようやく完成しました。 全く理解不足でしたが、大変勉強になりました。 本当にありがとうございました。 これからもよろしくお願いいたします。

  • ron3
  • ベストアンサー率35% (7/20)
回答No.1

CGIと、FORMタグの考え方がわかっていますか? わかっているものとして書きます。 そんなに難しいことではありません。 1.で入力した物を表示する。 そして、その確認画面の FORMタグの中身として、 inputタグのtypeをhiddenにして持たせてやる。 hiddenは、 inputタグの入力フォームの値を 隠してセットしてやるものと考えるといいでしょう。 あまりにも入力項目が多いとき、 2画面に分けたりするのに使ってもいいかも知れません。 そして、登録する場合は、 1.の登録のボタンと同じ方法で、 ボタンを使ってやるだけでOKです。 もうひとつの方法としては、 1.で、登録したものを仮データとして、 サーバがわの仮登録ファイルに書きこむ。 確認画面を表示し、 確認後、ファイルを書きこむ。 その後仮登録ファイルは削除。 また、確認画面までいった後、 ほったらかしにされたファイルを古い物は削除する という処理が必要です。 質問が、簡略すぎるので、 ・どれぐらいわかるか(作ったことがある。設定をいじったことがある) ・言語は何か(CGIだからperlでしょうけど。) ぐらい書くと、質問の解答がしてくれやすいです。 これだけだと、サンプル作成が結構つらいような気もします。 ということで。 勉強には、 http://tohoho.wakusei.ne.jp/www.htm が一番です。 がんばってください。

参考URL:
http://tohoho.wakusei.ne.jp/www.htm
tyabudai
質問者

お礼

アドバイスありがとうございます。 CGIはPerlで作成してます。 学び始めたばかりですが、参考書片手に簡単なものは 自作できました。 掲示板、カウンタなどです。 ファイルロックやセキュリティに関して理解が足りないので、自分のサイトでは借り物を使用してます。

tyabudai
質問者

補足

ながくなりますが、ソースを掲載します。 投稿フォームの確認ボタンが押されると起動するCGIです。 test.cgi ------------------------------------------- #!C:\Perl\bin\perl # ライブラリの読み込み require 'cgi-lib.pl'; # デコードサブルーチンの呼び出し &ReadParse(*form); # 投稿記事を保存するファイル名 $file = "test.log"; # ライブラリ require 'jcode.pl'; # 文字コード変換サブルーチン &jcode'convert(*form,'sjis'); # 連想配列から値だけを取り出し、区切り文字を追加 $data = "名前:$form{'name'}\nメール:$form{'mail'}\nタイトル:$form{'title'}\n記事:$form{'topic'}\n\n=========================\n\n"; &kakunin; exit; # 確認画面の表示サブルーチン sub kakunin { print "Content-type:text/html\n\n"; print << "END_OF_KAKUNIN"; <HTML> <HEAD> <TITLE>投稿内容確認</TITLE> </HEAD> <BODY> 以下の内容で投稿します <BR> <BR> 名前は $form{'name'}<BR> メールアドレスは $form{'mail'}<BR> アドレスの掲載は $form{'mail_up'}<BR> 映画のタイトルは $form{'title'}<BR> 投稿記事の内容は $form{'topic'}<BR> <form method="POST" action="test.cgi"> <INPUT TYPE="hidden" VALUE=$data> <INPUT TYPE="submit" VALUE="この内容で投稿する"> <INPUT TYPE=button VALUE='戻 る' onClick=' history.go(-1)'> </FONT> </BODY> </HTML> END_OF_KAKUNIN } # ---------書込みサブルーチン---------- sub write { # 追加書き込みモード open(ENQ, ">>$file") || die "File '$file' が開けません。"; #flock(ENQ, 2); print ENQ $data; #flock(ENQ, 8); close(ENQ); &write_ok; } # その他のサブルーチンは省略。 -------------------------------------------- 私の想像では sub KAKUNIN で送信ボタンが 押されたときに sub write に処理が飛ぶようにしようと 思ったのですが、方法がわかりません。 もともとは &kakunin; exit; のところが &write; でした。 そもそも、確認画面の表示の仕方がおかしいのでしょうか? お手数かけますがよろしくお願いいたします。