lsg

Lumidify Site Generator
git clone git://lumidify.org/lsg.git (fast, but not encrypted)
git clone https://lumidify.org/lsg.git (encrypted, but very slow)
git clone git://4kcetb7mo7hj6grozzybxtotsub5bempzo4lirzc3437amof2c2impyd.onion/lsg.git (over tor)
Log | Files | Refs | README | LICENSE

lsg.pl (8275B)


      1 #!/usr/bin/env perl
      2 
      3 # FIXME: standardize var names (e.g. $pageid, $page)
      4 
      5 # REQUIREMENTS: Text::Markdown
      6 
      7 # lsg.pl - Lumidify Site Generator
      8 # Written by lumidify <nobody@lumidify.org>
      9 #
     10 # To the extent possible under law, the author has dedicated
     11 # all copyright and related and neighboring rights to this
     12 # software to the public domain worldwide. This software is
     13 # distributed without any warranty.
     14 #
     15 # You should have received a copy of the CC0 Public Domain
     16 # Dedication along with this software. If not, see
     17 # <http://creativecommons.org/publicdomain/zero/1.0/>.
     18 
     19 use strict;
     20 use warnings;
     21 use FindBin;
     22 use lib "$FindBin::Bin";
     23 use LSG;
     24 
     25 my $path = $#ARGV >= 0 ? $ARGV[0] : ".";
     26 LSG::init($path);
     27 LSG::generate_site();
     28 
     29 __END__
     30 
     31 =head1 NAME
     32 
     33 lsg.pl - Multilingual static site generator
     34 
     35 =head1 SYNOPSIS
     36 
     37 B<lsg.pl> [directory]
     38 
     39 =head1 OPTIONS
     40 
     41 B<directory> specifies the directory of the source files for the site and
     42 defaults the the current directory.
     43 
     44 =head1 DESCRIPTION
     45 
     46 lsg.pl is a simple static site generator that is meant to simplify creating
     47 multilingual sites.
     48 
     49 This documentation is very rudimentary at the moment and the whole generator
     50 should really be rewritten at some point anyways. Contact me if you need help
     51 deciphering the meaning of the words written here.
     52 
     53 Do note that the code constituting this piece of software is not something
     54 to be proud of.
     55 
     56 =head1 FILES
     57 
     58 =over 8
     59 
     60 =item B<config.ini>
     61 
     62 The configuration for the site, see L</"CONFIGURATION">.
     63 
     64 =item B<modified_dates>
     65 
     66 A list of the timestamps of the source files for the site pages, in order
     67 to check which ones need to be regenerated (this is automatically generated)
     68 
     69 =item B<pages>
     70 
     71 The directory containing the source files for the site pages.
     72 
     73 =item B<templates>
     74 
     75 The directory containing the templates for the pages.
     76 
     77 =item B<site>
     78 
     79 The generated html pages.
     80 
     81 =item B<site/static>
     82 
     83 The directory containing static files such as images.
     84 
     85 =back
     86 
     87 =head1 CONFIGURATION
     88 
     89 The configuration file uses the INI format. There are currently only a few
     90 options:
     91 
     92 =over 8
     93 
     94 =item B<langs>
     95 
     96 Specifies the languages and their display names, e.g. "en=English".
     97 
     98 =item B<lang_dirs>
     99 
    100 Specifies the directions of the scripts the languages are written in
    101 (ltr or rtl). This is currently not used anywhere (I think?) but may
    102 come in handy someday.
    103 
    104 =item B<nav>
    105 
    106 This is outside the INI sections and just specifies the files that
    107 are supposed to be in the navigation menu, separated by colons.
    108 
    109 =back
    110 
    111 See the example site for more information.
    112 
    113 =head1 TEMPLATES
    114 
    115 The templates are simply html files with certain extra syntax
    116 parsed by the site generator. Note that backslashes need to be
    117 escaped.
    118 
    119 =over 8
    120 
    121 =item B<{var title}>
    122 
    123 Inserts the variable "title" set in the metadata of the page.
    124 
    125 =item B<{block block_name}>
    126 
    127 Starts a block named "block_name" which can be overwritten in
    128 child templates. The block named "content" is filled with the
    129 actual content from the page after it is converted to HTML.
    130 
    131 =item B<{func func_name}>
    132 
    133 Executes one of the functions from LSG::UserFuncs with the
    134 given arguments. Note that the function is executed separately
    135 for every page that is generated and can thus be used, for
    136 example, to generate relative links to a CSS file.
    137 
    138 =back
    139 
    140 At the very top of a template file, optional metadata can be
    141 specified:
    142 
    143 =over 8
    144 
    145 =item B<extends>
    146 
    147 Used to inherit from a parent template.
    148 
    149 =item B<metadata>
    150 
    151 Specifies the required metadata that needs to be specified in
    152 each page using this template.
    153 
    154 =back
    155 
    156 See the example site for details. This really isn't very polished,
    157 but I'm just trying to document it somewhat reasonably since I
    158 probably won't have time to properly rewrite it for a while.
    159 
    160 VERY IMPORTANT: There always needs to be a blank line between the
    161 metadata and the rest of the template, even when there is no
    162 metadata. A template with no metadata needs a blank line at the
    163 top. I could probably change that, but I don't feel like it at
    164 the moment. Fight me!
    165 
    166 =head1 PAGES
    167 
    168 The C<pages> directory contains the directory structure as it will
    169 be on the website, except that the pages are named "path/to/page.lang",
    170 which is changed to "lang/path/to/page.html" on the final website.
    171 
    172 Each page file contains metadata at the top. The minimum required
    173 metadata is "template" and "lang", since the template can then specify
    174 what metadata is required. "lang" should actually be redundant, but
    175 I don't have time to look into why I kept it that way right now...
    176 
    177 When a template named "article" is specified, the actual template that
    178 is loaded is "templates/article.lang.html", so a template needs to
    179 exist for every language.
    180 
    181 After the metadata, the rest of the file is the content, written in
    182 Markdown. All normal Markdown is supported since this just uses
    183 Text::Markdown for the parsing. There are some extra features, though.
    184 The special link syntax specified below is meant to provide some
    185 convenience and allows the site generator to check if the linked
    186 files actually exist on the server. The generated links are relative,
    187 so the site can also be browsed locally. Link titles, alt text for images,
    188 and reference-style links are not supported by this special format,
    189 however.
    190 
    191 (note that this was copied out of an old README and not formatted
    192 very well for this documentation page)
    193 
    194 B<Links:>
    195 
    196 [Whatever](@.pdf)-> [Whatever](relative/path/to/static/$name_of_page.pdf)
    197 
    198 [Whatever](#bob.pdf) -> [Whatever](relative/path/to/static/bob.pdf)
    199 
    200 [Whatever]($page.en) -> [Whatever](relative/path/to/en/page.html)
    201 
    202 If a link starts with "=", the HTML5 "download" attribute is added to the
    203 link so the file is downloaded directly in browsers that support it.
    204 This is a hack.
    205 
    206 B<Images:>
    207 
    208 ![Whatever](@.png)-> [Whatever](relative/path/to/static/$name_of_page.png)
    209 
    210 ![Whatever](#bob.png) -> [Whatever](relative/path/to/static/bob.png)
    211 
    212 B<Functions:>
    213 
    214 Functions can be used for more advanced features. They are written using Perl in the file
    215 C<LSG/UserFuncs.pm> and can be called from a markdown file as follows:
    216 
    217 C<{name_of_function}(argument1 argument2 argument3)>
    218 
    219 Note: this format may change in the future if more advanced arguments are needed.
    220 
    221 B<sort_books>
    222 
    223 B<Parameters:>
    224 
    225 - directory to take books from
    226 
    227 - mode
    228 
    229 - attribute(s) to sort by
    230 
    231 B<Purpose:>
    232 
    233 Generate sorted list of all pages in the given directory, first by the given attribute(s),
    234 which can be anything in the metadata, then by the titles. The mode argument can be used
    235 to either just list all books ("list"), list all books with subheadings for the different
    236 sorting attributes ("combined"), or generate different pages for the different values of
    237 the sorting attributes. Note that the display names for the attributes need to be defined
    238 in the configuration file config.ini. For instance, if a page contains metadata
    239 "category:stuff", config.ini must contain a section "[category:$lang]" for each language
    240 that contains a line "stuff=Display Name".
    241 
    242 This function was created for a book site, but it could probably be used for articles
    243 as well.
    244 
    245 Two more functions, C<gen_nav> and C<gen_lang_selector>, are defined, but they are
    246 currently only used internally in the templates and probably aren't needed for the
    247 actual pages.
    248 
    249 =head1 BUGS
    250 
    251 The C<modified_dates> behavior is buggy - pages should have proper dependency resolution
    252 so that pages which call other functions are still updated if the pages they require
    253 are modified but the page itself isn't. For instance, if one page has a list of books
    254 that is automatically generated, it won't be updated if the books change because the
    255 generator doesn't know that this page actually depends on all other pages. As a small
    256 workaround, there is now the C<always_update> metadata, so if C<always_update:true> is
    257 specified in the metadata, that page will always be updated.
    258 
    259 =head1 SEE ALSO
    260 
    261 Text::Markdown
    262 
    263 =head1 LICENSE
    264 
    265 Written in 2017-2023 by lumidify <nobody[at]lumidify.org>
    266 
    267 To the extent possible under law, the author has dedicated
    268 all copyright and related and neighboring rights to this
    269 software to the public domain worldwide. This software is
    270 distributed without any warranty.
    271 
    272 You should have received a copy of the CC0 Public Domain
    273 Dedication along with this software. If not, see
    274 <http://creativecommons.org/publicdomain/zero/1.0/>.
    275 
    276 =cut