=begin rakudoc
=config code :lang<text>
=TITLE Build a website from current directory
=SUBTITLE The Build component for the Elucid8 framework
=for AUTHOR :hidden
Richard Hainsworth, aka finanalyst
=for VERSION :hidden
v0.1.0
=begin SYNOPSIS
The component is part of the C<Elucid8> distribution and is installed as
=for code
    zef install Elucid8::Build Elucid8::Run-locally

Elucid8-build needs Dart sass, and Cro.

A minimal site can be generated in an empty directory with the following steps:
=numitem elucid8-setup
=numitem gather-sources
=numitem elucid8-build
=numitem run-locally
=end SYNOPSIS
=head Introduction

The utility C<elucid8-build> will generate a static website according
to the L<configuration|#Configuration> in the Current Working Directory (CWD).

If the CWD is empty, C<elucid8-setup> will create a default structure

If the CWD has a custom (localised) config file, which may be any localised name, and the
contents have the keys required (in English) but with localised values (eg. Kostom), then
C<elucid8-build --config=Kostom --install> then the subdirectories will be localised as well.

Elucid8 may be used in two ways:
=numitem All the RakuDoc sources are in the main website directory, under the C<sources>
subdirectory.
=numitem The RakuDoc sources may be located in various repositories.

For the second scenario, the C<gather-sources> utility is used first. See
L<Gather and Build|Build-Gather.*> for more information.

Once the website has been built, the C<run-locally> utility will serve the HTML files, and
can be browsed in a browser as C<localhost:5000>. (The port can be changed in the plugins-configuration config).

Run C<elucid8-build -h> to get information on command line flags.

Subsequent calls to C<elucid8-build> will only rebuild modified source files, but see I<-f> and I<-with-only>

=head Assumptions

The Build component of Elucid8 assumes the following structure.

=for code
sandpit                      # a test bed for a web site built with elucid8
    - config/                 # contains the website configuration
    - misc/                  # contains the dictionaries from the canonical to derived languages
    - site-sources/               # Only directories containing language sources permitted here
      - canonical/           # RakuDoc content in canonical language, which is en by default
      - xx/                  # content in language with code xx
      - xx-YY/               # regional content in language with code xx-YY

All names in the structure, except for C<config/>, may be modified by changing fields in
the files in C<config/>.

The name of the R<config/> directory may be changed by setting the C<--config>
option to C<elucid8-build>. For example, if the canonical language is Mandarin, and
the term used to mean 'config' is C<布局>, then

    elucid8-build --config=<布局>

will set the configuration directory I<布局>. This will be called the I<localised config>.

=head Plugins

The following HTML plugins are available:
=numitem L<UISwitcher|UISwitcher.*>
=numitem SiteMap - creates C<sitemap.xml> which can be read by robots
=numitem AutoIndex - creates a C<landing-page> file for the whole website from all glue files

Each website can have its own plugins, stored in C<local-lib>

=head Render workflow

For each human language (h-language), the sources files in the appropriately named sub-directory
of C<sources> (or local equivalent), each generate a separate web page.
=nested Elucid8 is being designed for large websites and currently these are not
optimally viewed using the I<single page> paradigm. In the future, this view may
change, in which case, each source will generate a section of the page.

The source files in an h-language directory are of two sorts:
=numdefn content
sources that are the basis of the website. They may contain explicit links to other pages.

=numdefn glue
sources that are automatically generated to contain links to web pages generated by
content (and possibly other glue) sources.

=numdefn info
sources that contain site information not to be included in the search, such License or about.

=numdefn landing-page
the name of the web page that is the default for a browser. By default it is
auto-generated from the TITLEs and SUBTITLEs of the glue files in each h-language.

Consequently,
=numitem content web pages must be generated first
=numitem info web pages must be generated next
=numitem glue web pages must be generated after all content sources
=numitem glue pages must be rendered in an explicit order
=numitem if no content sources have changed since the last rendering, then glue web pages
do not need to be re-generated, unless a glue source has itself been modified.

In addition,
=numitem a change in a canonical content source should trigger a change of style in the
L<equivalent content file|#Canonical<->derived links>
=numitem editing of derived sources will be more frequent than editing of the canonical
sources

For simplicity and initial development, the following are required:
=numitem glue sources must be exist for each language (no super-language glue sources)
=numitem the filename of each glue source must be the same in each directory
=numitem content sources are implicitly assigned a generation order of zero
=numitem the name and generation order of each glue source is defined in the config directory

Consequently, the render order is as follows:
=numitem the canonical language sources must be rendered first
=numitem a content source is only re-generated if:
=numitem2 the force flag is True
=numitem2 there is no existing rendered file with the same name
=numitem2 the content source is newer than the generate file
=numitem if a canonical content source is re-generated, the equivalent source in all of the h-language
directories must be re-generated too
=numitem if a source (content or glue) is regenerated, all the glue files at the next
generation order must be re-generated
=numitem if no sources are regenerated at some level, then the glue sources at the
next generation order do not need to be regenerated B<unless> the glue source itself
is modified. (This implies that changes cascade up the regeneration order)
=numitem the sources in each derived language are rendered in an unspecified order of languages
=numitem a content source is only re-generated if:
=numitem2 the force flag is True
=numitem2 the equivalent canonical source was rendered in this build cycle
=numitem2 there is no existing rendered file with the same name
=numitem2 the content source is newer than the generated file
=numitem the glue sources are generated as per the canonical glue sources
=numitem the B<landing-page> is generated
=numitem2 By default, a web page with the name B<landing-page>I<.html> is auto-generated
=numitem2 If a source with the name B<landing-page>I<.rakudoc> exists in the R<sources>
directory, it is used to generate the landing page. A custom block is defined to add the
glue contents that are auto-generated.

=head Configuration

A directory called C<config/> (or its preconfigured alternative) is required in the CWD.

The R<config/> directory follows the conventions set out in the distribution C<raku-config>.

If a I<localised config> has been specified, then one key must be called
by the same name, and must contain
a hash in which the key is a key of the default (English) I<config> and the
value is a string that is a key in the localised config.

If some of the keys in the default are missing in the localised config, then the value
of the default config is used.

This allows for some or all of the configuration to be specified in a
canonical language other than English.

The full set of L<configuration keys|#All configuration keys> and their defaults
are in English.

For example, suppose we have a web-site where Welsh is the canonical language
and the I<config> file is partially in Welsh. Suppose further that the build command is:
=for code
    elucid8-build --config=ffurfwedd

Then in this case, the directory C<ffurfwedd/> should contain a file,
typically named I<01-ffurfwedd.raku>, with the content:
=for code
    ffurfwedd => %(
        sources => 'ffynhonnell',
        canonical => 'gofyddebol',
        Misc => 'lleoliad',
    )

Then the web-site would need to be structured as follows
=begin code
<web-site directory>/
|- config/
|- lleoliad/
|- ffurfwedd/
    |- 01-ffurfwedd.raku
|- ffynhonnell/
    |- gofyddebol/
    |- en-GB/
=end code
The B<config> directory and its contents are needed because the localised
config is incomplete.

If B<all> the mandatory config keys are defined
in the I<localised config>, and all the keys have values, then the default
can be removed.

=head2 All configuration keys

The following is a list of all the mandatory config keys and their default values.
=begin table :!toc :caption('')
=row :header
    =cell Key name
    =cell Value
    =cell Description
=row
    =cell misc
    =cell misc
    =cell the directory containing global information for translation, and file-data, repo-info
=row
    =cell sources
    =cell sources
    =cell content as RakuDoc sources, sub-directories are for content by language. See repositories
=row
    =cell canonical
    =cell canonical
    =cell sub-directory of sources containing content, only sub-dir
    that needs defining in the config file
=row
    =cell extensions
    =cell <rakudoc rakumod>
    =cell an array of file extensions containing source
=row
    =cell quiet
    =cell False
    =cell output runtime progress information
=row
    =cell with-only
    =cell ()
    =cell a list of strings or regexes, matching filenames
          only will be rendered (useful for debugging)
=row
    =cell ignore
    =cell ()
    =cell list of strings or regexes, matching files will not be rendered
=row
    =cell publication
    =cell 'publication'
    =cell directory relative to CWD where HTML and assets are rendered
=row
    =cell landing-page
    =cell 'index'
    =cell the name of the page that is the default route for a web-site
=row
    =for cell :column-span(3)
    The plugins needed are more easily kept in a separate file, typically C<02-plugins.raku>
=row
    =cell plugins
    =cell <Bulma Hilite ListFiles>
    =cell plugins attached to the Rendering engine B<I<packaged with rakuast-rakudoc-render>>
=row
    =cell plugins
    =cell plugins ,= <Graphviz FontAwesome Latex LeafletMaps>
    =cell custom blocks B<I<packaged with rakuast-rakudoc-render>>
=row
    =cell plugins
    =cell plugins ,= 'UISwitcher',
    =cell Adds multi-lingual UI B<I<packaged with Elucid8>>
=row
    =cell plugins
    =cell plugins ,= 'SCSS',
    =cell must be last plugin enabled, converts SCSS in other plugins to CSS B<I<packaged with rakuast-rakudoc-render>>
=end table

=place semantic:AUTHOR :caption<Credits>
=place semantic:VERSION

=end rakudoc
