diff --git a/.envrc b/.envrc new file mode 100644 index 0000000..90500ef --- /dev/null +++ b/.envrc @@ -0,0 +1,2 @@ +use nix +eval "$(lorri direnv)" diff --git a/.ghci b/.ghci new file mode 100644 index 0000000..992189d --- /dev/null +++ b/.ghci @@ -0,0 +1,4 @@ +:def hoogle \x -> return $ ":!hoogle --count=15 \"" ++ x ++ "\"" +:def doc \x -> return $ ":!hoogle --info \"" ++ x ++ "\"" +:set -Wall +:set -fno-warn-type-defaults diff --git a/.github/FUNDING.yml b/.github/FUNDING.yml new file mode 100644 index 0000000..ba79d38 --- /dev/null +++ b/.github/FUNDING.yml @@ -0,0 +1,3 @@ +# These are supported funding model platforms + +github: rpearce diff --git a/.github/dependabot.yml b/.github/dependabot.yml new file mode 100644 index 0000000..1f97b0b --- /dev/null +++ b/.github/dependabot.yml @@ -0,0 +1,13 @@ +version: 2 +updates: + +- package-ecosystem: github-actions + directory: "/" + schedule: + interval: daily + time: '00:00' + timezone: UTC + open-pull-requests-limit: 10 + commit-message: + prefix: "chore" + include: "scope" diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml new file mode 100644 index 0000000..5802c51 --- /dev/null +++ b/.github/workflows/main.yml @@ -0,0 +1,55 @@ +name: CI + +on: + pull_request: + push: + +jobs: + build: + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v2 + + - name: Install Nix + uses: cachix/install-nix-action@v11 + with: + skip_adding_nixpkgs_channel: true + + - name: Build with cachix + uses: cachix/cachix-action@v6 + with: + name: my-site + signingKey: ${{ secrets.CACHIX_SIGNING_KEY }} + #authToken: ${{ secrets.CACHIX_AUTH_TOKEN }} + + - run: nix-build + - run: nix-shell --run "echo OK" + + - name: Artifact pages + uses: actions/upload-artifact@v2 + with: + name: pages + path: result/dist + + deploy: + if: github.ref == 'refs/heads/master' + runs-on: ubuntu-latest + needs: [build] + + steps: + - name: Download artifact + uses: actions/download-artifact@v2 + with: + name: pages + path: result + + - name: GitHub Pages + if: success() + uses: crazy-max/ghaction-github-pages@v2 + with: + build_dir: result + target_branch: gh-pages + keep_history: false + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..e6d56f2 --- /dev/null +++ b/.gitignore @@ -0,0 +1,7 @@ +.ghc.environment.* +.pre-commit-config.yaml +dist +dist-newstyle +hakyll-cache +node_modules +result diff --git a/README.md b/README.md index 6224274..396a24c 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,6 @@ -# hakyll-starter -Hakyll starter template +# hakyll-nix-starter + +[![built with nix](https://builtwithnix.org/badge.svg)](https://builtwithnix.org) + +[Hakyll](https://jaspervdj.be/hakyll/) + [Nix](https://nixos.org/) starter +template diff --git a/default.nix b/default.nix new file mode 100644 index 0000000..dda5d72 --- /dev/null +++ b/default.nix @@ -0,0 +1,26 @@ +let + cfg = import ./nix/default.nix {}; +in +{ pkgs ? cfg.pkgs }: + + pkgs.stdenv.mkDerivation { + name = "my-site"; + buildInputs = [ + cfg.generator + ]; + src = cfg.src; + + # https://github.com/jaspervdj/hakyll/issues/614 + # https://github.com/NixOS/nix/issues/318#issuecomment-52986702 + # https://github.com/MaxDaten/brutal-recipes/blob/source/default.nix#L24 + LOCALE_ARCHIVE = pkgs.lib.optionalString (pkgs.buildPlatform.libc == "glibc") "${pkgs.glibcLocales}/lib/locale/locale-archive"; + LANG = "en_US.UTF-8"; + + buildPhase = '' + hakyll-site build + ''; + installPhase = '' + mkdir -p "$out/dist" + cp -r ../dist/* "$out/dist" + ''; + } diff --git a/generator/LICENSE b/generator/LICENSE new file mode 100644 index 0000000..56fa0c3 --- /dev/null +++ b/generator/LICENSE @@ -0,0 +1,30 @@ +Copyright (c) 2019, Robert Pearce + +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + + * Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + + * Redistributions in binary form must reproduce the above + copyright notice, this list of conditions and the following + disclaimer in the documentation and/or other materials provided + with the distribution. + + * Neither the name of Robert Pearce nor the names of other + contributors may be used to endorse or promote products derived + from this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/generator/default.nix b/generator/default.nix new file mode 100644 index 0000000..f61076f --- /dev/null +++ b/generator/default.nix @@ -0,0 +1,3 @@ +{ pkgs }: + +(pkgs.callPackage ./hpkgs.nix {}).my-site diff --git a/generator/hakyll.patch b/generator/hakyll.patch new file mode 100644 index 0000000..e69de29 diff --git a/generator/hpkgs.nix b/generator/hpkgs.nix new file mode 100644 index 0000000..ee1f778 --- /dev/null +++ b/generator/hpkgs.nix @@ -0,0 +1,31 @@ +{ compiler ? "ghc884" +, pkgs +}: + +let + inherit (pkgs.lib.trivial) flip pipe; + inherit (pkgs.haskell.lib) appendPatch appendConfigureFlags dontCheck; + + hakyllFlags = [ "-f" "watchServer" "-f" "previewServer" ]; + + haskellPackages = pkgs.haskell.packages.${compiler}.override { + overrides = hpNew: hpOld: { + hakyll = + pipe + hpOld.hakyll + [ + (flip appendPatch ./hakyll.patch) + (flip appendConfigureFlags hakyllFlags) + ]; + + my-site = hpNew.callCabal2nix "my-site" ./. {}; + + # because hakyll is marked as broken in nixpkgs + hslua = dontCheck (hpNew.callHackage "hslua" "1.0.3.2" {}); + jira-wiki-markup = dontCheck (hpNew.callHackage "jira-wiki-markup" "1.1.4" {}); + pandoc = dontCheck (hpNew.callHackage "pandoc" "2.9.2.1" {}); + pandoc-types = dontCheck (hpNew.callHackage "pandoc-types" "1.20" {}); + }; + }; +in +haskellPackages diff --git a/generator/my-site.cabal b/generator/my-site.cabal new file mode 100644 index 0000000..43710d2 --- /dev/null +++ b/generator/my-site.cabal @@ -0,0 +1,19 @@ +cabal-version: 2.4 + +name: my-site +version: 0.1.0.0 +build-type: Simple +license: BSD-3-Clause +license-file: LICENSE + +executable hakyll-site + main-is: Main.hs + hs-source-dirs: src + build-depends: base == 4.* + , hakyll ^>= 4.13.3.0 + , pandoc >= 2.0.5 && < 2.10 + , text ^>= 1.2.4 + , time >= 1.8 && < 1.10 + other-modules: Slug + ghc-options: -Wall -threaded + default-language: Haskell2010 diff --git a/generator/shell.nix b/generator/shell.nix new file mode 100644 index 0000000..4c8c288 --- /dev/null +++ b/generator/shell.nix @@ -0,0 +1,21 @@ +let + cfg = import ../nix/default.nix {}; + hp = cfg.haskellPackages; +in +{}: + + hp.shellFor { + packages = p: [ + p.my-site + ]; + + buildInputs = with hp; [ + cabal-install + ghcid + hlint + hp.my-site + ormolu + ]; + + withHoogle = true; + } diff --git a/generator/src/Main.hs b/generator/src/Main.hs new file mode 100644 index 0000000..f9f4ddf --- /dev/null +++ b/generator/src/Main.hs @@ -0,0 +1,201 @@ +{-# LANGUAGE OverloadedStrings #-} + +import Control.Monad (forM_) +import Data.Maybe (fromMaybe) +import qualified Data.Text as T +import Hakyll +import Slug (toSlug) +import Text.Pandoc + ( Extension (Ext_auto_identifiers, Ext_fenced_code_attributes, Ext_footnotes, Ext_smart), + Extensions, + ReaderOptions, + WriterOptions, + extensionsFromList, + githubMarkdownExtensions, + readerExtensions, + writerExtensions, + ) + +-- CONFIG + +root :: String +root = + "https://mywebsite.com" + +siteName :: String +siteName = + "My Site Name" + +config :: Configuration +config = + defaultConfiguration + { destinationDirectory = "../dist", + ignoreFile = const False, + previewHost = "127.0.0.1", + previewPort = 8000, + providerDirectory = "../src", + storeDirectory = "../hakyll-cache", + tmpDirectory = "../hakyll-cache/tmp" + } + +-- BUILD + +main :: IO () +main = hakyllWith config $ do + forM_ + [ "CNAME", + "favicon.ico", + "robots.txt", + "_config.yml", + "images/*", + "js/*", + "fonts/*" + ] + $ \f -> match f $ do + route idRoute + compile copyFileCompiler + match "css/*" $ do + route idRoute + compile compressCssCompiler + match "posts/*" $ do + let ctx = constField "type" "article" <> postCtx + route $ metadataRoute titleRoute + compile $ + pandocCompilerCustom + >>= loadAndApplyTemplate "templates/post.html" ctx + >>= saveSnapshot "content" + >>= loadAndApplyTemplate "templates/default.html" ctx + match "index.html" $ do + route idRoute + compile $ do + posts <- recentFirst =<< loadAll "posts/*" + let indexCtx = + listField "posts" postCtx (return posts) + <> constField "root" root + <> constField "siteName" siteName + <> defaultContext + getResourceBody + >>= applyAsTemplate indexCtx + >>= loadAndApplyTemplate "templates/default.html" indexCtx + match "templates/*" $ compile templateBodyCompiler + create ["sitemap.xml"] $ do + route idRoute + compile $ do + posts <- recentFirst =<< loadAll "posts/*" + nzPages <- loadAll "new-zealand/**" + let pages = posts <> nzPages + sitemapCtx = + constField "root" root + <> constField "siteName" siteName + <> listField "pages" postCtx (return pages) + makeItem ("" :: String) + >>= loadAndApplyTemplate "templates/sitemap.xml" sitemapCtx + create ["rss.xml"] $ do + route idRoute + compile (feedCompiler renderRss) + create ["atom.xml"] $ do + route idRoute + compile (feedCompiler renderAtom) + +-- CONTEXT + +feedCtx :: Context String +feedCtx = + titleCtx + <> postCtx + <> bodyField "description" + +postCtx :: Context String +postCtx = + constField "root" root + <> constField "siteName" siteName + <> dateField "date" "%Y-%m-%d" + <> defaultContext + +titleCtx :: Context String +titleCtx = + field "title" updatedTitle + +-- TITLE HELPERS + +replaceAmp :: String -> String +replaceAmp = + replaceAll "&" (const "&") + +replaceTitleAmp :: Metadata -> String +replaceTitleAmp = + replaceAmp . safeTitle + +safeTitle :: Metadata -> String +safeTitle = + fromMaybe "no title" . lookupString "title" + +updatedTitle :: Item a -> Compiler String +updatedTitle = + fmap replaceTitleAmp . getMetadata . itemIdentifier + +-- PANDOC + +pandocCompilerCustom :: Compiler (Item String) +pandocCompilerCustom = + pandocCompilerWith pandocReaderOpts pandocWriterOpts + +pandocExtensionsCustom :: Extensions +pandocExtensionsCustom = + githubMarkdownExtensions + <> extensionsFromList + [ Ext_auto_identifiers, + Ext_fenced_code_attributes, + Ext_smart, + Ext_footnotes + ] + +pandocReaderOpts :: ReaderOptions +pandocReaderOpts = + defaultHakyllReaderOptions + { readerExtensions = pandocExtensionsCustom + } + +pandocWriterOpts :: WriterOptions +pandocWriterOpts = + defaultHakyllWriterOptions + { writerExtensions = pandocExtensionsCustom + } + +-- FEEDS + +type FeedRenderer = + FeedConfiguration -> + Context String -> + [Item String] -> + Compiler (Item String) + +feedCompiler :: FeedRenderer -> Compiler (Item String) +feedCompiler renderer = + renderer feedConfiguration feedCtx + =<< recentFirst + =<< loadAllSnapshots "posts/*" "content" + +feedConfiguration :: FeedConfiguration +feedConfiguration = + FeedConfiguration + { feedTitle = "My Site", + feedDescription = "My Site Description", + feedAuthorName = "My Name", + feedAuthorEmail = "me@myemail.com", + feedRoot = root + } + +-- CUSTOM ROUTE + +getTitleFromMeta :: Metadata -> String +getTitleFromMeta = + fromMaybe "no title" . lookupString "title" + +fileNameFromTitle :: Metadata -> FilePath +fileNameFromTitle = + T.unpack . (`T.append` ".html") . toSlug . T.pack . getTitleFromMeta + +titleRoute :: Metadata -> Routes +titleRoute = + constRoute . fileNameFromTitle diff --git a/generator/src/Slug.hs b/generator/src/Slug.hs new file mode 100644 index 0000000..08d2d79 --- /dev/null +++ b/generator/src/Slug.hs @@ -0,0 +1,22 @@ +{-# LANGUAGE OverloadedStrings #-} + +module Slug + ( toSlug, + ) +where + +import Data.Char (isAlphaNum) +import qualified Data.Text as T + +keepAlphaNum :: Char -> Char +keepAlphaNum x + | isAlphaNum x = x + | otherwise = ' ' + +clean :: T.Text -> T.Text +clean = + T.map keepAlphaNum . T.replace "'" "" . T.replace "&" "and" + +toSlug :: T.Text -> T.Text +toSlug = + T.intercalate (T.singleton '-') . T.words . T.toLower . clean diff --git a/nix/default.nix b/nix/default.nix new file mode 100644 index 0000000..361254b --- /dev/null +++ b/nix/default.nix @@ -0,0 +1,43 @@ +let + sources = import ./sources.nix; + config = { allowBroken = true; }; +in +{ pkgs ? import sources.nixpkgs { inherit config; } }: + + let + pre-commit-hooks = import sources."pre-commit-hooks.nix"; + haskellPackages = pkgs.callPackage ../generator/hpkgs.nix {}; + generator = haskellPackages.callPackage ../generator/default.nix {}; + src = ../src; + in + { + inherit generator haskellPackages pkgs src; + + tools = [ + # uncomment pkgs.cacert & pkgs.nix if nix-shell --pure + # (https://github.com/nmattia/niv/issues/222) + + #pkgs.cacert + #pkgs.nix + generator + pkgs.niv + pkgs.pre-commit + pre-commit-hooks.hlint + pre-commit-hooks.nixpkgs-fmt + pre-commit-hooks.ormolu + ]; + + ci = { + pre-commit-check = pre-commit-hooks.run { + inherit src; + + hooks = { + nix-linter.enable = true; + nixpkgs-fmt.enable = true; + ormolu.enable = true; + shellcheck.enable = true; + }; + excludes = [ "^nix/sources\.nix$" ]; + }; + }; + } diff --git a/nix/sources.json b/nix/sources.json new file mode 100644 index 0000000..d00e093 --- /dev/null +++ b/nix/sources.json @@ -0,0 +1,38 @@ +{ + "niv": { + "branch": "master", + "description": "Easy dependency management for Nix projects", + "homepage": "https://github.com/nmattia/niv", + "owner": "nmattia", + "repo": "niv", + "rev": "dd13098d01eaa6be68237e7e38f96782b0480755", + "sha256": "1cfjdbsn0219fjzam1k7nqzkz8fb1ypab50rhyj026qbklqq2kvq", + "type": "tarball", + "url": "https://github.com/nmattia/niv/archive/dd13098d01eaa6be68237e7e38f96782b0480755.tar.gz", + "url_template": "https://github.com///archive/.tar.gz" + }, + "nixpkgs": { + "branch": "nixos-20.09", + "description": "A read-only mirror of NixOS/nixpkgs tracking the released channels. Send issues and PRs to", + "homepage": "https://github.com/NixOS/nixpkgs", + "owner": "NixOS", + "repo": "nixpkgs-channels", + "rev": "a40c69ed4768fe8bfadebc083cd60a01a4e59263", + "sha256": "0izmsc96l9qjypr4smhpzbrqxikg0d8zi9wn40w5cydy8ya88n2i", + "type": "tarball", + "url": "https://github.com/NixOS/nixpkgs-channels/archive/a40c69ed4768fe8bfadebc083cd60a01a4e59263.tar.gz", + "url_template": "https://github.com///archive/.tar.gz" + }, + "pre-commit-hooks.nix": { + "branch": "master", + "description": "Seamless integration of https://pre-commit.com git hooks with Nix.", + "homepage": "", + "owner": "cachix", + "repo": "pre-commit-hooks.nix", + "rev": "a3f7609ba73eb9ce3fe434d4339101017a430912", + "sha256": "05mi3s7c30wylfyxfb3hab0w9cbjahskmz4abidbxsmchjyici6a", + "type": "tarball", + "url": "https://github.com/cachix/pre-commit-hooks.nix/archive/a3f7609ba73eb9ce3fe434d4339101017a430912.tar.gz", + "url_template": "https://github.com///archive/.tar.gz" + } +} diff --git a/nix/sources.nix b/nix/sources.nix new file mode 100644 index 0000000..8a725cb --- /dev/null +++ b/nix/sources.nix @@ -0,0 +1,134 @@ +# This file has been generated by Niv. + +let + + # + # The fetchers. fetch_ fetches specs of type . + # + + fetch_file = pkgs: spec: + if spec.builtin or true then + builtins_fetchurl { inherit (spec) url sha256; } + else + pkgs.fetchurl { inherit (spec) url sha256; }; + + fetch_tarball = pkgs: spec: + if spec.builtin or true then + builtins_fetchTarball { inherit (spec) url sha256; } + else + pkgs.fetchzip { inherit (spec) url sha256; }; + + fetch_git = spec: + builtins.fetchGit { url = spec.repo; inherit (spec) rev ref; }; + + fetch_builtin-tarball = spec: + builtins.trace + '' + WARNING: + The niv type "builtin-tarball" will soon be deprecated. You should + instead use `builtin = true`. + + $ niv modify -a type=tarball -a builtin=true + '' + builtins_fetchTarball { inherit (spec) url sha256; }; + + fetch_builtin-url = spec: + builtins.trace + '' + WARNING: + The niv type "builtin-url" will soon be deprecated. You should + instead use `builtin = true`. + + $ niv modify -a type=file -a builtin=true + '' + (builtins_fetchurl { inherit (spec) url sha256; }); + + # + # Various helpers + # + + # The set of packages used when specs are fetched using non-builtins. + mkPkgs = sources: + let + sourcesNixpkgs = + import (builtins_fetchTarball { inherit (sources.nixpkgs) url sha256; }) {}; + hasNixpkgsPath = builtins.any (x: x.prefix == "nixpkgs") builtins.nixPath; + hasThisAsNixpkgsPath = == ./.; + in + if builtins.hasAttr "nixpkgs" sources + then sourcesNixpkgs + else if hasNixpkgsPath && ! hasThisAsNixpkgsPath then + import {} + else + abort + '' + Please specify either (through -I or NIX_PATH=nixpkgs=...) or + add a package called "nixpkgs" to your sources.json. + ''; + + # The actual fetching function. + fetch = pkgs: name: spec: + + if ! builtins.hasAttr "type" spec then + abort "ERROR: niv spec ${name} does not have a 'type' attribute" + else if spec.type == "file" then fetch_file pkgs spec + else if spec.type == "tarball" then fetch_tarball pkgs spec + else if spec.type == "git" then fetch_git spec + else if spec.type == "builtin-tarball" then fetch_builtin-tarball spec + else if spec.type == "builtin-url" then fetch_builtin-url spec + else + abort "ERROR: niv spec ${name} has unknown type ${builtins.toJSON spec.type}"; + + # Ports of functions for older nix versions + + # a Nix version of mapAttrs if the built-in doesn't exist + mapAttrs = builtins.mapAttrs or ( + f: set: with builtins; + listToAttrs (map (attr: { name = attr; value = f attr set.${attr}; }) (attrNames set)) + ); + + # fetchTarball version that is compatible between all the versions of Nix + builtins_fetchTarball = { url, sha256 }@attrs: + let + inherit (builtins) lessThan nixVersion fetchTarball; + in + if lessThan nixVersion "1.12" then + fetchTarball { inherit url; } + else + fetchTarball attrs; + + # fetchurl version that is compatible between all the versions of Nix + builtins_fetchurl = { url, sha256 }@attrs: + let + inherit (builtins) lessThan nixVersion fetchurl; + in + if lessThan nixVersion "1.12" then + fetchurl { inherit url; } + else + fetchurl attrs; + + # Create the final "sources" from the config + mkSources = config: + mapAttrs ( + name: spec: + if builtins.hasAttr "outPath" spec + then abort + "The values in sources.json should not have an 'outPath' attribute" + else + spec // { outPath = fetch config.pkgs name spec; } + ) config.sources; + + # The "config" used by the fetchers + mkConfig = + { sourcesFile ? ./sources.json + , sources ? builtins.fromJSON (builtins.readFile sourcesFile) + , pkgs ? mkPkgs sources + }: rec { + # The sources, i.e. the attribute set of spec name to spec + inherit sources; + + # The "pkgs" (evaluated nixpkgs) to use for e.g. non-builtin fetchers + inherit pkgs; + }; +in +mkSources (mkConfig {}) // { __functor = _: settings: mkSources (mkConfig settings); } diff --git a/shell.nix b/shell.nix new file mode 100644 index 0000000..80355bd --- /dev/null +++ b/shell.nix @@ -0,0 +1,14 @@ +let + sources = import ./nix/sources.nix; +in +{ pkgs ? import sources.nixpkgs {} }: + + let + cfg = import ./nix/default.nix {}; + in + pkgs.mkShell { + buildInputs = cfg.tools; + shellHook = '' + ${cfg.ci.pre-commit-check.shellHook} + ''; + } diff --git a/src/CNAME b/src/CNAME new file mode 100644 index 0000000..2534915 --- /dev/null +++ b/src/CNAME @@ -0,0 +1 @@ +mywebsite.com diff --git a/src/_config.yaml b/src/_config.yaml new file mode 100644 index 0000000..7a30e5f --- /dev/null +++ b/src/_config.yaml @@ -0,0 +1 @@ +include: [] diff --git a/src/css/article.css b/src/css/article.css new file mode 100644 index 0000000..97e078b --- /dev/null +++ b/src/css/article.css @@ -0,0 +1,44 @@ +:root { + font-size: 62.5%; + box-sizing: border-box; + -ms-text-size-adjust: 100%; + -webkit-text-size-adjust: 100%; +} +*, +*:before, +*:after { + box-sizing: inherit; +} +html, +body { + min-height: 100vh; +} +body { + font-kerning: normal; + -moz-font-feature-settings: "kern", "liga", "clig", "calt"; + -ms-font-feature-settings: "kern", "liga", "clig", "calt"; + -webkit-font-feature-settings: "kern", "liga", "clig", "calt"; + font-feature-settings: "kern", "liga", "clig", "calt"; + scroll-behavior: smooth; +} +article h1, +article small, +article p { + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} +article small, +article p { + font-family: Tahoma, Arial, sans-serif; +} +article h1 { + font-size: 4.0rem; +} +article small { + font-size: 1.6rem; + font-style: italic; +} +article p { + font-family: Tahoma, Arial, sans-serif; + font-size: 1.8rem; +} diff --git a/src/css/default.css b/src/css/default.css new file mode 100644 index 0000000..7a3a707 --- /dev/null +++ b/src/css/default.css @@ -0,0 +1,30 @@ +:root { + font-size: 62.5%; + box-sizing: border-box; + -ms-text-size-adjust: 100%; + -webkit-text-size-adjust: 100%; +} +*, +*:before, +*:after { + box-sizing: inherit; +} +html, +body { + min-height: 100vh; +} +body { + font-kerning: normal; + -moz-font-feature-settings: "kern", "liga", "clig", "calt"; + -ms-font-feature-settings: "kern", "liga", "clig", "calt"; + -webkit-font-feature-settings: "kern", "liga", "clig", "calt"; + font-feature-settings: "kern", "liga", "clig", "calt"; + scroll-behavior: smooth; +} +.ffs { font-family: "Palatino Linotype", "Book Antiqua", Palatino, serif; } +.ffss { font-family: Tahoma, Arial, sans-serif; } +.fs { -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; } +.fs14 { font-size: 1.4rem; } +.fs18 { font-size: 1.8rem; } +.fs32 { font-size: 3.2rem; } +.fs40 { font-size: 4.0rem; } diff --git a/src/favicon.ico b/src/favicon.ico new file mode 100644 index 0000000..2096d33 Binary files /dev/null and b/src/favicon.ico differ diff --git a/src/images/robert-pearce-UwHN0jU_YqQ-unsplash-800w.jpg b/src/images/robert-pearce-UwHN0jU_YqQ-unsplash-800w.jpg new file mode 100644 index 0000000..5a35972 Binary files /dev/null and b/src/images/robert-pearce-UwHN0jU_YqQ-unsplash-800w.jpg differ diff --git a/src/images/waiheke-stony-batter.jpg b/src/images/waiheke-stony-batter.jpg new file mode 100644 index 0000000..eb9211d Binary files /dev/null and b/src/images/waiheke-stony-batter.jpg differ diff --git a/src/index.html b/src/index.html new file mode 100644 index 0000000..e3a49b6 --- /dev/null +++ b/src/index.html @@ -0,0 +1,29 @@ +--- +description: "This is me saying hello to the world" +image: "/images/robert-pearce-UwHN0jU_YqQ-unsplash-800w.jpg" +lang: "en" +stylesheet: "default" +title: "Hello, world!" +--- + +
+

Hello, world!

+ A woman sitting on a bench amongst trees at the end of a boardwalk leading to a pond with mountains in the background +
+
+
+

Blog Posts

+
    + $for(posts)$ +
  • + + $date$ +
  • + $endfor$ +
+
+
diff --git a/src/js/script.js b/src/js/script.js new file mode 100644 index 0000000..4fc48a9 --- /dev/null +++ b/src/js/script.js @@ -0,0 +1,3 @@ +;(function(w, d) { + console.log('Hello, world!', w, d) +})(window, document); diff --git a/src/posts/2020-09-21-hello-world.md b/src/posts/2020-09-21-hello-world.md new file mode 100644 index 0000000..82674d7 --- /dev/null +++ b/src/posts/2020-09-21-hello-world.md @@ -0,0 +1,19 @@ +--- +author: "My name" +authorTwitter: "@MyName" +description: "I announce myself to the world" +image: "/images/waiheke-stony-batter.jpg" +keywords: "hello, announcement" +lang: "en" +stylesheet: "article" +title: "Hello, world!" +updated: "2020-09-22T12:00:00Z" +--- + +Hello, world! I am here! + +Grapevines among rolling hills leading to the sea diff --git a/src/posts/2020-09-22-hola-mundo.md b/src/posts/2020-09-22-hola-mundo.md new file mode 100644 index 0000000..9a01c80 --- /dev/null +++ b/src/posts/2020-09-22-hola-mundo.md @@ -0,0 +1,19 @@ +--- +author: "Mi nombre" +authorTwitter: "@MiNombre" +description: "Me anuncio al mundo" +image: "/images/waiheke-stony-batter.jpg" +keywords: "hola, anuncio" +lang: "es" +stylesheet: "article" +title: "¡Hola Mundo!" +updated: "2020-09-23T12:00:00Z" +--- + +¡Hola Mundo! ¡Estoy aquí! + +Grapevines among rolling hills leading to the sea diff --git a/src/robots.txt b/src/robots.txt new file mode 100644 index 0000000..eb05362 --- /dev/null +++ b/src/robots.txt @@ -0,0 +1,2 @@ +User-agent: * +Disallow: diff --git a/src/templates/default.html b/src/templates/default.html new file mode 100644 index 0000000..fe7bd0a --- /dev/null +++ b/src/templates/default.html @@ -0,0 +1,48 @@ + + + + $title$ + + + + + $if(author)$ + + $endif$ + $if(keywords)$ + + $endif$ + + + + + + $if(image)$ + + $endif$ + $if(type)$ + + $else$ + + $endif$ + + + + + + $if(image)$ + + $endif$ + $if(authorTwitter)$ + + $endif$ + + + + + + + $body$ + + + diff --git a/src/templates/post.html b/src/templates/post.html new file mode 100644 index 0000000..5809bb8 --- /dev/null +++ b/src/templates/post.html @@ -0,0 +1,18 @@ +
+
+
+

+ $title$ +

+
+ $date$ + $if(updated)$ + (updated: $updated$) + $endif$ +
+
+
+ $body$ +
+
+
diff --git a/src/templates/sitemap.xml b/src/templates/sitemap.xml new file mode 100644 index 0000000..10b9945 --- /dev/null +++ b/src/templates/sitemap.xml @@ -0,0 +1,16 @@ + + + + $root$ + daily + 1.0 + +$for(pages)$ + + $root$$url$ + $if(updated)$$updated$$else$$if(date)$$date$$endif$$endif$ + weekly + 0.8 + +$endfor$ +