/[pub]/suikawiki/script/lib/SuikaWiki/Plugin/WikiLinking.wp2
Suika

Contents of /suikawiki/script/lib/SuikaWiki/Plugin/WikiLinking.wp2

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1.3 - (show annotations) (download)
Fri Dec 26 06:40:30 2003 UTC (22 years, 6 months ago) by wakaba
Branch: MAIN
Changes since 1.2: +311 -13 lines
Link to some resource other than WikiPage is implemented

1 #?SuikaWikiConfig/2.0
2
3 Plugin:
4 @Name: WikiLinking
5 @Description:
6 @@@: Wiki hyperlinking support
7 @@lang:en
8 @License: %%GPL%%
9 @Author:
10 @@Name:
11 @@@@: Wakaba
12 @@@lang:ja
13 @@@script:Latn
14 @@Mail[list]: w@suika.fam.cx
15 @Date.RCS: $Date: 2003/12/01 07:31:52 $
16 @Use:
17 use Message::Util::Error;
18 our $NestLevel = 0;
19
20 PluginConst:
21 @NS_XHTML1:
22 http://www.w3.org/1999/xhtml
23 @NS_XHTML2:
24 http://www.w3.org/2002/06/xhtml2
25 @NS_XLINK:
26 http://www.w3.org/1999/xlink
27 @NS_HLINK:
28 http://www.w3.org/2002/06/hlink
29
30 FormattingRule:
31 @Category[list]:
32 view
33 view-resource
34 form-input
35 @Name: link-to-wikipage
36 @Description:
37 @@@:
38 Creating "from" anchor field of a link whose "to" is a WikiPage
39 @@lang: en
40 @Parameter:
41 @@Name: base-page
42 @@Type: WikiName
43 @@Default: (current)
44 @@Description:
45 @@@@:Base WikiName (Relative WikiName is resolved with)
46 @@@lang:en
47 @Parameter:
48 @@Name: hreflang
49 @@Type:
50 HTML4:LanguageCode
51 @@Default:(none)
52 @@Description:
53 @@@@:(Human) language the linked WikiPage written in
54 @@@lang:en
55 @Parameter:
56 @@Name: hreftype
57 @@Type:
58 HTML4:ContentType
59 @@Default:(none)
60 @@Description:
61 @@@@:Media type the linked WikiPage provided with
62 @@@lang:en
63 @Parameter:
64 @@Name:label
65 @@Type:CDATA
66 @@Default:(auto)
67 @@Description:
68 @@@@:Source anchor label
69 @@@lang:en
70 @Parameter:
71 @@Name: mode
72 @@Type: WikiMode
73 @@Default:(default)
74 @@Description:
75 @@@@:Mode of the Wiki linked to
76 @@@lang:en
77 @Parameter:
78 @@Name: page
79 @@Type: WikiName
80 @@Default: (current)
81 @@Description:
82 @@@@:WikiPage linked to
83 @@@lang:en
84 @Parameter:
85 @@Name: page-anchor-name
86 @@Type:
87 XML:ID
88 @@Default: (none)
89 @@Description:
90 @@@@:Identifier in the WikiPage linked to
91 @@@lang:en
92 @Parameter:
93 @@Name: page-anchor-no
94 @@Type:
95 SGML:NUMBER
96 @@Default: (none)
97 @@Description:
98 @@@@:Numeral anchor index in the WikiPage linked to
99 @@@lang:en
100 @Parameter:
101 @@Name: page-title
102 @@Type:CDATA
103 @@Default:(auto)
104 @@Description:
105 @@@@:Title of the WikiPage linked to
106 @@@lang:en
107 @Parameter:
108 @@Name: rel
109 @@Type:
110 HTML4:LinkTypes
111 @@Default:(none)
112 @@Description:
113 @@@@:Link relationships
114 @@@lang:en
115 @Parameter:
116 @@Name: rev
117 @@Type:
118 HTML4:LinkTypes
119 @@Default:(none)
120 @@Description:
121 @@@@:Link relationship (reverse)
122 @@@lang:en
123 @Parameter:
124 @@Name: up-to-date
125 @@Type: boolean
126 @@Default: "0"
127 @@Description:
128 @@@@:Appends random "up-to-date" parameter to the URI reference
129 @@@lang:en
130 @Parameter:
131 @@Name: with-lm
132 @@Type: boolean
133 @@Default:"0"
134 @@Description:
135 @@@@:Appends "last-modified" parameter to the URI reference
136 @@@lang:en
137 @Formatting:
138 __ATTRNODE:%page_title__;
139 __ATTRTEXT:%class__;
140 __ATTRTEXT:%label__;
141 __ATTRTEXT:%page__;__ATTRTEXT:%base_page__;__ATTRTEXT:%page_anchor_no__;
142 __ATTRTEXT:%with_lm__;__ATTRTEXT:%up_to_date__;
143 __ATTRTEXT:%page_anchor_name__;
144 __ATTRTEXT:%hreflang__;__ATTRTEXT:%hreftype__;
145 __ATTRTEXT:%mode__;
146 __ATTRTEXT:%rel__;__ATTRTEXT:%rev__;
147 __FUNCPACK__->to_wikipage_in_html ({
148 label => ($p->{label}),
149 } => {
150 base => [split m#//#, ($p->{base_page}||$o->{page})],
151 page_name_relative => $p->{page} ? [split m#//#, $p->{page}]
152 : $o->{wiki}->{var}->{page},
153 page_anchor_no => $p->{page_anchor_no},
154 page_anchor_name => $p->{page_anchor_name},
155 page_title => $p->{page_title},
156 wiki_mode => $p->{mode},
157 _with_lm => $p->{with_lm},
158 _up_to_date => $p->{up_to_date},
159 -hreflang => $p->{hreflang},
160 -hreftype => $p->{type},
161 }, {
162 o => $o,
163 parent => $p->{-parent},
164 -rel => $p->{rel},
165 -rev => $p->{rev},
166 });
167
168 FormattingRule:
169 @Category[list]:
170 view
171 view-resource
172 form-input
173 @Name: link-to-resource
174 @Description:
175 @@@:
176 Creating source anchor field of a link whose destination is a resource
177 @@lang: en
178 @Parameter
179 @@Name: hreflang
180 @@Type:
181 HTML4:LanguageCode
182 @@Default:(none)
183 @@Description:
184 @@@@:(Human) language the linked WikiPage written in (advisory)
185 @@@lang:en
186 @Parameter:
187 @@Name: hreftype
188 @@Type:
189 HTML4:ContentType
190 @@Default:(none)
191 @@Description:
192 @@@@:Media type the linked WikiPage provided with (advisory)
193 @@@lang:en
194 @Parameter:
195 @@Name:label
196 @@Type:CDATA
197 @@Default:(auto)
198 @@Description:
199 @@@@:Source anchor label
200 @@@lang:en
201 @Parameter:
202 @@Name: rel
203 @@Type:
204 HTML4:LinkTypes
205 @@Default:(none)
206 @@Description:
207 @@@@:Link relationships
208 @@@lang:en
209 @Parameter:
210 @@Name: rev
211 @@Type:
212 HTML4:LinkTypes
213 @@Default:(none)
214 @@Description:
215 @@@@:Link relationship (reverse)
216 @@@lang:en
217 @Parameter:
218 @@Name: uri
219 @@Type:
220 HTML4:URI
221 @@Default:(required)
222 @@Description:
223 @@@@:URI reference of the resoruce referred to
224 @@@lang:en
225 @Formatting:
226 __ATTRTEXT:%class__;
227 __ATTRTEXT:%label__;
228 __ATTRTEXT:%hreflang__;__ATTRTEXT:%hreftype__;
229 __ATTRTEXT:%rel__;__ATTRTEXT:%rev__;
230 __ATTRTEXT:%uri__;
231 __FUNCPACK__->to_resource_in_html ({
232 label => ($p->{label}),
233 } => {
234 #base_uri => ...
235 uri => $p->{uri},
236 -hreflang => $p->{hreflang},
237 -hreftype => $p->{type},
238 }, {
239 o => $o,
240 parent => $p->{-parent},
241 -rel => $p->{rel},
242 -rev => $p->{rev},
243 });
244
245 FormattingRule:
246 @Category[list]:
247 page-link
248 link-to-resource
249 @Name: link-to-it
250 @Description:
251 @@@:
252 Source anchor
253 @@lang: en
254 @Parameter:
255 @@Name: class
256 @@Type:
257 HTML4:class
258 @@Default: (none)
259 @@Description:
260 @@@@: Class names
261 @@@lang:en
262 @Parameter:
263 @@Name: description
264 @@Type: CDATA
265 @@Default: (none)
266 @@Description:
267 @@@@: Description of the anchor or link
268 @@@lang:en
269 @Parameter:
270 @@Name: label
271 @@Type: CDATA
272 @@Default: ""
273 @@Description:
274 @@@@: Source anchor label (content)
275 @@@lang:en
276 @Formatting:
277 __ATTRTEXT:%class__;
278 __ATTRTEXT:%description__;
279 my $A = $p->{-parent}->append_new_node (type => '#element',
280 namespace_uri => $NS_XHTML1,
281 local_name => 'a');
282 $A->set_attribute (href => $o->{link}->{dest}->{uri});
283
284 __ATTRNODE:%label->{$A}__;
285 $A->set_attribute (title => $p->{description}) if $p->{description};
286 my @class = split /\s+/, $p->{class};
287 ## TODO:
288 if ($o->{wiki}->uri_is_part_of_wiki ($o->{link}->{dest}->{absolute_uri} or
289 $o->{link}->{dest}->{uri})) {
290 push @class, 'wiki'; ## Link to the page within the Wiki
291 }
292 $A->set_attribute (class => join ' ', @class) if @class;
293
294 $A->set_attribute (rel => $o->{link}->{option}->{-rel})
295 if $o->{link}->{option}->{-rel};
296 $A->set_attribute (rev => $o->{link}->{option}->{-rev})
297 if $o->{link}->{option}->{-rev};
298
299 $A->set_attribute (hreflang => $o->{link}->{dest}->{-lang})
300 if $o->{link}->{dest}->{-lang};
301 $A->set_attribute (type => $o->{link}->{dest}->{-type})
302 if $o->{link}->{dest}->{-type};
303
304 FormattingRule:
305 @Category[list]:
306 page-link
307 link-to-resource
308 @Name: uri-reference
309 @Description:
310 @@@: URI Reference of destination anchor
311 @@lang:en
312 @Formatting:
313 $p->{-parent}->append_text ($o->{link}->{dest}->{absolute_uri} or
314 $o->{link}->{dest}->{uri});
315
316 FormattingRule:
317 @Category[list]: link-to-resource
318 @Name: link-resource-scheme
319 @Description:
320 @@@: Linking scheme (defined as ReferenceScheme in SuikaWiki/0.9 syntax)
321 @@lang:en
322 @Formatting:
323 $p->{-parent}->append_text ($o->{link}->{dest}->{resource_scheme});
324
325 FormattingRule:
326 @Category[list]: link-to-resource
327 @Name: link-resource-parameters
328 @Description:
329 @@@: Linking parameters (defined as ReferenceParameter in SuikaWiki/0.9 syntax)
330 @@lang:en
331 @Formatting:
332 $p->{-parent}->append_text ($o->{link}->{dest}->{resource_parameter});
333
334 FormattingRule:
335 @Category[list]: page-link
336 @Name: link-base-page-name
337 @Description:
338 @@@: Base WikiPage name
339 @@lang: en
340 @Formatting:
341 $p->{-parent}->append_text (join '//', @{$o->{link}->{dest}->{base}});
342
343 FormattingRule:
344 @Category[list]: page-link
345 @Name: link-dest-anchor-no
346 @Description:
347 @@@: Anchor number in the WikiPage linked to, if specified
348 @@lang: en
349 @Formatting:
350 $p->{-parent}->append_text ($o->{link}->{dest}->{page_anchor_no});
351
352 FormattingRule:
353 @Category[list]: link-to-resource
354 @Name: if-link-resource-scheme
355 @Description:
356 @@@: If or if not resource pointing scheme matches to
357 @@lang:en
358 @Parameter:
359 @@Name: name
360 @@Type:
361 SW09:name
362 @@Default:(required)
363 @@Description:
364 @@@@: Scheme name
365 @@@lang:en
366 @Formatting:
367 __ATTRTEXT:%name__;
368 my $rule;
369 if ($o->{link}->{dest}->{resource_scheme} eq $p->{name}) {
370 $rule = __ATTRTEXT:%true__;
371 } else {
372 $rule = __ATTRTEXT:%false__;
373 }
374 SuikaWiki::Plugin->formatter ($f->{-category_name})
375 ->replace ($rule, param => $o, -parent => $p->{-parent});
376
377 FormattingRule:
378 @Category[list]: link-to-resource
379 @Name: select-link-resource-scheme
380 @Description:
381 @@@: Selecting template by resource pointing scheme matches to
382 @@lang:en
383 @Parameter:
384 @@Name: SCHEMENAME
385 @@Type:
386 template
387 @@Default:(none)
388 @@Description:
389 @@@@: Template used when scheme name is SCHEMENAME
390 @@@lang:en
391 @Parameter:
392 @@Name: otherwise
393 @@Type:
394 template
395 @@Default:(none)
396 @@Description:
397 @@@@: Template used when no SCHEMENAME parameter matches
398 @@@lang:en
399 @Formatting:
400 my $rule;
401 if (defined $p->{$o->{link}->{dest}->{resource_scheme}}) {
402 $rule = __ATTRTEXT:%{$o->{link}->{dest}->{resource_scheme}}__;
403 } else {
404 $rule = __ATTRTEXT:%otherwise__;
405 }
406 SuikaWiki::Plugin->formatter ($f->{-category_name})
407 ->replace ($rule, param => $o, -parent => $p->{-parent});
408
409 FormattingRule:
410 @Category[list]: page-link
411 @Name: if-linked-wikipage-exist
412 @Description:
413 @@@: If or if not linked WikiPage exists, then
414 @@lang: en
415 @Formatting:
416 my $page = $o->{link}->{dest}->{page_name};
417 my $rule;
418 if ($o->{wiki}->{db}->exist (content => $page)) {
419 $rule = __ATTRTEXT:%true__;
420 } else {
421 $rule = __ATTRTEXT:%false__;
422 }
423 SuikaWiki::Plugin->formatter ('page-link')
424 ->replace ($rule, param => $o, -parent => $p->{-parent});
425
426 FormattingRule:
427 @Category[list]: page-link
428 @Name: if-link-has-dest-anchor-no
429 @Description:
430 @@@: If or if the link has destination numeral anchor
431 @@lang: en
432 @Formatting:
433 my $rule;
434 if ($o->{link}->{dest}->{page_anchor_no}) {
435 $rule = __ATTRTEXT:%true__;
436 } else {
437 $rule = __ATTRTEXT:%false__;
438 }
439 SuikaWiki::Plugin->formatter ('page-link')
440 ->replace ($rule, param => $o, -parent => $p->{-parent});
441
442 FormattingRule:
443 @Category[list]:
444 page-link
445 link-to-resource
446 @Name:-bare-text
447 @Formatting:
448 $p->{-parent}->append_text ($p->{-bare_text});
449
450 Function:
451 @Name: to_resource_in_html
452 @Description:
453 @@@Make a link to the resource (outputted in HTML)
454 @@lang:en
455 @Main:
456 my (undef, $src => $dest, $opt) = @_;
457 if ($dest->{resource_scheme} eq 'URI' or
458 $dest->{resource_scheme} eq 'URL') {
459 $dest->{uri} = $dest->{resource_parameter};
460 ## TODO: Check syntax of URI reference
461 } elsif ($dest->{resource_scheme} eq 'IW') {
462 $dest->{uri} = SuikaWiki::Plugin->module_package ('WikiLinking')#('InterWikiCore')
463 ->interwikireference_to_urireference
464 (packed => $dest->{resource_parameter});
465 } elsif ($dest->{resource_scheme} eq 'MAIL') {
466 $dest->{uri} = 'mailto:'.$dest->{resource_parameter};
467 } else {
468 ## TODO: Unknown scheme error
469 }
470 __FUNCPACK__->to_resource_by_uri_in_html ($src => $dest, $opt);
471
472 Function:
473 @Name: to_resource_by_uri_in_html
474 @Description:
475 @@@:Make a link to the resource by URI reference (outputted in HTML)
476 @@lang:en
477 @Main:
478 my (undef, $src => $dest, $opt) = @_;
479 local $NestLevel = $NestLevel + 1;
480 if (100 < $NestLevel) {
481 $opt->{parent}->append_new_node (type => '#comment',
482 value => $src->{label});
483 SuikaWiki::Plugin->module_package ('Error')
484 ## TODO:
485 ->report_error_simple
486 ($opt->{o}->{wiki},
487 'Condition' => 'Link nesting too deep',
488 'Template' => $src->{label},
489 -trace => 1);
490 return;
491 }
492 local $opt->{o}->{link} = {
493 src => $src,
494 dest => $dest,
495 option => $opt,
496 };
497 $src->{label} ||= SuikaWiki::Plugin->resource
498 ('Link:toResource:SourceLabel');
499 try {
500 SuikaWiki::Plugin->formatter ('link_to_resource')
501 ->replace ($src->{label}, param => $opt->{o}, -parent => $opt->{parent});
502 } catch Message::Util::Formatter::error with {
503 my $err = shift;
504 if ($err->{-formatter}->{-category_name} eq 'link_to_resource') {
505 my $wiki = $err->{-option}->{param}->{wiki};
506 __FUNCPACK__->logging_template_error ($err, $wiki,
507 template => $src->{label});
508 undef;
509 } else {
510 $err->throw;
511 }
512 };
513
514 Function:
515 @Name: to_wikipage_in_html
516 @Description:
517 @@@:Make a link to the WikiPage (outputed in HTML)
518 @@lang:en
519 @Main:
520 my (undef, $src => $dest, $opt) = @_;
521 local $NestLevel = $NestLevel + 1;
522 if (100 < $NestLevel) {
523 $opt->{parent}->append_new_node (type => '#comment',
524 value => $src->{label});
525 SuikaWiki::Plugin->module_package ('Error')
526 ->report_error_simple
527 ($opt->{o}->{wiki},
528 'Condition' => 'Link nesting too deep',
529 'Template' => $src->{label},
530 -trace => 1);
531 return;
532 }
533 #$dest->{page_name} = SuikaWiki::Plugin::WikiNamespace->resolve_relative_name
534 # ($dest->{base} => $dest->{page_name_relative});
535 $dest->{page_name} = $dest->{page_name_relative};
536 ($dest->{uri}, $dest->{absolute_uri})
537 = $opt->{o}->{wiki}->uri_reference
538 (page => $dest->{page_name},
539 mode => $dest->{wiki_mode},
540 anchor_no => $dest->{page_anchor_no},
541 up_to_date => $dest->{_up_to_date},
542 with_lm => $dest->{_with_lm},
543 fragment => $dest->{page_anchor_name},
544 base => $dest->{-use_absolute_uri} ? undef:
545 ($src->{base_uri} || 1));
546
547 local $opt->{o}->{link} = {
548 src => $src,
549 dest => $dest,
550 option => $opt,
551 };
552 $src->{label} ||= SuikaWiki::Plugin->resource ('Link:toWikiPage:SourceLabel');
553 try {
554 SuikaWiki::Plugin->formatter ('page_link')
555 ->replace ($src->{label}, param => $opt->{o}, -parent => $opt->{parent});
556 } catch Message::Util::Formatter::error with {
557 my $err = shift;
558 if ($err->{-formatter}->{-category_name} eq 'page_link') {
559 my $wiki = $err->{-option}->{param}->{wiki};
560 __FUNCPACK__->logging_template_error ($err, $wiki,
561 template => $src->{label});
562 undef;
563 } else {
564 $err->throw;
565 }
566 };
567
568 Function:
569 @Name: interwikireference_to_urireference
570 @Description:
571 @@@:
572 Converting InterWikiReference to URI Reference.
573 \
574 Note that only SuikaWiki 2 compatible InterWiki mechanism is
575 currently implemented. More study is needed for SuikaWiki 3 InterWiki.
576 @@lang:en
577 @Main:
578 ## TODO: Implements SuikaWiki 3 InterWiki
579 my (undef, %opt) = @_;
580 my ($name, $param);
581 if ($opt{packed}) {
582 if ($opt{packed} =~ /^(?:(\w+)|"([^"]*(?>[^"]*|\\.)*)"):(?:(\w+)|"([^"]*(?>[^"]*|\\.)*)")/) {
583 ($name, $param) = (defined $1 ? $1 : $2, defined $3 ? $3 : $4);
584 $name =~ s/\\(.)/$1/g; $param =~ s/\\(.)/$1/g;
585 } else {
586 ## TODO:
587 }
588 }
589
590 return "$name:$param";
591
592 Function:
593 @Name: logging_template_error
594 @Description:
595 @@@:
596 Logging formatting-template-text error
597 @@lang:en
598 @Main:
599 my (undef, $err, $wiki, %opt) = @_;
600 my $error = {};
601 my $dl = $error->{description}
602 = new Message::Markup::XML::Node
603 (type => '#element',
604 namespace_uri => $NS_XHTML1,
605 local_name => 'dl');
606 ## TODO: Use resource
607 $dl->append_new_node (type => '#element',
608 namespace_uri => $NS_XHTML1,
609 local_name => 'dt')
610 ->append_text ('Template');
611 $dl->append_new_node (type => '#element',
612 namespace_uri => $NS_XHTML1,
613 local_name => 'dd')
614 ->append_text ($opt{template});
615 $dl->append_new_node (type => '#element',
616 namespace_uri => $NS_XHTML1,
617 local_name => 'dt')
618 ->append_text ('Error condition');
619 $dl->append_new_node (type => '#element',
620 namespace_uri => $NS_XHTML1,
621 local_name => 'dd')
622 ->append_text ($err->text);
623 $dl->append_new_node (type => '#element',
624 namespace_uri => $NS_XHTML1,
625 local_name => 'dt')
626 ->append_text ('Formatting context');
627 $dl->append_new_node (type => '#element',
628 namespace_uri => $NS_XHTML1,
629 local_name => 'dd')
630 ->append_text (qq($err->{-formatter}->{-category_name}));
631
632 push @{$wiki->{var}->{error}||=[]}, $error;
633
634 PluginCategory:
635 @Name: page-link
636 @Description:
637 @@@: Source anchor label of link whose destination is a WikiPage
638 @@lang:en
639
640 PluginCategory:
641 @Name: link-to-resource
642 @Description:
643 @@@: Source anchor label of link whose destination is a resource
644 @@lang:en
645
646 Resource:
647 @Link:toResource:SourceLabel:
648 @@@:
649 %select-link-resource-scheme (
650 URI => {<%link-to-it(
651 label => {%uri-reference;}p,
652 );>},
653 MAIL => {<%link-to-it(
654 label => {%link-resource-parameters;}p,
655 description
656 => {%res (name=>{Link:MailAddress=});<%link-resource-parameters;>}p,
657 );>},
658 otherwise => {<%link-to-it(
659 label => {%link-resource-scheme;:%link-resource-parameters;}p,
660 description => {%res (name=>{Link:URIReference=});<%uri-reference;>}p,
661 );>},
662 );
663 @Link:toWikiPage:SourceLabel:
664 @@@:
665 %link-to-it(
666 label=>{%page-title (relative);%if-linked-wikipage-exist(
667 true=>{%if-link-has-dest-anchor-no(true=>{>>%link-dest-anchor-no;});},
668 false=>{%res(name=>{Link:toWikiPage:NotExist:Mark});}
669 );}p,
670 description=>{%page-name(absolute);; %if-linked-wikipage-exist(
671 true=>{%page-headline;},
672 false=>{(%res(name=>{Link:toWikiPage:NotExist:Description});)},
673 );}p,
674 class=>{%if-linked-wikipage-exist(false=>{not-exist});}p,
675 );
676 @Link:MailAddress=:
677 @@@:
678 Internet Mail Address:
679 @@lang:en
680 @Link:URIReference=:
681 @@@:
682 URI Reference:
683 @@lang:en

admin@suikawiki.org
ViewVC Help
Powered by ViewVC 1.1.24