#!/usr/local/bin/prologcgi

:-s_charset(_,utf8).
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%     ＜テンプレートの利用＞
%% 画面構成部分とデータ部分を切り離し、同一の画面イメージ（テンプレート）で複数のページを容易に生成する
%% ことが可能となります。
%% このＣＧＩでは、選択一覧リストを存在する .\dat\xxxx.datより自動生成していますが、データそのものを
%% ＲＤＢに持たせ一覧作成とデータ取得をこれからおこなえば、よりスマートになるでしょう。
%% 
%% 【　テンプレートファイル　】 
%% 任意のＨＴＭＬファイルを用意し、データ部分（文字列、写真ファイル名など）を変数書式に置き換えます。
%% この変数部分は、変数と値の対応を定義することにより、自動的に置き換えられます。(実ファイルを参照してください）
%% 　　書式：　<TMPL_VAR NAME=変数名>
%% 
%% 特定の変数が値充足されたときのみ生かしたい行があるときは、条件文で囲うことで切り分けができます。
%% 　　書式：　<TMPL_IF NAME=変数名>  ...生かしたいＨＴＭＬ文...  </TMPL_IF>
%%  
%%  【　変数と対応値の定義　】
%% 単位節： tmp_name(変数名,   値). 　を静的・動的に定義するか、あらかじめ定義されているファイルから読込みます。
%% このデモではデータ部分をページごとの xxxxx.dat ファイルに分けて選択されたファイルを都度読み込みんでいます。
%% 値はアトム、数値または文字列リストです。(実ファイルを参照してください）
%%
%% 【　テンプレートの表示述語　】 
%%　下記、３つの方法で、テンプレートを出力することができます。
%%　
%%     html_tmplate(テンプレートファイル名） 　　　　　　　　　　　　　　　　　tmp_name/2 をassert後に呼び出す
%%     html_tmplate(テンプレートファイル名,データファイル名アトム）　　　　　　定義ファイルを指定して呼び出す
%%     html_tmplate(テンプレートファイル名,[変数名1=値1,変数名2=値2.....]）　　変数と値の組を渡して呼び出す
%%
%% 【　その他、本ＣＧＩで利用されているユーティリティ述語　】
%%　　●　get_param/2   　   ＣＧＩ呼び出しの際の引数を取得します。指定タグが引数にないときは失敗します。
%%  　　    ?-get_param(+タグ名,-値 ).    
%%
%%　　●　param_assoc_list/1 ＣＧＩ呼び出しの際の全引数をタグと値の組のリストで取得します。
%%　　　　　　　　　　　　　　チェックリストのように、値が異なる複数の同一タグ一覧を処理するときに利用できます。
%%  　　    ?-param_assoc_list(-リスト).
%%
%%　　●　html_call/1        リストを引数とし、リストの各要素を　write　します。要素が文字列リストの場合は全要素
%%                       　　をputします。また、要素が call(述語）の場合のみ、Ｐｒｏｌｏｇ述語呼び出しを行います。 
%%
%%　　●　write_listnl/1     リストを引数とし、リストの各要素を　write　し、最後に改行(nl)を出力します。
%%
%%　　●　s_child/5　　　　　子プロセスを立ち上げ、そのプロセスＩＤと入出力ストリームを取得します。
%%   　　   ?- s_child(+起動プログラム,+[引数並びリスト],-入力ストリーム,-出力ストリーム,-プロセスＩＤ）.
%%
%%　　●　get_chars_list/4　 s_child/5の第４引数値、see/2の第２引数値、または'con' から区切り文字コードを指定し、この区切り
%%　　　　　　　　　　　 　　文字までの出力値をリストに読み込みます。
%%                      　　 ストリームが終わりのとき、ステータスに 'end'、終了していないときは、'cont' を返します。
%%  　　    ?- get_chars_list(+出力ストリーム,+区切り文字コード,-ステータス,-読み込み文字列リスト).
%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

top_call:-
   errormode(_,0),
   (get_param(yama,File);File=''),!,                                              % 引数パラメータを得る。
   html_call([
    "content-Type: text/html; charset=utf-8

    <html>
     <head>
       <meta http-equiv='Content-Type' content='text/html; charset=utf-8'>
       <title>テンプレートキックCGIサンプル</title>
       <script type='text/javascript'>
         function mymenu(URL,MNU){if(URL !=''){MNU.selectedIndex=0;window.location.href=URL;}}
       </script>
     </head>
     <body><center><H2> テンプレートキックCGIサンプル </H2> 
     <select onchange='mymenu(this.options[this.selectedIndex].value,this)'>",
         call( my_child(InStream,OutStream,PId,Type) ), 
         call( \+ disp_options(OutStream,cont,'',【記事を選択してください】,Type)),
         call( (seen(OutStream),told(InStream),s_wait(PId,_,_) ) ),
     "</select>
     <select onchange='mymenu(this.options[this.selectedIndex].value,this)'>
        <option value=''                           >【ソースの閲覧】
        <option value='puttxt.exe?templatetest.cgi'>ＣＧＩソース
        <option value='puttxt.exe?template.tmp'    >テンプレートソース
        <option value='puttxt.exe?",File,"'        >選択されているデータ
     </select>　　
     <INPUT TYPE='button' VALUE='戻る' onClick='history.back()'><br>",
        call(html_tmplate('template.tmp',File)),                                  % Prolog Call: 選択されたファイルでテンプレートを表示する
     "Special Thanks For 【 http://www.noyama.com/ 】
     </center></body></html>"]).

   % OSコマンド(dir /B data\*.dat)を実行
my_child(InStream,OutStream,PID,linux):-
	s_version(_,'LINUX',_,_),!,
        s_child('/bin/bash',[],InStream,OutStream,PID),
	write(InStream,'ls data/*.dat'),nl(InStream),told(InStream).
my_child(InStream,OutStream,PID,windows):-
        s_child(cmd,['/c dir /B data\*.dat'],InStream,OutStream,PID).
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% select オプションリストを存在するファイルから生成する

disp_options(OutS,cont,F,D,Type):-
    write_listnl(['<option value="./templatetest.cgi?yama=',F,'">',D]),
  % optionを表示する
    get_chars_list(OutS,31,Status,Data),
  % ストリームから行末は３１であると指定し文字列1行読込み
    (Type=linux -> name(File,Data); name(File,[100,97,116,97,47|Data]) ),
  % "data/"を頭につけてアトム化（ファイル名）
    errorset( (see(File),repeat,read(tmp_name(山名,Disp)),seen),_),!,
  % ファイルから山の名前を取り出す
    disp_options(OutS,Status,File,Disp,Type).
  % 次の行の処理をおこなう。disp_options 再帰

