dot.cgi
1 #!/usr/bin/perl
2 # by Ward Cunningham
3 # Copyright (c) Eclipse Foundation
4 # Released under EPL v1.0
5
6 use strict;
7
8 print "Content-type: text/plain\n\n";
9 print "digraph eclipse { node [ style=filled ]\n";
10
11 for (<pages/*/current>) {
12 my $node = $1 if /\/(.*)\//;
13 open (F, "$_") or die($!);
14 circle ($node);
15 while (<F>) {
16 arc ($node, $1) if /^\d+:\s*(.*)/;
17 }
18 }
19
20 print "}";
21
22 sub arc {
23 my ($node, $text) = @_;
24 my $to = mangle($text);
25 print circle($node) . " -> " . circle($to) . ";\n";
26 }
27
28 my %have;
29 sub circle {
30 my ($name) = @_;
31 my $color = "color=yellow" if -e "pages/$name";
32 my $label = $name;
33 $name =~ s/\.//g;
34 return $name if $have{$name}++;
35 $label =~ s/_/\\n/g;
36 $label =~ s/([a-z])(A-Z)/$1\\n$2/g;
37 $label =~ s/\\n\\n/\\n/g;
38 return $name unless $color or $name ne $label;
39 print "$name [label = \"$label\" $color];\n";
40 return $name;
41 }
42
43 sub mangle {
44 my ($name) = @_;
45 $name =~ s/[^A-Za-z0-9 \_]//g;
46 $name =~ s/ /_/g;
47 return $name;
48 }
49
index.cgi
1 #!/usr/bin/perl
2 # by Ward Cunningham
3 # Copyright (c) Eclipse Foundation
4 # Released under EPL v1.0
5
6 use strict;
7 print "Content-type: text/html\n\n";
8
9 $_ = $ENV{QUERY_STRING};
10 my $depth = (/depth=(\d)/) ? $1 : 2;
11 my $files = (/file=([A-Za-z0-9\_\.]+)/) ? $1 : 'Eclipse';
12 my @files = split /\./, $files;
13 my $edit = (/edit=(on)/) ? $1 : "";
14
15 print <<;
16 <center>
17 <br><br>
18
19 my ($first) = $files =~ /([^\.]+)/;
20 table ($first, 0, $depth, $first);
21 about();
22 my ($last) = $files =~ /([^\.]+)$/;
23 edit ($last, 0) if $edit;
24
25 my %shown;
26 sub table {
27 my ($name, $deep, $goal, $path) = @_;
28 my $file = &mangle ($name);
29 my $there;
30 if ($files =~ /(.*\b$file\b)/) {
31 $path = $1;
32 $goal = $deep + $depth;
33 $there = $path eq $files;
34 }
35 print "<table border=1 cellpadding=10><tr><td>" if $there && $deep;
36
37 if (! -f "pages/$file/current") {
38 print "$name";
39 } else {
40 my %db = &readdb($file);
41 my $color = $db{color} || ($deep%2 ? '#cccccc' : '#eeeeee');
42 my $ref = $files[$#files] eq $file ? $file : "$path.$file";
43 print "<a href=?file=$ref&depth=$depth>$db{what}</a>";
44 if ($deep == $goal || $shown{$file}++) {
45 print $name if !$db{what};
46 } else {
47 print "<table cellspacing=5 cellpadding=10>";
48 print "<tr>" if $db{horz};
49 for (1..10) {
50 $_ = $db{$_};
51 next unless $_;
52 print "<tr>" unless $db{horz};
53 print "<td bgcolor=$color>";
54 &table ($_, $deep+1, $goal, $path);
55 }
56 print "</table>\n";
57 print "<br><br>" if $there and !$deep;
58 node ($file, %db) if $there;
59 }
60 }
61 print "</table>\n" if $there && $deep;
62 }
63
64 sub node {
65 my ($file, %db) = @_;
66 print <<;
67 <table width=500><tr><td>
68 <font color=gray>
69
70 print << if $db{why};
71 $db{why}
72 <p/>
73
74 print << if $db{who};
75 This information provided by $db{who}.
76
77 print << if $db{where};
78 See this <a href="$db{where}">site</a> for more information.
79
80 print << if -e 'save.cgi' && ! $edit;
81 Use <a href=?file=$file&depth=$depth&edit=on>edit</a>
82 to change this and nearby elements.
83
84 print <<;
85 </font></table>
86
87 # Focus on <a href=?file=$file&depth=$depth>these</a> elements.
88 }
89
90 sub about {
91 my ($more, $less) = ($depth+1, $depth-1);
92 print <<;
93 <table width=500><tr><td><font color=gray>
94 Browse this architecture by choosing hyperlinks to drill into
95 layers and choices. You can choose to see
96 <a href=?file=$files&depth=$more>more</a> or
97 <a href=?file=$files&depth=$less>less</a> detail.
98
99 print << if -e 'list.cgi';
100 Use <a href=list.cgi>list</a> to see all element definitions at once.
101
102 print << if -e 'lost.cgi';
103 See a table of contents and all nodes <a href=lost.cgi?file=$files[0]>lost</a> from it.
104
105 print << if -e 'dot.cgi' && -e 'xml.cgi';
106 Use graphviz to plot this <a href=dot.cgi>
107 dot</a> version of the graph or parse <a href=xml.cgi>xml</a>
108 and draw your own.
109
110 print << if -e 'source.cgi';
111 Read the <a href=source.cgi>code</a> for this program, the wikitect.
112
113 print << if -e 'login';
114 Try <a href=login/?file=$files&depth=$depth>login</a> for more options.
115
116 print <<;
117 </font></table><br><br>
118
119 }
120
121 sub edit {
122 my ($name, $deep) = @_;
123 my $file = &mangle ($name);
124 my %db = &readdb($file);
125 return if $db{what} && $deep;
126 $_ = `cat 'pages/$file/current'`;
127 s/&/&/g;
128 s/</</g;
129 s/>/>/g;
130 print <<;
131 <table bgcolor=#ffffcc cellpadding=15><tr><td>
132 <form method=post action="save.cgi?file=$file">
133 <font size=+1>$name</font>
134 <input type=submit value=save><br><br>
135 <textarea name=Text rows=12 cols=60 wrap=virtual>$_</textarea>
136 </form></table><br>
137
138 for (1..10) {
139 $_ = $db{$_};
140 next unless $_;
141 &edit ($_, $deep+1);
142 }
143 }
144
145 sub mangle {
146 my ($name) = @_;
147 $name =~ s/[^A-Za-z0-9 \_]//g;
148 $name =~ s/ /_/g;
149 return $name;
150 }
151
152 sub readdb {
153 my ($file) = @_;
154 open (F, "pages/$file/current");
155 $_ = join '', <F>;
156 s/\bname:/what:/;
157 s/\n\s*\n/\n/g;
158 s/((^|\n)\w+)\s*:\s*/$1\n/g;
159 return split "\n";
160 }
list.cgi
1 #!/usr/bin/perl
2 # by Ward Cunningham
3 # Copyright (c) Eclipse Foundation
4 # Released under EPL v1.0
5 use strict;
6 print "Content-type: text/html\n\n";
7 my @mo = qw(Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec);
8
9 opendir D, "pages";
10 my @files = grep !/^\./, readdir D;
11 for my $file (sort @files) {
12 opendir D, "pages/$file";
13 my @dates = grep /\d{8}/, "pages/$file/$_", readdir D;
14 print <<;
15 <table bgcolor=#ffffcc cellpadding=10><tr><td>
16 <a href=index.cgi?file=$file&edit=on><font size=+1>$file</font></a>
17
18 my $time = -M "pages/$file/current";
19 for my $date (reverse sort @dates) {
20 my $vers = $mo[$2-1] . " $3, $1" if $date =~ /(\d\d\d\d)(\d\d)(\d\d)/;
21 my $text = `cat 'pages/$file/$date'`;
22 $text =~ s/\n/<br>\n/g;
23 my $color = "bgcolor=white" if $time == -M "pages/$file/$date";
24 print <<;
25 <font color=gray>$vers</font><br><br>
26 <table $color cellpadding=5 width=500><tr><td>
27 <font face=courier>$text</font>
28 </table><br>
29
30 }
31 print <<;
32 </table><br>
33
34 }
lost.cgi
1 #!/usr/bin/perl
2 # by Ward Cunningham
3 # Copyright (c) Ward Cunningham
4 # Released under EPL v1.0
5
6 use strict;
7 print "Content-type: text/html\n\n";
8 print "<pre>\n";
9
10 $_ = $ENV{QUERY_STRING};
11 my $file = (/file=([A-Za-z0-9\_]+)/) ? $1 : 'Eclipse';
12
13 print "<h1>Found</h1>\n";
14 walk ($file, "");
15 print "<h1>Lost</h1>\n";
16 scan ();
17
18 my %shown;
19
20 sub walk {
21 my ($name, $pad) = @_;
22 my $file = &mangle ($name);
23 if ($shown{$file}++) {
24 print "$pad$file again\n";
25 } elsif (! -f "pages/$file/current") {
26 print "$pad$file leaf\n";
27 } else {
28 my %db = &readdb($file);
29 my $tag = $db{horz} ? 'choice' : 'stack';
30 print "$pad<a href=index.cgi?file=$file>$file</a>\n";
31 for (1..10) {
32 $_ = $db{$_};
33 next unless $_;
34 &walk ($_, "$pad ");
35 }
36 }
37 }
38
39 sub field {
40 my ($tag, $pad, %db) = @_;
41 print "$pad <$tag>", escape($db{$tag}), "</$tag>\n" if $db{$tag};
42 }
43
44 sub scan {
45 for (<pages/*/current>) {
46 my $node = $1 if /\/(.*)\//;
47 next if $shown{$node};
48 print "<a href=index.cgi?file=$node>$node</a>\n";
49 open (F, "$_") or die($!);
50 while (<F>) {
51 next unless /^\d+:\s*(.*)/;
52 my $ref = mangle($1);
53 my $found = $shown{$ref} ? " found" : "";
54 print " $ref$found\n";
55 }
56 }
57 }
58
59 sub escape {
60 ($_) = @_;
61 s/&/&/g;
62 s/</</g;
63 s/>/>/g;
64 return $_;
65 }
66
67 sub mangle {
68 my ($name) = @_;
69 $name =~ s/[^A-Za-z0-9 \_]//g;
70 $name =~ s/ /_/g;
71 return $name;
72 }
73
74 sub readdb {
75 my ($file) = @_;
76 open (F, "pages/$file/current");
77 $_ = join '', <F>;
78 s/\bname:/what:/;
79 s/\n\s*\n/\n/g;
80 s/((^|\n)\w+)\s*:\s*/$1\n/g;
81 return split "\n";
82 }
save.cgi
1 #!/usr/bin/perl
2 # by Ward Cunningham
3 # Copyright (c) Eclipse Foundation
4 # Released under EPL v1.0
5 use strict;
6 print "Content-type: text/html\n\n";
7
8 sub trouble {
9 my ($msg) = @_;
10 print "<h1>Trouble</h1>$msg\n";
11 die $msg;
12 }
13
14 $_ = $ENV{QUERY_STRING};
15 my $file = (/file=([A-Za-z0-9 \_\.]+)/) ? $1 : trouble ("bad file");
16 trouble ("expect post") unless $ENV{REQUEST_METHOD} eq 'POST';
17
18 my ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = localtime(time);
19 $year += 1900;
20 $mon += 1;
21 my $date = sprintf ("%04d%02d%02d", $year, $mon, $mday);
22
23 read(STDIN, $_, $ENV{CONTENT_LENGTH});
24 my ($body, %body);
25 foreach $_ (split(/&/, $_)) {
26 s/\+/ /g;
27 s/\%(..)/pack('C', hex($1))/geo;
28 ($_, $body) = split (/=/, $_, 2);
29 $body{$_} = $body;
30 }
31
32 $_ = $body{Text};
33 s/\r\n/\n/g;
34 s/\r/\n/g;
35
36 mkdir ("pages/$file", 0777) or trouble ("can't mkdir: $!") unless -d "pages/$file";
37 open (F, ">pages/$file/$date") or trouble ("can't write: $!");
38 flock (F, 2); #exclusive
39 print F;
40 unlink "pages/$file/current";
41 link "pages/$file/$date", "pages/$file/current" if $_;
42 flock (F, 8); #unlock
43 close (F);
44
45 print <<;
46 <br><br><center><table width=400><tr><td>
47 The <a href=index.cgi?file=$file&edit=on>$file</a> entry has been saved.
48 You may <b>back</b> up to the edit form and make further changes.
49 Remember to <b>reload</b> affected pages and especially
50 other copies of the editor.</i>
51 </table>
52
source.cgi
1 #!/usr/bin/perl
2 # by Ward Cunningham
3 # Copyright (c) Ward Cunningham
4 # Released under EPL v1.0
5
6 use strict;
7 print "Content-type: text/html\n\n";
8 print "<pre>";
9
10 $_ = $ENV{QUERY_STRING};
11 my ($file) = (/file=([A-Za-z0-9\_\.]+)/);
12
13 if ($file) {
14 &show($file);
15 } else {
16 &search();
17 }
18
19 sub show {
20 my ($file) = @_;
21 my ($script) = $file =~ (/(\w+)/);
22 print "<h1>$file</h1>\n";
23 open (F, $file) or print "Can't locate source. Try <i>login</i> where more options are available.\n";
24 my $line;
25 for (<F>) {
26 $line++;
27 s/&/&/g;
28 s/</</g;
29 s/^sub (\w+)/sub <a href=index.cgi?file=Code_Written.\u$script.\u${1}_Sub&depth=2><b>$1<\/b><\/a>/;
30 print "<font color=gray>$line</font>\t$_";
31 }
32 }
33
34 sub search {
35 for (<*.cgi>) {
36 show($_);
37 }
38 }