summaryrefslogtreecommitdiff
path: root/IkiWiki/Plugin/rst.pm
blob: 1fd13d1f5ceca92262cbbfb70d86e979c9ff7d88 (plain)
  1. #!/usr/bin/perl
  2. # Very simple reStructuredText processor.
  3. #
  4. # This plugin calls python and requires python-docutils to transform the text
  5. # into html.
  6. #
  7. # Its main problem is that it does not support ikiwiki's WikiLinks nor
  8. # Preprocessor Directives.
  9. #
  10. # Probably Wikilinks and Preprocessor Directives should support a list of
  11. # extensions to process (i.e. the linkify function could be transformed into
  12. # reStructuredText instead of HTML using a hook on rst.py instead of the
  13. # current linkify function)
  14. #
  15. # by Sergio Talens-Oliag <sto@debian.org>
  16. package IkiWiki::Plugin::rst;
  17. use warnings;
  18. use strict;
  19. use IkiWiki;
  20. use IPC::Open2;
  21. # Simple python script, maybe it should be implemented using an external script.
  22. # The settings_overrides are given to avoid potential security risks when
  23. # reading external files or if raw html is included on rst pages.
  24. my $pyCmnd = "
  25. from docutils.core import publish_string;
  26. from sys import stdin;
  27. html = publish_string(stdin.read(), writer_name='html',
  28. settings_overrides = { 'halt_level': 6,
  29. 'file_insertion_enabled': 0,
  30. 'raw_enabled': 0 }
  31. );
  32. print html[html.find('<body>')+6:html.find('</body>')].strip();
  33. ";
  34. sub import { #{{{
  35. hook(type => "htmlize", id => "rst", call => \&htmlize);
  36. } # }}}
  37. sub htmlize (@) { #{{{
  38. my %params=@_;
  39. my $content=$params{content};
  40. my $tries=10;
  41. my $pid;
  42. while (1) {
  43. eval {
  44. # Try to call python and run our command
  45. $pid=open2(*IN, *OUT, "python", "-c", $pyCmnd)
  46. or return $content;
  47. };
  48. last unless $@;
  49. $tries--;
  50. if ($tries < 1) {
  51. debug("failed to run python to convert rst: $@");
  52. return $content;
  53. }
  54. }
  55. # open2 doesn't respect "use open ':utf8'"
  56. binmode (IN, ':utf8');
  57. binmode (OUT, ':utf8');
  58. print OUT $content;
  59. close OUT;
  60. local $/ = undef;
  61. my $ret=<IN>;
  62. close IN;
  63. waitpid $pid, 0;
  64. return $ret;
  65. } # }}}
  66. 1