/[pub]/suikawiki/script/wiki.cgi
Suika

Diff of /suikawiki/script/wiki.cgi

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.1 by wakaba, Mon Feb 4 13:19:08 2002 UTC revision 1.7 by wakaba, Mon Feb 4 15:27:22 2002 UTC
# Line 1  Line 1 
1  #!/usr/local/bin/perl  #!/usr/bin/perl
2  use lib "../lib";  use lib "../lib";
3  use CGI::Carp 'fatalsToBrowser';  use CGI::Carp 'fatalsToBrowser';
4  use Algorithm::Diff qw(traverse_sequences);  use Algorithm::Diff qw(traverse_sequences);
5  # use strict;  # use strict;
6  #  #
7  # yukiwiki.cgi - Yet another WikiWikiWeb clone.  # yukiwiki.cgi - Yet another WikiWikiWeb clone.
8  #  #
9  # Copyright (C) 2000,2001 by Hiroshi Yuki.  # Copyright (C) 2000,2001 by Hiroshi Yuki.
10  # <hyuki@hyuki.com>  # <hyuki@hyuki.com>
11  # http://www.hyuki.com/yukiwiki/  # http://www.hyuki.com/yukiwiki/
12  #  #
13  # This program is free software; you can redistribute it and/or modify  # This program is free software; you can redistribute it and/or modify
14  # it under the terms of the GNU General Public License as published by  # it under the terms of the GNU General Public License as published by
15  # the Free Software Foundation; either version 2 of the License, or  # the Free Software Foundation; either version 2 of the License, or
16  # (at your option) any later version.  # (at your option) any later version.
17  #  #
18  # This program is distributed in the hope that it will be useful,  # This program is distributed in the hope that it will be useful,
19  # but WITHOUT ANY WARRANTY; without even the implied warranty of  # but WITHOUT ANY WARRANTY; without even the implied warranty of
20  # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the  # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
21  # GNU General Public License for more details.  # GNU General Public License for more details.
22  #  #
23  # $Id$  # $Id$
24  ##############################  ##############################
25  my $version = "1.6.6";  my $version = "1.6.6";
26  ##############################  ##############################
27  # 単独テストのときには 1 にする。  # テアニネ・ニ・ケ・ネ、ホ、ネ、ュ、ヒ、マ 1 、ヒ、ケ、。」
28  my $testing = 0;  my $testing = 0;
29  ##############################  ##############################
30  # 漢字ライブラリ  # エチサ・鬣、・ヨ・鬣
31  my $jcodelib = 'jcode.pl';  my $jcodelib = 'jcode.pl';
32  ##############################  ##############################
33  # 保存・表示の漢字コード  # ハンツク。ヲノスシィ、ホエチサ・ウ。シ・ノ
34  my $kanjicode = 'sjis';     # 'sjis' 'euc'  my $kanjicode = 'euc';     # 'sjis' 'euc'
35  my $charset = 'Shift_JIS';  # 'Shift_JIS' 'EUC-JP'  my $charset = 'euc-jisx0213';  # 'Shift_JIS' 'EUC-JP'
36  ##############################  ##############################
37  # dbmopenが使えるなら1、使えないなら0  # dbmopen、ャサネ、ィ、、ハ、1。「サネ、ィ、ハ、、、ハ、0
38  my $dbmopen = 0;  my $dbmopen = 0;
39  ##############################  ##############################
40  # データベース名(.pag, .dir, .dbなどは不要)  # ・ヌ。シ・ソ・ル。シ・ケフセ。ハ.pag, .dir, .db、ハ、ノ、マノヤヘラ。ヒ
41  # $dbmopen = 1のときはデータベース名、  # $dbmopen = 1、ホ、ネ、ュ、マ・ヌ。シ・ソ・ル。シ・ケフセ。「
42  # $dbmopen = 0のときはディレクトリ名になる。  # $dbmopen = 0、ホ、ネ、ュ、マ・ヌ・」・・ッ・ネ・フセ、ヒ、ハ、。」
43  my $dbname = './yukiwiki';  my $dbname = './wikidata';
44  my $diffdbname = './yukidiff';  my $diffdbname = './wikidiff';
45  ##############################  ##############################
46  # 修正者の氏名(自由に変更してください)  # ス、タオシヤ、ホサ睥セ。ハシォヘウ、ヒハムケケ、キ、ニ、ッ、タ、オ、、。ヒ
47  my $modifier = 'Hiroshi Yuki';  my $modifier = 'suika';
48  ##############################  ##############################
49  # 修正者のWebページ(自由に変更してください)  # ス、タオシヤ、ホWeb・レ。シ・ク。ハシォヘウ、ヒハムケケ、キ、ニ、ッ、タ、オ、、。ヒ
50  my $modifierlink = 'http://www.hyuki.com/';  my $modifierlink = 'http://suika.fam.cx/';
51  ##############################  ##############################
52  # このページのURL  # 、ウ、ホ・レ。シ・ク、ホURL
53  my $thisurl = 'yukiwiki.cgi';  my $thisurl = 'wiki';
54  ##############################  ##############################
55  # 開始ページ名  # ウォサマ・レ。シ・クフセ
56  my $toppage = 'FrontPage';  my $toppage = 'HomePage';
57  ##############################  ##############################
58  # 最終更新ページ名  # コヌスェケケソキ・レ。シ・クフセ
59  my $whatsnew = 'RecentChanges';  my $whatsnew = 'RecentChanges';
60  ##############################  ##############################
61  # 最終更新に掲載するページ数  # コヌスェケケソキ、ヒキヌコワ、ケ、・レ。シ・クソ
62  my $maxnew = 50;  my $maxnew = 50;
63  ##############################  ##############################
64  # アイコンファイル名(カラー版)  # ・「・、・ウ・・ユ・。・、・フセ。ハ・ォ・鬘シネヌ。ヒ
65  my $iconfile = 'yukiwiki.gif';  my $iconfile = '';
66  ##############################  ##############################
67  # アイコンファイル名(モノクロ版)  # ・「・、・ウ・・ユ・。・、・フセ。ハ・筵ホ・ッ・ネヌ。ヒ
68  # my $iconfile = 'yukimono.gif';  # my $iconfile = '';
69  ##############################  ##############################
70  # ページを変更したときにtouchするファイル(''なら何もしない)  # ・レ。シ・ク、ハムケケ、キ、ソ、ネ、ュ、ヒtouch、ケ、・ユ・。・、・。ハ''、ハ、魎ソ、筅キ、ハ、、。ヒ
71  my $touchfile = 'touch.txt';  my $touchfile = 'touch.txt';
72  ##############################  ##############################
73  # プレビュー用の背景色  # ・ラ・・モ・蝪シヘム、ホヌリキハソァ
74  my $preview_color = '#FFCCCC';  my $preview_color = '#FFCCCC';
75  ##############################  ##############################
76  # 全ページのスタイル  # チエ・レ。シ・ク、ホ・ケ・ソ・、・
77  my $style = <<'EOD';  my $style = <<'EOD';
78  pre, dl, ul, ol, p, blockquote { line-height:120%; }  pre, dl, ul, ol, p, blockquote { line-height:120%; }
79  a { text-decoration: none; }  a { text-decoration: none; }
80  a:link { color: #0000FF; background-color: #FFFFFF; }  a:link { color: #0000FF; background-color: #FFFFFF; }
81  a:visited { color: #9900CC; background-color: #FFFFFF; }  a:visited { color: #9900CC; background-color: #FFFFFF; }
82  a:hover { text-decoration: underline; }  a:hover { text-decoration: underline; }
83  EOD  EOD
84  ##############################  ##############################
85  # テキスト入力部分の大きさ  # ・ニ・ュ・ケ・ネニホマノハャ、ホツ遉ュ、オ
86  my $cols = 80;  my $cols = 80;
87  my $rows = 20;  my $rows = 20;
88  ##############################  ##############################
89  my %form = ();  my %form = ();
90  my %database = ();  my %database = ();
91  my %diffbase = ();  my %diffbase = ();
92  my $diff_text = '';  my $diff_text = '';
93  my @diff_added = ();  my @diff_added = ();
94  my @diff_deleted = ();  my @diff_deleted = ();
95  my $msgrefA;  my $msgrefA;
96  my $msgrefB;  my $msgrefB;
97  ##############################  ##############################
98  # 編集不可ページ名一覧  # ハヤスクノヤイト・レ。シ・クフセーヘ
99  my @uneditable = ( $whatsnew );  my @uneditable = ( $whatsnew );
100  ##############################  ##############################
101  # リンク用の正規表現  # ・・・ッヘム、ホタオオャノスクス
102  # YukiWikiのリンクは2種類ある。  # YukiWiki、ホ・・・ッ、マ2シホ爨「、。」
103  #  #
104  # (1) WikiName (RecentChangesとかFrontPageのようなもの)  # (1) WikiName (RecentChanges、ネ、ォFrontPage、ホ、隍ヲ、ハ、筅ホ)
105  # (2) BracketName ([[結城浩]]とか[[トラブルシュート]]のようなもの)  # (2) BracketName ([[キセケタ]]、ネ、ォ[[・ネ・鬣ヨ・・キ・蝪シ・ネ]]、ホ、隍ヲ、ハ、筅ホ)
106  #  #
107  # ※シフトJISの2バイト目には ']' が来うるので、  # 「ィ・キ・ユ・ネJIS、ホ2・ミ・、・ネフワ、ヒ、マ ']' 、ャヘ隍ヲ、、ホ、ヌ。「
108  # 文字']'を1つ多くとるようにしている。  # ハクサ']'、1、トツソ、ッ、ネ、、隍ヲ、ヒ、キ、ニ、、、。」
109  #  #
110  my $WikiName = '([A-Z][a-z]+([A-Z][a-z]+)+)';  my $WikiName = '([A-Z][a-z]+([A-Z][a-z]+)+)';
111  my $BracketName = '\[\[([^>\s]+?\]?)\]\]';  my $BracketName = '\[\[([^>\s]+?\]?)\]\]';
112    
113  # アイコン部分のタグ  # ・「・、・ウ・ノハャ、ホ・ソ・ー
114  my $IconTag = <<"EOD";  my $IconTag = ''; #<<"EOD";
115  <a href="http://www.hyuki.com/yukiwiki/"><img src="$iconfile"  #<a href="http://www.hyuki.com/yukiwiki/"><img src="$iconfile"
116   border="0" width="80" height="80" alt="[YukiWiki]" /></a>  # border="0" width="80" height="80" alt="[YukiWiki]" /></a>
117  EOD  #EOD
118    
119  require "$jcodelib";  require "$jcodelib";
120    
121  &init_form($kanjicode);  &init_form($kanjicode);
122    
123  if ($testing) {  if ($testing) {
124      %form = (      %form = (
125          # 'mycmd' => 'write',          # 'mycmd' => 'write',
126          'mycmd' => 'read',          'mycmd' => 'read',
127          #'mycmd' => 'search',          #'mycmd' => 'search',
128          #'mycmd' => 'edit',          #'mycmd' => 'edit',
129          'mymsg' => <<"EOD",          'mymsg' => <<"EOD",
130  はじめまして。  、マ、ク、皃゙、キ、ニ。」
131  これからいろいろ書き込みますね。  、ウ、、ォ、鬢、、、、、ス、ュケ、゚、゙、ケ、ヘ。」
132  LinkPageも見てください。  LinkPage、篋ォ、ニ、ッ、タ、オ、、。」
133  TestPageはどうでしょうか。  TestPage、マ、ノ、ヲ、ヌ、キ、遉ヲ、ォ。」
134  どうぞよろしく。  、ノ、ヲ、セ、隍、キ、ッ。」
135  http://www.hyuki.com/  http://www.hyuki.com/
136  [[結城浩]]  [[キセケタ]]
137  EOD  EOD
138          'mypage' => '<結城浩>',          'mypage' => '<キセケタ>',
139          'myword' => '結',          'myword' => 'キ',
140          # '3C8C8B8FE98D5F3E' => '',          # '3C8C8B8FE98D5F3E' => '',
141          # 'TestPage' => '',          # 'TestPage' => '',
142      );      );
143  }  }
144  &main;  &main;
145  exit(0);  exit(0);
146    
147  # メイン  # ・皈、・
148  sub main {  sub main {
149      &normalize_form;      &normalize_form;
150      if ($dbmopen) {      if ($dbmopen) {
151          if (!dbmopen(%database, $dbname, 0666)) {          if (!dbmopen(%database, $dbname, 0666)) {
152              &print_error("(dbmopen) $dbname が作れません。");              &print_error("(dbmopen) $dbname 、ャコ、、゙、サ、。」");
153          }          }
154      } else {      } else {
155          if (!tie(%database, "YukiWikiDB", $dbname)) {          if (!tie(%database, "YukiWikiDB", $dbname)) {
156              &print_error("(tie error)");              &print_error("(tie error)");
157          }          }
158      }      }
159    
160      # myspecial対応      # myspecialツミア
161      foreach (keys %form) {      foreach (keys %form) {
162          if (/^myspecial_(.*)/) {          if (/^myspecial_(.*)/) {
163              $form{mycmd} = $1;              $form{mycmd} = $1;
164              last;              last;
165          }          }
166      }      }
167    
168      if ($form{mycmd} eq 'read') {      if ($form{mycmd} eq 'read') {
169          &do_read;          &do_read;
170      } elsif ($form{mycmd} eq 'preview') {      } elsif ($form{mycmd} eq 'preview') {
171          &do_preview;          &do_preview;
172      } elsif ($form{mycmd} eq 'write') {      } elsif ($form{mycmd} eq 'write') {
173          &do_write;          &do_write;
174      } elsif ($form{mycmd} eq 'edit') {      } elsif ($form{mycmd} eq 'edit') {
175          &do_edit;          &do_edit;
176      } elsif ($form{mycmd} eq 'reedit') {      } elsif ($form{mycmd} eq 'reedit') {
177          &do_reedit;          &do_reedit;
178      } elsif ($form{mycmd} eq 'search') {      } elsif ($form{mycmd} eq 'search') {
179          &do_search;          &do_search;
180      } elsif ($form{mycmd} eq 'list') {      } elsif ($form{mycmd} eq 'list') {
181          &do_list;          &do_list;
182      } elsif ($form{mycmd} eq 'diff') {      } elsif ($form{mycmd} eq 'diff') {
183          &do_diff;          &do_diff;
184      } else {      } else {
185          $form{mypage} = $toppage;          $form{mypage} = $toppage;
186          &do_read;          &do_read;
187      }      }
188      if ($dbmopen) {      if ($dbmopen) {
189          dbmclose(%database);          dbmclose(%database);
190      } else {      } else {
191          untie(%database);          untie(%database);
192      }      }
193  }  }
194    
195  # ページの表示  # ・レ。シ・ク、ホノスシィ
196  sub do_read {  sub do_read {
197      my $page_name = $form{mypage};      my $page_name = $form{mypage};
198      my $percent_name = &encode_percent($page_name);      my $percent_name = &encode_percent($page_name);
199      &print_header($page_name);      &print_header($page_name);
200      print qq|<h1>$IconTag<a href="$thisurl?mycmd=search&myword=$percent_name">$page_name</a></h1>\n|;      print qq|<h1>$IconTag<a href="$thisurl?mycmd=search;myword=$percent_name">$page_name</a></h1>\n|;
201      &print_toolbar($page_name);      &print_toolbar($page_name);
202      print &convert_html(&get_page($page_name));      print &convert_html(&get_page($page_name));
203      &print_footer;      &print_footer;
204  }  }
205    
206  # ページの編集  # ・レ。シ・ク、ホハヤスク
207  sub do_edit {  sub do_edit {
208      if (not &is_editable($form{mypage})) {      if (not &is_editable($form{mypage})) {
209          # 編集不可ページは表示のみ          # ハヤスクノヤイト・レ。シ・ク、マノスシィ、ホ、゚
210          &do_read;          &do_read;
211          return;          return;
212      }      }
213      &editpage(&get_page($form{mypage}));      &editpage(&get_page($form{mypage}));
214  }  }
215    
216  # ページの再編集  # ・レ。シ・ク、ホコニハヤスク
217  sub do_reedit {  sub do_reedit {
218      if (not &is_editable($form{mypage})) {      if (not &is_editable($form{mypage})) {
219          # 編集不可ページは表示のみ          # ハヤスクノヤイト・レ。シ・ク、マノスシィ、ホ、゚
220          &do_read;          &do_read;
221      } else {      } else {
222          &editpage($form{mymsg});          &editpage($form{mymsg});
223      }      }
224  }  }
225    
226  sub editpage {  sub editpage {
227      my $page_msg = shift;      my $page_msg = shift;
228      my $page_name = $form{mypage};      my $page_name = $form{mypage};
229      my $digest = &calc_message_digest($page_msg);      my $digest = &calc_message_digest($page_msg);
230      &print_header($page_name);      &print_header($page_name);
231      print qq|<h1>$IconTag${page_name}の編集</h1>\n|;      print qq|<h1>$IconTag${page_name}、ホハヤスク</h1>\n|;
232      &print_toolbar($page_name);      &print_toolbar($page_name);
233      $page_msg = &escape($page_msg);      $page_msg = &escape($page_msg);
234      print <<"EOD";      print <<"EOD";
235  <form action="$thisurl" method="post">  <form action="$thisurl" method="post">
236  <input type="hidden" name="mycmd" value="preview">  <!--<input type="hidden" name="mycmd" value="preview">-->
237  <input type="hidden" name="mypage" value="$page_name">  <input type="hidden" name="mypage" value="$page_name">
238  <input type="hidden" name="mydigest" value="$digest">  <input type="hidden" name="mydigest" value="$digest">
239  <textarea cols="$cols" rows="$rows" name="mymsg" wrap="virtual">$page_msg</textarea><br>  <textarea cols="$cols" rows="$rows" name="mymsg" wrap="virtual">$page_msg</textarea><br>
240  <input type="submit" value="プレビュー">  <input type="submit" name="myspecial_preview" value="ウホヌァ">
241  </form>  <input type="submit" name="myspecial_write" value="ウホヌァ、サ、コハムケケ">
242  <hr>  </form>
243  <h3>テキスト整形のルール</h3>  <hr>
244    <h3>・ニ・ュ・ケ・ネターキチ、ホ・。シ・</h3>
245  <p>通常は入力した文字がそのまま出力されますが、  
246  以下のルールに従ってテキスト整形を行うことができます。</p>  <p>トフセ、マニホマ、キ、ソハクサ、ャ、ス、ホ、゙、゙スミホマ、オ、、゙、ケ、ャ。「
247    ーハイシ、ホ・。シ・、ヒスセ、テ、ニ・ニ・ュ・ケ・ネターキチ、ケヤ、ヲ、ウ、ネ、ャ、ヌ、ュ、゙、ケ。」</p>
248  <ul>  
249  <li>  <ul>
250  空行は段落の区切りとなります。  <li>
251    カケヤ、マテハヘ、ホカ霏レ、熙ネ、ハ、熙゙、ケ。」
252  <li>  
253  HTMLのタグは書けません。  <li>
254    HTML、ホ・ソ・ー、マス、ア、゙、サ、。」
255  <li>  
256  ''ボールド''のようにシングルクォート二つではさむと、ボールドになります。  <li>
257    ''カットエ''、ホ、隍ヲ、ヒ・キ・・ー・・ッ・ゥ。シ・ネニ、ト、ヌ、マ、オ、爨ネ。「カットエ、ヒ、ハ、熙゙、ケ。」
258  <li>  
259  '''イタリック'''のようにシングルクォート三つではさむと、イタリックになります。  <li>
260    '''ケケ、ヒカットエ'''、ホ、隍ヲ、ヒ・キ・・ー・・ッ・ゥ。シ・ネサー、ト、ヌ、マ、オ、爨ネ。「ケケ、ヒカットエ、ヒ、ハ、熙゙、ケ。」
261  <li>  
262  ----のようにマイナス4つがあると、水平線になります。  <li>
263    ----、ホ、隍ヲ、ヒ・゙・、・ハ・ケ4、ト、ャ、「、、ネ。「ソ衞ソタ、ヒ、ハ、熙゙、ケ。」
264  <li>  
265  *を行頭に書くと大見出しになります。  <li>
266    *、ケヤニャ、ヒス、ッ、ネツ邵ォスミ、キ、ヒ、ハ、熙゙、ケ。」
267  <li>  
268  **を行頭に書くと小見出しになります。  <li>
269    **、ケヤニャ、ヒス、ッ、ネセョクォスミ、キ、ヒ、ハ、熙゙、ケ。」
270  <li>  
271  -を行頭に書くと箇条書きになります。- -- --- の3レベルがあります。  <li>
272    -、ケヤニャ、ヒス、ッ、ネイユセス、ュ、ヒ、ハ、熙゙、ケ。」- -- --- 、ホ3・・ル・、ャ、「、熙゙、ケ。」
273  <li>  
274  :を行頭に書くと用語と解説文が作れます。  <li>
275    :、ケヤニャ、ヒス、ッ、ネヘムク、ネイタ簗ク、ャコ、、゙、ケ。」
276  <pre>  
277      :用語1:いろいろ書いた解説文1  <pre>
278      :用語2:いろいろ書いた解説文2      :ヘムク1:、、、、、、ス、、、ソイタ簗ク1
279      :用語3:いろいろ書いた解説文3      :ヘムク2:、、、、、、ス、、、ソイタ簗ク2
280  </pre>      :ヘムク3:、、、、、、ス、、、ソイタ簗ク3
281    </pre>
282  <li>  
283  http://www.hyuki.com/ のようなURLは自動的にリンクになります。  <li>
284    http://www.hyuki.com/ 、ホ、隍ヲ、ハURL、マシォニーナェ、ヒ・・・ッ、ヒ、ハ、熙゙、ケ。」
285  <li>  
286  YukiWikiのように大文字小文字を混ぜた英文字列を書くと、  <li>
287  YukiWikiのページ名になります。  YukiWiki、ホ、隍ヲ、ヒツ醋クサセョハクサ、コョ、シ、ソアムハクサホ、ス、ッ、ネ。「
288    YukiWiki、ホ・レ。シ・クフセ、ヒ、ハ、熙゙、ケ。」
289  <li>  
290  [[結城浩]]のように二重の大かっこ[[ ]]でくくった文字列を書くと、  <li>
291  YukiWikiのページ名になります。  [[キセケタ]]、ホ、隍ヲ、ヒニスナ、ホツ遉ォ、テ、ウ[[ ]]、ヌ、ッ、ッ、テ、ソハクサホ、ス、ッ、ネ。「
292  大かっこの中にはスペースを含めてはいけません。  YukiWiki、ホ・レ。シ・クフセ、ヒ、ハ、熙゙、ケ。」
293  日本語も使えます。  ツ遉ォ、テ、ウ、ホテ讀ヒ、マ・ケ・レ。シ・ケ、エ゙、皃ニ、マ、、、ア、゙、サ、。」
294    ニヒワク、篏ネ、ィ、゙、ケ。」
295  <li>  
296  行頭がスペースで始まっていると、  <li>
297  その段落は整形済み扱われます。  ケヤニャ、ャ・ケ・レ。シ・ケ、ヌサマ、゙、テ、ニ、、、、ネ。「
298  プログラムを書き込むときに使うと便利です。  、ス、ホテハヘ、マターキチコム、゚ーキ、、、゙、ケ。」
299    ・ラ・・ー・鬣爨ス、ュケ、爨ネ、ュ、ヒサネ、ヲ、ネハリヘ、ヌ、ケ。」
300  <li>  
301  > を行頭に書くと、  <li>
302  引用文が書けます。  &gt; 、ケヤニャ、ヒス、ッ、ネ。「
303  >の数が多いとインデントが深くなります(3レベルまで)。  ーヘムハク、ャス、ア、゙、ケ。」
304    &gt; 、ホソ、ャツソ、、、ネ・、・・ヌ・・ネ、ャソシ、ッ、ハ、熙゙、ケ。ハ3・・ル・、゙、ヌ。ヒ。」
305  </ul>  
306  EOD  </ul>
307      &print_footer;  EOD
308  }      &print_footer;
309    }
310  # ページの検索  
311  sub do_search {  # ・レ。シ・ク、ホク。コ
312      if ($form{myword}) {  sub do_search {
313          &print_header('検索結果');      if ($form{myword}) {
314          print qq|<h1>$IconTag$form{myword}の検索結果</h1>\n|;          &print_header('ク。コキイフ');
315          &print_toolbar();          print qq|<h1>$IconTag$form{myword}、ホク。コキイフ</h1>\n|;
316          print qq|<ul>\n|;          &print_toolbar();
317          my $count = 0;          print qq|<ul>\n|;
318          foreach my $page_name (sort keys %database) {    # sortするのは無謀かな          my $count = 0;
319              if ($database{$page_name} =~ /\Q$form{'myword'}\E/) {          foreach my $page_name (sort keys %database) {    # sort、ケ、、ホ、マフオヒナ、ォ、ハ
320                  my $encoded = &encode_percent($page_name);              if ($database{$page_name} =~ /\Q$form{'myword'}\E/) {
321                  print qq|<li><a href="$thisurl?mycmd=read&mypage=$encoded">$page_name</a>\n|;                  my $encoded = &encode_percent($page_name);
322                  $count++;                  print qq|<li><a href="$thisurl?mycmd=read;mypage=$encoded">$page_name</a>\n|;
323              }                  $count++;
324          }              }
325          print qq|</ul>\n|;          }
326          if ($count > 0) {          print qq|</ul>\n|;
327              print qq|<p><b>$form{myword}</b>を含むページは、上に示す<b>$count</b>ページです。</p>\n|;          if ($count > 0) {
328          } else {              print qq|<p><strong>$form{myword}</strong>、エ゙、爭レ。シ・ク、マ。「セ螟ヒシィ、ケ<strong>$count</strong> ・レ。シ・ク、ヌ、ケ。」</p>\n|;
329              print qq|<p><b>$form{myword}</b>を含むページは見つかりません。</p>\n|;          } else {
330          }              print qq|<p><strong>$form{myword}</strong>、エ゙、爭レ。シ・ク、マクォ、ト、ォ、熙゙、サ、。」</p>\n|;
331      } else {          }
332          &print_header('単語検索');      } else {
333          print qq|<h1>$IconTag単語検索</h1>\n|;          &print_header('テアクク。コ');
334          &print_toolbar();          print qq|<h1>$IconTagテアクク。コ</h1>\n|;
335      }          &print_toolbar();
336      print <<"EOD";      }
337  <p>      print <<"EOD";
338  <form action="$thisurl" method="post">  <p>
339  <input type="hidden" name="mycmd" value="search">  <form action="$thisurl" method="post">
340  <input type="text" name="myword" size="20" value="$form{myword}">  <input type="hidden" name="mycmd" value="search">
341  <input type="submit" value="単語検索">  <input type="text" name="myword" size="20" value="$form{myword}">
342  </form>  <input type="submit" value="テアクク。コ">
343  </p>  </form>
344  EOD  </p>
345      &print_footer;  EOD
346  }      &print_footer;
347    }
348  # ページの一覧  
349  sub do_list {  # ・レ。シ・ク、ホーヘ
350      &print_header('ページ一覧');  sub do_list {
351      print qq|<h1>$IconTag ページ一覧</h1>\n|;      &print_header('・レ。シ・クーヘ');
352      &print_toolbar();      print qq|<h1>$IconTag ・レ。シ・クーヘ</h1>\n|;
353      print qq|<ul>\n|;      &print_toolbar();
354      foreach my $page_name (sort keys %database) {    # sortするのは無謀かな      print qq|<ul>\n|;
355          my $encoded = &encode_percent($page_name);      foreach my $page_name (sort keys %database) {    # sort、ケ、、ホ、マフオヒナ、ォ、ハ
356          print qq|<li><a href="$thisurl?mycmd=read&mypage=$encoded">$page_name</a>\n|          my $encoded = &encode_percent($page_name);
357      }          print qq|<li><a href="$thisurl?mycmd=read;mypage=$encoded">$page_name</a>\n|
358      print qq|</ul>\n|;      }
359      &print_footer;      print qq|</ul>\n|;
360  }      &print_footer;
361    }
362  # プレビュー  
363  sub do_preview {  # ・ラ・・モ・蝪シ
364      my $page_name = $form{mypage};  sub do_preview {
365      my $escapedmsg = &escape($form{mymsg});      my $page_name = $form{mypage};
366      &print_header($page_name);      my $escapedmsg = &escape($form{mymsg});
367      print qq|<h1>$IconTag${page_name}のプレビュー</h1>\n|;      &print_header($page_name);
368      &print_toolbar($page_name);      print qq|<h1>$IconTag${page_name}、ホ・ラ・・モ・蝪シ</h1>\n|;
369      # local $percent_name = &encode_percent($page_name);      &print_toolbar($page_name);
370      print qq|<p>以下のプレビューを確認して、よければページ下部のボタンで更新してください。</p>\n|;      # local $percent_name = &encode_percent($page_name);
371      if ($form{mymsg}) {      print qq|<p>ーハイシ、ホ・ラ・・モ・蝪シ、ウホヌァ、キ、ニ。「、隍ア、、ミ・レ。シ・クイシノ、ホ・ワ・ソ・、ヌケケソキ、キ、ニ、ッ、タ、オ、、。」</p>\n|;
372          print qq|<table width="100%" bgcolor="$preview_color" ><tr><td>\n|;      if ($form{mymsg}) {
373          # print &convert_html($escapedmsg);          print qq|<table width="100%" bgcolor="$preview_color" ><tr><td>\n|;
374          print &convert_html($form{mymsg});          # print &convert_html($escapedmsg);
375          print qq|</td></tr></table>\n|;          print &convert_html($form{mymsg});
376      } else {          print qq|</td></tr></table>\n|;
377          print qq|<p>(ページの内容は空です。更新するとこのページは<b>削除</b>されます。)</p>\n|;      } else {
378      }          print qq|<p>。ハ・レ。シ・ク、ホニ簣ニ、マカ、ヌ、ケ。」ケケソキ、ケ、、ネ、ウ、ホ・レ。シ・ク、マ<strong>コス</strong>、オ、、゙、ケ。」。ヒ</p>\n|;
379      &print_preview_buttons($page_name, $escapedmsg, $form{mydigest});      }
380      &print_footer;      &print_preview_buttons($page_name, $escapedmsg, $form{mydigest});
381  }      &print_footer;
382    }
383  sub print_preview_buttons {  
384      my ($page_name, $escapedmsg, $digest) = @_;  sub print_preview_buttons {
385      print <<"EOD";      my ($page_name, $escapedmsg, $digest) = @_;
386      <form action="$thisurl" method="post">      print <<"EOD";
387      <textarea cols="$cols" rows="$rows" name="mymsg" wrap="virtual">$escapedmsg</textarea>      <form action="$thisurl" method="post">
388      <br />      <textarea cols="$cols" rows="$rows" name="mymsg" wrap="virtual">$escapedmsg</textarea>
389      <input type="hidden" name="mypage" value="$page_name">      <br />
390      <input type="hidden" name="mydigest" value="$digest">      <input type="hidden" name="mypage" value="$page_name">
391      <input type="submit" name="myspecial_preview" value="再度プレビュー">      <input type="hidden" name="mydigest" value="$digest">
392      <input type="submit" name="myspecial_write" value="ページの更新">      <input type="submit" name="myspecial_preview" value="コニナル・ラ・・モ・蝪シ">
393      </form>      <input type="submit" name="myspecial_write" value="・レ。シ・ク、ホケケソキ">
394  EOD      </form>
395  }  EOD
396    }
397  # 書き込む  
398  sub do_write {  # ス、ュケ、
399      if (not &is_editable($form{mypage})) {  sub do_write {
400          # 編集不可ページは表示のみ      if (not &is_editable($form{mypage})) {
401          &do_read;          # ハヤスクノヤイト・レ。シ・ク、マノスシィ、ホ、゚
402          return;          &do_read;
403      }          return;
404        }
405      my $page_name = $form{mypage};  
406        my $page_name = $form{mypage};
407      # digestを使って、更新の衝突チェック  
408      my $original_digest = &calc_message_digest(&get_page($page_name));      # digest、サネ、テ、ニ。「ケケソキ、ホセラニヘ・チ・ァ・テ・ッ
409      if ($form{mydigest} ne $original_digest) {      my $original_digest = &calc_message_digest(&get_page($page_name));
410          &print_header($page_name);      if ($form{mydigest} ne $original_digest) {
411          print qq|<h1>$IconTag${page_name}で【更新の衝突】が起きました</h1>\n|;          &print_header($page_name);
412          print <<"EOD";          print qq|<h1>$IconTag${page_name}、ヌ。レケケソキ、ホセラニヘ。ロ、ャオッ、ュ、゙、キ、ソ</h1>\n|;
413  <p>あなたがこのページを編集している間に、          print <<"EOD";
414  他の人が同じページを更新してしまったようです。  <p>、「、ハ、ソ、ャ、ウ、ホ・レ。シ・ク、ハヤスク、キ、ニ、、、エヨ、ヒ。「
415  </p><p>  ツセ、ホソヘ、ャニア、ク・レ。シ・ク、ケケソキ、キ、ニ、キ、゙、テ、ソ、隍ヲ、ヌ、ケ。」
416  以下に、あなたの編集したテキストがありますので、  </p><p>
417  あなたの編集内容が失われないように、  ーハイシ、ヒ。「、「、ハ、ソ、ホハヤスク、キ、ソ・ニ・ュ・ケ・ネ、ャ、「、熙゙、ケ、ホ、ヌ。「
418  いますぐ、メモ帳などにコピー&ペーストしてください。  、「、ハ、ソ、ホハヤスクニ簣ニ、ャシコ、、、ハ、、、隍ヲ、ヒ。「
419  </p><p>  、、、゙、ケ、ー。「・皈籠「、ハ、ノ、ヒ・ウ・ヤ。シ。・レ。シ・ケ・ネ、キ、ニ、ッ、タ、オ、、。」
420  コピー&ペーストが済んでから、  </p><p>
421  最新の内容を見て再度編集し直してください。  ・ウ・ヤ。シ。・レ。シ・ケ・ネ、ャコム、、ヌ、ォ、鬘「
422  最新の内容は  コヌソキ、ホニ簣ニ、クォ、ニコニナルハヤスク、キトセ、キ、ニ、ッ、タ、オ、、。」
423  <a target="_blank" href="$thisurl?mycmd=read&mypage=$form{mypage}">$form{mypage}</a>  コヌソキ、ホニ簣ニ、マ
424  で見ることができます。  <a target="_blank" href="$thisurl?mycmd=read;mypage=$form{mypage}">$form{mypage}</a>
425  </p>  、ヌクォ、、ウ、ネ、ャ、ヌ、ュ、゙、ケ。」
426  EOD  </p>
427          # &print_toolbar($page_name);  EOD
428          &print_preview_buttons($page_name, &escape($form{mymsg}), $form{mydigest});          # &print_toolbar($page_name);
429          &print_footer;          &print_preview_buttons($page_name, &escape($form{mymsg}), $form{mydigest});
430          return;          &print_footer;
431      }          return;
432        }
433      # diff生成  
434      {      # diffタクタョ
435          &opendiff;      {
436          my @msg1 = split(/\n/, &get_page($page_name));          &opendiff;
437          my @msg2 = split(/\n/, $form{mymsg});          my @msg1 = split(/\n/, &get_page($page_name));
438          $msgrefA = \@msg1;          my @msg2 = split(/\n/, $form{mymsg});
439          $msgrefB = \@msg2;          $msgrefA = \@msg1;
440          &diff_check;          $msgrefB = \@msg2;
441          $diffbase{$form{mypage}} = $diff_text;          &diff_check;
442          $diff_text = '';          $diffbase{$form{mypage}} = $diff_text;
443          &closediff;          $diff_text = '';
444      }          &closediff;
445        }
446      &print_header($page_name);  
447      &set_page($page_name, $form{mymsg});      &print_header($page_name);
448      if ($form{mymsg}) {      &set_page($page_name, $form{mymsg});
449          print qq|<h1>$IconTag${page_name}を更新しました</h1>\n|;      if ($form{mymsg}) {
450          &print_toolbar($page_name);          print qq|<h1>$IconTag${page_name}、ケケソキ、キ、゙、キ、ソ</h1>\n|;
451          print &convert_html(&get_page($page_name));          &print_toolbar($page_name);
452      } else {          print &convert_html(&get_page($page_name));
453          print qq|<h1>$IconTag${page_name}を削除しました</h1>\n|;      } else {
454          &print_toolbar($page_name);          print qq|<h1>$IconTag${page_name}、コス、キ、゙、キ、ソ</h1>\n|;
455          print qq|<p>${page_name}を削除しました。</p>\n|;          &print_toolbar($page_name);
456      }          print qq|<p>${page_name}、コス、キ、゙、キ、ソ。」</p>\n|;
457      &print_footer;      }
458      # 更新されたのでタッチしておく。      &print_footer;
459      if ($touchfile) {      # ケケソキ、オ、、ソ、ホ、ヌ・ソ・テ・チ、キ、ニ、ェ、ッ。」
460          open(FILE, "> $touchfile");      if ($touchfile) {
461          print FILE "\n";          open(FILE, "> $touchfile");
462          close(FILE);          print FILE "\n";
463      }          close(FILE);
464  }      }
465    }
466  # ページの変更点  
467  sub do_diff {  # ・レ。シ・ク、ホハムケケナタ
468      if (not &is_editable($form{mypage})) {  sub do_diff {
469          # 編集不可ページは表示のみ      if (not &is_editable($form{mypage})) {
470          &do_read;          # ハヤスクノヤイト・レ。シ・ク、マノスシィ、ホ、゚
471          return;          &do_read;
472      }          return;
473      &opendiff;      }
474      &print_header($form{mypage} . 'の変更点');      &opendiff;
475      print qq|<h1>$IconTag <a href="$thisurl?mycmd=read&mypage=$form{mypage}">$form{mypage}</a>の変更点</h1>\n|;      &print_header($form{mypage} . '、ホハムケケナタ');
476      &print_toolbar();      print qq|<h1>$IconTag <a href="$thisurl?mycmd=read&mypage=$form{mypage}">$form{mypage}</a>、ホハムケケナタ</h1>\n|;
477      $_ = &escape($diffbase{$form{mypage}});      &print_toolbar();
478      print <<"EOD";      $_ = &escape($diffbase{$form{mypage}});
479  <ul>      print <<"EOD";
480  <li>追加された行は<font color="blue">青色</font>です。  <ul>
481  <li>削除された行は<font color="red">赤色</font>です。  <li>トノイテ、オ、、ソケヤ、マ<ins>タトソァ</ins>、ヌ、ケ。」
482  <li><a href="$thisurl?mycmd=read&mypage=$form{mypage}">$form{mypage}</a>へ行く。  <li>コス、オ、、ソケヤ、マ<del>タヨソァ</del>、ヌ、ケ。」
483  </ul>  <li><a href="$thisurl?mycmd=read;mypage=$form{mypage}">$form{mypage}</a>、リケヤ、ッ。」
484  <hr />  </ul>
485  EOD  <hr />
486      print qq|<pre>\n|;  EOD
487      foreach (split(/\n/, $_)) {      print qq|<pre>\n|;
488          if (/^\+(.*)/) {      foreach (split(/\n/, $_)) {
489              print qq|<font color="blue">$1</font>\n|;          if (/^\+(.*)/) {
490          } elsif (/^\-(.*)/) {              print qq|<ins>$1</ins>\n|;
491              print qq|<font color="red">$1</font>\n|;          } elsif (/^\-(.*)/) {
492          } elsif (/^\=(.*)/) {              print qq|<del>$1</del>\n|;
493              print qq|$1\n|;          } elsif (/^\=(.*)/) {
494          } else {              print qq|$1\n|;
495              print qq|??? $_\n|;          } else {
496          }              print qq|??? $_\n|;
497      }          }
498      print qq|</pre>\n|;      }
499      &print_footer;      print qq|</pre>\n|;
500      &closediff;      &print_footer;
501  }      &closediff;
502    }
503  sub opendiff {  
504      if ($dbmopen) {  sub opendiff {
505          if (!dbmopen(%diffbase, $diffdbname, 0666)) {      if ($dbmopen) {
506              &print_error("(dbmopen) $diffdbname が作れません。");          if (!dbmopen(%diffbase, $diffdbname, 0666)) {
507          }              &print_error("(dbmopen) $diffdbname 、ャコ、、゙、サ、。」");
508      } else {          }
509          if (!tie(%diffbase, "YukiWikiDB", $diffdbname)) {      } else {
510              &print_error("(tie error)");          if (!tie(%diffbase, "YukiWikiDB", $diffdbname)) {
511          }              &print_error("(tie error)");
512      }          }
513  }      }
514    }
515  sub closediff {  
516      if ($dbmopen) {  sub closediff {
517          dbmclose(%diffbase);      if ($dbmopen) {
518      } else {          dbmclose(%diffbase);
519          untie(%diffbase);      } else {
520      }          untie(%diffbase);
521  }      }
522    }
523  # フォームからの情報を連想配列 %form に入れる  
524  # &init_form('euc');  # ・ユ・ゥ。シ・爨ォ、鬢ホセハ、マ「チロヌロホ %form 、ヒニ、、
525  sub init_form {  # &init_form('euc');
526      my ($charcode) = @_;  sub init_form {
527      my $query;      my ($charcode) = @_;
528      if ($ENV{REQUEST_METHOD} =~ /^post$/i) {      my $query;
529          read(STDIN, $query, $ENV{CONTENT_LENGTH});      if ($ENV{REQUEST_METHOD} =~ /^post$/i) {
530      } else {          read(STDIN, $query, $ENV{CONTENT_LENGTH});
531          $query = $ENV{QUERY_STRING};      } else {
532      }          $query = $ENV{QUERY_STRING};
533      my @assocarray = split(/&/, $query);      }
534      foreach my $assoc (@assocarray) {      my @assocarray = split(/[&;]/, $query);
535          my ($property, $value) = split(/=/, $assoc);      foreach my $assoc (@assocarray) {
536          $value =~ tr/+/ /;          my ($property, $value) = split(/=/, $assoc);
537          $value =~ s/%([A-Fa-f0-9][A-Fa-f0-9])/pack("C", hex($1))/eg;          $value =~ tr/+/ /;
538          &jcode::convert(\$value, $charcode);          $value =~ s/%([A-Fa-f0-9][A-Fa-f0-9])/pack("C", hex($1))/eg;
539          $form{$property} = $value;          &jcode::convert(\$value, $charcode);
540      }          $form{$property} = $value;
541  }      }
542    }
543  # エラーページを出力する  
544  sub print_error {  # ・ィ・鬘シ・レ。シ・ク、スミホマ、ケ、
545      my ($msg) = @_;  sub print_error {
546      &print_header('Error');      my ($msg) = @_;
547      print "<h1>$IconTag$msg</h1></body></html>";      &print_header('Error');
548      exit(0);      print "<h1>$IconTag$msg</h1></body></html>";
549  }      exit(0);
550    }
551  sub escape {  
552      my ($line) = shift;  sub escape {
553      $line =~ s|<|&lt;|g;      my ($line) = shift;
554      $line =~ s|>|&gt;|g;      $line =~ s|<|&lt;|g;
555      $line =~ s|"|&quot;|g;      $line =~ s|>|&gt;|g;
556      # $line =~ s|\&|&amp;|g;      $line =~ s|"|&quot;|g;
557      return $line;      # $line =~ s|\&|&amp;|g;
558  }      return $line;
559    }
560  sub inline {  
561      my ($line) = shift;  sub inline {
562      $line = &escape($line);      my ($line) = shift;
563      $line =~ s|'''([^']+?)'''|<i>$1</i>|g;              # Italic      $line = &escape($line);
564      $line =~ s|''([^']+?)''|<b>$1</b>|g;                # Bold      $line =~ s|'''([^']+?)'''|<strong>$1</strong>|g;
565      $line =~ s!      $line =~ s|''([^']+?)''|<em>$1</em>|g;          
566                  (      $line =~ s!
567                      ((mailto|http|https|ftp):[\x21-\x7E]*) # Direct http://...         (
568                          |           (?:&lt;(?:mailto|http|https|ftp|urn):[\x21-\x7E]*)&gt;
569                      ($WikiName)                         # LocalLinkLikeThis         | (?:$WikiName)                         # LocalLinkLikeThis
570                          |         | (?:$BracketName)                      # [[ニヒワク・・・ッ]]
571                      ($BracketName)                      # [[日本語リンク]]         )
572                  )              !
573              !                  &make_link($1)
574                  &make_link($1)              !gex;
575              !gex;      return $line;
576      return $line;  }
577  }  
578    # ・レ。シ・ク、ホ・ソ・、・ネ・、ォ、鬣レ。シ・ク、ホニ簣ニ、ニタ、
579  # ページのタイトルからページの内容を得る  sub get_page {
580  sub get_page {      my $page_name = shift;
581      my $page_name = shift;      return $database{$page_name};
582      return $database{$page_name};  }
583  }  
584    # ・レ。シ・ク、ホニ簣ニ、ヘソ、ィ、
585  # ページの内容を与える  # &set_page($title, $txt)
586  # &set_page($title, $txt)  sub set_page {
587  sub set_page {      # ・レ。シ・ク、ケケソキ、ケ、
588      # ページを更新する      my $title = $_[0];
589      my $title = $_[0];      $database{$title} = $_[1];
590      $database{$title} = $_[1];      # カ・レ。シ・ク、ハ、鮗ス、ケ、
591      # 空ページなら削除する      unless ($database{$title}) {
592      unless ($database{$title}) {          delete $database{$title};
593          delete $database{$title};      }
594      }      # RecentChanges、ケケソキ、ケ、
595      # RecentChangesを更新する      my $delim = ' - ';
596      my $delim = ' - ';      my @pages = split(/\n/, $database{$whatsnew});
597      my @pages = split(/\n/, $database{$whatsnew});      my $datestr = &get_current_datestr;
598      my $datestr = &get_current_datestr;      unshift(@pages, qq|-$datestr$delim$title|);
599      unshift(@pages, qq|-$datestr$delim$title|);      # ニアー・レ。シ・ク、ホケケソキ、マコヌソキ、ホ、筅ホ、ホ、゚、ヒ、キ。「
600      # 同一ページの更新は最新のもののみにし、      # ツクコ゚、キ、ハ、、・レ。シ・ク、マ・ケ・ュ・テ・ラ、ケ、。」
601      # 存在しないページはスキップする。      my %count;
602      my %count;      my @newpages;
603      my @newpages;      foreach my $line (@pages) {
604      foreach my $line (@pages) {          my ($prefix, $title) = split(/$delim/, $line);
605          my ($prefix, $title) = split(/$delim/, $line);          $count{$title}++;
606          $count{$title}++;          if ($count{$title} == 1 and exists($database{$title})) {
607          if ($count{$title} == 1 and exists($database{$title})) {              push(@newpages, qq|$prefix - $title|);
608              push(@newpages, qq|$prefix - $title|);          }
609          }      }
610      }      # 、ウ、ウ、ヌヒワナ、ヒケケソキ
611      # ここで本当に更新      $database{$whatsnew} = join("\n", splice(@newpages, 0, $maxnew));
612      $database{$whatsnew} = join("\n", splice(@newpages, 0, $maxnew));  }
613  }  
614    # ・レ。シ・ク、ホ・リ・テ・タ、スミホマ
615  # ページのヘッダを出力  sub print_header {
616  sub print_header {      my $title = shift;
617      my $title = shift;      print <<"EOD";
618      print <<"EOD";  Content-type: text/html
619  Content-type: text/html  
620    <html><head>
621  <html><head>  <title>$title</title>
622  <title>$title</title>  <style type="text/css">
623  <style type="text/css">  $style
624  <!--  </style>
625  $style  </head>
626  -->  <body>
627  </style>  EOD
628  </head>  }
629  <body bgcolor="white">  
630  EOD  # ・ト。シ・・ミ。シ、スミホマ
631  }  sub print_toolbar {
632        my $page_name = shift;
633  # ツールバーを出力      my $percent_name = &encode_percent($page_name);
634  sub print_toolbar {      my $editlink = '';
635      my $page_name = shift;      if ($page_name ne '' and &is_editable($page_name)) {
636      my $percent_name = &encode_percent($page_name);          $editlink = <<"EOD";
637      my $editlink = '';  <a href="$thisurl?mycmd=edit;mypage=$percent_name">ハヤスク</a> |
638      if ($page_name ne '' and &is_editable($page_name)) {  <a href="$thisurl?mycmd=diff;mypage=$percent_name">コケハャ</a> |
639          $editlink = <<"EOD";  EOD
640  <a href="$thisurl?mycmd=edit&mypage=$percent_name">編集</a> |      }
641  <a href="$thisurl?mycmd=diff&mypage=$percent_name">差分</a> |      print <<"EOD";
642  EOD  <p>
643      }   [
644      print <<"EOD";  <a href="$thisurl?mycmd=read;mypage=$toppage">・ネ・テ・ラ</a> |
645  <p>  <a href="$thisurl?mycmd=list">ーヘ</a> |
646   [  $editlink
647  <a href="$thisurl?mycmd=read&mypage=$toppage">トップ</a> |  <a href="$thisurl?mycmd=search">テアクク。コ</a> |
648  <a href="$thisurl?mycmd=list">一覧</a> |  <a href="$thisurl?mycmd=read;mypage=$whatsnew">コヌスェケケソキ</a>
649  $editlink   ]
650  <a href="$thisurl?mycmd=search">単語検索</a> |  </p>
651  <a href="$thisurl?mycmd=read&mypage=$whatsnew">最終更新</a>  EOD
652   ]  }
653  </p>  
654  EOD  # ・レ。シ・ク、ホ・ユ・テ・ソ、スミホマ
655  }  sub print_footer {
656        print <<"EOD";
657  # ページのフッタを出力  <address>
658  sub print_footer {  <a href="http://www.hyuki.com/yukiwiki/">YukiWiki</a> 1.6.6 Copyright (C) 2000,2001 by <a href="http://www.hyuki.com/">Hiroshi Yuki.</a>
659      print <<"EOD";  + <a href="$modifierlink">$modifier</a> ${version}.
660  <hr>  [<a href="/" title="、ウ、ホ・オ。シ・ミ。シ、ホシハヌ">/</a>
661  <p>  <a href="/map" title="、ウ、ホ・オ。シ・ミ。シ、ホーニニ">テマゾ</a>
662  <a href="http://www.hyuki.com/yukiwiki/">YukiWiki</a> $version Copyright (C) 2000,2001 by <a href="http://www.hyuki.com/">Hiroshi Yuki.</a><br />  <a href="/search/" title="、ウ、ホ・オ。シ・ミ。シ、ホク。コ">ク。コ</a>]
663  Modified by <a href="$modifierlink">$modifier</a>.<br/>  </address>
664  </p>  </body></html>
665  </body></html>  EOD
666  EOD  }
667  }  
668    # URL、茹レ。シ・ク、ホフセチー、ォ、鬣・・ッ、コ、
669  # URLやページの名前からリンクを作る  sub make_link {
670  sub make_link {      my $name = shift;
671      my $name = shift;      $name =~ s/^&lt;(.*)&gt;$/$1/;
672      if ($name =~ /^(http|https|ftp).*?(\.gif|\.png|\.jpeg|\.jpg)?$/) {      if ($name =~ /^(http|https|ftp).*?(\.png|\.jpeg|\.jpg)?$/) {
673          if ($2) {          if ($2) {
674              return qq|<a href="$name"><img border="0" src="$name" /></a>|;              return qq|<a href="$name"><img border="0" src="$name" /></a>|;
675          } else {          } else {
676              return qq|<a href="$name">$name</a>|;              return qq|&lt;<a href="$name">$name</a>&gt;|;
677          }          }
678      } elsif ($name =~ /^mailto:(.*)/) {      } elsif ($name =~ /^mailto:(.*)/) {
679          my $address = $1;          my $address = $1;
680          return qq|<a href="$name">$address</a>|;          return qq|&lt;<a href="$name">$address</a>&gt;|;
681      } elsif ($database{$name}) {      } elsif ($name =~ /^urn:[0-9A-Za-z_:-]+/) {
682          my $percent_name = &encode_percent($name);          return qq|&lt;<a href="/uri-res/N2L?${name}">$name</a>&gt;|;
683          return qq|<a href="$thisurl?mycmd=read&mypage=$percent_name">$name</a>|;      } elsif ($database{$name}) {
684      } else {          my $percent_name = &encode_percent($name);
685          my $percent_name = &encode_percent($name);          return qq|<a href="$thisurl?mycmd=read;mypage=$percent_name">$name</a>|;
686          return qq|$name<a href="$thisurl?mycmd=edit&mypage=$percent_name">?</a>|;      } else {
687      }          my $percent_name = &encode_percent($name);
688  }          return qq|$name<a href="$thisurl?mycmd=edit;mypage=$percent_name">?</a>|;
689        }
690  # %xx の形式にエンコードする  }
691  # これは、  
692  # http://www.hyuki.com/yukiwiki/yukiwiki.cgi?mycmd=read&mypage=%3C%8C%8B%8F%E9%8D_%3E  # %xx 、ホキチシー、ヒ・ィ・・ウ。シ・ノ、ケ、
693  # という形式のために使われる。  # 、ウ、、マ。「
694  # '<結城浩>' → '%3C%8C%8B%8F%E9%8D_%3E'  # http://www.hyuki.com/yukiwiki/yukiwiki.cgi?mycmd=read&mypage=%3C%8C%8B%8F%E9%8D_%3E
695  sub encode_percent {  # 、ネ、、、ヲキチシー、ホ、ソ、皃ヒサネ、、、。」
696      my $name = shift;  # '<キセケタ>' 「ェ '%3C%8C%8B%8F%E9%8D_%3E'
697      my $encoded = '';  sub encode_percent {
698      foreach my $ch (split(//, $name)) {      my $name = shift;
699          if ($ch =~ /[A-Za-z0-9_]/) {      my $encoded = '';
700              $encoded .= $ch;      foreach my $ch (split(//, $name)) {
701          } else {          if ($ch =~ /[A-Za-z0-9_]/) {
702              $encoded .= '%' . sprintf("%02X", ord($ch));              $encoded .= $ch;
703          }          } else {
704      }              $encoded .= '%' . sprintf("%02X", ord($ch));
705      return $encoded;          }
706  }      }
707        return $encoded;
708  # テキスト本体をHTMLに変換する  }
709  sub convert_html {  
710      my ($txt) = shift;  # ・ニ・ュ・ケ・ネヒワツホ、HTML、ヒハムエケ、ケ、
711      my (@txt) = split(/\n/, $txt);  sub convert_html {
712      foreach (@txt) {      my ($txt) = shift;
713          chomp;      my (@txt) = split(/\n/, $txt);
714          if (/^\*\*(.*)/) {      foreach (@txt) {
715              push(@result, splice(@saved), '<h3>' . &inline($1) . '</h3>');          chomp;
716          } elsif (/^\*(.*)/) {          if (/^\*\*(.*)/) {
717              push(@result, splice(@saved), '<h2>' . &inline($1) . '</h2>');              push(@result, splice(@saved), '<h3>' . &inline($1) . '</h3>');
718          } elsif (/^----/) {          } elsif (/^\*(.*)/) {
719              push(@result, splice(@saved), '<hr>');              push(@result, splice(@saved), '<h2>' . &inline($1) . '</h2>');
720          } elsif (/^(-{1,3})(.*)/) {          } elsif (/^----/) {
721              &back_push('ul', length($1));              push(@result, splice(@saved), '<hr>');
722              push(@result, '<li>' . &inline($2) . '</li>');          } elsif (/^(-{1,3})(.*)/) {
723          } elsif (/^:([^:]+):(.*)/) {              &back_push('ul', length($1));
724              &back_push('dl', 1);              push(@result, '<li>' . &inline($2) . '</li>');
725              push(@result, '<dt>' . &inline($1) . '</dt>', '<dd>' . &inline($2) . '</dd>');          } elsif (/^:([^:]+):(.*)/) {
726          } elsif (/^(>{1,3})(.*)/) {              &back_push('dl', 1);
727              &back_push('blockquote', length($1));              push(@result, '<dt>' . &inline($1) . '</dt>', '<dd>' . &inline($2) . '</dd>');
728              push(@result, &inline($2));          } elsif (/^(>{1,3})(.*)/) {
729          } elsif (/^\s*$/) {              &back_push('blockquote', length($1));
730              push(@result, splice(@saved));              push(@result, &inline($2));
731              unshift(@saved, "</p>");          } elsif (/^\s*$/) {
732              push(@result, "<p>");              push(@result, splice(@saved));
733          } elsif (/^(\s+.*)$/) {              unshift(@saved, "</p>");
734              &back_push('pre', 1);              push(@result, "<p>");
735              push(@result, &escape($1)); # Not &inline, but &escape          } elsif (/^(\s+.*)$/) {
736          } else {              &back_push('pre', 1);
737              push(@result, &inline($_));              push(@result, &escape($1)); # Not &inline, but &escape
738          }          } else {
739      }              push(@result, &inline($_));
740      push(@result, splice(@saved));          }
741      return join("\n", @result);      }
742  }      push(@result, splice(@saved));
743        return join("\n", @result);
744  # &back_push($tag, $count)  }
745  # $tagのタグを$levelレベルまで詰める。  
746  sub back_push {  # &back_push($tag, $count)
747      my ($tag, $level) = @_;  # $tag、ホ・ソ・ー、$level・・ル・、゙、ヌオヘ、皃。」
748      while (@saved > $level) {  sub back_push {
749          push(@result, shift(@saved));      my ($tag, $level) = @_;
750      }      while (@saved > $level) {
751      if ($saved[0] ne "</$tag>") {          push(@result, shift(@saved));
752          push(@result, splice(@saved));      }
753      }      if ($saved[0] ne "</$tag>") {
754      while (@saved < $level) {          push(@result, splice(@saved));
755          unshift(@saved, "</$tag>");      }
756          push(@result, "<$tag>");      while (@saved < $level) {
757      }          unshift(@saved, "</$tag>");
758  }          push(@result, "<$tag>");
759        }
760  # 編集可能ページか?  }
761  sub is_editable {  
762      my ($pagename) = @_;  # ハヤスクイトヌス・レ。シ・ク、ォ。ゥ
763      foreach (@uneditable) {  sub is_editable {
764          if ($pagename eq $_) {      my ($pagename) = @_;
765              return 0;      foreach (@uneditable) {
766          }          if ($pagename eq $_) {
767      }              return 0;
768      if (&is_valid_name($pagename)) {          }
769          return 1;      }
770      }      if (&is_valid_name($pagename)) {
771      return 0;          return 1;
772  }      }
773        return 0;
774  # Validな名前か?  }
775  sub is_valid_name {  
776      my ($pagename) = @_;  # Valid、ハフセチー、ォ。ゥ
777      if ($pagename =~ /^$WikiName$/) {  sub is_valid_name {
778          return 1;      my ($pagename) = @_;
779      } elsif ($pagename =~ /^$BracketName$/) {      if ($pagename =~ /^$WikiName$/) {
780          return 1;          return 1;
781      } else {      } elsif ($pagename =~ /^$BracketName$/) {
782          return 0;          return 1;
783      }      } else {
784  }          return 0;
785        }
786  # 現在時刻の文字列を得る  }
787  sub get_current_datestr {  
788      my (@wdays) = ( "日", "月", "火", "水", "木", "金", "土" );  # クスコ゚サケ、ホハクサホ、ニタ、
789      my ($sec, $min, $hour, $mday, $mon, $year, $wday) = localtime(time);  sub get_current_datestr {
790      return sprintf("%4d-%02d-%02d (%s) %02d:%02d:%02d",      my (@wdays) = ( "ニ", "キ", "イミ", "ソ", "フレ", "カ", "ナレ" );
791          $year + 1900, $mon + 1, $mday, $wdays[$wday], $hour, $min, $sec);      my ($sec, $min, $hour, $mday, $mon, $year, $wday) = localtime(time);
792  }      return sprintf("%4d-%02d-%02d (%s) %02d:%02d:%02d",
793            $year + 1900, $mon + 1, $mday, $wdays[$wday], $hour, $min, $sec);
794  # URL?SomePageや、  }
795  # URL?[[結城浩]]の形式だった場合、(not yet)  
796  # 強制的にmycmdをreadにして$formの内容を設定する。  # URL?SomePage、茖「
797  sub normalize_form {  # URL?[[キセケタ]]、ホキチシー、タ、テ、ソセケ遑「(not yet)
798      foreach my $key (keys %form) {  # カッタゥナェ、ヒmycmd、read、ヒ、キ、ニ$form、ホニ簣ニ、タ゚ト熙ケ、。」
799          if ($key =~ /^$WikiName$/) {  sub normalize_form {
800              $form{mycmd} = 'read';      foreach my $key (keys %form) {
801              $form{mypage} = $1;          if ($key =~ /^$WikiName$/) {
802              last;              $form{mycmd} = 'read';
803          } elsif ($key =~ /^$BracketName$/) {              $form{mypage} = $1;
804              $form{mycmd} = 'read';              last;
805              $form{mypage} = $1;          } elsif ($key =~ /^$BracketName$/) {
806              last;              $form{mycmd} = 'read';
807          }              $form{mypage} = $1;
808      }              last;
809  }          }
810        }
811  # 変換テストを行なうときのサンプル  }
812  sub print_sample {  
813      my $txt = &convert_html(<<"EOD");  # ハムエケ・ニ・ケ・ネ、ケヤ、ハ、ヲ、ネ、ュ、ホ・オ・・ラ・
814  *大見出し1  sub print_sample {
815  **小見出し1-1      my $txt = &convert_html(<<"EOD");
816  -項目1  *ツ邵ォスミ、キ1
817  -項目2  **セョクォスミ、キ1-1
818  -項目3  -ケ猯ワ1
819  段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1  -ケ猯ワ2
820  段落1段落1段落1段落1段落1段落''強調''1段落1段落1段落1段落1段落1  -ケ猯ワ3
821  段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1  テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1
822    テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ''カットエ''1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1
823  段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2  テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1
824  段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2  
825  段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2  テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2
826  **小見出し1-2  テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2
827  :用語1:いろいろ書いた解説文1と''強調単語''  テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2
828  段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1  **セョクォスミ、キ1-2
829  段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1  :ヘムク1:、、、、、、ス、、、ソイタ簗ク1、ネ''カットエテアク''
830  段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1  テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1
831  :用語2:いろいろ書いた解説文2  テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1
832  :用語3:いろいろ書いた解説文3  テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1
833  ----  :ヘムク2:、、、、、、ス、、、ソイタ簗ク2
834  *大見出し2  :ヘムク3:、、、、、、ス、、、ソイタ簗ク3
835  **小見出し2-1  ----
836  http://www.hyuki.com/  *ツ邵ォスミ、キ2
837  **小見出し2-2  **セョクォスミ、キ2-1
838    &lt;http://suika.fam.cx/&gt;
839  [[結城浩]]  **セョクォスミ、キ2-2
840    
841  段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1段落1  [[キセケタ]]
842  段落1段落1段落1段落'''イタリック'''1段落1段落1段落1段落1段落1段落1段落1  
843  段落1段落1段落1段落'''''イタボールド'''''1段落1段落1段落1段落1段落1段落1段落1段落1  テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1
844  >段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2  テハヘ1テハヘ1テハヘ1テハヘ'''カットエ'''1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1
845  >段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2  テハヘ1テハヘ1テハヘ1テハヘ'''''カッ、、カットエ'''''1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1テハヘ1
846  >段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2段落2  >テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2
847    >テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2
848  レベル0レベル0レベル0レベル0レベル0レベル0  >テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2テハヘ2
849    
850  >レベル1  ・・ル・0・・ル・0・・ル・0・・ル・0・・ル・0・・ル・0
851  >レベル1  
852  >レベル1  >・・ル・1
853  >>レベル2  >・・ル・1
854  >>レベル2  >・・ル・1
855  >>レベル2  >>・・ル・2
856  >>>レベル3  >>・・ル・2
857  -はろ1  >>・・ル・2
858  --はろ2  >>>・・ル・3
859  ろろろろ2  -、マ、1
860  ---はろ3  --、マ、2
861  --はろ2  、、、、2
862  ---はろ3  ---、マ、3
863  --はろ2  --、マ、2
864  ---はろ3  ---、マ、3
865  >>>レベル3  --、マ、2
866  >>>レベル3  ---、マ、3
867  >>>レベル3  >>>・・ル・3
868  EOD  >>>・・ル・3
869      print $txt;  >>>・・ル・3
870      exit;  EOD
871  }      print $txt;
872        exit;
873  sub diff_check {  }
874      traverse_sequences(  
875              $msgrefA, $msgrefB,  sub diff_check {
876              {      traverse_sequences(
877                  MATCH => \&df_match,              $msgrefA, $msgrefB,
878                  DISCARD_A => \&df_delete,              {
879                  DISCARD_B => \&df_add,                  MATCH => \&df_match,
880              }                  DISCARD_A => \&df_delete,
881      );                  DISCARD_B => \&df_add,
882      &diff_flush;              }
883  }      );
884        &diff_flush;
885  sub diff_flush {  }
886      $diff_text .= join('', map { "-$_\n" } splice(@diff_deleted));  
887      $diff_text .= join('', map { "+$_\n" } splice(@diff_added));  sub diff_flush {
888  }      $diff_text .= join('', map { "-$_\n" } splice(@diff_deleted));
889        $diff_text .= join('', map { "+$_\n" } splice(@diff_added));
890  sub df_match {  }
891      my ($a, $b) = @_;  
892      &diff_flush;  sub df_match {
893      $diff_text .= "=$msgrefA->[$a]\n";      my ($a, $b) = @_;
894  }      &diff_flush;
895        $diff_text .= "=$msgrefA->[$a]\n";
896  sub df_delete {  }
897      my ($a, $b) = @_;  
898      push(@diff_deleted, $msgrefA->[$a]);  sub df_delete {
899  }      my ($a, $b) = @_;
900        push(@diff_deleted, $msgrefA->[$a]);
901  sub df_add {  }
902      my ($a, $b) = @_;  
903      push(@diff_added, $msgrefB->[$b]);  sub df_add {
904  }      my ($a, $b) = @_;
905        push(@diff_added, $msgrefB->[$b]);
906  sub calc_message_digest {   # You have to use MD5...  }
907      my $text = shift;  
908      my @text = split(//, $text);  sub calc_message_digest {   # You have to use MD5...
909      my $len = length($text);      my $text = shift;
910      my $checksum = 0;      my @text = split(//, $text);
911      foreach (@text) {      my $len = length($text);
912          $checksum += ord($_);      my $checksum = 0;
913          $checksum = ($checksum * 2) % 65536 + (($checksum & 32768) ? 1 : 0); # 16bit rotate      foreach (@text) {
914      }          $checksum += ord($_);
915      return "$len:$checksum";          $checksum = ($checksum * 2) % 65536 + (($checksum & 32768) ? 1 : 0); # 16bit rotate
916  }      }
917        return "$len:$checksum";
918  # Definition of YukiWikiDB  }
919  package YukiWikiDB;  
920    # Definition of YukiWikiDB
921  my $debug = 1;  package YukiWikiDB;
922    
923  # Constructor  my $debug = 1;
924  sub new {  
925      return shift->TIEHASH(@_);  # Constructor
926  }  sub new {
927        return shift->TIEHASH(@_);
928  # tying  }
929  sub TIEHASH {  
930      my ($class, $dbname) = @_;  # tying
931      my $self = {  sub TIEHASH {
932          dir => $dbname,      my ($class, $dbname) = @_;
933          keys => [],      my $self = {
934      };          dir => $dbname,
935      if (not -d $self->{dir}) {          keys => [],
936          if (!mkdir($self->{dir}, 0777)) {      };
937              print "mkdir(" . $self->{dir} . ") fail\n" if ($debug);      if (not -d $self->{dir}) {
938              return undef;          if (!mkdir($self->{dir}, 0777)) {
939          }              print "mkdir(" . $self->{dir} . ") fail\n" if ($debug);
940      }              return undef;
941      return bless($self, $class);          }
942  }      }
943        return bless($self, $class);
944  # Store  }
945  sub STORE {  
946      my ($self, $key, $val) = @_;  # Store
947      my $file = &make_filename($self, $key);  sub STORE {
948      if (open(FILE,"> $file")) {      my ($self, $key, $val) = @_;
949          binmode(FILE);      my $file = &make_filename($self, $key);
950          print FILE $val;      if (open(FILE,"> $file")) {
951          close(FILE);          binmode(FILE);
952          return $self->{$key} = $val;          print FILE $val;
953      } else {          close(FILE);
954          print "$file create error.";          return $self->{$key} = $val;
955      }      } else {
956  }          print "$file create error.";
957        }
958  # Fetch  }
959  sub FETCH {  
960      my ($self, $key) = @_;  # Fetch
961      my $file = &make_filename($self, $key);  sub FETCH {
962      if (open(FILE, $file)) {      my ($self, $key) = @_;
963          local $/;      my $file = &make_filename($self, $key);
964          $self->{$key} = <FILE>;      if (open(FILE, $file)) {
965          close(FILE);          local $/;
966      }          $self->{$key} = <FILE>;
967      return $self->{$key};          close(FILE);
968  }      }
969        return $self->{$key};
970  # Exists  }
971  sub EXISTS {  
972      my ($self, $key) = @_;  # Exists
973      my $file = &make_filename($self, $key);  sub EXISTS {
974      return -e($file);      my ($self, $key) = @_;
975  }      my $file = &make_filename($self, $key);
976        return -e($file);
977  # Delete  }
978  sub DELETE {  
979      my ($self, $key) = @_;  # Delete
980      my $file = &make_filename($self, $key);  sub DELETE {
981      unlink $file;      my ($self, $key) = @_;
982      return delete $self->{$key};      my $file = &make_filename($self, $key);
983  }      unlink $file;
984        return delete $self->{$key};
985  sub FIRSTKEY {  }
986      my ($self) = @_;  
987      opendir(DIR, $self->{dir}) or die $self->{dir};  sub FIRSTKEY {
988      @{$self->{keys}} = grep /\.txt$/, readdir(DIR);      my ($self) = @_;
989      foreach my $name (@{$self->{keys}}) {      opendir(DIR, $self->{dir}) or die $self->{dir};
990          $name =~ s/\.txt$//;      @{$self->{keys}} = grep /\.txt$/, readdir(DIR);
991          $name =~ s/[0-9A-F][0-9A-F]/pack("C", hex($&))/eg;      foreach my $name (@{$self->{keys}}) {
992      }          $name =~ s/\.txt$//;
993      return shift @{$self->{keys}};          $name =~ s/[0-9A-F][0-9A-F]/pack("C", hex($&))/eg;
994  }      }
995        return shift @{$self->{keys}};
996  sub NEXTKEY {  }
997      my ($self) = @_;  
998      return shift @{$self->{keys}};  sub NEXTKEY {
999  }      my ($self) = @_;
1000        return shift @{$self->{keys}};
1001  sub make_filename {  }
1002      my ($self, $key) = @_;  
1003      my $enkey = '';  sub make_filename {
1004      foreach my $ch (split(//, $key)) {      my ($self, $key) = @_;
1005          $enkey .= sprintf("%02X", ord($ch));      my $enkey = '';
1006      }      foreach my $ch (split(//, $key)) {
1007      return $self->{dir} . "/$enkey.txt";          $enkey .= sprintf("%02X", ord($ch));
1008  }      }
1009  __END__      return $self->{dir} . "/$enkey.txt";
1010    }
1011  =head1 NAME  __END__
1012    
1013  YukiWiki - 自由にページを追加・削除・編集できるWebページ構築CGI  =head1 NAME
1014    
1015      Copyright (C) 2000,2001 by Hiroshi Yuki.  YukiWiki - シォヘウ、ヒ・レ。シ・ク、トノイテ。ヲコス。ヲハヤスク、ヌ、ュ、Web・レ。シ・クケステロCGI
1016      結城浩 <hyuki@hyuki.com>  
1017      http://www.hyuki.com/      Copyright (C) 2000,2001 by Hiroshi Yuki.
1018      http://www.hyuki.com/yukiwiki/      キセケタ <hyuki@hyuki.com>
1019        http://www.hyuki.com/
1020  =head1 SYNOPSIS      http://www.hyuki.com/yukiwiki/
1021    
1022      http://www.hyuki.com/yukiwiki/yukiwiki.cgi  =head1 SYNOPSIS
1023    
1024  =head1 DESCRIPTION      http://www.hyuki.com/yukiwiki/yukiwiki.cgi
1025    
1026  YukiWiki(結城ウィキィ)は参加者が自由にページを追加・削除・編集できる  =head1 DESCRIPTION
1027  不思議なWebページ群を作るCGIです。  
1028  Webで動作する掲示板とちょっと似ていますが、  YukiWiki。ハキセ・ヲ・」・ュ・」。ヒ、マサイイテシヤ、ャシォヘウ、ヒ・レ。シ・ク、トノイテ。ヲコス。ヲハヤスク、ヌ、ュ、
1029  Web掲示板が単にメッセージを追加するだけなのに対して、  ノヤサラオト、ハWeb・レ。シ・クキイ、コ、CGI、ヌ、ケ。」
1030  YukiWikiは、Webページ全体を自由に変更することができます。  Web、ヌニーコ、ケ、キヌシィネト、ネ、チ、遉テ、ネサ、ニ、、、゙、ケ、ャ。「
1031    Webキヌシィネト、ャテア、ヒ・皈テ・サ。シ・ク、トノイテ、ケ、、タ、ア、ハ、ホ、ヒツミ、キ、ニ。「
1032  YukiWikiは、Cunningham & CunninghamのWikiWikiWebの  YukiWiki、マ。「Web・レ。シ・クチエツホ、シォヘウ、ヒハムケケ、ケ、、ウ、ネ、ャ、ヌ、ュ、゙、ケ。」
1033  仕様を参考にして独自に作られました。  
1034    YukiWiki、マ。「Cunningham & Cunningham、ホWikiWikiWeb、ホ
1035  YukiWikiはPerlで書かれたCGIスクリプトとして実現されていますので、  サナヘヘ、サイケヘ、ヒ、キ、ニニネシォ、ヒコ、鬢、゙、キ、ソ。」
1036  Perlが動作するWebサーバならば比較的容易に設置できます。  
1037    YukiWiki、マPerl、ヌス、ォ、、ソCGI・ケ・ッ・・ラ・ネ、ネ、キ、ニシツクス、オ、、ニ、、、゙、ケ、ホ、ヌ。「
1038  あとはdbmopenが使える環境ならば設置できます(Version 1.5.0以降ならdbmopenが使えなくても設置できます)。  Perl、ャニーコ、ケ、Web・オ。シ・ミ、ハ、鬢ミネ豕モナェヘニーラ、ヒタ゚テヨ、ヌ、ュ、゙、ケ。」
1039    
1040    、「、ネ、マdbmopen、ャサネ、ィ、エトカュ、ハ、鬢ミタ゚テヨ、ヌ、ュ、゙、ケ(Version 1.5.0ーハケ゚、ハ、馘bmopen、ャサネ、ィ、ハ、ッ、ニ、簑゚テヨ、ヌ、ュ、゙、ケ)。」
1041  YukiWikiはフリーソフトです。  
1042  ご自由にお使いください。  
1043    YukiWiki、マ・ユ・遙シ・ス・ユ・ネ、ヌ、ケ。」
1044  =head1 設置方法  、エシォヘウ、ヒ、ェサネ、、、ッ、タ、オ、、。」
1045    
1046  =head2 入手  =head1 タ゚テヨハヒ。
1047    
1048  YukiWikiの最新版は、  =head2 ニシ
1049  http://www.hyuki.com/yukiwiki/  
1050  から入手できます。  YukiWiki、ホコヌソキネヌ、マ。「
1051    http://www.hyuki.com/yukiwiki/
1052  =head2 ファイル一覧  、ォ、鯣シ熙ヌ、ュ、゙、ケ。」
1053    
1054      readme.txt      ドキュメント  =head2 ・ユ・。・、・ーヘ
1055      yukiwiki.cgi    YukiWiki本体  
1056      yukiwiki.gif    ロゴ(カラー版)      readme.txt      ・ノ・ュ・螂皈・ネ
1057      yukimono.gif    ロゴ(モノクロ版)      yukiwiki.cgi    YukiWikiヒワツホ
1058      jcode.pl        漢字コードライブラリ      yukiwiki.gif    ・・エ。ハ・ォ・鬘シネヌ。ヒ
1059        yukimono.gif    ・・エ。ハ・筵ホ・ッ・ネヌ。ヒ
1060  =head2 インストール      jcode.pl        エチサ・ウ。シ・ノ・鬣、・ヨ・鬣
1061    
1062  =over 4  =head2 ・、・・ケ・ネ。シ・
1063    
1064  =item 1.  =over 4
1065    
1066  アーカイブを解く。  =item 1.
1067    
1068  =item 2.  ・「。シ・ォ・、・ヨ、イ、ッ。」
1069    
1070  yukiwiki.cgiのはじめの方にある設定を確認します。  =item 2.
1071  通常は何もしなくてよいが、  
1072  はじめは$touchfileを''にした方がよいでしょう。  yukiwiki.cgi、ホ、マ、ク、皃ホハ、ヒ、「、タ゚ト熙ウホヌァ、キ、゙、ケ。」
1073    トフセ、マイソ、筅キ、ハ、ッ、ニ、隍、、ャ。「
1074  =item 3.  、マ、ク、皃マ$touchfile、''、ヒ、キ、ソハ、ャ、隍、、ヌ、キ、遉ヲ。」
1075    
1076  yukiwiki.cgiとjcode.plを同じところに設置します。  =item 3.
1077    
1078  =item 4.  yukiwiki.cgi、ネjcode.pl、ニア、ク、ネ、ウ、、ヒタ゚テヨ、キ、゙、ケ。」
1079    
1080  サイズ0のyukiwiki.dbというファイルを設置します。  =item 4.
1081  (Perlシステムによってはyukiwiki.pag, yukiwiki.dir)  
1082    ・オ・、・コ0、ホyukiwiki.db、ネ、、、ヲ・ユ・。・、・、タ゚テヨ、キ、゙、ケ。」
1083  =item 5.  。ハPerl・キ・ケ・ニ・爨ヒ、隍テ、ニ、マyukiwiki.pag, yukiwiki.dir。ヒ
1084    
1085  yukiwiki.cgiにブラウザからアクセスします。  =item 5.
1086    
1087  =back  yukiwiki.cgi、ヒ・ヨ・鬣ヲ・カ、ォ、鬣「・ッ・サ・ケ、キ、゙、ケ。」
1088    
1089  =head2 パーミッション  =back
1090    
1091          ファイル        パーミッション      転送モード  =head2 ・ム。シ・゚・テ・キ・逾
1092          yukiwiki.cgi    755                 ASCII  
1093          yukiwiki.gif    644                 BINARY          ・ユ・。・、・        ・ム。シ・゚・テ・キ・逾      ナセチ・筍シ・ノ
1094          yukimono.gif    644                 BINARY          yukiwiki.cgi    755                 ASCII
1095          jcode.pl        644                 ASCII          yukiwiki.gif    644                 BINARY
1096            yukimono.gif    644                 BINARY
1097      $dbmopen = 1; にした場合:          jcode.pl        644                 ASCII
1098          yukiwiki.db     666                 BINARY  
1099          (yukiwiki.pag, yukiwiki.dirの場合もあり)      $dbmopen = 1; 、ヒ、キ、ソセケ:
1100            yukiwiki.db     666                 BINARY
1101      $dbmopen = 0; にした場合: (カレントディレクトリを777にしておく)          (yukiwiki.pag, yukiwiki.dir、ホセケ遉筅「、遙ヒ
1102          .               777                 (転送しない)  
1103        $dbmopen = 0; 、ヒ、キ、ソセケ: (・ォ・・・ネ・ヌ・」・・ッ・ネ・熙777、ヒ、キ、ニ、ェ、ッ)
1104  =head1 データのバックアップ方法          .               777                 (ナセチ、キ、ハ、、)
1105    
1106  $dbmopen = 1;の場合は、  =head1 ・ヌ。シ・ソ、ホ・ミ・テ・ッ・「・テ・ラハヒ。
1107  データはすべてyukiwiki.db(.dir, .pag)に入る。  
1108  これをバックアップすればよい。  $dbmopen = 1;、ホセケ遉マ。「
1109    ・ヌ。シ・ソ、マ、ケ、ル、ニyukiwiki.db(.dir, .pag)、ヒニ、。」
1110  $dbmopen = 0;の場合は、  、ウ、、・ミ・テ・ッ・「・テ・ラ、ケ、、ミ、隍、。」
1111  yukiwikiというディレクトリができるので、  
1112  これ以下をバックアップすればよい。  $dbmopen = 0;、ホセケ遉マ。「
1113    yukiwiki、ネ、、、ヲ・ヌ・」・・ッ・ネ・熙ャ、ヌ、ュ、、ホ、ヌ。「
1114  =head1 新しいページの作り方  、ウ、ーハイシ、・ミ・テ・ッ・「・テ・ラ、ケ、、ミ、隍、。」
1115    
1116  =over 4  =head1 ソキ、キ、、・レ。シ・ク、ホコ、ハ
1117    
1118  =item 1.  =over 4
1119    
1120  まず、適当なページ(例えばFrontPage)を選び、  =item 1.
1121  ページの下にある「編集」リンクをたどります。  
1122    、゙、コ。「ナャナ、ハ・レ。シ・ク。ハホ网ィ、ミFrontPage。ヒ、チェ、モ。「
1123  =item 2.  ・レ。シ・ク、ホイシ、ヒ、「、。ヨハヤスク。ラ・・・ッ、、ソ、ノ、熙゙、ケ。」
1124    
1125  するとテキスト入力ができる状態になるので、  =item 2.
1126  そこにNewPageのような単語  
1127  (大文字小文字混在している英文字列)  、ケ、、ネ・ニ・ュ・ケ・ネニホマ、ャ、ヌ、ュ、セツヨ、ヒ、ハ、、ホ、ヌ。「
1128  を書いて「保存」します。  、ス、ウ、ヒNewPage、ホ、隍ヲ、ハテアク
1129    。ハツ醋クサセョハクサコョコ゚、キ、ニ、、、アムハクサホ。ヒ
1130  =item 3.  、ス、、、ニ。ヨハンツク。ラ、キ、゙、ケ。」
1131    
1132  保存すると、FrontPageのページが書き換わり、  =item 3.
1133  あなたが書いたNewPageという文字列の後ろに ? というリンクが表示されます。  
1134  この ? はそのページがまだ存在しないことを示す印です。  ハンツク、ケ、、ネ。「FrontPage、ホ・レ。シ・ク、ャス、ュエケ、、遙「
1135    、「、ハ、ソ、ャス、、、ソNewPage、ネ、、、ヲハクサホ、ホク螟、ヒ ? 、ネ、、、ヲ・・・ッ、ャノスシィ、オ、、゙、ケ。」
1136  =item 4.  、ウ、ホ ? 、マ、ス、ホ・レ。シ・ク、ャ、゙、タツクコ゚、キ、ハ、、、ウ、ネ、シィ、ケー、ヌ、ケ。」
1137    
1138  その ? をクリックすると新しいページNewPageができますので、  =item 4.
1139  あなたの好きな文章をその新しいページに書いて保存します。  
1140    、ス、ホ ? 、・ッ・・テ・ッ、ケ、、ネソキ、キ、、・レ。シ・クNewPage、ャ、ヌ、ュ、゙、ケ、ホ、ヌ。「
1141  =item 5.  、「、ハ、ソ、ホケ・、ュ、ハハクセマ、、ス、ホソキ、キ、、・レ。シ・ク、ヒス、、、ニハンツク、キ、゙、ケ。」
1142    
1143  NewPageページができるとFrontPageの ? は消えて、リンクとなります。  =item 5.
1144    
1145  =back  NewPage・レ。シ・ク、ャ、ヌ、ュ、、ネFrontPage、ホ ? 、マセテ、ィ、ニ。「・・・ッ、ネ、ハ、熙゙、ケ。」
1146    
1147  =head1 テキスト整形のルール  =back
1148    
1149  =over 4  =head1 ・ニ・ュ・ケ・ネターキチ、ホ・。シ・
1150    
1151  =item *  =over 4
1152    
1153  連続した複数行はフィルされて表示されます。  =item *
1154    
1155  =item *  マ「ツウ、キ、ソハ」ソケヤ、マ・ユ・」・、オ、、ニノスシィ、オ、、゙、ケ。」
1156    
1157  空行は段落C<< <p> >>の区切りとなります。  =item *
1158    
1159  =item *  カケヤ、マテハヘC<< <p> >>、ホカ霏レ、熙ネ、ハ、熙゙、ケ。」
1160    
1161  HTMLのタグは書けません。  =item *
1162    
1163  =item *  HTML、ホ・ソ・ー、マス、ア、゙、サ、。」
1164    
1165  B<''ボールド''>のようにシングルクォート二つではさむと、  =item *
1166  ボールドC<< <b> >>になります。  
1167    B<''・ワ。シ・・ノ''>、ホ、隍ヲ、ヒ・キ・・ー・・ッ・ゥ。シ・ネニ、ト、ヌ、マ、オ、爨ネ。「
1168  =item *  ・ワ。シ・・ノC<< <b> >>、ヒ、ハ、熙゙、ケ。」
1169    
1170  B<'''イタリック'''>のようにシングルクォート三つではさむと、  =item *
1171  イタリックC<< <i> >>になります。  
1172    B<'''・、・ソ・・テ・ッ'''>、ホ、隍ヲ、ヒ・キ・・ー・・ッ・ゥ。シ・ネサー、ト、ヌ、マ、オ、爨ネ。「
1173  =item *  ・、・ソ・・テ・ッC<< <i> >>、ヒ、ハ、熙゙、ケ。」
1174    
1175  B<---->のようにマイナス4つがあると、  =item *
1176  水平線C<< <hr> >>になります。  
1177    B<---->、ホ、隍ヲ、ヒ・゙・、・ハ・ケ4、ト、ャ、「、、ネ。「
1178  =item *  ソ衞ソタC<< <hr> >>、ヒ、ハ、熙゙、ケ。」
1179    
1180  行をB<*>ではじめると、  =item *
1181  大見出しC<< <h2> >>になります。  
1182    ケヤ、B<*>、ヌ、マ、ク、皃、ネ。「
1183  =item *  ツ邵ォスミ、キC<< <h2> >>、ヒ、ハ、熙゙、ケ。」
1184    
1185  行をB<**>ではじめると、  =item *
1186  小見出しC<< <h3> >>になります。  
1187    ケヤ、B<**>、ヌ、マ、ク、皃、ネ。「
1188  =item *  セョクォスミ、キC<< <h3> >>、ヒ、ハ、熙゙、ケ。」
1189    
1190  行をマイナス-ではじめると、  =item *
1191  箇条書きC<< <ul> >>になります。  
1192  マイナスの数が増えるとレベルが下がります(3レベルまで)  ケヤ、・゙・、・ハ・ケ-、ヌ、マ、ク、皃、ネ。「
1193    イユセス、ュC<< <ul> >>、ヒ、ハ、熙゙、ケ。」
1194      -項目1  ・゙・、・ハ・ケ、ホソ、ャチ、ィ、、ネ・・ル・、ャイシ、ャ、熙゙、ケ。ハ3・・ル・、゙、ヌ。ヒ
1195      --項目1-1  
1196      --項目1-2      -ケ猯ワ1
1197      -項目2      --ケ猯ワ1-1
1198      -項目3      --ケ猯ワ1-2
1199      --項目3-1      -ケ猯ワ2
1200      ---項目3-1-1      -ケ猯ワ3
1201      ---項目3-1-2      --ケ猯ワ3-1
1202      --項目3-2      ---ケ猯ワ3-1-1
1203        ---ケ猯ワ3-1-2
1204  =item *      --ケ猯ワ3-2
1205    
1206  コロンを使うと、  =item *
1207  用語と解説文のリストC<< <dl> >>が書けます。  
1208    ・ウ・・、サネ、ヲ、ネ。「
1209      :用語1:いろいろ書いた解説文1  ヘムク、ネイタ簗ク、ホ・・ケ・ネC<< <dl> >>、ャス、ア、゙、ケ。」
1210      :用語2:いろいろ書いた解説文2  
1211      :用語3:いろいろ書いた解説文3      :ヘムク1:、、、、、、ス、、、ソイタ簗ク1
1212        :ヘムク2:、、、、、、ス、、、ソイタ簗ク2
1213  =item *      :ヘムク3:、、、、、、ス、、、ソイタ簗ク3
1214    
1215  リンク  =item *
1216    
1217  =over 4  ・・・ッ
1218    
1219  =item *  =over 4
1220    
1221  LinkToSomePageやFrontPageのように、  =item *
1222  英単語の最初の一文字を大文字にしたものが  
1223  二つ以上連続したものはYukiWikiのページ名となり、  LinkToSomePage、腱rontPage、ホ、隍ヲ、ヒ。「
1224  それが文章中に含まれるとリンクになります。  アムテアク、ホコヌス鬢ホーハクサ、ツ醋クサ、ヒ、キ、ソ、筅ホ、ャ
1225    ニ、トーハセ袞「ツウ、キ、ソ、筅ホ、マYukiWiki、ホ・レ。シ・クフセ、ネ、ハ、遙「
1226  =item *  、ス、、ャハクセマテ讀ヒエ゙、゙、、、ネ・・・ッ、ヒ、ハ、熙゙、ケ。」
1227    
1228  http://www.hyuki.com/ のようなURLは自動的にリンクになります。  =item *
1229    
1230  =item *  http://www.hyuki.com/ 、ホ、隍ヲ、ハURL、マシォニーナェ、ヒ・・・ッ、ヒ、ハ、熙゙、ケ。」
1231    
1232  二重の大かっこ[[ ]]でくくった文字列も、  =item *
1233  YukiWikiのページ名になります。  
1234  大かっこの中にはスペースを含めてはいけません。  ニスナ、ホツ遉ォ、テ、ウ[[ ]]、ヌ、ッ、ッ、テ、ソハクサホ、筍「
1235  日本語も使えます。  YukiWiki、ホ・レ。シ・クフセ、ヒ、ハ、熙゙、ケ。」
1236    ツ遉ォ、テ、ウ、ホテ讀ヒ、マ・ケ・レ。シ・ケ、エ゙、皃ニ、マ、、、ア、゙、サ、。」
1237  =back  ニヒワク、篏ネ、ィ、゙、ケ。」
1238    
1239  =item *  =back
1240    
1241  行頭がスペースやタブで始まっていると、  =item *
1242  それは整形済みの段落C<< <pre> >>として扱われます。  
1243  プログラムの表示などに使うと便利です。  ケヤニャ、ャ・ケ・レ。シ・ケ、茹ソ・ヨ、ヌサマ、゙、テ、ニ、、、、ネ。「
1244    、ス、、マターキチコム、゚、ホテハヘC<< <pre> >>、ネ、キ、ニーキ、、、゙、ケ。」
1245    ・ラ・・ー・鬣爨ホノスシィ、ハ、ノ、ヒサネ、ヲ、ネハリヘ、ヌ、ケ。」
1246  =item *  
1247    
1248  行を > ではじめると、  =item *
1249  引用文C<< <blockquote> >>が書けます。  
1250  >の数が多いとインデントが深くなります(3レベルまで)。  ケヤ、 > 、ヌ、マ、ク、皃、ネ。「
1251    ーヘムハクC<< <blockquote> >>、ャス、ア、゙、ケ。」
1252      >文章  >、ホソ、ャツソ、、、ネ・、・・ヌ・・ネ、ャソシ、ッ、ハ、熙゙、ケ。ハ3・・ル・、゙、ヌ。ヒ。」
1253      >文章  
1254      >>さらなる引用      >ハクセマ
1255      >文章      >ハクセマ
1256        >>、オ、鬢ハ、ーヘム
1257  =back      >ハクセマ
1258    
1259  =head1 更新履歴  =back
1260    
1261  =over 4  =head1 ケケソキヘホ
1262    
1263  =item *  =over 4
1264    
1265  2001年10月20日、Version 1.6.6。  =item *
1266    
1267  更新の衝突対策。  2001ヌッ10キ20ニ。「Version 1.6.6。」
1268  元ページの簡単なチェックサムを取っておき、  
1269  更新前にチェックサムを比較する。  ケケソキ、ホセラニヘツミコ。」
1270  修正個所はdigestという文字列を検索すれば分かる。  クオ・レ。シ・ク、ホエハテア、ハ・チ・ァ・テ・ッ・オ・爨シ隍テ、ニ、ェ、ュ。「
1271  本来はMD5などでちゃんとやった方がいいのだけれど。  ケケソキチー、ヒ・チ・ァ・テ・ッ・オ・爨ネ豕モ、ケ、。」
1272    ス、タオクトス熙マdigest、ネ、、、ヲハクサホ、ク。コ、ケ、、ミハャ、ォ、。」
1273  衝突時に表示されるメッセージなどは「極悪」さんのページを参考にした。  ヒワヘ隍マMD5、ハ、ノ、ヌ、チ、网、ネ、荀テ、ソハ、ャ、、、、、ホ、タ、ア、、ノ。」
1274    
1275  =item *  セラニヘサ、ヒノスシィ、オ、、・皈テ・サ。シ・ク、ハ、ノ、マ。ヨカヒーュ。ラ、オ、、ホ・レ。シ・ク、サイケヘ、ヒ、キ、ソ。」
1276    
1277  2001年10月17日、Version 1.6.5。  =item *
1278    
1279  プレビュー画面で、更新ボタンを押したときに送信される  2001ヌッ10キ17ニ。「Version 1.6.5。」
1280  メッセージの内容をinput要素のtype="hidden"を使って埋め込むのをやめる。  
1281  代わりに、textarea要素を使う。  ・ラ・・モ・蝪シイ靂フ、ヌ。「ケケソキ・ワ・ソ・、イ。、キ、ソ、ネ、ュ、ヒチソョ、オ、、
1282  再プレビュー用にmyspecial_を導入。でもきれいな対策ではない。  ・皈テ・サ。シ・ク、ホニ簣ニ、inputヘラチヌ、ホtype="hidden"、サネ、テ、ニヒ荀盪、爨ホ、、荀皃。」
1283    ツ螟、熙ヒ。「textareaヘラチヌ、サネ、ヲ。」
1284  =item *  コニ・ラ・・モ・蝪シヘム、ヒmyspecial_、ニウニ。」、ヌ、筅ュ、、、、ハツミコ、ヌ、マ、ハ、、。」
1285    
1286  2001年8月30日、Version 1.6.4。  =item *
1287    
1288  URLでダイレクトにページ名を指定しても、  2001ヌッ8キ30ニ。「Version 1.6.4。」
1289  $WikiNameと$BracketName以外のページを作れないようにした。  
1290  (is_valid_nameとis_editable参照)。  URL、ヌ・タ・、・・ッ・ネ、ヒ・レ。シ・クフセ、サリト熙キ、ニ、筍「
1291    $WikiName、ネ$BracketNameーハウー、ホ・レ。シ・ク、コ、、ハ、、、隍ヲ、ヒ、キ、ソ。」
1292  =item *  (is_valid_name、ネis_editableサイセネ)。」
1293    
1294  2001年8月30日、Version 1.6.3。  =item *
1295    
1296  RecentChangesを編集・再編集不可とした。  2001ヌッ8キ30ニ。「Version 1.6.3。」
1297  編集不可ページは@uneditableにページ名を入れる。  
1298    RecentChanges、ハヤスク。ヲコニハヤスクノヤイト、ネ、キ、ソ。」
1299  =item *  ハヤスクノヤイト・レ。シ・ク、マ@uneditable、ヒ・レ。シ・クフセ、ニ、、。」
1300    
1301  2001年2月25日、Version 1.6.1, 1.6.2。  =item *
1302    
1303  差分機能のバグ修正。  2001ヌッ2キ25ニ。「Version 1.6.1, 1.6.2。」
1304  do_previewで'>'が扱えないバグを修正  
1305  (ユーザからの指摘)。  コケハャオ。ヌス、ホ・ミ・ース、タオ。」
1306    do_preview、ヌ'>'、ャーキ、ィ、ハ、、・ミ・ー、ス、タオ
1307  =item *  。ハ・譯シ・カ、ォ、鬢ホサリナヲ。ヒ。」
1308    
1309  2001年2月22日、Version 1.6.0。  =item *
1310  差分機能を実装した。  
1311    2001ヌッ2キ22ニ。「Version 1.6.0。」
1312  =item *  コケハャオ。ヌス、シツチ、キ、ソ。」
1313    
1314  2001年2月19日、Version 1.5.4。  =item *
1315  画像ファイルへのリンクは画像にしてみた。  
1316    2001ヌッ2キ19ニ。「Version 1.5.4。」
1317  =item *  イ霖・ユ・。・、・、リ、ホ・・・ッ、マイ霖、ヒ、キ、ニ、゚、ソ。」
1318    
1319  2001年2月19日、Version 1.5.3。  =item *
1320  RecentChangesの中に削除したページがあるのをやめた。  
1321  use strict;で引っかかる部分を少し整理(完全ではない)。  2001ヌッ2キ19ニ。「Version 1.5.3。」
1322    RecentChanges、ホテ讀ヒコス、キ、ソ・レ。シ・ク、ャ、「、、ホ、、荀皃ソ。」
1323  =item *  use strict;、ヌー、テ、ォ、ォ、ノハャ、セッ、キターヘ(エーチエ、ヌ、マ、ハ、、)。」
1324    
1325  2001年2月16日、Version 1.5.2。  =item *
1326  textareaに表示およびプレビューする前に < や > を &lt; や &gt; に変換した  
1327  (do_preview, editpage, print_preview_buttons)。  2001ヌッ2キ16ニ。「Version 1.5.2。」
1328    textarea、ヒノスシィ、ェ、隍モ・ラ・・モ・蝪シ、ケ、チー、ヒ < 、 > 、 &lt; 、 &gt; 、ヒハムエケ、キ、ソ
1329  =item *  (do_preview, editpage, print_preview_buttons)。」
1330    
1331  2000年12月27日、Version 1.5.1。  =item *
1332  プレビュー画面を整理した。  
1333    2000ヌッ12キ27ニ。「Version 1.5.1。」
1334  =item *  ・ラ・・モ・蝪シイ靂フ、ターヘ、キ、ソ。」
1335    
1336  2000年12月22日、Version 1.5.0。  =item *
1337  全体的にずいぶん書き直した。  
1338  一覧を別途作成するようにした(do_list)。  2000ヌッ12キ22ニ。「Version 1.5.0。」
1339  書き込む前に確認画面を出すようにした(do_preview)。  チエツホナェ、ヒ、コ、、、ヨ、ス、ュトセ、キ、ソ。」
1340  テキストの書き方を編集画面に入れた(do_edit, do_reedit)。  ーヘ、ハフナモコタョ、ケ、、隍ヲ、ヒ、キ、ソ(do_list)。」
1341  WhatsNew→RecentChanges、TopPage→FrontPageに変更した。  ス、ュケ、狠ー、ヒウホヌァイ靂フ、スミ、ケ、隍ヲ、ヒ、キ、ソ(do_preview)。」
1342    ・ニ・ュ・ケ・ネ、ホス、ュハ、ハヤスクイ靂フ、ヒニ、、ソ(do_edit, do_reedit)。」
1343  =item *  WhatsNew「ェRecentChanges。「TopPage「ェFrontPage、ヒハムケケ、キ、ソ。」
1344    
1345  2000年12月20日、Version 1.1.0。  =item *
1346  tieを利用して、dbmopenが使えない場合でも動作するように修正。  
1347  利用者の1人である「極悪」さんから  2000ヌッ12キ20ニ。「Version 1.1.0。」
1348  送っていただいたコードを元にしています。  tie、ヘヘム、キ、ニ。「dbmopen、ャサネ、ィ、ハ、、セケ遉ヌ、簇ーコ、ケ、、隍ヲ、ヒス、タオ。」
1349    ヘヘムシヤ、ホ1ソヘ、ヌ、「、。ヨカヒーュ。ラ、オ、、ォ、
1350  =item *  チ、テ、ニ、、、ソ、タ、、、ソ・ウ。シ・ノ、クオ、ヒ、キ、ニ、、、゙、ケ。」
1351    
1352  2000年9月5日、Version 1.0.2。  =item *
1353   <body color=...> → <body bgcolor=...>  
1354  利用者からの指摘による。感謝。  2000ヌッ9キ5ニ。「Version 1.0.2。」
1355     <body color=...> 「ェ <body bgcolor=...>
1356  =item *  ヘヘムシヤ、ォ、鬢ホサリナヲ、ヒ、隍。」エカシユ。」
1357    
1358  2000年8月6日、Version 1.0.1を公開。  =item *
1359  C MAGAZINE(ソフトバンクパブリッシング)  
1360  2000年10月号連載記事向け公開版。  2000ヌッ8キ6ニ。「Version 1.0.1、クウォ。」
1361  [[ ]] の最後が「望」のようにシフトJISで  C MAGAZINE。ハ・ス・ユ・ネ・ミ・・ッ・ム・ヨ・・テ・キ・・ー。ヒ
1362  0x5Dになる場合の回避を行なった。  2000ヌッ10キケ賺「コワオュサク、アクウォネヌ。」
1363    [[ ]] 、ホコヌク螟ャ。ヨヒセ。ラ、ホ、隍ヲ、ヒ・キ・ユ・ネJIS、ヌ
1364  =item *  0x5D、ヒ、ハ、セケ遉ホイネ、ケヤ、ハ、テ、ソ。」
1365    
1366  2000年8月5日、Version 1.0.0を公開。  =item *
1367    
1368  =item *  2000ヌッ8キ5ニ。「Version 1.0.0、クウォ。」
1369    
1370  2000年7月23日、Version 0.82を公開。  =item *
1371  編集時のリンクミス。  
1372  <textarea>の属性変更。  2000ヌッ7キ23ニ。「Version 0.82、クウォ。」
1373    ハヤスクサ、ホ・・・ッ・゚・ケ。」
1374  =item *  <textarea>、ホツータュハムケケ。」
1375    
1376  2000年7月22日、Version 0.81を公開。  =item *
1377  ロゴを組み込む。  
1378    2000ヌッ7キ22ニ。「Version 0.81、クウォ。」
1379  =item *  ・・エ、チネ、゚ケ、爍」
1380    
1381  2000年7月21日、Version 0.80を公開。  =item *
1382  PODをCGI中に書き込む。  
1383    2000ヌッ7キ21ニ。「Version 0.80、クウォ。」
1384  =item *  POD、CGIテ讀ヒス、ュケ、爍」
1385    
1386  2000年7月19日、Version 0.70を公開。  =item *
1387  '''イタリック'''や、--、---、>>、>>>などを実装。  
1388    2000ヌッ7キ19ニ。「Version 0.70、クウォ。」
1389  =item *  '''・、・ソ・・テ・ッ'''、茖「--。「---。「>>。「>>>、ハ、ノ、シツチ。」
1390    
1391  2000年7月18日、Version 0.60を公開。  =item *
1392  *太字*を''太字''に変更  
1393    2000ヌッ7キ18ニ。「Version 0.60、クウォ。」
1394  =item *  *ツタサ*、''ツタサ''、ヒハムケケ
1395    
1396  2000年7月17日、Version 0.50を公開。  =item *
1397    
1398  =item *  2000ヌッ7キ17ニ。「Version 0.50、クウォ。」
1399    
1400  2000年7月17日、さらにいろいろ追加する。  =item *
1401    
1402  =item *  2000ヌッ7キ17ニ。「、オ、鬢ヒ、、、、、、トノイテ、ケ、。」
1403    
1404  2000年7月16日、いろいろ追加。  =item *
1405    
1406  =item *  2000ヌッ7キ16ニ。「、、、、、、トノイテ。」
1407    
1408  2000年7月15日、公開。  =item *
1409    
1410  =back  2000ヌッ7キ15ニ。「クウォ。」
1411    
1412  =head1 TODO  =back
1413    
1414      - テキスト表示モード  =head1 TODO
1415      - Charsetを明示。  
1416      - textarea中の閉じタグ対応      - ・ニ・ュ・ケ・ネノスシィ・筍シ・ノ
1417      - メニューの英語表記付記      - Charset、フタシィ。」
1418      - プレビューのボタンで、mymsgをinputのvalueに入れているが、改行をそのままvalueにいれてはいけないのではないか。      - textareaテ讀ホハト、ク・ソ・ーツミア
1419      - 「再編集」の機能はブラウザの back で充分ではないか。プレビューはもっとシンプルに。      - ・皈ヒ・蝪シ、ホアムクノスオュノユオュ
1420      - ページタイトル(Wikiname)が検索にかかるようにする。      - ・ラ・・モ・蝪シ、ホ・ワ・ソ・、ヌ。「mymsg、input、ホvalue、ヒニ、、ニ、、、、ャ。「イケヤ、、ス、ホ、゙、゙value、ヒ、、、、ニ、マ、、、ア、ハ、、、ホ、ヌ、マ、ハ、、、ォ。」
1421      - InterWiki風の機能「URLを隠しつつ、リンクを張る」      - 。ヨコニハヤスク。ラ、ホオ。ヌス、マ・ヨ・鬣ヲ・カ、ホ back 、ヌスシハャ、ヌ、マ、ハ、、、ォ。」・ラ・・モ・蝪シ、マ、筅テ、ネ・キ・・ラ・、ヒ。」
1422        - ・レ。シ・ク・ソ・、・ネ・。ハWikiname。ヒ、ャク。コ、ヒ、ォ、ォ、、隍ヲ、ヒ、ケ、。」
1423  =head1 作者      - InterWikiノ、ホオ。ヌス。ヨURL、ア」、キ、ト、ト。「・・・ッ、ト・、。ラ
1424    
1425      Copyright (C) 2000 by Hiroshi Yuki.  =head1 コシヤ
1426      結城浩 <hyuki@hyuki.com>  
1427      http://www.hyuki.com/      Copyright (C) 2000 by Hiroshi Yuki.
1428      http://www.hyuki.com/yukiwiki/      キセケタ <hyuki@hyuki.com>
1429        http://www.hyuki.com/
1430  質問、意見、バグ報告は hyuki@hyuki.com にメールしてください。      http://www.hyuki.com/yukiwiki/
1431    
1432  =head1 配布条件  シチフ茖「ーユクォ。「・ミ・ーハケ、マ hyuki@hyuki.com 、ヒ・癸シ・、キ、ニ、ッ、タ、オ、、。」
1433    
1434  YukiWikiは、  =head1 ヌロノロセキ
1435  GNU General Public Licenseにて公開します。  
1436    YukiWiki、マ。「
1437  YukiWikiはフリーソフトです。  GNU General Public License、ヒ、ニクウォ、キ、゙、ケ。」
1438  ご自由にお使いください。  
1439  自分好みのYukiWikiが作れるようにシンプルにしてあります。  YukiWiki、マ・ユ・遙シ・ス・ユ・ネ、ヌ、ケ。」
1440    、エシォヘウ、ヒ、ェサネ、、、ッ、タ、オ、、。」
1441  =head1 謝辞  シォハャケ・、゚、ホYukiWiki、ャコ、、、隍ヲ、ヒ・キ・・ラ・、ヒ、キ、ニ、「、熙゙、ケ。」
1442    
1443  本家のWikiWikiを作ったCunningham & Cunningham, Inc.に  =head1 シユシュ
1444  感謝します。  
1445    ヒワイネ、ホWikiWiki、コ、テ、ソCunningham & Cunningham, Inc.、ヒ
1446  YukiWikiを楽しんで使ってくださる  エカシユ、キ、゙、ケ。」
1447  ネット上の方々に感謝します。  
1448    YukiWiki、ウレ、キ、、ヌサネ、テ、ニ、ッ、タ、オ、
1449  YukiWikiのロゴをデザインしてくださった橋本礼奈さん  ・ヘ・テ・ネセ螟ホハ。ケ、ヒエカシユ、キ、゙、ケ。」
1450  http://city.hokkai.or.jp/~reina/  
1451  に感謝します。  YukiWiki、ホ・・エ、・ヌ・カ・、・、キ、ニ、ッ、タ、オ、テ、ソカカヒワホ鯣爨オ、
1452    http://city.hokkai.or.jp/~reina/
1453  tieを使った版の元になるコードを送ってくださった  、ヒエカシユ、キ、゙、ケ。」
1454  「極悪」さんに感謝します。  
1455    tie、サネ、テ、ソネヌ、ホクオ、ヒ、ハ、・ウ。シ・ノ、チ、テ、ニ、ッ、タ、オ、テ、ソ
1456  =head1 参照リンク  。ヨカヒーュ。ラ、オ、、ヒエカシユ、キ、゙、ケ。」
1457    
1458  =over 4  =head1 サイセネ・・・ッ
1459    
1460  =item *  =over 4
1461    
1462  YukiWikiホームページ  =item *
1463  http://www.hyuki.com/yukiwiki/  
1464    YukiWiki・ロ。シ・爭レ。シ・ク
1465  =item *  http://www.hyuki.com/yukiwiki/
1466    
1467  本家のWikiWiki  =item *
1468  http://c2.com/cgi/wiki?WikiWikiWeb  
1469    ヒワイネ、ホWikiWiki
1470  =item *  http://c2.com/cgi/wiki?WikiWikiWeb
1471    
1472  本家のWikiWikiの作者(Cunningham & Cunningham, Inc.)  =item *
1473  http://c2.com/  
1474    ヒワイネ、ホWikiWiki、ホコシヤ(Cunningham & Cunningham, Inc.)
1475  =item *  http://c2.com/
1476    
1477  YukiWikiのロゴデザインをしてくださった橋本礼奈さんのページ  =item *
1478  http://city.hokkai.or.jp/~reina/  
1479    YukiWiki、ホ・・エ・ヌ・カ・、・、、キ、ニ、ッ、タ、オ、テ、ソカカヒワホ鯣爨オ、、ホ・レ。シ・ク
1480  =back  http://city.hokkai.or.jp/~reina/
1481    
1482  =cut  =back
1483    
1484    =cut

Legend:
Removed from v.1.1  
changed lines
  Added in v.1.7

admin@suikawiki.org
ViewVC Help
Powered by ViewVC 1.1.24