2017-04-09 04:33:04 -04:00
|
|
|
// Copyright 2017 The Hugo Authors. All rights reserved.
|
2013-07-04 11:32:55 -04:00
|
|
|
//
|
2015-11-23 22:16:36 -05:00
|
|
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
2013-07-04 11:32:55 -04:00
|
|
|
// you may not use this file except in compliance with the License.
|
|
|
|
// You may obtain a copy of the License at
|
2015-11-23 22:16:36 -05:00
|
|
|
// http://www.apache.org/licenses/LICENSE-2.0
|
2013-07-04 11:32:55 -04:00
|
|
|
//
|
|
|
|
// Unless required by applicable law or agreed to in writing, software
|
|
|
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
|
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
|
|
// See the License for the specific language governing permissions and
|
|
|
|
// limitations under the License.
|
|
|
|
|
|
|
|
package hugolib
|
|
|
|
|
|
|
|
import (
|
2018-10-01 22:08:10 -04:00
|
|
|
"context"
|
2014-01-29 17:50:31 -05:00
|
|
|
"fmt"
|
|
|
|
"html/template"
|
|
|
|
"io"
|
2018-07-18 13:58:39 -04:00
|
|
|
"log"
|
2017-04-04 12:05:19 -04:00
|
|
|
"mime"
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
"net/url"
|
2014-01-29 17:50:31 -05:00
|
|
|
"os"
|
2014-12-27 08:11:19 -05:00
|
|
|
"path/filepath"
|
2017-04-28 03:40:50 -04:00
|
|
|
"sort"
|
2014-08-29 13:40:21 -04:00
|
|
|
"strconv"
|
2014-01-29 17:50:31 -05:00
|
|
|
"strings"
|
|
|
|
"time"
|
2014-03-31 13:23:34 -04:00
|
|
|
|
2018-10-03 08:58:09 -04:00
|
|
|
_errors "github.com/pkg/errors"
|
|
|
|
|
|
|
|
"github.com/gohugoio/hugo/common/herrors"
|
2018-07-06 08:12:10 -04:00
|
|
|
"github.com/gohugoio/hugo/common/maps"
|
2018-08-05 05:13:49 -04:00
|
|
|
"github.com/gohugoio/hugo/publisher"
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
"github.com/gohugoio/hugo/resource"
|
|
|
|
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
"github.com/gohugoio/hugo/langs"
|
|
|
|
|
|
|
|
src "github.com/gohugoio/hugo/source"
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
"golang.org/x/sync/errgroup"
|
|
|
|
|
2017-06-13 12:42:45 -04:00
|
|
|
"github.com/gohugoio/hugo/config"
|
2017-04-04 03:12:33 -04:00
|
|
|
|
2017-06-13 12:42:45 -04:00
|
|
|
"github.com/gohugoio/hugo/media"
|
2018-10-20 05:16:18 -04:00
|
|
|
"github.com/gohugoio/hugo/parser/metadecoders"
|
2017-04-04 03:12:33 -04:00
|
|
|
|
2017-08-01 06:17:51 -04:00
|
|
|
"github.com/markbates/inflect"
|
2015-01-30 14:51:06 -05:00
|
|
|
|
2016-04-20 10:28:26 -04:00
|
|
|
"github.com/fsnotify/fsnotify"
|
2017-06-13 12:42:45 -04:00
|
|
|
bp "github.com/gohugoio/hugo/bufferpool"
|
|
|
|
"github.com/gohugoio/hugo/deps"
|
|
|
|
"github.com/gohugoio/hugo/helpers"
|
hugolib: Extract date and slug from filename
This commit makes it possible to extract the date from the content filename. Also, the filenames in these cases will make for very poor permalinks, so we will also use the remaining part as the page `slug` if that value is not set in front matter.
This should make it easier to move content from Jekyll to Hugo.
To enable, put this in your `config.toml`:
```toml
[frontmatter]
date = [":filename", ":default"]
```
This commit is also a spring cleaning of how the different dates are configured in Hugo. Hugo will check for dates following the configuration from left to right, starting with `:filename` etc.
So, if you want to use the `file modification time`, this can be a good configuration:
```toml
[frontmatter]
date = [ "date",":fileModTime", ":default"]
lastmod = ["lastmod" ,":fileModTime", ":default"]
```
The current `:default` values for the different dates are
```toml
[frontmatter]
date = ["date","publishDate", "lastmod"]
lastmod = ["lastmod", "date","publishDate"]
publishDate = ["publishDate", "date"]
expiryDate = ["expiryDate"]
```
The above will now be the same as:
```toml
[frontmatter]
date = [":default"]
lastmod = [":default"]
publishDate = [":default"]
expiryDate = [":default"]
```
Note:
* We have some built-in aliases to the above: lastmod => modified, publishDate => pubdate, published and expiryDate => unpublishdate.
* If you want a new configuration for, say, `date`, you can provide only that line, and the rest will be preserved.
* All the keywords to the right that does not start with a ":" maps to front matter parameters, and can be any date param (e.g. `myCustomDateParam`).
* The keywords to the left are the **4 predefined dates in Hugo**, i.e. they are constant values.
* The current "special date handlers" are `:fileModTime` and `:filename`. We will soon add `:git` to that list.
Fixes #285
Closes #3310
Closes #3762
Closes #4340
2018-03-11 06:32:55 -04:00
|
|
|
"github.com/gohugoio/hugo/hugolib/pagemeta"
|
2017-06-13 12:42:45 -04:00
|
|
|
"github.com/gohugoio/hugo/output"
|
2017-08-19 07:16:00 -04:00
|
|
|
"github.com/gohugoio/hugo/related"
|
2017-06-13 12:42:45 -04:00
|
|
|
"github.com/gohugoio/hugo/source"
|
|
|
|
"github.com/gohugoio/hugo/tpl"
|
2017-06-13 13:07:35 -04:00
|
|
|
"github.com/spf13/afero"
|
|
|
|
"github.com/spf13/cast"
|
2014-03-31 13:23:34 -04:00
|
|
|
"github.com/spf13/nitro"
|
2014-04-05 01:26:43 -04:00
|
|
|
"github.com/spf13/viper"
|
2013-07-04 11:32:55 -04:00
|
|
|
)
|
|
|
|
|
2016-03-09 08:05:31 -05:00
|
|
|
// used to indicate if run as a test.
|
|
|
|
var testMode bool
|
|
|
|
|
2016-03-23 04:43:04 -04:00
|
|
|
var defaultTimer *nitro.B
|
2013-08-07 20:21:22 -04:00
|
|
|
|
2013-10-17 23:57:25 -04:00
|
|
|
// Site contains all the information relevant for constructing a static
|
2013-09-01 00:13:04 -04:00
|
|
|
// site. The basic flow of information is as follows:
|
|
|
|
//
|
|
|
|
// 1. A list of Files is parsed and then converted into Pages.
|
|
|
|
//
|
|
|
|
// 2. Pages contain sections (based on the file they were generated from),
|
|
|
|
// aliases and slugs (included in a pages frontmatter) which are the
|
2013-11-18 04:35:56 -05:00
|
|
|
// various targets that will get generated. There will be canonical
|
|
|
|
// listing. The canonical path can be overruled based on a pattern.
|
2013-09-01 00:13:04 -04:00
|
|
|
//
|
2014-04-08 23:15:57 -04:00
|
|
|
// 3. Taxonomies are created via configuration and will present some aspect of
|
2013-09-01 00:13:04 -04:00
|
|
|
// the final page and typically a perm url.
|
|
|
|
//
|
|
|
|
// 4. All Pages are passed through a template based on their desired
|
2013-11-18 04:35:56 -05:00
|
|
|
// layout based on numerous different elements.
|
2013-09-01 00:13:04 -04:00
|
|
|
//
|
|
|
|
// 5. The entire collection of files is written to disk.
|
2013-07-04 11:32:55 -04:00
|
|
|
type Site struct {
|
2016-08-09 14:06:15 -04:00
|
|
|
owner *HugoSites
|
|
|
|
|
2016-11-03 19:34:25 -04:00
|
|
|
*PageCollections
|
|
|
|
|
|
|
|
Taxonomies TaxonomyList
|
2016-10-31 14:53:33 -04:00
|
|
|
|
|
|
|
// Plural is what we get in the folder, so keep track of this mapping
|
|
|
|
// to get the singular form from that value.
|
|
|
|
taxonomiesPluralSingular map[string]string
|
|
|
|
|
2017-06-13 12:47:17 -04:00
|
|
|
// This is temporary, see https://github.com/gohugoio/hugo/issues/2835
|
2016-12-26 13:30:57 -05:00
|
|
|
// Maps "actors-gerard-depardieu" to "Gérard Depardieu" when preserveTaxonomyNames
|
|
|
|
// is set.
|
|
|
|
taxonomiesOrigKey map[string]string
|
|
|
|
|
2017-03-03 04:47:43 -05:00
|
|
|
Sections Taxonomy
|
|
|
|
Info SiteInfo
|
|
|
|
Menus Menus
|
|
|
|
timer *nitro.B
|
|
|
|
|
2017-03-06 07:18:33 -05:00
|
|
|
layoutHandler *output.LayoutHandler
|
|
|
|
|
2017-03-03 04:47:43 -05:00
|
|
|
draftCount int
|
|
|
|
futureCount int
|
|
|
|
expiredCount int
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
|
|
|
|
Data map[string]interface{}
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
Language *langs.Language
|
2017-01-03 11:28:51 -05:00
|
|
|
|
2017-02-18 04:02:12 -05:00
|
|
|
disabledKinds map[string]bool
|
|
|
|
|
2017-03-22 06:34:17 -04:00
|
|
|
// Output formats defined in site config per Page Kind, or some defaults
|
|
|
|
// if not set.
|
|
|
|
// Output formats defined in Page front matter will override these.
|
|
|
|
outputFormats map[string]output.Formats
|
2017-03-09 13:19:29 -05:00
|
|
|
|
2017-04-04 03:12:33 -04:00
|
|
|
// All the output formats and media types available for this site.
|
|
|
|
// These values will be merged from the Hugo defaults, the site config and,
|
|
|
|
// finally, the language settings.
|
|
|
|
outputFormatsConfig output.Formats
|
|
|
|
mediaTypesConfig media.Types
|
|
|
|
|
2018-07-18 13:58:39 -04:00
|
|
|
siteConfig SiteConfig
|
|
|
|
|
hugolib: Extract date and slug from filename
This commit makes it possible to extract the date from the content filename. Also, the filenames in these cases will make for very poor permalinks, so we will also use the remaining part as the page `slug` if that value is not set in front matter.
This should make it easier to move content from Jekyll to Hugo.
To enable, put this in your `config.toml`:
```toml
[frontmatter]
date = [":filename", ":default"]
```
This commit is also a spring cleaning of how the different dates are configured in Hugo. Hugo will check for dates following the configuration from left to right, starting with `:filename` etc.
So, if you want to use the `file modification time`, this can be a good configuration:
```toml
[frontmatter]
date = [ "date",":fileModTime", ":default"]
lastmod = ["lastmod" ,":fileModTime", ":default"]
```
The current `:default` values for the different dates are
```toml
[frontmatter]
date = ["date","publishDate", "lastmod"]
lastmod = ["lastmod", "date","publishDate"]
publishDate = ["publishDate", "date"]
expiryDate = ["expiryDate"]
```
The above will now be the same as:
```toml
[frontmatter]
date = [":default"]
lastmod = [":default"]
publishDate = [":default"]
expiryDate = [":default"]
```
Note:
* We have some built-in aliases to the above: lastmod => modified, publishDate => pubdate, published and expiryDate => unpublishdate.
* If you want a new configuration for, say, `date`, you can provide only that line, and the rest will be preserved.
* All the keywords to the right that does not start with a ":" maps to front matter parameters, and can be any date param (e.g. `myCustomDateParam`).
* The keywords to the left are the **4 predefined dates in Hugo**, i.e. they are constant values.
* The current "special date handlers" are `:fileModTime` and `:filename`. We will soon add `:git` to that list.
Fixes #285
Closes #3310
Closes #3762
Closes #4340
2018-03-11 06:32:55 -04:00
|
|
|
// How to handle page front matter.
|
|
|
|
frontmatterHandler pagemeta.FrontMatterHandler
|
|
|
|
|
2017-04-28 03:40:50 -04:00
|
|
|
// We render each site for all the relevant output formats in serial with
|
|
|
|
// this rendering context pointing to the current one.
|
|
|
|
rc *siteRenderingContext
|
|
|
|
|
|
|
|
// The output formats that we need to render this site in. This slice
|
|
|
|
// will be fixed once set.
|
|
|
|
// This will be the union of Site.Pages' outputFormats.
|
|
|
|
// This slice will be sorted.
|
|
|
|
renderFormats output.Formats
|
|
|
|
|
2017-01-03 11:28:51 -05:00
|
|
|
// Logger etc.
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
*deps.Deps `json:"-"`
|
2017-03-24 04:19:51 -04:00
|
|
|
|
2017-07-30 11:46:04 -04:00
|
|
|
// The func used to title case titles.
|
|
|
|
titleFunc func(s string) string
|
|
|
|
|
2017-08-19 07:16:00 -04:00
|
|
|
relatedDocsHandler *relatedDocsHandler
|
2018-07-18 13:58:39 -04:00
|
|
|
siteRefLinker
|
2018-10-18 04:21:23 -04:00
|
|
|
// Set in some tests
|
|
|
|
shortcodePlaceholderFunc func() string
|
2018-08-05 05:13:49 -04:00
|
|
|
|
|
|
|
publisher publisher.Publisher
|
2017-03-24 04:19:51 -04:00
|
|
|
}
|
|
|
|
|
2017-04-28 03:40:50 -04:00
|
|
|
type siteRenderingContext struct {
|
|
|
|
output.Format
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *Site) initRenderFormats() {
|
|
|
|
formatSet := make(map[string]bool)
|
|
|
|
formats := output.Formats{}
|
|
|
|
for _, p := range s.Pages {
|
|
|
|
for _, f := range p.outputFormats {
|
|
|
|
if !formatSet[f.Name] {
|
|
|
|
formats = append(formats, f)
|
|
|
|
formatSet[f.Name] = true
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
sort.Sort(formats)
|
|
|
|
s.renderFormats = formats
|
|
|
|
}
|
|
|
|
|
2017-02-18 04:02:12 -05:00
|
|
|
func (s *Site) isEnabled(kind string) bool {
|
|
|
|
if kind == kindUnknown {
|
|
|
|
panic("Unknown kind")
|
|
|
|
}
|
|
|
|
return !s.disabledKinds[kind]
|
|
|
|
}
|
|
|
|
|
2016-08-07 18:12:06 -04:00
|
|
|
// reset returns a new Site prepared for rebuild.
|
|
|
|
func (s *Site) reset() *Site {
|
2017-03-09 13:19:29 -05:00
|
|
|
return &Site{Deps: s.Deps,
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
layoutHandler: output.NewLayoutHandler(),
|
2017-04-04 03:12:33 -04:00
|
|
|
disabledKinds: s.disabledKinds,
|
2017-07-30 11:46:04 -04:00
|
|
|
titleFunc: s.titleFunc,
|
2017-08-19 07:16:00 -04:00
|
|
|
relatedDocsHandler: newSearchIndexHandler(s.relatedDocsHandler.cfg),
|
2018-07-18 13:58:39 -04:00
|
|
|
siteRefLinker: s.siteRefLinker,
|
2017-04-04 03:12:33 -04:00
|
|
|
outputFormats: s.outputFormats,
|
2018-04-23 23:57:33 -04:00
|
|
|
rc: s.rc,
|
2017-04-04 03:12:33 -04:00
|
|
|
outputFormatsConfig: s.outputFormatsConfig,
|
hugolib: Extract date and slug from filename
This commit makes it possible to extract the date from the content filename. Also, the filenames in these cases will make for very poor permalinks, so we will also use the remaining part as the page `slug` if that value is not set in front matter.
This should make it easier to move content from Jekyll to Hugo.
To enable, put this in your `config.toml`:
```toml
[frontmatter]
date = [":filename", ":default"]
```
This commit is also a spring cleaning of how the different dates are configured in Hugo. Hugo will check for dates following the configuration from left to right, starting with `:filename` etc.
So, if you want to use the `file modification time`, this can be a good configuration:
```toml
[frontmatter]
date = [ "date",":fileModTime", ":default"]
lastmod = ["lastmod" ,":fileModTime", ":default"]
```
The current `:default` values for the different dates are
```toml
[frontmatter]
date = ["date","publishDate", "lastmod"]
lastmod = ["lastmod", "date","publishDate"]
publishDate = ["publishDate", "date"]
expiryDate = ["expiryDate"]
```
The above will now be the same as:
```toml
[frontmatter]
date = [":default"]
lastmod = [":default"]
publishDate = [":default"]
expiryDate = [":default"]
```
Note:
* We have some built-in aliases to the above: lastmod => modified, publishDate => pubdate, published and expiryDate => unpublishdate.
* If you want a new configuration for, say, `date`, you can provide only that line, and the rest will be preserved.
* All the keywords to the right that does not start with a ":" maps to front matter parameters, and can be any date param (e.g. `myCustomDateParam`).
* The keywords to the left are the **4 predefined dates in Hugo**, i.e. they are constant values.
* The current "special date handlers" are `:fileModTime` and `:filename`. We will soon add `:git` to that list.
Fixes #285
Closes #3310
Closes #3762
Closes #4340
2018-03-11 06:32:55 -04:00
|
|
|
frontmatterHandler: s.frontmatterHandler,
|
2017-04-04 03:12:33 -04:00
|
|
|
mediaTypesConfig: s.mediaTypesConfig,
|
|
|
|
Language: s.Language,
|
|
|
|
owner: s.owner,
|
2018-08-05 05:13:49 -04:00
|
|
|
publisher: s.publisher,
|
2018-07-18 13:58:39 -04:00
|
|
|
siteConfig: s.siteConfig,
|
2017-04-04 03:12:33 -04:00
|
|
|
PageCollections: newPageCollections()}
|
2018-07-18 13:58:39 -04:00
|
|
|
|
2016-07-26 04:24:27 -04:00
|
|
|
}
|
|
|
|
|
2017-01-10 04:55:03 -05:00
|
|
|
// newSite creates a new site with the given configuration.
|
|
|
|
func newSite(cfg deps.DepsCfg) (*Site, error) {
|
2016-11-03 19:34:25 -04:00
|
|
|
c := newPageCollections()
|
2017-01-09 19:36:59 -05:00
|
|
|
|
2017-01-10 04:55:03 -05:00
|
|
|
if cfg.Language == nil {
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
cfg.Language = langs.NewDefaultLanguage(cfg.Cfg)
|
2017-01-09 19:36:59 -05:00
|
|
|
}
|
|
|
|
|
2017-02-18 04:02:12 -05:00
|
|
|
disabledKinds := make(map[string]bool)
|
|
|
|
for _, disabled := range cast.ToStringSlice(cfg.Language.Get("disableKinds")) {
|
|
|
|
disabledKinds[disabled] = true
|
|
|
|
}
|
|
|
|
|
2017-04-04 03:12:33 -04:00
|
|
|
var (
|
|
|
|
mediaTypesConfig []map[string]interface{}
|
|
|
|
outputFormatsConfig []map[string]interface{}
|
|
|
|
|
|
|
|
siteOutputFormatsConfig output.Formats
|
|
|
|
siteMediaTypesConfig media.Types
|
|
|
|
err error
|
|
|
|
)
|
|
|
|
|
|
|
|
// Add language last, if set, so it gets precedence.
|
|
|
|
for _, cfg := range []config.Provider{cfg.Cfg, cfg.Language} {
|
|
|
|
if cfg.IsSet("mediaTypes") {
|
|
|
|
mediaTypesConfig = append(mediaTypesConfig, cfg.GetStringMap("mediaTypes"))
|
|
|
|
}
|
|
|
|
if cfg.IsSet("outputFormats") {
|
|
|
|
outputFormatsConfig = append(outputFormatsConfig, cfg.GetStringMap("outputFormats"))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
siteMediaTypesConfig, err = media.DecodeTypes(mediaTypesConfig...)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
|
|
|
siteOutputFormatsConfig, err = output.DecodeFormats(siteMediaTypesConfig, outputFormatsConfig...)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
2017-03-22 06:34:17 -04:00
|
|
|
|
2017-04-04 03:12:33 -04:00
|
|
|
outputFormats, err := createSiteOutputFormats(siteOutputFormatsConfig, cfg.Language)
|
2017-03-22 06:34:17 -04:00
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
2017-03-09 13:19:29 -05:00
|
|
|
|
2017-08-19 07:16:00 -04:00
|
|
|
var relatedContentConfig related.Config
|
|
|
|
|
|
|
|
if cfg.Language.IsSet("related") {
|
|
|
|
relatedContentConfig, err = related.DecodeConfig(cfg.Language.Get("related"))
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
relatedContentConfig = related.DefaultConfig
|
|
|
|
taxonomies := cfg.Language.GetStringMapString("taxonomies")
|
|
|
|
if _, found := taxonomies["tag"]; found {
|
|
|
|
relatedContentConfig.Add(related.IndexConfig{Name: "tags", Weight: 80})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-07-30 11:46:04 -04:00
|
|
|
titleFunc := helpers.GetTitleFunc(cfg.Language.GetString("titleCaseStyle"))
|
|
|
|
|
hugolib: Extract date and slug from filename
This commit makes it possible to extract the date from the content filename. Also, the filenames in these cases will make for very poor permalinks, so we will also use the remaining part as the page `slug` if that value is not set in front matter.
This should make it easier to move content from Jekyll to Hugo.
To enable, put this in your `config.toml`:
```toml
[frontmatter]
date = [":filename", ":default"]
```
This commit is also a spring cleaning of how the different dates are configured in Hugo. Hugo will check for dates following the configuration from left to right, starting with `:filename` etc.
So, if you want to use the `file modification time`, this can be a good configuration:
```toml
[frontmatter]
date = [ "date",":fileModTime", ":default"]
lastmod = ["lastmod" ,":fileModTime", ":default"]
```
The current `:default` values for the different dates are
```toml
[frontmatter]
date = ["date","publishDate", "lastmod"]
lastmod = ["lastmod", "date","publishDate"]
publishDate = ["publishDate", "date"]
expiryDate = ["expiryDate"]
```
The above will now be the same as:
```toml
[frontmatter]
date = [":default"]
lastmod = [":default"]
publishDate = [":default"]
expiryDate = [":default"]
```
Note:
* We have some built-in aliases to the above: lastmod => modified, publishDate => pubdate, published and expiryDate => unpublishdate.
* If you want a new configuration for, say, `date`, you can provide only that line, and the rest will be preserved.
* All the keywords to the right that does not start with a ":" maps to front matter parameters, and can be any date param (e.g. `myCustomDateParam`).
* The keywords to the left are the **4 predefined dates in Hugo**, i.e. they are constant values.
* The current "special date handlers" are `:fileModTime` and `:filename`. We will soon add `:git` to that list.
Fixes #285
Closes #3310
Closes #3762
Closes #4340
2018-03-11 06:32:55 -04:00
|
|
|
frontMatterHandler, err := pagemeta.NewFrontmatterHandler(cfg.Logger, cfg.Cfg)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
2017-03-09 13:19:29 -05:00
|
|
|
s := &Site{
|
2017-04-04 03:12:33 -04:00
|
|
|
PageCollections: c,
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
layoutHandler: output.NewLayoutHandler(),
|
2017-04-04 03:12:33 -04:00
|
|
|
Language: cfg.Language,
|
|
|
|
disabledKinds: disabledKinds,
|
2017-07-30 11:46:04 -04:00
|
|
|
titleFunc: titleFunc,
|
2017-08-19 07:16:00 -04:00
|
|
|
relatedDocsHandler: newSearchIndexHandler(relatedContentConfig),
|
2017-04-04 03:12:33 -04:00
|
|
|
outputFormats: outputFormats,
|
2018-04-23 23:57:33 -04:00
|
|
|
rc: &siteRenderingContext{output.HTMLFormat},
|
2017-04-04 03:12:33 -04:00
|
|
|
outputFormatsConfig: siteOutputFormatsConfig,
|
|
|
|
mediaTypesConfig: siteMediaTypesConfig,
|
hugolib: Extract date and slug from filename
This commit makes it possible to extract the date from the content filename. Also, the filenames in these cases will make for very poor permalinks, so we will also use the remaining part as the page `slug` if that value is not set in front matter.
This should make it easier to move content from Jekyll to Hugo.
To enable, put this in your `config.toml`:
```toml
[frontmatter]
date = [":filename", ":default"]
```
This commit is also a spring cleaning of how the different dates are configured in Hugo. Hugo will check for dates following the configuration from left to right, starting with `:filename` etc.
So, if you want to use the `file modification time`, this can be a good configuration:
```toml
[frontmatter]
date = [ "date",":fileModTime", ":default"]
lastmod = ["lastmod" ,":fileModTime", ":default"]
```
The current `:default` values for the different dates are
```toml
[frontmatter]
date = ["date","publishDate", "lastmod"]
lastmod = ["lastmod", "date","publishDate"]
publishDate = ["publishDate", "date"]
expiryDate = ["expiryDate"]
```
The above will now be the same as:
```toml
[frontmatter]
date = [":default"]
lastmod = [":default"]
publishDate = [":default"]
expiryDate = [":default"]
```
Note:
* We have some built-in aliases to the above: lastmod => modified, publishDate => pubdate, published and expiryDate => unpublishdate.
* If you want a new configuration for, say, `date`, you can provide only that line, and the rest will be preserved.
* All the keywords to the right that does not start with a ":" maps to front matter parameters, and can be any date param (e.g. `myCustomDateParam`).
* The keywords to the left are the **4 predefined dates in Hugo**, i.e. they are constant values.
* The current "special date handlers" are `:fileModTime` and `:filename`. We will soon add `:git` to that list.
Fixes #285
Closes #3310
Closes #3762
Closes #4340
2018-03-11 06:32:55 -04:00
|
|
|
frontmatterHandler: frontMatterHandler,
|
2017-03-09 13:19:29 -05:00
|
|
|
}
|
2016-10-24 07:45:30 -04:00
|
|
|
|
2017-01-10 04:55:03 -05:00
|
|
|
return s, nil
|
2016-07-26 04:24:27 -04:00
|
|
|
|
2013-07-04 11:32:55 -04:00
|
|
|
}
|
|
|
|
|
2017-01-10 04:55:03 -05:00
|
|
|
// NewSite creates a new site with the given dependency configuration.
|
|
|
|
// The site will have a template system loaded and ready to use.
|
|
|
|
// Note: This is mainly used in single site tests.
|
|
|
|
func NewSite(cfg deps.DepsCfg) (*Site, error) {
|
|
|
|
s, err := newSite(cfg)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
2016-08-01 17:04:44 -04:00
|
|
|
}
|
|
|
|
|
2018-07-18 13:58:39 -04:00
|
|
|
if err = applyDeps(cfg, s); err != nil {
|
2017-01-10 04:55:03 -05:00
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
|
|
|
return s, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
// NewSiteDefaultLang creates a new site in the default language.
|
|
|
|
// The site will have a template system loaded and ready to use.
|
|
|
|
// Note: This is mainly used in single site tests.
|
2018-03-18 06:07:24 -04:00
|
|
|
// TODO(bep) test refactor -- remove
|
2017-03-27 14:43:49 -04:00
|
|
|
func NewSiteDefaultLang(withTemplate ...func(templ tpl.TemplateHandler) error) (*Site, error) {
|
2017-02-04 22:20:06 -05:00
|
|
|
v := viper.New()
|
2017-09-25 02:59:02 -04:00
|
|
|
if err := loadDefaultSettingsFor(v); err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
return newSiteForLang(langs.NewDefaultLanguage(v), withTemplate...)
|
2017-01-10 04:55:03 -05:00
|
|
|
}
|
|
|
|
|
2017-02-15 04:00:34 -05:00
|
|
|
// NewEnglishSite creates a new site in English language.
|
2017-01-10 04:55:03 -05:00
|
|
|
// The site will have a template system loaded and ready to use.
|
|
|
|
// Note: This is mainly used in single site tests.
|
2018-03-18 06:07:24 -04:00
|
|
|
// TODO(bep) test refactor -- remove
|
2017-03-27 14:43:49 -04:00
|
|
|
func NewEnglishSite(withTemplate ...func(templ tpl.TemplateHandler) error) (*Site, error) {
|
2017-02-04 22:20:06 -05:00
|
|
|
v := viper.New()
|
2017-09-25 02:59:02 -04:00
|
|
|
if err := loadDefaultSettingsFor(v); err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
return newSiteForLang(langs.NewLanguage("en", v), withTemplate...)
|
2017-02-15 04:00:34 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
// newSiteForLang creates a new site in the given language.
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
func newSiteForLang(lang *langs.Language, withTemplate ...func(templ tpl.TemplateHandler) error) (*Site, error) {
|
2017-03-27 14:43:49 -04:00
|
|
|
withTemplates := func(templ tpl.TemplateHandler) error {
|
2017-01-10 04:55:03 -05:00
|
|
|
for _, wt := range withTemplate {
|
|
|
|
if err := wt(templ); err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return nil
|
2016-08-01 17:04:44 -04:00
|
|
|
}
|
2017-02-04 22:20:06 -05:00
|
|
|
|
2018-07-18 13:58:39 -04:00
|
|
|
cfg := deps.DepsCfg{WithTemplate: withTemplates, Cfg: lang}
|
2017-02-15 04:00:34 -05:00
|
|
|
|
2017-02-04 22:20:06 -05:00
|
|
|
return NewSiteForCfg(cfg)
|
2017-02-15 04:00:34 -05:00
|
|
|
|
|
|
|
}
|
|
|
|
|
2017-02-04 22:20:06 -05:00
|
|
|
// NewSiteForCfg creates a new site for the given configuration.
|
|
|
|
// The site will have a template system loaded and ready to use.
|
|
|
|
// Note: This is mainly used in single site tests.
|
|
|
|
func NewSiteForCfg(cfg deps.DepsCfg) (*Site, error) {
|
2018-07-18 13:58:39 -04:00
|
|
|
h, err := NewHugoSites(cfg)
|
2017-01-10 04:55:03 -05:00
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
2018-07-18 13:58:39 -04:00
|
|
|
return h.Sites[0], nil
|
2016-10-24 07:45:30 -04:00
|
|
|
|
2016-08-01 17:04:44 -04:00
|
|
|
}
|
|
|
|
|
2018-03-15 04:37:30 -04:00
|
|
|
type SiteInfos []*SiteInfo
|
|
|
|
|
|
|
|
// First is a convenience method to get the first Site, i.e. the main language.
|
|
|
|
func (s SiteInfos) First() *SiteInfo {
|
|
|
|
if len(s) == 0 {
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
return s[0]
|
|
|
|
}
|
|
|
|
|
2013-07-04 11:32:55 -04:00
|
|
|
type SiteInfo struct {
|
2016-11-03 19:34:25 -04:00
|
|
|
Taxonomies TaxonomyList
|
|
|
|
Authors AuthorList
|
|
|
|
Social SiteSocial
|
|
|
|
*PageCollections
|
2018-07-18 13:58:39 -04:00
|
|
|
Menus *Menus
|
|
|
|
Hugo *HugoInfo
|
|
|
|
Title string
|
|
|
|
RSSLink string
|
|
|
|
Author map[string]interface{}
|
|
|
|
LanguageCode string
|
|
|
|
Copyright string
|
|
|
|
LastChange time.Time
|
|
|
|
Permalinks PermalinkOverrides
|
|
|
|
Params map[string]interface{}
|
|
|
|
BuildDrafts bool
|
|
|
|
canonifyURLs bool
|
|
|
|
relativeURLs bool
|
|
|
|
uglyURLs func(p *Page) bool
|
|
|
|
preserveTaxonomyNames bool
|
|
|
|
Data *map[string]interface{}
|
2016-08-09 14:06:15 -04:00
|
|
|
owner *HugoSites
|
2017-01-10 04:55:03 -05:00
|
|
|
s *Site
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
Language *langs.Language
|
2016-08-08 07:55:18 -04:00
|
|
|
LanguagePrefix string
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
Languages langs.Languages
|
2016-08-08 07:55:18 -04:00
|
|
|
defaultContentLanguageInSubdir bool
|
2016-11-23 16:06:15 -05:00
|
|
|
sectionPagesMenu string
|
2014-04-23 02:52:01 -04:00
|
|
|
}
|
2014-04-23 02:55:43 -04:00
|
|
|
|
2018-07-18 13:58:39 -04:00
|
|
|
func (s *SiteInfo) Config() SiteConfig {
|
|
|
|
return s.s.siteConfig
|
|
|
|
}
|
|
|
|
|
2016-11-13 08:27:10 -05:00
|
|
|
func (s *SiteInfo) String() string {
|
|
|
|
return fmt.Sprintf("Site(%q)", s.Title)
|
|
|
|
}
|
|
|
|
|
2017-04-07 12:33:28 -04:00
|
|
|
func (s *SiteInfo) BaseURL() template.URL {
|
|
|
|
return template.URL(s.s.PathSpec.BaseURL.String())
|
|
|
|
}
|
|
|
|
|
2017-11-12 04:03:56 -05:00
|
|
|
// ServerPort returns the port part of the BaseURL, 0 if none found.
|
|
|
|
func (s *SiteInfo) ServerPort() int {
|
|
|
|
ps := s.s.PathSpec.BaseURL.URL().Port()
|
|
|
|
if ps == "" {
|
|
|
|
return 0
|
|
|
|
}
|
|
|
|
p, err := strconv.Atoi(ps)
|
|
|
|
if err != nil {
|
|
|
|
return 0
|
|
|
|
}
|
|
|
|
return p
|
|
|
|
}
|
|
|
|
|
2018-05-22 08:40:06 -04:00
|
|
|
// GoogleAnalytics is kept here for historic reasons.
|
|
|
|
func (s *SiteInfo) GoogleAnalytics() string {
|
2018-07-18 13:58:39 -04:00
|
|
|
return s.Config().Services.GoogleAnalytics.ID
|
2018-05-22 08:40:06 -04:00
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
// DisqusShortname is kept here for historic reasons.
|
|
|
|
func (s *SiteInfo) DisqusShortname() string {
|
2018-07-18 13:58:39 -04:00
|
|
|
return s.Config().Services.Disqus.Shortname
|
2016-08-07 08:03:03 -04:00
|
|
|
}
|
|
|
|
|
2014-12-09 13:33:55 -05:00
|
|
|
// SiteSocial is a place to put social details on a site level. These are the
|
|
|
|
// standard keys that themes will expect to have available, but can be
|
|
|
|
// expanded to any others on a per site basis
|
|
|
|
// github
|
|
|
|
// facebook
|
|
|
|
// facebook_admin
|
|
|
|
// twitter
|
|
|
|
// twitter_domain
|
|
|
|
// googleplus
|
|
|
|
// pinterest
|
|
|
|
// instagram
|
|
|
|
// youtube
|
|
|
|
// linkedin
|
|
|
|
type SiteSocial map[string]string
|
|
|
|
|
2017-02-19 17:53:48 -05:00
|
|
|
// Param is a convenience method to do lookups in SiteInfo's Params map.
|
2016-10-17 13:30:21 -04:00
|
|
|
//
|
|
|
|
// This method is also implemented on Page and Node.
|
|
|
|
func (s *SiteInfo) Param(key interface{}) (interface{}, error) {
|
|
|
|
keyStr, err := cast.ToStringE(key)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
keyStr = strings.ToLower(keyStr)
|
|
|
|
return s.Params[keyStr], nil
|
|
|
|
}
|
|
|
|
|
2016-08-07 08:03:03 -04:00
|
|
|
func (s *SiteInfo) IsMultiLingual() bool {
|
|
|
|
return len(s.Languages) > 1
|
|
|
|
}
|
|
|
|
|
2018-03-30 14:15:22 -04:00
|
|
|
func (s *SiteInfo) IsServer() bool {
|
|
|
|
return s.owner.running
|
|
|
|
}
|
|
|
|
|
2018-07-18 13:58:39 -04:00
|
|
|
type siteRefLinker struct {
|
|
|
|
s *Site
|
|
|
|
|
|
|
|
errorLogger *log.Logger
|
|
|
|
notFoundURL string
|
|
|
|
}
|
|
|
|
|
|
|
|
func newSiteRefLinker(cfg config.Provider, s *Site) (siteRefLinker, error) {
|
|
|
|
logger := s.Log.ERROR
|
|
|
|
|
|
|
|
notFoundURL := cfg.GetString("refLinksNotFoundURL")
|
|
|
|
errLevel := cfg.GetString("refLinksErrorLevel")
|
|
|
|
if strings.EqualFold(errLevel, "warning") {
|
|
|
|
logger = s.Log.WARN
|
|
|
|
}
|
|
|
|
return siteRefLinker{s: s, errorLogger: logger, notFoundURL: notFoundURL}, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s siteRefLinker) logNotFound(ref, what string, p *Page) {
|
|
|
|
if p != nil {
|
2018-08-24 03:23:01 -04:00
|
|
|
s.errorLogger.Printf("[%s] REF_NOT_FOUND: Ref %q: %s", s.s.Lang(), ref, what)
|
2018-07-18 13:58:39 -04:00
|
|
|
} else {
|
2018-08-24 03:23:01 -04:00
|
|
|
s.errorLogger.Printf("[%s] REF_NOT_FOUND: Ref %q from page %q: %s", s.s.Lang(), ref, p.absoluteSourceRef(), what)
|
2018-07-18 13:58:39 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *siteRefLinker) refLink(ref string, page *Page, relative bool, outputFormat string) (string, error) {
|
|
|
|
|
2015-03-11 13:34:57 -04:00
|
|
|
var refURL *url.URL
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
var err error
|
|
|
|
|
2017-07-15 05:05:14 -04:00
|
|
|
ref = filepath.ToSlash(ref)
|
|
|
|
|
2015-03-11 13:34:57 -04:00
|
|
|
refURL, err = url.Parse(ref)
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
|
|
|
|
if err != nil {
|
2018-07-18 13:58:39 -04:00
|
|
|
return s.notFoundURL, err
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
}
|
|
|
|
|
2015-03-07 06:53:20 -05:00
|
|
|
var target *Page
|
|
|
|
var link string
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
|
2015-03-11 13:34:57 -04:00
|
|
|
if refURL.Path != "" {
|
2018-07-18 13:58:39 -04:00
|
|
|
target, err := s.s.getPageNew(page, refURL.Path)
|
2018-05-29 21:35:27 -04:00
|
|
|
|
|
|
|
if err != nil {
|
2018-07-19 11:17:35 -04:00
|
|
|
s.logNotFound(refURL.Path, err.Error(), page)
|
|
|
|
return s.notFoundURL, nil
|
2018-05-29 21:35:27 -04:00
|
|
|
}
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
|
|
|
|
if target == nil {
|
2018-07-18 13:58:39 -04:00
|
|
|
s.logNotFound(refURL.Path, "page not found", page)
|
|
|
|
return s.notFoundURL, nil
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
}
|
|
|
|
|
2017-04-04 12:14:41 -04:00
|
|
|
var permalinker Permalinker = target
|
|
|
|
|
|
|
|
if outputFormat != "" {
|
|
|
|
o := target.OutputFormats().Get(outputFormat)
|
|
|
|
|
|
|
|
if o == nil {
|
2018-07-18 13:58:39 -04:00
|
|
|
s.logNotFound(refURL.Path, fmt.Sprintf("output format %q", outputFormat), page)
|
|
|
|
return s.notFoundURL, nil
|
2017-04-04 12:14:41 -04:00
|
|
|
}
|
|
|
|
permalinker = o
|
|
|
|
}
|
|
|
|
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
if relative {
|
2017-04-04 12:14:41 -04:00
|
|
|
link = permalinker.RelPermalink()
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
} else {
|
2017-04-04 12:14:41 -04:00
|
|
|
link = permalinker.Permalink()
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2015-03-11 13:34:57 -04:00
|
|
|
if refURL.Fragment != "" {
|
|
|
|
link = link + "#" + refURL.Fragment
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
|
2015-03-11 13:34:57 -04:00
|
|
|
if refURL.Path != "" && target != nil && !target.getRenderingConfig().PlainIDAnchors {
|
|
|
|
link = link + ":" + target.UniqueID()
|
|
|
|
} else if page != nil && !page.getRenderingConfig().PlainIDAnchors {
|
|
|
|
link = link + ":" + page.UniqueID()
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return link, nil
|
|
|
|
}
|
|
|
|
|
2016-01-15 18:28:48 -05:00
|
|
|
// Ref will give an absolute URL to ref in the given Page.
|
2017-04-04 12:14:41 -04:00
|
|
|
func (s *SiteInfo) Ref(ref string, page *Page, options ...string) (string, error) {
|
|
|
|
outputFormat := ""
|
|
|
|
if len(options) > 0 {
|
|
|
|
outputFormat = options[0]
|
|
|
|
}
|
|
|
|
|
2018-07-18 13:58:39 -04:00
|
|
|
return s.s.refLink(ref, page, false, outputFormat)
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
}
|
|
|
|
|
2016-01-15 18:28:48 -05:00
|
|
|
// RelRef will give an relative URL to ref in the given Page.
|
2017-04-04 12:14:41 -04:00
|
|
|
func (s *SiteInfo) RelRef(ref string, page *Page, options ...string) (string, error) {
|
|
|
|
outputFormat := ""
|
|
|
|
if len(options) > 0 {
|
|
|
|
outputFormat = options[0]
|
|
|
|
}
|
|
|
|
|
2018-07-18 13:58:39 -04:00
|
|
|
return s.s.refLink(ref, page, true, outputFormat)
|
Provide (relative) reference funcs & shortcodes.
- `.Ref` and `.RelRef` take a reference (the logical filename for a
page, including extension and/or a document fragment ID) and return
a permalink (or relative permalink) to the referenced document.
- If the reference is a page name (such as `about.md`), the page
will be discovered and the permalink will be returned: `/about/`
- If the reference is a page name with a fragment (such as
`about.md#who`), the page will be discovered and used to add the
`page.UniqueID()` to the resulting fragment and permalink:
`/about/#who:deadbeef`.
- If the reference is a fragment and `.*Ref` has been called from
a `Node` or `SiteInfo`, it will be returned as is: `#who`.
- If the reference is a fragment and `.*Ref` has been called from
a `Page`, it will be returned with the page’s unique ID:
`#who:deadbeef`.
- `.*Ref` can be called from either `Node`, `SiteInfo` (e.g.,
`Node.Site`), `Page` objects, or `ShortcodeWithPage` objects in
templates.
- `.*Ref` cannot be used in content, so two shortcodes have been
created to provide the functionality to content: `ref` and `relref`.
These are intended to be used within markup, like `[Who]({{% ref
about.md#who %}})` or `<a href="{{% ref about.md#who %}}">Who</a>`.
- There are also `ref` and `relref` template functions (used to create
the shortcodes) that expect a `Page` or `Node` object and the
reference string (e.g., `{{ relref . "about.md" }}` or `{{
"about.md" | ref . }}`). It actually looks for `.*Ref` as defined on
`Node` or `Page` objects.
- Shortcode handling had to use a *differently unique* wrapper in
`createShortcodePlaceholder` because of the way that the `ref` and
`relref` are intended to be used in content.
2014-11-24 01:15:34 -05:00
|
|
|
}
|
|
|
|
|
2016-04-07 14:03:03 -04:00
|
|
|
func (s *Site) running() bool {
|
2018-04-23 23:57:33 -04:00
|
|
|
return s.owner != nil && s.owner.running
|
2013-10-25 18:03:14 -04:00
|
|
|
}
|
|
|
|
|
2018-07-18 13:58:39 -04:00
|
|
|
func (s *Site) multilingual() *Multilingual {
|
|
|
|
return s.owner.multilingual
|
|
|
|
}
|
|
|
|
|
2013-10-03 09:44:45 -04:00
|
|
|
func init() {
|
2016-03-23 04:43:04 -04:00
|
|
|
defaultTimer = nitro.Initalize()
|
2013-10-03 09:44:45 -04:00
|
|
|
}
|
|
|
|
|
2013-08-07 20:21:22 -04:00
|
|
|
func (s *Site) timerStep(step string) {
|
2014-01-29 17:50:31 -05:00
|
|
|
if s.timer == nil {
|
2016-03-23 04:43:04 -04:00
|
|
|
s.timer = defaultTimer
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
|
|
|
s.timer.Step(step)
|
2013-07-04 11:32:55 -04:00
|
|
|
}
|
|
|
|
|
2016-08-12 18:33:17 -04:00
|
|
|
type whatChanged struct {
|
|
|
|
source bool
|
|
|
|
other bool
|
2018-01-28 05:46:48 -05:00
|
|
|
files map[string]bool
|
2016-08-12 18:33:17 -04:00
|
|
|
}
|
|
|
|
|
2017-04-04 12:05:19 -04:00
|
|
|
// RegisterMediaTypes will register the Site's media types in the mime
|
|
|
|
// package, so it will behave correctly with Hugo's built-in server.
|
|
|
|
func (s *Site) RegisterMediaTypes() {
|
|
|
|
for _, mt := range s.mediaTypesConfig {
|
2018-07-10 05:55:22 -04:00
|
|
|
for _, suffix := range mt.Suffixes {
|
|
|
|
_ = mime.AddExtensionType(mt.Delimiter+suffix, mt.Type()+"; charset=utf-8")
|
|
|
|
}
|
2017-04-04 12:05:19 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
func (s *Site) filterFileEvents(events []fsnotify.Event) []fsnotify.Event {
|
|
|
|
var filtered []fsnotify.Event
|
|
|
|
seen := make(map[fsnotify.Event]bool)
|
|
|
|
|
|
|
|
for _, ev := range events {
|
|
|
|
// Avoid processing the same event twice.
|
|
|
|
if seen[ev] {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
seen[ev] = true
|
|
|
|
|
|
|
|
if s.SourceSpec.IgnoreFile(ev.Name) {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
// Throw away any directories
|
|
|
|
isRegular, err := s.SourceSpec.IsRegularSourceFile(ev.Name)
|
|
|
|
if err != nil && os.IsNotExist(err) && (ev.Op&fsnotify.Remove == fsnotify.Remove || ev.Op&fsnotify.Rename == fsnotify.Rename) {
|
|
|
|
// Force keep of event
|
|
|
|
isRegular = true
|
|
|
|
}
|
|
|
|
if !isRegular {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
filtered = append(filtered, ev)
|
|
|
|
}
|
|
|
|
|
|
|
|
return filtered
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *Site) translateFileEvents(events []fsnotify.Event) []fsnotify.Event {
|
|
|
|
var filtered []fsnotify.Event
|
|
|
|
|
|
|
|
eventMap := make(map[string][]fsnotify.Event)
|
|
|
|
|
|
|
|
// We often get a Remove etc. followed by a Create, a Create followed by a Write.
|
|
|
|
// Remove the superflous events to mage the update logic simpler.
|
|
|
|
for _, ev := range events {
|
|
|
|
eventMap[ev.Name] = append(eventMap[ev.Name], ev)
|
|
|
|
}
|
|
|
|
|
|
|
|
for _, ev := range events {
|
|
|
|
mapped := eventMap[ev.Name]
|
|
|
|
|
|
|
|
// Keep one
|
|
|
|
found := false
|
|
|
|
var kept fsnotify.Event
|
|
|
|
for i, ev2 := range mapped {
|
|
|
|
if i == 0 {
|
|
|
|
kept = ev2
|
|
|
|
}
|
|
|
|
|
|
|
|
if ev2.Op&fsnotify.Write == fsnotify.Write {
|
|
|
|
kept = ev2
|
|
|
|
found = true
|
|
|
|
}
|
|
|
|
|
|
|
|
if !found && ev2.Op&fsnotify.Create == fsnotify.Create {
|
|
|
|
kept = ev2
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
filtered = append(filtered, kept)
|
|
|
|
}
|
|
|
|
|
|
|
|
return filtered
|
|
|
|
}
|
|
|
|
|
2016-08-08 03:05:16 -04:00
|
|
|
// reBuild partially rebuilds a site given the filesystem events.
|
2016-07-28 03:30:58 -04:00
|
|
|
// It returns whetever the content source was changed.
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
// TODO(bep) clean up/rewrite this method.
|
|
|
|
func (s *Site) processPartial(events []fsnotify.Event) (whatChanged, error) {
|
|
|
|
|
|
|
|
events = s.filterFileEvents(events)
|
|
|
|
events = s.translateFileEvents(events)
|
|
|
|
|
2017-01-10 04:55:03 -05:00
|
|
|
s.Log.DEBUG.Printf("Rebuild for events %q", events)
|
2016-07-26 08:44:37 -04:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
h := s.owner
|
|
|
|
|
2015-12-22 00:10:01 -05:00
|
|
|
s.timerStep("initialize rebuild")
|
2016-07-26 08:44:37 -04:00
|
|
|
|
2015-12-22 00:10:01 -05:00
|
|
|
// First we need to determine what changed
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
var (
|
|
|
|
sourceChanged = []fsnotify.Event{}
|
|
|
|
sourceReallyChanged = []fsnotify.Event{}
|
|
|
|
contentFilesChanged []string
|
|
|
|
tmplChanged = []fsnotify.Event{}
|
|
|
|
dataChanged = []fsnotify.Event{}
|
|
|
|
i18nChanged = []fsnotify.Event{}
|
|
|
|
shortcodesChanged = make(map[string]bool)
|
2018-01-28 05:46:48 -05:00
|
|
|
sourceFilesChanged = make(map[string]bool)
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
|
|
|
|
// prevent spamming the log on changes
|
|
|
|
logger = helpers.NewDistinctFeedbackLogger()
|
|
|
|
)
|
2016-01-28 09:31:25 -05:00
|
|
|
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
cachePartitions := make([]string, len(events))
|
|
|
|
|
|
|
|
for i, ev := range events {
|
|
|
|
cachePartitions[i] = resource.ResourceKeyPartition(ev.Name)
|
|
|
|
|
2016-07-10 13:37:27 -04:00
|
|
|
if s.isContentDirEvent(ev) {
|
2017-06-08 14:00:05 -04:00
|
|
|
logger.Println("Source changed", ev)
|
2016-01-11 12:06:52 -05:00
|
|
|
sourceChanged = append(sourceChanged, ev)
|
2015-12-22 00:10:01 -05:00
|
|
|
}
|
2016-09-11 13:47:12 -04:00
|
|
|
if s.isLayoutDirEvent(ev) {
|
2017-06-08 14:00:05 -04:00
|
|
|
logger.Println("Template changed", ev)
|
2016-01-11 12:06:52 -05:00
|
|
|
tmplChanged = append(tmplChanged, ev)
|
2017-03-10 14:54:50 -05:00
|
|
|
|
|
|
|
if strings.Contains(ev.Name, "shortcodes") {
|
|
|
|
clearIsInnerShortcodeCache()
|
|
|
|
shortcode := filepath.Base(ev.Name)
|
|
|
|
shortcode = strings.TrimSuffix(shortcode, filepath.Ext(shortcode))
|
|
|
|
shortcodesChanged[shortcode] = true
|
|
|
|
}
|
2015-12-22 00:10:01 -05:00
|
|
|
}
|
2016-07-10 13:37:27 -04:00
|
|
|
if s.isDataDirEvent(ev) {
|
2017-06-08 14:00:05 -04:00
|
|
|
logger.Println("Data changed", ev)
|
2016-01-28 09:31:25 -05:00
|
|
|
dataChanged = append(dataChanged, ev)
|
2015-12-22 00:10:01 -05:00
|
|
|
}
|
2016-09-11 13:47:12 -04:00
|
|
|
if s.isI18nEvent(ev) {
|
2017-06-08 14:00:05 -04:00
|
|
|
logger.Println("i18n changed", ev)
|
2016-07-28 03:30:58 -04:00
|
|
|
i18nChanged = append(dataChanged, ev)
|
|
|
|
}
|
2015-12-22 00:10:01 -05:00
|
|
|
}
|
|
|
|
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
// These in memory resource caches will be rebuilt on demand.
|
|
|
|
for _, s := range s.owner.Sites {
|
|
|
|
s.ResourceSpec.ResourceCache.DeletePartitions(cachePartitions...)
|
|
|
|
}
|
|
|
|
|
2017-02-04 22:20:06 -05:00
|
|
|
if len(tmplChanged) > 0 || len(i18nChanged) > 0 {
|
2017-01-10 04:55:03 -05:00
|
|
|
sites := s.owner.Sites
|
|
|
|
first := sites[0]
|
|
|
|
|
|
|
|
// TOD(bep) globals clean
|
2017-02-04 22:20:06 -05:00
|
|
|
if err := first.Deps.LoadResources(); err != nil {
|
2018-07-18 05:53:04 -04:00
|
|
|
return whatChanged{}, err
|
2017-01-10 04:55:03 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
for i := 1; i < len(sites); i++ {
|
|
|
|
site := sites[i]
|
|
|
|
var err error
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
depsCfg := deps.DepsCfg{
|
2018-08-05 05:13:49 -04:00
|
|
|
Language: site.Language,
|
|
|
|
MediaTypes: site.mediaTypesConfig,
|
|
|
|
OutputFormats: site.outputFormatsConfig,
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
}
|
|
|
|
site.Deps, err = first.Deps.ForLanguage(depsCfg)
|
2017-01-10 04:55:03 -05:00
|
|
|
if err != nil {
|
|
|
|
return whatChanged{}, err
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2015-12-22 00:10:01 -05:00
|
|
|
s.timerStep("template prep")
|
|
|
|
}
|
|
|
|
|
|
|
|
if len(dataChanged) > 0 {
|
2017-04-06 11:39:20 -04:00
|
|
|
if err := s.readDataFromSourceFS(); err != nil {
|
|
|
|
s.Log.ERROR.Println(err)
|
|
|
|
}
|
2015-12-22 00:10:01 -05:00
|
|
|
}
|
|
|
|
|
2016-03-17 10:51:52 -04:00
|
|
|
for _, ev := range sourceChanged {
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
removed := false
|
|
|
|
|
2016-03-17 10:51:52 -04:00
|
|
|
if ev.Op&fsnotify.Remove == fsnotify.Remove {
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
removed = true
|
2016-03-17 10:51:52 -04:00
|
|
|
}
|
2016-01-25 14:40:44 -05:00
|
|
|
|
2016-03-17 10:51:52 -04:00
|
|
|
// Some editors (Vim) sometimes issue only a Rename operation when writing an existing file
|
|
|
|
// Sometimes a rename operation means that file has been renamed other times it means
|
|
|
|
// it's been updated
|
|
|
|
if ev.Op&fsnotify.Rename == fsnotify.Rename {
|
|
|
|
// If the file is still on disk, it's only been updated, if it's not, it's been moved
|
2017-01-10 04:55:03 -05:00
|
|
|
if ex, err := afero.Exists(s.Fs.Source, ev.Name); !ex || err != nil {
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
removed = true
|
2016-01-11 12:06:52 -05:00
|
|
|
}
|
2016-03-17 10:51:52 -04:00
|
|
|
}
|
2018-09-19 01:48:17 -04:00
|
|
|
if removed && IsContentFile(ev.Name) {
|
2018-03-21 12:21:46 -04:00
|
|
|
h.removePageByFilename(ev.Name)
|
2017-06-07 16:31:57 -04:00
|
|
|
}
|
|
|
|
|
2016-07-28 03:30:58 -04:00
|
|
|
sourceReallyChanged = append(sourceReallyChanged, ev)
|
2018-01-28 05:46:48 -05:00
|
|
|
sourceFilesChanged[ev.Name] = true
|
2016-03-17 10:51:52 -04:00
|
|
|
}
|
2016-07-28 03:30:58 -04:00
|
|
|
|
2017-03-27 19:18:15 -04:00
|
|
|
for shortcode := range shortcodesChanged {
|
2017-03-10 14:54:50 -05:00
|
|
|
// There are certain scenarios that, when a shortcode changes,
|
|
|
|
// it isn't sufficient to just rerender the already parsed shortcode.
|
|
|
|
// One example is if the user adds a new shortcode to the content file first,
|
|
|
|
// and then creates the shortcode on the file system.
|
|
|
|
// To handle these scenarios, we must do a full reprocessing of the
|
|
|
|
// pages that keeps a reference to the changed shortcode.
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
pagesWithShortcode := h.findPagesByShortcode(shortcode)
|
2017-03-10 14:54:50 -05:00
|
|
|
for _, p := range pagesWithShortcode {
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
contentFilesChanged = append(contentFilesChanged, p.File.Filename())
|
2017-03-10 14:54:50 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
if len(sourceReallyChanged) > 0 || len(contentFilesChanged) > 0 {
|
|
|
|
var filenamesChanged []string
|
|
|
|
for _, e := range sourceReallyChanged {
|
|
|
|
filenamesChanged = append(filenamesChanged, e.Name)
|
|
|
|
}
|
|
|
|
if len(contentFilesChanged) > 0 {
|
|
|
|
filenamesChanged = append(filenamesChanged, contentFilesChanged...)
|
|
|
|
}
|
2016-01-07 21:48:13 -05:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
filenamesChanged = helpers.UniqueStrings(filenamesChanged)
|
2016-01-07 21:48:13 -05:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
if err := s.readAndProcessContent(filenamesChanged...); err != nil {
|
|
|
|
return whatChanged{}, err
|
2016-09-23 13:04:19 -04:00
|
|
|
}
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
|
2016-09-23 13:04:19 -04:00
|
|
|
}
|
|
|
|
|
2016-08-12 18:33:17 -04:00
|
|
|
changed := whatChanged{
|
2018-07-19 06:50:24 -04:00
|
|
|
source: len(sourceChanged) > 0 || len(shortcodesChanged) > 0,
|
2016-08-12 18:33:17 -04:00
|
|
|
other: len(tmplChanged) > 0 || len(i18nChanged) > 0 || len(dataChanged) > 0,
|
2018-01-28 05:46:48 -05:00
|
|
|
files: sourceFilesChanged,
|
2016-08-12 18:33:17 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
return changed, nil
|
2016-05-14 00:35:16 -04:00
|
|
|
|
2015-12-22 00:10:01 -05:00
|
|
|
}
|
|
|
|
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
func (s *Site) loadData(fs afero.Fs) (err error) {
|
|
|
|
spec := src.NewSourceSpec(s.PathSpec, fs)
|
|
|
|
fileSystem := spec.NewFilesystem("")
|
2015-01-20 17:08:01 -05:00
|
|
|
s.Data = make(map[string]interface{})
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
for _, r := range fileSystem.Files() {
|
|
|
|
if err := s.handleDataFile(r); err != nil {
|
|
|
|
return err
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
}
|
|
|
|
}
|
2015-01-20 17:08:01 -05:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
return
|
|
|
|
}
|
2015-01-20 17:08:01 -05:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
func (s *Site) handleDataFile(r source.ReadableFile) error {
|
|
|
|
var current map[string]interface{}
|
2015-04-22 12:36:07 -04:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
f, err := r.Open()
|
|
|
|
if err != nil {
|
2018-10-03 08:58:09 -04:00
|
|
|
return _errors.Wrapf(err, "Failed to open data file %q:", r.LogicalName())
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
}
|
|
|
|
defer f.Close()
|
|
|
|
|
|
|
|
// Crawl in data tree to insert data
|
|
|
|
current = s.Data
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
keyParts := strings.Split(r.Dir(), helpers.FilePathSeparator)
|
|
|
|
// The first path element is the virtual folder (typically theme name), which is
|
|
|
|
// not part of the key.
|
|
|
|
if len(keyParts) > 1 {
|
|
|
|
for _, key := range keyParts[1:] {
|
|
|
|
if key != "" {
|
|
|
|
if _, ok := current[key]; !ok {
|
|
|
|
current[key] = make(map[string]interface{})
|
|
|
|
}
|
|
|
|
current = current[key].(map[string]interface{})
|
2015-01-20 17:08:01 -05:00
|
|
|
}
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
}
|
|
|
|
}
|
2015-01-20 17:08:01 -05:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
data, err := s.readData(r)
|
|
|
|
if err != nil {
|
2018-02-02 01:35:26 -05:00
|
|
|
s.Log.ERROR.Printf("Failed to read data from %s: %s", filepath.Join(r.Path(), r.LogicalName()), err)
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
|
|
|
if data == nil {
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2018-02-11 18:34:03 -05:00
|
|
|
// filepath.Walk walks the files in lexical order, '/' comes before '.'
|
|
|
|
// this warning could happen if
|
|
|
|
// 1. A theme uses the same key; the main data folder wins
|
|
|
|
// 2. A sub folder uses the same key: the sub folder wins
|
|
|
|
higherPrecedentData := current[r.BaseFileName()]
|
|
|
|
|
|
|
|
switch data.(type) {
|
|
|
|
case nil:
|
|
|
|
// hear the crickets?
|
|
|
|
|
|
|
|
case map[string]interface{}:
|
|
|
|
|
|
|
|
switch higherPrecedentData.(type) {
|
|
|
|
case nil:
|
|
|
|
current[r.BaseFileName()] = data
|
|
|
|
case map[string]interface{}:
|
|
|
|
// merge maps: insert entries from data for keys that
|
|
|
|
// don't already exist in higherPrecedentData
|
|
|
|
higherPrecedentMap := higherPrecedentData.(map[string]interface{})
|
|
|
|
for key, value := range data.(map[string]interface{}) {
|
|
|
|
if _, exists := higherPrecedentMap[key]; exists {
|
|
|
|
s.Log.WARN.Printf("Data for key '%s' in path '%s' is overridden higher precedence data already in the data tree", key, r.Path())
|
|
|
|
} else {
|
|
|
|
higherPrecedentMap[key] = value
|
|
|
|
}
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
}
|
2018-02-11 18:34:03 -05:00
|
|
|
default:
|
|
|
|
// can't merge: higherPrecedentData is not a map
|
|
|
|
s.Log.WARN.Printf("The %T data from '%s' overridden by "+
|
|
|
|
"higher precedence %T data already in the data tree", data, r.Path(), higherPrecedentData)
|
2015-02-11 14:24:56 -05:00
|
|
|
}
|
2015-01-20 17:08:01 -05:00
|
|
|
|
2018-02-11 18:34:03 -05:00
|
|
|
case []interface{}:
|
|
|
|
if higherPrecedentData == nil {
|
|
|
|
current[r.BaseFileName()] = data
|
|
|
|
} else {
|
|
|
|
// we don't merge array data
|
|
|
|
s.Log.WARN.Printf("The %T data from '%s' overridden by "+
|
|
|
|
"higher precedence %T data already in the data tree", data, r.Path(), higherPrecedentData)
|
|
|
|
}
|
|
|
|
|
|
|
|
default:
|
|
|
|
s.Log.ERROR.Printf("unexpected data type %T in file %s", data, r.LogicalName())
|
|
|
|
}
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
|
|
|
|
return nil
|
2015-01-20 17:08:01 -05:00
|
|
|
}
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
func (s *Site) readData(f source.ReadableFile) (interface{}, error) {
|
|
|
|
file, err := f.Open()
|
|
|
|
if err != nil {
|
2018-10-03 08:58:09 -04:00
|
|
|
return nil, _errors.Wrap(err, "readData: failed to open data file")
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
}
|
|
|
|
defer file.Close()
|
|
|
|
content := helpers.ReaderToBytes(file)
|
|
|
|
|
2018-10-20 05:16:18 -04:00
|
|
|
format := metadecoders.FormatFromString(f.Extension())
|
|
|
|
return metadecoders.Unmarshal(content, format)
|
2016-07-28 03:30:58 -04:00
|
|
|
}
|
|
|
|
|
2016-04-07 14:03:03 -04:00
|
|
|
func (s *Site) readDataFromSourceFS() error {
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
err := s.loadData(s.PathSpec.BaseFs.Data.Fs)
|
2015-12-22 00:10:01 -05:00
|
|
|
s.timerStep("load data")
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
|
2016-11-10 14:55:52 -05:00
|
|
|
func (s *Site) process(config BuildCfg) (err error) {
|
2015-12-22 00:10:01 -05:00
|
|
|
if err = s.initialize(); err != nil {
|
|
|
|
return
|
|
|
|
}
|
2017-01-10 04:55:03 -05:00
|
|
|
s.timerStep("initialize")
|
2015-12-22 00:10:01 -05:00
|
|
|
|
2016-04-07 14:03:03 -04:00
|
|
|
if err = s.readDataFromSourceFS(); err != nil {
|
2015-01-20 17:08:01 -05:00
|
|
|
return
|
|
|
|
}
|
2015-02-08 15:09:14 -05:00
|
|
|
|
2016-05-14 00:35:16 -04:00
|
|
|
s.timerStep("load i18n")
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
|
|
|
|
if err := s.readAndProcessContent(); err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
s.timerStep("read and convert pages from source")
|
|
|
|
|
|
|
|
return err
|
2016-05-14 00:35:16 -04:00
|
|
|
|
2016-07-28 03:30:58 -04:00
|
|
|
}
|
|
|
|
|
2017-02-19 05:15:08 -05:00
|
|
|
func (s *Site) setupSitePages() {
|
|
|
|
var siteLastChange time.Time
|
|
|
|
|
2017-02-28 03:06:33 -05:00
|
|
|
for i, page := range s.RegularPages {
|
2018-09-24 18:06:29 -04:00
|
|
|
if i > 0 {
|
|
|
|
page.NextPage = s.RegularPages[i-1]
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2013-09-20 20:03:43 -04:00
|
|
|
|
2018-09-24 18:06:29 -04:00
|
|
|
if i < len(s.RegularPages)-1 {
|
|
|
|
page.PrevPage = s.RegularPages[i+1]
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2017-02-19 05:15:08 -05:00
|
|
|
|
|
|
|
// Determine Site.Info.LastChange
|
|
|
|
// Note that the logic to determine which date to use for Lastmod
|
|
|
|
// is already applied, so this is *the* date to use.
|
|
|
|
// We cannot just pick the last page in the default sort, because
|
|
|
|
// that may not be ordered by date.
|
|
|
|
if page.Lastmod.After(siteLastChange) {
|
|
|
|
siteLastChange = page.Lastmod
|
|
|
|
}
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2017-02-19 05:15:08 -05:00
|
|
|
|
|
|
|
s.Info.LastChange = siteLastChange
|
2013-09-20 20:03:43 -04:00
|
|
|
}
|
|
|
|
|
Only re-render the view(s) you're working on
Hugo already, in its server mode, support partial rebuilds. To put it simply: If you change `about.md`, only that content page is read and processed, then Hugo does some processing (taxonomies etc.) and the full site is rendered.
This commit covers the rendering part: We now only re-render the pages you work on, i.e. the last n pages you watched in the browser (which obviously also includes the page in the example above).
To be more specific: When you are running the hugo server in watch (aka. livereload) mode, and change a template or a content file, then we do a partial re-rendering of the following:
* The current content page (if it is a content change)
* The home page
* Up to the last 10 pages you visited on the site.
This should in most cases be enough, but if you navigate to something completely different, you may see stale content. Doing an edit will then refresh that page.
Note that this feature is enabled by default. To turn it off, run `hugo server --disableFastRender`.
Fixes #3962
See #1643
2017-10-14 07:40:43 -04:00
|
|
|
func (s *Site) render(config *BuildCfg, outFormatIdx int) (err error) {
|
2018-09-21 05:01:59 -04:00
|
|
|
// Clear the global page cache.
|
|
|
|
spc.clear()
|
2017-05-05 03:24:37 -04:00
|
|
|
|
|
|
|
if outFormatIdx == 0 {
|
|
|
|
if err = s.preparePages(); err != nil {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
s.timerStep("prepare pages")
|
|
|
|
|
2017-06-20 04:30:40 -04:00
|
|
|
// Note that even if disableAliases is set, the aliases themselves are
|
|
|
|
// preserved on page. The motivation with this is to be able to generate
|
|
|
|
// 301 redirects in a .htacess file and similar using a custom output format.
|
|
|
|
if !s.Cfg.GetBool("disableAliases") {
|
|
|
|
// Aliases must be rendered before pages.
|
|
|
|
// Some sites, Hugo docs included, have faulty alias definitions that point
|
|
|
|
// to itself or another real page. These will be overwritten in the next
|
|
|
|
// step.
|
|
|
|
if err = s.renderAliases(); err != nil {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
s.timerStep("render and write aliases")
|
2017-05-05 03:24:37 -04:00
|
|
|
}
|
2017-02-18 04:02:12 -05:00
|
|
|
|
2016-10-31 05:23:01 -04:00
|
|
|
}
|
|
|
|
|
2018-01-30 04:33:57 -05:00
|
|
|
if err = s.renderPages(config); err != nil {
|
2014-01-29 17:50:31 -05:00
|
|
|
return
|
|
|
|
}
|
2017-05-05 03:24:37 -04:00
|
|
|
|
|
|
|
s.timerStep("render and write pages")
|
2016-11-08 17:34:52 -05:00
|
|
|
|
2017-04-28 03:40:50 -04:00
|
|
|
// TODO(bep) render consider this, ref. render404 etc.
|
2017-05-05 03:24:37 -04:00
|
|
|
if outFormatIdx > 0 {
|
|
|
|
return
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2016-11-08 17:34:52 -05:00
|
|
|
|
2016-04-07 14:03:03 -04:00
|
|
|
if err = s.renderSitemap(); err != nil {
|
2014-05-06 06:50:23 -04:00
|
|
|
return
|
|
|
|
}
|
|
|
|
s.timerStep("render and write Sitemap")
|
2015-12-08 16:13:09 -05:00
|
|
|
|
2016-04-07 14:03:03 -04:00
|
|
|
if err = s.renderRobotsTXT(); err != nil {
|
2015-12-08 16:13:09 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
s.timerStep("render and write robots.txt")
|
|
|
|
|
2016-11-08 17:34:52 -05:00
|
|
|
if err = s.render404(); err != nil {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
s.timerStep("render and write 404")
|
|
|
|
|
2014-01-29 17:50:31 -05:00
|
|
|
return
|
2013-07-04 11:32:55 -04:00
|
|
|
}
|
|
|
|
|
2014-05-01 13:20:58 -04:00
|
|
|
func (s *Site) Initialise() (err error) {
|
|
|
|
return s.initialize()
|
|
|
|
}
|
|
|
|
|
2013-09-25 00:24:49 -04:00
|
|
|
func (s *Site) initialize() (err error) {
|
2016-07-28 03:30:58 -04:00
|
|
|
s.Menus = Menus{}
|
|
|
|
|
2018-05-04 04:18:45 -04:00
|
|
|
return s.initializeSiteInfo()
|
2013-09-12 19:17:53 -04:00
|
|
|
}
|
|
|
|
|
2016-08-05 10:11:03 -04:00
|
|
|
// HomeAbsURL is a convenience method giving the absolute URL to the home page.
|
2016-08-04 16:12:19 -04:00
|
|
|
func (s *SiteInfo) HomeAbsURL() string {
|
2016-08-07 16:01:55 -04:00
|
|
|
base := ""
|
2016-08-07 08:03:03 -04:00
|
|
|
if s.IsMultiLingual() {
|
2016-08-04 16:12:19 -04:00
|
|
|
base = s.Language.Lang
|
|
|
|
}
|
2017-01-10 04:55:03 -05:00
|
|
|
return s.owner.AbsURL(base, false)
|
2016-08-04 16:12:19 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
// SitemapAbsURL is a convenience method giving the absolute URL to the sitemap.
|
|
|
|
func (s *SiteInfo) SitemapAbsURL() string {
|
2017-02-04 22:20:06 -05:00
|
|
|
sitemapDefault := parseSitemap(s.s.Cfg.GetStringMap("sitemap"))
|
2016-09-30 10:24:09 -04:00
|
|
|
p := s.HomeAbsURL()
|
|
|
|
if !strings.HasSuffix(p, "/") {
|
|
|
|
p += "/"
|
|
|
|
}
|
|
|
|
p += sitemapDefault.Filename
|
|
|
|
return p
|
2016-08-04 16:12:19 -04:00
|
|
|
}
|
|
|
|
|
2018-05-04 04:18:45 -04:00
|
|
|
func (s *Site) initializeSiteInfo() error {
|
2016-07-24 07:58:27 -04:00
|
|
|
var (
|
2016-11-21 17:02:52 -05:00
|
|
|
lang = s.Language
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
languages langs.Languages
|
2016-07-24 07:58:27 -04:00
|
|
|
)
|
|
|
|
|
2016-08-08 04:12:39 -04:00
|
|
|
if s.owner != nil && s.owner.multilingual != nil {
|
|
|
|
languages = s.owner.multilingual.Languages
|
2016-07-24 07:58:27 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
params := lang.Params()
|
2014-04-05 01:26:43 -04:00
|
|
|
|
2014-05-10 20:27:49 -04:00
|
|
|
permalinks := make(PermalinkOverrides)
|
2017-02-04 22:20:06 -05:00
|
|
|
for k, v := range s.Cfg.GetStringMapString("permalinks") {
|
2016-03-24 22:12:03 -04:00
|
|
|
permalinks[k] = pathPattern(v)
|
2014-04-05 01:26:43 -04:00
|
|
|
}
|
|
|
|
|
2017-02-04 22:20:06 -05:00
|
|
|
defaultContentInSubDir := s.Cfg.GetBool("defaultContentLanguageInSubdir")
|
|
|
|
defaultContentLanguage := s.Cfg.GetString("defaultContentLanguage")
|
2016-08-08 07:55:18 -04:00
|
|
|
|
2016-05-14 00:35:16 -04:00
|
|
|
languagePrefix := ""
|
2016-08-08 07:55:18 -04:00
|
|
|
if s.multilingualEnabled() && (defaultContentInSubDir || lang.Lang != defaultContentLanguage) {
|
2016-07-24 07:58:27 -04:00
|
|
|
languagePrefix = "/" + lang.Lang
|
2016-05-14 00:35:16 -04:00
|
|
|
}
|
|
|
|
|
2018-01-11 11:46:43 -05:00
|
|
|
var uglyURLs = func(p *Page) bool {
|
|
|
|
return false
|
|
|
|
}
|
|
|
|
|
|
|
|
v := s.Cfg.Get("uglyURLs")
|
|
|
|
if v != nil {
|
2018-01-28 11:03:10 -05:00
|
|
|
switch vv := v.(type) {
|
|
|
|
case bool:
|
2018-01-11 11:46:43 -05:00
|
|
|
uglyURLs = func(p *Page) bool {
|
|
|
|
return vv
|
|
|
|
}
|
2018-01-28 11:03:10 -05:00
|
|
|
case string:
|
|
|
|
// Is what be get from CLI (--uglyURLs)
|
|
|
|
vvv := cast.ToBool(vv)
|
|
|
|
uglyURLs = func(p *Page) bool {
|
|
|
|
return vvv
|
|
|
|
}
|
|
|
|
default:
|
2018-01-11 11:46:43 -05:00
|
|
|
m := cast.ToStringMapBool(v)
|
|
|
|
uglyURLs = func(p *Page) bool {
|
|
|
|
return m[p.Section()]
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-04-24 12:18:47 -04:00
|
|
|
s.Info = SiteInfo{
|
2016-10-24 14:56:00 -04:00
|
|
|
Title: lang.GetString("title"),
|
2016-09-18 13:10:11 -04:00
|
|
|
Author: lang.GetStringMap("author"),
|
2016-08-08 07:55:18 -04:00
|
|
|
Social: lang.GetStringMapString("social"),
|
2016-10-24 14:56:00 -04:00
|
|
|
LanguageCode: lang.GetString("languageCode"),
|
2016-08-08 07:55:18 -04:00
|
|
|
Copyright: lang.GetString("copyright"),
|
|
|
|
Language: lang,
|
|
|
|
LanguagePrefix: languagePrefix,
|
|
|
|
Languages: languages,
|
|
|
|
defaultContentLanguageInSubdir: defaultContentInSubDir,
|
2016-11-23 16:06:15 -05:00
|
|
|
sectionPagesMenu: lang.GetString("sectionPagesMenu"),
|
2017-02-04 22:20:06 -05:00
|
|
|
BuildDrafts: s.Cfg.GetBool("buildDrafts"),
|
|
|
|
canonifyURLs: s.Cfg.GetBool("canonifyURLs"),
|
2017-02-20 03:52:06 -05:00
|
|
|
relativeURLs: s.Cfg.GetBool("relativeURLs"),
|
2018-01-11 11:46:43 -05:00
|
|
|
uglyURLs: uglyURLs,
|
2016-10-24 14:56:00 -04:00
|
|
|
preserveTaxonomyNames: lang.GetBool("preserveTaxonomyNames"),
|
2016-11-03 19:34:25 -04:00
|
|
|
PageCollections: s.PageCollections,
|
2016-08-08 07:55:18 -04:00
|
|
|
Menus: &s.Menus,
|
|
|
|
Params: params,
|
|
|
|
Permalinks: permalinks,
|
|
|
|
Data: &s.Data,
|
2016-08-09 14:06:15 -04:00
|
|
|
owner: s.owner,
|
2017-01-10 04:55:03 -05:00
|
|
|
s: s,
|
2018-06-10 14:53:28 -04:00
|
|
|
// TODO(bep) make this Menu and similar into delegate methods on SiteInfo
|
|
|
|
Taxonomies: s.Taxonomies,
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2016-10-24 07:45:30 -04:00
|
|
|
|
2017-05-17 12:57:44 -04:00
|
|
|
rssOutputFormat, found := s.outputFormats[KindHome].GetByName(output.RSSFormat.Name)
|
|
|
|
|
|
|
|
if found {
|
|
|
|
s.Info.RSSLink = s.permalink(rssOutputFormat.BaseFilename())
|
|
|
|
}
|
2018-05-04 04:18:45 -04:00
|
|
|
|
|
|
|
return nil
|
2013-07-04 11:32:55 -04:00
|
|
|
}
|
|
|
|
|
2016-09-11 13:47:12 -04:00
|
|
|
func (s *Site) isI18nEvent(e fsnotify.Event) bool {
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
return s.BaseFs.SourceFilesystems.IsI18n(e.Name)
|
2016-05-14 00:35:16 -04:00
|
|
|
}
|
|
|
|
|
2016-07-10 13:37:27 -04:00
|
|
|
func (s *Site) isDataDirEvent(e fsnotify.Event) bool {
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
return s.BaseFs.SourceFilesystems.IsData(e.Name)
|
2016-09-11 13:47:12 -04:00
|
|
|
}
|
|
|
|
|
2016-07-10 13:37:27 -04:00
|
|
|
func (s *Site) isLayoutDirEvent(e fsnotify.Event) bool {
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
return s.BaseFs.SourceFilesystems.IsLayout(e.Name)
|
2016-09-11 13:47:12 -04:00
|
|
|
}
|
|
|
|
|
2013-08-07 20:21:22 -04:00
|
|
|
func (s *Site) absContentDir() string {
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
return s.PathSpec.AbsPathify(s.PathSpec.ContentDir)
|
2013-08-07 20:21:22 -04:00
|
|
|
}
|
|
|
|
|
2016-07-10 13:37:27 -04:00
|
|
|
func (s *Site) isContentDirEvent(e fsnotify.Event) bool {
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
return s.BaseFs.IsContent(e.Name)
|
2013-07-04 11:32:55 -04:00
|
|
|
}
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
type contentCaptureResultHandler struct {
|
2018-01-25 11:03:29 -05:00
|
|
|
defaultContentProcessor *siteContentProcessor
|
|
|
|
contentProcessors map[string]*siteContentProcessor
|
|
|
|
}
|
|
|
|
|
|
|
|
func (c *contentCaptureResultHandler) getContentProcessor(lang string) *siteContentProcessor {
|
|
|
|
proc, found := c.contentProcessors[lang]
|
|
|
|
if found {
|
|
|
|
return proc
|
|
|
|
}
|
|
|
|
return c.defaultContentProcessor
|
2016-01-07 21:48:13 -05:00
|
|
|
}
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
func (c *contentCaptureResultHandler) handleSingles(fis ...*fileInfo) {
|
|
|
|
for _, fi := range fis {
|
2018-01-25 11:03:29 -05:00
|
|
|
proc := c.getContentProcessor(fi.Lang())
|
2018-03-24 04:19:49 -04:00
|
|
|
proc.processSingle(fi)
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2015-12-21 19:47:48 -05:00
|
|
|
}
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
func (c *contentCaptureResultHandler) handleBundles(d *bundleDirs) {
|
|
|
|
for _, b := range d.bundles {
|
2018-01-25 11:03:29 -05:00
|
|
|
proc := c.getContentProcessor(b.fi.Lang())
|
2018-03-24 04:19:49 -04:00
|
|
|
proc.processBundle(b)
|
2014-10-20 20:15:33 -04:00
|
|
|
}
|
2015-12-21 19:47:48 -05:00
|
|
|
}
|
|
|
|
|
2018-03-21 12:21:46 -04:00
|
|
|
func (c *contentCaptureResultHandler) handleCopyFiles(files ...pathLangFile) {
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
for _, proc := range c.contentProcessors {
|
2018-03-21 12:21:46 -04:00
|
|
|
proc.processAssets(files)
|
2014-09-05 06:57:32 -04:00
|
|
|
}
|
2014-08-29 13:40:21 -04:00
|
|
|
}
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
func (s *Site) readAndProcessContent(filenames ...string) error {
|
|
|
|
ctx := context.Background()
|
|
|
|
g, ctx := errgroup.WithContext(ctx)
|
2014-08-29 13:40:21 -04:00
|
|
|
|
2018-01-25 11:03:29 -05:00
|
|
|
defaultContentLanguage := s.SourceSpec.DefaultContentLanguage
|
2014-08-29 13:40:21 -04:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
contentProcessors := make(map[string]*siteContentProcessor)
|
2018-01-25 11:03:29 -05:00
|
|
|
var defaultContentProcessor *siteContentProcessor
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
sites := s.owner.langSite()
|
|
|
|
for k, v := range sites {
|
2018-03-21 12:21:46 -04:00
|
|
|
if v.Language.Disabled {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
proc := newSiteContentProcessor(ctx, len(filenames) > 0, v)
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
contentProcessors[k] = proc
|
2018-01-25 11:03:29 -05:00
|
|
|
if k == defaultContentLanguage {
|
|
|
|
defaultContentProcessor = proc
|
|
|
|
}
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
g.Go(func() error {
|
|
|
|
return proc.process(ctx)
|
|
|
|
})
|
2014-09-05 06:57:32 -04:00
|
|
|
}
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
var (
|
|
|
|
handler captureResultHandler
|
|
|
|
bundleMap *contentChangeMap
|
|
|
|
)
|
2016-01-11 10:48:23 -05:00
|
|
|
|
2018-01-25 11:03:29 -05:00
|
|
|
mainHandler := &contentCaptureResultHandler{contentProcessors: contentProcessors, defaultContentProcessor: defaultContentProcessor}
|
2016-01-11 10:48:23 -05:00
|
|
|
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
sourceSpec := source.NewSourceSpec(s.PathSpec, s.BaseFs.Content.Fs)
|
2018-03-21 12:21:46 -04:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
if s.running() {
|
|
|
|
// Need to track changes.
|
|
|
|
bundleMap = s.owner.ContentChanges
|
|
|
|
handler = &captureResultHandlerChain{handlers: []captureBundlesHandler{mainHandler, bundleMap}}
|
2014-08-29 13:40:21 -04:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
} else {
|
|
|
|
handler = mainHandler
|
2016-01-07 21:48:13 -05:00
|
|
|
}
|
2014-08-29 13:40:21 -04:00
|
|
|
|
2018-03-21 12:21:46 -04:00
|
|
|
c := newCapturer(s.Log, sourceSpec, handler, bundleMap, filenames...)
|
2016-01-08 18:37:37 -05:00
|
|
|
|
2018-03-24 04:19:49 -04:00
|
|
|
err1 := c.capture()
|
2016-01-07 21:48:13 -05:00
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
for _, proc := range contentProcessors {
|
|
|
|
proc.closeInput()
|
2014-08-29 13:40:21 -04:00
|
|
|
}
|
2014-10-20 20:15:33 -04:00
|
|
|
|
2018-03-24 04:19:49 -04:00
|
|
|
err2 := g.Wait()
|
|
|
|
|
|
|
|
if err1 != nil {
|
|
|
|
return err1
|
|
|
|
}
|
|
|
|
return err2
|
2013-07-04 11:32:55 -04:00
|
|
|
}
|
|
|
|
|
2016-04-07 14:03:03 -04:00
|
|
|
func (s *Site) buildSiteMeta() (err error) {
|
2016-11-10 14:55:52 -05:00
|
|
|
defer s.timerStep("build Site meta")
|
2016-11-03 19:34:25 -04:00
|
|
|
|
2016-11-11 03:01:47 -05:00
|
|
|
if len(s.Pages) == 0 {
|
2014-04-23 02:59:19 -04:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
s.assembleTaxonomies()
|
2016-11-03 19:34:25 -04:00
|
|
|
|
2016-11-11 03:01:47 -05:00
|
|
|
for _, p := range s.AllPages {
|
2016-11-16 11:52:03 -05:00
|
|
|
// this depends on taxonomies
|
|
|
|
p.setValuesForKind(s)
|
2016-11-03 19:34:25 -04:00
|
|
|
}
|
|
|
|
|
2014-04-23 02:59:19 -04:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
2014-04-24 18:11:08 -04:00
|
|
|
func (s *Site) getMenusFromConfig() Menus {
|
|
|
|
|
|
|
|
ret := Menus{}
|
|
|
|
|
2016-09-12 14:41:52 -04:00
|
|
|
if menus := s.Language.GetStringMap("menu"); menus != nil {
|
2014-04-24 18:11:08 -04:00
|
|
|
for name, menu := range menus {
|
|
|
|
m, err := cast.ToSliceE(menu)
|
|
|
|
if err != nil {
|
2017-01-10 04:55:03 -05:00
|
|
|
s.Log.ERROR.Printf("unable to process menus in site config\n")
|
|
|
|
s.Log.ERROR.Println(err)
|
2014-04-24 18:11:08 -04:00
|
|
|
} else {
|
|
|
|
for _, entry := range m {
|
2017-01-10 04:55:03 -05:00
|
|
|
s.Log.DEBUG.Printf("found menu: %q, in site config\n", name)
|
2014-04-24 18:11:08 -04:00
|
|
|
|
|
|
|
menuEntry := MenuEntry{Menu: name}
|
|
|
|
ime, err := cast.ToStringMapE(entry)
|
|
|
|
if err != nil {
|
2017-01-10 04:55:03 -05:00
|
|
|
s.Log.ERROR.Printf("unable to process menus in site config\n")
|
|
|
|
s.Log.ERROR.Println(err)
|
2014-04-24 18:11:08 -04:00
|
|
|
}
|
|
|
|
|
2016-03-22 19:29:39 -04:00
|
|
|
menuEntry.marshallMap(ime)
|
2015-05-09 14:54:11 -04:00
|
|
|
menuEntry.URL = s.Info.createNodeMenuEntryURL(menuEntry.URL)
|
2014-12-12 14:28:28 -05:00
|
|
|
|
2014-04-24 18:11:08 -04:00
|
|
|
if ret[name] == nil {
|
|
|
|
ret[name] = &Menu{}
|
|
|
|
}
|
2016-03-22 19:29:39 -04:00
|
|
|
*ret[name] = ret[name].add(&menuEntry)
|
2014-04-24 18:11:08 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return ret
|
|
|
|
}
|
|
|
|
return ret
|
|
|
|
}
|
|
|
|
|
2015-05-09 14:54:11 -04:00
|
|
|
func (s *SiteInfo) createNodeMenuEntryURL(in string) string {
|
|
|
|
|
|
|
|
if !strings.HasPrefix(in, "/") {
|
|
|
|
return in
|
|
|
|
}
|
|
|
|
// make it match the nodes
|
|
|
|
menuEntryURL := in
|
2017-01-10 04:55:03 -05:00
|
|
|
menuEntryURL = helpers.SanitizeURLKeepTrailingSlash(s.s.PathSpec.URLize(menuEntryURL))
|
2015-05-09 14:54:11 -04:00
|
|
|
if !s.canonifyURLs {
|
2017-04-07 12:33:28 -04:00
|
|
|
menuEntryURL = helpers.AddContextRoot(s.s.PathSpec.BaseURL.String(), menuEntryURL)
|
2015-05-09 14:54:11 -04:00
|
|
|
}
|
|
|
|
return menuEntryURL
|
|
|
|
}
|
|
|
|
|
2014-04-23 02:59:19 -04:00
|
|
|
func (s *Site) assembleMenus() {
|
2015-12-22 00:10:01 -05:00
|
|
|
s.Menus = Menus{}
|
2014-04-23 02:59:19 -04:00
|
|
|
|
|
|
|
type twoD struct {
|
|
|
|
MenuName, EntryName string
|
|
|
|
}
|
|
|
|
flat := map[twoD]*MenuEntry{}
|
|
|
|
children := map[twoD]Menu{}
|
|
|
|
|
2017-01-22 06:28:31 -05:00
|
|
|
// add menu entries from config to flat hash
|
2014-04-24 18:11:08 -04:00
|
|
|
menuConfig := s.getMenusFromConfig()
|
|
|
|
for name, menu := range menuConfig {
|
|
|
|
for _, me := range *menu {
|
2014-05-14 18:01:13 -04:00
|
|
|
flat[twoD{name, me.KeyName()}] = me
|
2014-04-24 18:11:08 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2016-11-23 16:06:15 -05:00
|
|
|
sectionPagesMenu := s.Info.sectionPagesMenu
|
2016-11-11 03:01:47 -05:00
|
|
|
pages := s.Pages
|
2017-01-22 06:28:31 -05:00
|
|
|
|
|
|
|
if sectionPagesMenu != "" {
|
|
|
|
for _, p := range pages {
|
|
|
|
if p.Kind == KindSection {
|
2017-04-09 04:33:04 -04:00
|
|
|
// From Hugo 0.22 we have nested sections, but until we get a
|
|
|
|
// feel of how that would work in this setting, let us keep
|
|
|
|
// this menu for the top level only.
|
2017-02-20 03:33:35 -05:00
|
|
|
id := p.Section()
|
|
|
|
if _, ok := flat[twoD{sectionPagesMenu, id}]; ok {
|
2017-01-22 06:28:31 -05:00
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
2017-02-20 03:33:35 -05:00
|
|
|
me := MenuEntry{Identifier: id,
|
2017-01-22 06:28:31 -05:00
|
|
|
Name: p.LinkTitle(),
|
|
|
|
Weight: p.Weight,
|
|
|
|
URL: p.RelPermalink()}
|
|
|
|
flat[twoD{sectionPagesMenu, me.KeyName()}] = &me
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2015-01-06 12:11:06 -05:00
|
|
|
|
2017-01-22 06:28:31 -05:00
|
|
|
// Add menu entries provided by pages
|
|
|
|
for _, p := range pages {
|
2014-04-23 02:59:19 -04:00
|
|
|
for name, me := range p.Menus() {
|
2014-05-14 18:01:13 -04:00
|
|
|
if _, ok := flat[twoD{name, me.KeyName()}]; ok {
|
2017-01-10 04:55:03 -05:00
|
|
|
s.Log.ERROR.Printf("Two or more menu items have the same name/identifier in Menu %q: %q.\nRename or set an unique identifier.\n", name, me.KeyName())
|
2015-01-22 11:23:01 -05:00
|
|
|
continue
|
2014-05-14 18:01:13 -04:00
|
|
|
}
|
|
|
|
flat[twoD{name, me.KeyName()}] = me
|
2014-04-23 02:59:19 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Create Children Menus First
|
|
|
|
for _, e := range flat {
|
|
|
|
if e.Parent != "" {
|
2016-03-22 19:29:39 -04:00
|
|
|
children[twoD{e.Menu, e.Parent}] = children[twoD{e.Menu, e.Parent}].add(e)
|
2014-04-23 02:59:19 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Placing Children in Parents (in flat)
|
|
|
|
for p, childmenu := range children {
|
|
|
|
_, ok := flat[twoD{p.MenuName, p.EntryName}]
|
|
|
|
if !ok {
|
2015-03-18 01:16:54 -04:00
|
|
|
// if parent does not exist, create one without a URL
|
|
|
|
flat[twoD{p.MenuName, p.EntryName}] = &MenuEntry{Name: p.EntryName, URL: ""}
|
2014-04-23 02:59:19 -04:00
|
|
|
}
|
|
|
|
flat[twoD{p.MenuName, p.EntryName}].Children = childmenu
|
|
|
|
}
|
|
|
|
|
|
|
|
// Assembling Top Level of Tree
|
|
|
|
for menu, e := range flat {
|
|
|
|
if e.Parent == "" {
|
|
|
|
_, ok := s.Menus[menu.MenuName]
|
|
|
|
if !ok {
|
|
|
|
s.Menus[menu.MenuName] = &Menu{}
|
|
|
|
}
|
2016-03-22 19:29:39 -04:00
|
|
|
*s.Menus[menu.MenuName] = s.Menus[menu.MenuName].add(e)
|
2014-04-23 02:59:19 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-01-10 04:55:03 -05:00
|
|
|
func (s *Site) getTaxonomyKey(key string) string {
|
|
|
|
if s.Info.preserveTaxonomyNames {
|
|
|
|
// Keep as is
|
|
|
|
return key
|
|
|
|
}
|
|
|
|
return s.PathSpec.MakePathSanitized(key)
|
|
|
|
}
|
2017-02-18 04:02:12 -05:00
|
|
|
|
|
|
|
// We need to create the top level taxonomy early in the build process
|
|
|
|
// to be able to determine the page Kind correctly.
|
|
|
|
func (s *Site) createTaxonomiesEntries() {
|
2014-04-08 23:15:57 -04:00
|
|
|
s.Taxonomies = make(TaxonomyList)
|
2017-02-18 04:02:12 -05:00
|
|
|
taxonomies := s.Language.GetStringMapString("taxonomies")
|
|
|
|
for _, plural := range taxonomies {
|
|
|
|
s.Taxonomies[plural] = make(Taxonomy)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *Site) assembleTaxonomies() {
|
2016-10-31 14:53:33 -04:00
|
|
|
s.taxonomiesPluralSingular = make(map[string]string)
|
2016-12-26 13:30:57 -05:00
|
|
|
s.taxonomiesOrigKey = make(map[string]string)
|
2014-01-29 17:50:31 -05:00
|
|
|
|
2016-11-18 17:21:45 -05:00
|
|
|
taxonomies := s.Language.GetStringMapString("taxonomies")
|
2016-12-26 13:30:57 -05:00
|
|
|
|
2017-01-10 04:55:03 -05:00
|
|
|
s.Log.INFO.Printf("found taxonomies: %#v\n", taxonomies)
|
2014-04-07 23:29:35 -04:00
|
|
|
|
2016-10-31 14:53:33 -04:00
|
|
|
for singular, plural := range taxonomies {
|
|
|
|
s.taxonomiesPluralSingular[plural] = singular
|
2016-11-09 14:55:42 -05:00
|
|
|
|
2016-11-11 03:01:47 -05:00
|
|
|
for _, p := range s.Pages {
|
2015-05-31 14:30:53 -04:00
|
|
|
vals := p.getParam(plural, !s.Info.preserveTaxonomyNames)
|
2018-10-02 21:54:36 -04:00
|
|
|
|
2018-10-02 23:26:08 -04:00
|
|
|
w := p.getParamToLower(plural + "_weight")
|
|
|
|
weight, err := cast.ToIntE(w)
|
2018-10-02 21:54:36 -04:00
|
|
|
if err != nil {
|
2018-10-02 23:26:08 -04:00
|
|
|
s.Log.ERROR.Printf("Unable to convert taxonomy weight %#v to int for %s", w, p.Source.File.Path())
|
2018-10-02 21:54:36 -04:00
|
|
|
// weight will equal zero, so let the flow continue
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2018-10-02 21:54:36 -04:00
|
|
|
|
2014-01-29 17:50:31 -05:00
|
|
|
if vals != nil {
|
2014-09-05 09:29:01 -04:00
|
|
|
if v, ok := vals.([]string); ok {
|
2014-01-29 17:50:31 -05:00
|
|
|
for _, idx := range v {
|
2018-10-02 21:54:36 -04:00
|
|
|
x := WeightedPage{weight, p}
|
2017-01-10 04:55:03 -05:00
|
|
|
s.Taxonomies[plural].add(s.getTaxonomyKey(idx), x)
|
2016-12-26 13:30:57 -05:00
|
|
|
if s.Info.preserveTaxonomyNames {
|
|
|
|
// Need to track the original
|
2017-01-10 04:55:03 -05:00
|
|
|
s.taxonomiesOrigKey[fmt.Sprintf("%s-%s", plural, s.PathSpec.MakePathSanitized(idx))] = idx
|
2016-12-26 13:30:57 -05:00
|
|
|
}
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2014-09-05 09:29:01 -04:00
|
|
|
} else if v, ok := vals.(string); ok {
|
2018-10-02 21:54:36 -04:00
|
|
|
x := WeightedPage{weight, p}
|
2017-01-10 04:55:03 -05:00
|
|
|
s.Taxonomies[plural].add(s.getTaxonomyKey(v), x)
|
2016-12-26 13:30:57 -05:00
|
|
|
if s.Info.preserveTaxonomyNames {
|
|
|
|
// Need to track the original
|
2017-01-10 04:55:03 -05:00
|
|
|
s.taxonomiesOrigKey[fmt.Sprintf("%s-%s", plural, s.PathSpec.MakePathSanitized(v))] = v
|
2016-12-26 13:30:57 -05:00
|
|
|
}
|
2014-01-29 17:50:31 -05:00
|
|
|
} else {
|
2017-01-10 04:55:03 -05:00
|
|
|
s.Log.ERROR.Printf("Invalid %s in %s\n", plural, p.File.Path())
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2014-04-08 23:15:57 -04:00
|
|
|
for k := range s.Taxonomies[plural] {
|
|
|
|
s.Taxonomies[plural][k].Sort()
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-04-23 02:59:19 -04:00
|
|
|
s.Info.Taxonomies = s.Taxonomies
|
|
|
|
}
|
|
|
|
|
2016-07-28 03:30:58 -04:00
|
|
|
// Prepare site for a new full build.
|
|
|
|
func (s *Site) resetBuildState() {
|
|
|
|
|
2017-08-19 07:16:00 -04:00
|
|
|
s.relatedDocsHandler = newSearchIndexHandler(s.relatedDocsHandler.cfg)
|
2016-11-09 03:58:18 -05:00
|
|
|
s.PageCollections = newPageCollectionsFromPages(s.rawAllPages)
|
2017-01-05 14:57:24 -05:00
|
|
|
// TODO(bep) get rid of this double
|
|
|
|
s.Info.PageCollections = s.PageCollections
|
2016-03-06 10:33:32 -05:00
|
|
|
|
2016-07-28 03:30:58 -04:00
|
|
|
s.draftCount = 0
|
|
|
|
s.futureCount = 0
|
2017-02-21 07:55:08 -05:00
|
|
|
|
2016-07-28 03:30:58 -04:00
|
|
|
s.expiredCount = 0
|
2016-03-06 10:33:32 -05:00
|
|
|
|
2018-07-19 06:20:01 -04:00
|
|
|
for _, p := range s.rawAllPages {
|
2017-04-09 04:33:04 -04:00
|
|
|
p.subSections = Pages{}
|
|
|
|
p.parent = nil
|
2018-07-06 08:12:10 -04:00
|
|
|
p.scratch = maps.NewScratch()
|
2018-06-05 03:32:08 -04:00
|
|
|
p.mainPageOutput = nil
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2013-07-04 11:32:55 -04:00
|
|
|
}
|
|
|
|
|
2016-11-16 11:52:03 -05:00
|
|
|
func (s *Site) kindFromSections(sections []string) string {
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
if len(sections) == 0 {
|
|
|
|
return KindSection
|
|
|
|
}
|
|
|
|
|
2016-11-01 11:47:15 -04:00
|
|
|
if _, isTaxonomy := s.Taxonomies[sections[0]]; isTaxonomy {
|
|
|
|
if len(sections) == 1 {
|
2016-11-13 05:43:23 -05:00
|
|
|
return KindTaxonomyTerm
|
2016-11-01 11:47:15 -04:00
|
|
|
}
|
2016-11-13 05:43:23 -05:00
|
|
|
return KindTaxonomy
|
2016-10-31 14:53:33 -04:00
|
|
|
}
|
2016-11-13 05:43:23 -05:00
|
|
|
return KindSection
|
2016-10-31 14:53:33 -04:00
|
|
|
}
|
|
|
|
|
2017-03-26 13:34:30 -04:00
|
|
|
func (s *Site) layouts(p *PageOutput) ([]string, error) {
|
2018-01-13 11:21:42 -05:00
|
|
|
return s.layoutHandler.For(p.layoutDescriptor, p.outputFormat)
|
2017-03-07 08:20:39 -05:00
|
|
|
}
|
|
|
|
|
2016-10-31 05:23:01 -04:00
|
|
|
func (s *Site) preparePages() error {
|
|
|
|
var errors []error
|
|
|
|
|
2016-11-11 03:01:47 -05:00
|
|
|
for _, p := range s.Pages {
|
2016-10-31 05:23:01 -04:00
|
|
|
if err := p.prepareLayouts(); err != nil {
|
|
|
|
errors = append(errors, err)
|
|
|
|
}
|
2016-10-31 13:03:02 -04:00
|
|
|
if err := p.prepareData(s); err != nil {
|
2016-10-31 05:23:01 -04:00
|
|
|
errors = append(errors, err)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2018-10-03 08:58:09 -04:00
|
|
|
return s.pickOneAndLogTheRest(errors)
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *Site) errorCollator(results <-chan error, errs chan<- error) {
|
|
|
|
var errors []error
|
|
|
|
for e := range results {
|
|
|
|
errors = append(errors, e)
|
2016-10-31 05:23:01 -04:00
|
|
|
}
|
|
|
|
|
2018-10-03 08:58:09 -04:00
|
|
|
errs <- s.pickOneAndLogTheRest(errors)
|
|
|
|
|
|
|
|
close(errs)
|
2016-10-31 05:23:01 -04:00
|
|
|
}
|
|
|
|
|
2018-10-03 08:58:09 -04:00
|
|
|
func (s *Site) pickOneAndLogTheRest(errors []error) error {
|
|
|
|
if len(errors) == 0 {
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
|
|
|
var i int
|
|
|
|
|
|
|
|
for j, err := range errors {
|
|
|
|
// If this is in server mode, we want to return an error to the client
|
|
|
|
// with a file context, if possible.
|
|
|
|
if herrors.UnwrapErrorWithFileContext(err) != nil {
|
|
|
|
i = j
|
|
|
|
break
|
2014-09-14 07:01:40 -04:00
|
|
|
}
|
|
|
|
}
|
2018-10-03 08:58:09 -04:00
|
|
|
|
|
|
|
// Log the rest, but add a threshold to avoid flooding the log.
|
|
|
|
const errLogThreshold = 5
|
|
|
|
|
|
|
|
for j, err := range errors {
|
|
|
|
if j == i {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
if j >= errLogThreshold {
|
|
|
|
break
|
|
|
|
}
|
|
|
|
|
|
|
|
s.Log.ERROR.Println(err)
|
2014-09-14 07:01:40 -04:00
|
|
|
}
|
2018-10-03 08:58:09 -04:00
|
|
|
|
|
|
|
return errors[i]
|
2013-07-04 11:32:55 -04:00
|
|
|
}
|
|
|
|
|
2014-04-10 08:10:12 -04:00
|
|
|
func (s *Site) appendThemeTemplates(in []string) []string {
|
2017-02-19 17:53:48 -05:00
|
|
|
if !s.PathSpec.ThemeSet() {
|
2016-03-17 18:36:11 -04:00
|
|
|
return in
|
|
|
|
}
|
|
|
|
|
|
|
|
out := []string{}
|
|
|
|
// First place all non internal templates
|
|
|
|
for _, t := range in {
|
|
|
|
if !strings.HasPrefix(t, "_internal/") {
|
|
|
|
out = append(out, t)
|
2014-04-10 08:10:12 -04:00
|
|
|
}
|
2016-03-17 18:36:11 -04:00
|
|
|
}
|
2014-04-10 08:10:12 -04:00
|
|
|
|
2016-03-17 18:36:11 -04:00
|
|
|
// Then place theme templates with the same names
|
|
|
|
for _, t := range in {
|
|
|
|
if !strings.HasPrefix(t, "_internal/") {
|
|
|
|
out = append(out, "theme/"+t)
|
2014-04-10 08:10:12 -04:00
|
|
|
}
|
2016-03-17 18:36:11 -04:00
|
|
|
}
|
2014-11-14 12:14:52 -05:00
|
|
|
|
2016-03-17 18:36:11 -04:00
|
|
|
// Lastly place internal templates
|
|
|
|
for _, t := range in {
|
|
|
|
if strings.HasPrefix(t, "_internal/") {
|
|
|
|
out = append(out, t)
|
2014-04-10 08:10:12 -04:00
|
|
|
}
|
|
|
|
}
|
2016-03-17 18:36:11 -04:00
|
|
|
return out
|
|
|
|
|
2014-04-10 08:10:12 -04:00
|
|
|
}
|
|
|
|
|
2018-05-29 21:35:27 -04:00
|
|
|
// GetPage looks up a page of a given type for the given ref.
|
2018-07-17 05:18:29 -04:00
|
|
|
// In Hugo <= 0.44 you had to add Page Kind (section, home) etc. as the first
|
|
|
|
// argument and then either a unix styled path (with or without a leading slash))
|
|
|
|
// or path elements separated.
|
|
|
|
// When we now remove the Kind from this API, we need to make the transition as painless
|
|
|
|
// as possible for existing sites. Most sites will use {{ .Site.GetPage "section" "my/section" }},
|
|
|
|
// i.e. 2 arguments, so we test for that.
|
|
|
|
func (s *SiteInfo) GetPage(ref ...string) (*Page, error) {
|
2018-07-19 12:26:10 -04:00
|
|
|
return s.getPageOldVersion(ref...)
|
2016-11-12 11:30:21 -05:00
|
|
|
}
|
|
|
|
|
2017-03-23 15:05:10 -04:00
|
|
|
func (s *Site) permalinkForOutputFormat(link string, f output.Format) (string, error) {
|
|
|
|
var (
|
|
|
|
baseURL string
|
|
|
|
err error
|
|
|
|
)
|
|
|
|
|
|
|
|
if f.Protocol != "" {
|
|
|
|
baseURL, err = s.PathSpec.BaseURL.WithProtocol(f.Protocol)
|
|
|
|
if err != nil {
|
|
|
|
return "", err
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
baseURL = s.PathSpec.BaseURL.String()
|
|
|
|
}
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
return s.PathSpec.PermalinkForBaseURL(link, baseURL), nil
|
2017-03-23 15:05:10 -04:00
|
|
|
}
|
|
|
|
|
2017-03-09 13:19:29 -05:00
|
|
|
func (s *Site) permalink(link string) string {
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
return s.PathSpec.PermalinkForBaseURL(link, s.PathSpec.BaseURL.String())
|
2017-03-23 15:05:10 -04:00
|
|
|
|
|
|
|
}
|
2014-10-18 14:25:10 -04:00
|
|
|
|
2018-08-05 05:13:49 -04:00
|
|
|
func (s *Site) renderAndWriteXML(statCounter *uint64, name string, targetPath string, d interface{}, layouts ...string) error {
|
|
|
|
s.Log.DEBUG.Printf("Render XML for %q to %q", name, targetPath)
|
2015-01-30 14:51:06 -05:00
|
|
|
renderBuffer := bp.GetBuffer()
|
|
|
|
defer bp.PutBuffer(renderBuffer)
|
|
|
|
renderBuffer.WriteString("<?xml version=\"1.0\" encoding=\"utf-8\" standalone=\"yes\" ?>\n")
|
2014-12-18 14:59:39 -05:00
|
|
|
|
2017-04-04 07:32:29 -04:00
|
|
|
if err := s.renderForLayouts(name, d, renderBuffer, layouts...); err != nil {
|
2018-10-03 08:58:09 -04:00
|
|
|
return err
|
2016-07-25 16:22:09 -04:00
|
|
|
}
|
|
|
|
|
2018-08-05 05:13:49 -04:00
|
|
|
var path string
|
2017-02-20 03:52:06 -05:00
|
|
|
if s.Info.relativeURLs {
|
2018-08-05 05:13:49 -04:00
|
|
|
path = helpers.GetDottedRelativePath(targetPath)
|
2015-05-15 18:11:39 -04:00
|
|
|
} else {
|
2017-11-12 04:03:56 -05:00
|
|
|
s := s.PathSpec.BaseURL.String()
|
2015-05-15 18:11:39 -04:00
|
|
|
if !strings.HasSuffix(s, "/") {
|
|
|
|
s += "/"
|
|
|
|
}
|
2018-08-05 05:13:49 -04:00
|
|
|
path = s
|
2015-05-15 18:11:39 -04:00
|
|
|
}
|
2018-08-05 05:13:49 -04:00
|
|
|
|
|
|
|
pd := publisher.Descriptor{
|
|
|
|
Src: renderBuffer,
|
|
|
|
TargetPath: targetPath,
|
|
|
|
StatCounter: statCounter,
|
|
|
|
// For the minification part of XML,
|
|
|
|
// we currently only use the MIME type.
|
|
|
|
OutputFormat: output.RSSFormat,
|
|
|
|
AbsURLPath: path,
|
2017-04-06 11:39:20 -04:00
|
|
|
}
|
2015-01-30 14:51:06 -05:00
|
|
|
|
2018-08-05 05:13:49 -04:00
|
|
|
return s.publisher.Publish(pd)
|
2015-01-30 14:51:06 -05:00
|
|
|
|
2014-11-04 00:39:37 -05:00
|
|
|
}
|
2013-10-01 22:58:15 -04:00
|
|
|
|
2018-08-05 05:13:49 -04:00
|
|
|
func (s *Site) renderAndWritePage(statCounter *uint64, name string, targetPath string, p *PageOutput, layouts ...string) error {
|
2015-01-30 15:05:05 -05:00
|
|
|
renderBuffer := bp.GetBuffer()
|
|
|
|
defer bp.PutBuffer(renderBuffer)
|
|
|
|
|
2017-04-04 07:32:29 -04:00
|
|
|
if err := s.renderForLayouts(p.Kind, p, renderBuffer, layouts...); err != nil {
|
2018-10-03 08:58:09 -04:00
|
|
|
|
|
|
|
return err
|
2016-07-25 16:22:09 -04:00
|
|
|
}
|
|
|
|
|
2017-04-23 16:03:25 -04:00
|
|
|
if renderBuffer.Len() == 0 {
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2018-08-05 05:13:49 -04:00
|
|
|
isHTML := p.outputFormat.IsHTML
|
2014-01-29 17:50:31 -05:00
|
|
|
|
2018-08-05 05:13:49 -04:00
|
|
|
var path string
|
2014-01-29 17:50:31 -05:00
|
|
|
|
2018-08-05 05:13:49 -04:00
|
|
|
if s.Info.relativeURLs {
|
|
|
|
path = helpers.GetDottedRelativePath(targetPath)
|
|
|
|
} else if s.Info.canonifyURLs {
|
|
|
|
url := s.PathSpec.BaseURL.String()
|
|
|
|
if !strings.HasSuffix(url, "/") {
|
|
|
|
url += "/"
|
|
|
|
}
|
|
|
|
path = url
|
|
|
|
}
|
|
|
|
|
|
|
|
pd := publisher.Descriptor{
|
|
|
|
Src: renderBuffer,
|
|
|
|
TargetPath: targetPath,
|
|
|
|
StatCounter: statCounter,
|
|
|
|
OutputFormat: p.outputFormat,
|
|
|
|
}
|
2014-01-29 17:50:31 -05:00
|
|
|
|
2017-04-07 05:01:36 -04:00
|
|
|
if isHTML {
|
|
|
|
if s.Info.relativeURLs || s.Info.canonifyURLs {
|
2018-08-05 05:13:49 -04:00
|
|
|
pd.AbsURLPath = path
|
2017-04-07 05:01:36 -04:00
|
|
|
}
|
2014-05-16 17:49:27 -04:00
|
|
|
|
2017-04-07 05:01:36 -04:00
|
|
|
if s.running() && s.Cfg.GetBool("watch") && !s.Cfg.GetBool("disableLiveReload") {
|
2018-08-05 05:13:49 -04:00
|
|
|
pd.LiveReloadPort = s.Cfg.GetInt("liveReloadPort")
|
2017-04-07 05:01:36 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
// For performance reasons we only inject the Hugo generator tag on the home page.
|
|
|
|
if p.IsHome() {
|
2018-08-05 05:13:49 -04:00
|
|
|
pd.AddHugoGeneratorTag = !s.Cfg.GetBool("disableHugoGeneratorInject")
|
2015-05-15 18:11:39 -04:00
|
|
|
}
|
|
|
|
|
2017-04-06 11:39:20 -04:00
|
|
|
}
|
2015-01-30 15:05:05 -05:00
|
|
|
|
2018-08-05 05:13:49 -04:00
|
|
|
return s.publisher.Publish(pd)
|
2014-11-04 00:39:37 -05:00
|
|
|
}
|
2014-01-29 17:50:31 -05:00
|
|
|
|
2017-07-14 04:26:51 -04:00
|
|
|
func (s *Site) renderForLayouts(name string, d interface{}, w io.Writer, layouts ...string) (err error) {
|
|
|
|
var templ tpl.Template
|
|
|
|
|
|
|
|
templ = s.findFirstTemplate(layouts...)
|
2017-03-27 14:43:49 -04:00
|
|
|
if templ == nil {
|
2018-10-03 08:58:09 -04:00
|
|
|
s.Log.WARN.Printf("[%s] Unable to locate layout for %q: %s\n", s.Language.Lang, name, layouts)
|
|
|
|
return nil
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
|
|
|
|
2017-07-14 04:26:51 -04:00
|
|
|
if err = templ.Execute(w, d); err != nil {
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
if p, ok := d.(*PageOutput); ok {
|
2018-10-03 08:58:09 -04:00
|
|
|
return p.errorf(err, "render of %q failed", name)
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2018-10-03 08:58:09 -04:00
|
|
|
return _errors.Wrapf(err, "render of %q failed", name)
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
2017-07-14 04:26:51 -04:00
|
|
|
return
|
2013-10-01 22:58:15 -04:00
|
|
|
}
|
|
|
|
|
2017-03-27 14:43:49 -04:00
|
|
|
func (s *Site) findFirstTemplate(layouts ...string) tpl.Template {
|
2014-04-08 23:15:57 -04:00
|
|
|
for _, layout := range layouts {
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
if templ, found := s.Tmpl.Lookup(layout); found {
|
2017-03-27 14:43:49 -04:00
|
|
|
return templ
|
2014-01-29 17:50:31 -05:00
|
|
|
}
|
|
|
|
}
|
2017-03-27 14:43:49 -04:00
|
|
|
return nil
|
2013-08-27 05:09:50 -04:00
|
|
|
}
|
|
|
|
|
:sparkles: Implement Page bundling and image handling
This commit is not the smallest in Hugo's history.
Some hightlights include:
* Page bundles (for complete articles, keeping images and content together etc.).
* Bundled images can be processed in as many versions/sizes as you need with the three methods `Resize`, `Fill` and `Fit`.
* Processed images are cached inside `resources/_gen/images` (default) in your project.
* Symbolic links (both files and dirs) are now allowed anywhere inside /content
* A new table based build summary
* The "Total in nn ms" now reports the total including the handling of the files inside /static. So if it now reports more than you're used to, it is just **more real** and probably faster than before (see below).
A site building benchmark run compared to `v0.31.1` shows that this should be slightly faster and use less memory:
```bash
▶ ./benchSite.sh "TOML,num_langs=.*,num_root_sections=5,num_pages=(500|1000),tags_per_page=5,shortcodes,render"
benchmark old ns/op new ns/op delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 101785785 78067944 -23.30%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 185481057 149159919 -19.58%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 103149918 85679409 -16.94%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 203515478 169208775 -16.86%
benchmark old allocs new allocs delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 532464 391539 -26.47%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1056549 772702 -26.87%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 555974 406630 -26.86%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 1086545 789922 -27.30%
benchmark old bytes new bytes delta
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 53243246 43598155 -18.12%
BenchmarkSiteBuilding/TOML,num_langs=1,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 105811617 86087116 -18.64%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=500,tags_per_page=5,shortcodes,render-4 54558852 44545097 -18.35%
BenchmarkSiteBuilding/TOML,num_langs=3,num_root_sections=5,num_pages=1000,tags_per_page=5,shortcodes,render-4 106903858 86978413 -18.64%
```
Fixes #3651
Closes #3158
Fixes #1014
Closes #2021
Fixes #1240
Updates #3757
2017-07-24 03:00:23 -04:00
|
|
|
func (s *Site) publish(statCounter *uint64, path string, r io.Reader) (err error) {
|
|
|
|
s.PathSpec.ProcessingStats.Incr(statCounter)
|
|
|
|
|
Add support for theme composition and inheritance
This commit adds support for theme composition and inheritance in Hugo.
With this, it helps thinking about a theme as a set of ordered components:
```toml
theme = ["my-shortcodes", "base-theme", "hyde"]
```
The theme definition example above in `config.toml` creates a theme with the 3 components with presedence from left to right.
So, Hugo will, for any given file, data entry etc., look first in the project, and then in `my-shortcode`, `base-theme` and lastly `hyde`.
Hugo uses two different algorithms to merge the filesystems, depending on the file type:
* For `i18n` and `data` files, Hugo merges deeply using the translation id and data key inside the files.
* For `static`, `layouts` (templates) and `archetypes` files, these are merged on file level. So the left-most file will be chosen.
The name used in the `theme` definition above must match a folder in `/your-site/themes`, e.g. `/your-site/themes/my-shortcodes`. There are plans to improve on this and get a URL scheme so this can be resolved automatically.
Also note that a component that is part of a theme can have its own configuration file, e.g. `config.toml`. There are currently some restrictions to what a theme component can configure:
* `params` (global and per language)
* `menu` (global and per language)
* `outputformats` and `mediatypes`
The same rules apply here: The left-most param/menu etc. with the same ID will win. There are some hidden and experimental namespace support in the above, which we will work to improve in the future, but theme authors are encouraged to create their own namespaces to avoid naming conflicts.
A final note: Themes/components can also have a `theme` definition in their `config.toml` and similar, which is the "inheritance" part of this commit's title. This is currently not supported by the Hugo theme site. We will have to wait for some "auto dependency" feature to be implemented for that to happen, but this can be a powerful feature if you want to create your own theme-variant based on others.
Fixes #4460
Fixes #4450
2018-03-01 09:01:25 -05:00
|
|
|
return helpers.WriteToDisk(filepath.Clean(path), r, s.BaseFs.PublishFs)
|
2017-03-16 04:09:26 -04:00
|
|
|
}
|
|
|
|
|
2014-08-29 13:40:21 -04:00
|
|
|
func getGoMaxProcs() int {
|
|
|
|
if gmp := os.Getenv("GOMAXPROCS"); gmp != "" {
|
|
|
|
if p, err := strconv.Atoi(gmp); err != nil {
|
|
|
|
return p
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return 1
|
|
|
|
}
|
2016-11-16 15:06:10 -05:00
|
|
|
|
2017-03-17 11:35:09 -04:00
|
|
|
func (s *Site) newNodePage(typ string, sections ...string) *Page {
|
2017-03-06 07:18:33 -05:00
|
|
|
p := &Page{
|
2018-04-19 12:06:40 -04:00
|
|
|
language: s.Language,
|
|
|
|
pageInit: &pageInit{},
|
|
|
|
pageContentInit: &pageContentInit{},
|
|
|
|
Kind: typ,
|
|
|
|
Source: Source{File: &source.FileInfo{}},
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
data: make(map[string]interface{}),
|
2018-04-19 12:06:40 -04:00
|
|
|
Site: &s.Info,
|
|
|
|
sections: sections,
|
|
|
|
s: s}
|
2017-03-17 11:35:09 -04:00
|
|
|
|
2017-03-22 06:34:17 -04:00
|
|
|
p.outputFormats = p.s.outputFormats[p.Kind]
|
2017-03-17 11:35:09 -04:00
|
|
|
|
2017-03-06 07:18:33 -05:00
|
|
|
return p
|
|
|
|
|
2016-11-16 15:06:10 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
func (s *Site) newHomePage() *Page {
|
|
|
|
p := s.newNodePage(KindHome)
|
2018-01-15 14:40:39 -05:00
|
|
|
p.title = s.Info.Title
|
2016-11-16 15:06:10 -05:00
|
|
|
pages := Pages{}
|
Add Hugo Piper with SCSS support and much more
Before this commit, you would have to use page bundles to do image processing etc. in Hugo.
This commit adds
* A new `/assets` top-level project or theme dir (configurable via `assetDir`)
* A new template func, `resources.Get` which can be used to "get a resource" that can be further processed.
This means that you can now do this in your templates (or shortcodes):
```bash
{{ $sunset := (resources.Get "images/sunset.jpg").Fill "300x200" }}
```
This also adds a new `extended` build tag that enables powerful SCSS/SASS support with source maps. To compile this from source, you will also need a C compiler installed:
```
HUGO_BUILD_TAGS=extended mage install
```
Note that you can use output of the SCSS processing later in a non-SCSSS-enabled Hugo.
The `SCSS` processor is a _Resource transformation step_ and it can be chained with the many others in a pipeline:
```bash
{{ $css := resources.Get "styles.scss" | resources.ToCSS | resources.PostCSS | resources.Minify | resources.Fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
The transformation funcs above have aliases, so it can be shortened to:
```bash
{{ $css := resources.Get "styles.scss" | toCSS | postCSS | minify | fingerprint }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Digest }}" media="screen">
```
A quick tip would be to avoid the fingerprinting part, and possibly also the not-superfast `postCSS` when you're doing development, as it allows Hugo to be smarter about the rebuilding.
Documentation will follow, but have a look at the demo repo in https://github.com/bep/hugo-sass-test
New functions to create `Resource` objects:
* `resources.Get` (see above)
* `resources.FromString`: Create a Resource from a string.
New `Resource` transformation funcs:
* `resources.ToCSS`: Compile `SCSS` or `SASS` into `CSS`.
* `resources.PostCSS`: Process your CSS with PostCSS. Config file support (project or theme or passed as an option).
* `resources.Minify`: Currently supports `css`, `js`, `json`, `html`, `svg`, `xml`.
* `resources.Fingerprint`: Creates a fingerprinted version of the given Resource with Subresource Integrity..
* `resources.Concat`: Concatenates a list of Resource objects. Think of this as a poor man's bundler.
* `resources.ExecuteAsTemplate`: Parses and executes the given Resource and data context (e.g. .Site) as a Go template.
Fixes #4381
Fixes #4903
Fixes #4858
2018-02-20 04:02:14 -05:00
|
|
|
p.data["Pages"] = pages
|
2016-11-16 15:06:10 -05:00
|
|
|
p.Pages = pages
|
|
|
|
return p
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *Site) newTaxonomyPage(plural, key string) *Page {
|
|
|
|
|
2017-03-17 11:35:09 -04:00
|
|
|
p := s.newNodePage(KindTaxonomy, plural, key)
|
2016-11-16 15:06:10 -05:00
|
|
|
|
|
|
|
if s.Info.preserveTaxonomyNames {
|
2018-09-06 09:45:29 -04:00
|
|
|
p.title = key
|
2016-11-16 15:06:10 -05:00
|
|
|
} else {
|
2018-01-15 14:40:39 -05:00
|
|
|
p.title = strings.Replace(s.titleFunc(key), "-", " ", -1)
|
2016-11-16 15:06:10 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
return p
|
|
|
|
}
|
|
|
|
|
2017-04-09 04:33:04 -04:00
|
|
|
func (s *Site) newSectionPage(name string) *Page {
|
2017-03-17 11:35:09 -04:00
|
|
|
p := s.newNodePage(KindSection, name)
|
2016-11-16 15:06:10 -05:00
|
|
|
|
2017-04-09 04:33:04 -04:00
|
|
|
sectionName := helpers.FirstUpper(name)
|
2017-02-04 22:20:06 -05:00
|
|
|
if s.Cfg.GetBool("pluralizeListTitles") {
|
2018-01-15 14:40:39 -05:00
|
|
|
p.title = inflect.Pluralize(sectionName)
|
2016-11-16 15:06:10 -05:00
|
|
|
} else {
|
2018-01-15 14:40:39 -05:00
|
|
|
p.title = sectionName
|
2016-11-16 15:06:10 -05:00
|
|
|
}
|
|
|
|
return p
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *Site) newTaxonomyTermsPage(plural string) *Page {
|
2017-03-17 11:35:09 -04:00
|
|
|
p := s.newNodePage(KindTaxonomyTerm, plural)
|
2018-01-15 14:40:39 -05:00
|
|
|
p.title = s.titleFunc(plural)
|
2016-11-16 15:06:10 -05:00
|
|
|
return p
|
|
|
|
}
|