Let's fuck like freaks

You used to sit, write down all sorts of things that you yourself always forget, and suddenly you wanted to start doing good to people and bringing joy despite their wishes, and then people periodically ask, so you need to get fleas, but not in a sweater, but one that will be comfortable, fast, protected, beautiful and will not depend on fashion trends on the next one-day platform, will not be smeared with strange pop-ups, banners, propaganda…

But writing a new engine from scratch or using constantly leaky PHP blogs is not a noble thing to do, and I don’t want to deal with all this mess of rotten dependencies.

Markdown

We will write simple, easy-to-read text, from any convenient place, practically from the first refrigerator we come across, in any first editor we come across, even in vim, as our grandfathers squealed, without being distracted in a creative frenzy by software problems, cloud availability, new cloud bells and whistles, bells and whistles updates and other pop-ups and distractions. The simpler – the better. Reliable as a brick. We will be helped in this by warm, tube Markdown, which is supported quite well everywhere while remaining quite simple and can expand well. Well, in general, everyone knows and can do Markdown.

Hugo

We will roll out Markdown into a static site, which is by definition fast, caches well, indexes and is not hackable, not to mention that there are simply no dependencies that will go bad and fall off out of the box. GitHub Pages is pushing Jekyll, but there is a divine and fast Hugowith its hundreds of templates optimized for every taste and color, from mobile and Accessibility (which, if done correctly, helps not only people with problems, but is also very useful for all sorts of convenient things like vimium), to SEO, comments and normal support for options like Reader View in Firefox. Hugo is written in Go, so it is available for all major platforms and without squatting with the environment and dependencies – just download and work. Only we will most likely need SCSS, so we download hugo from the assemblies extended. Now I can go read documentation.

But we are lazy, and Hugo is old enough that if you launch him from the console, he will tell you about it himself. hugo help newwell, and then it's business as usual

> hugo new site my-blog
Congratulations! Your new Hugo site was created in D:\Projects\my-blog.
Just a few more steps...
1. Change the current directory to D:\Projects\my-blog.
2. Create or install a theme:   
  - Create a new theme with the command "hugo new theme <THEMENAME>"   
  - Or, install a theme from https://themes.gohugo.io/
3. Edit hugo.toml, setting the "theme" property to the theme name.
4. Create new content with the command "hugo new content <SECTIONNAME>\<FILENAME>.<FORMAT>".
5. Start the embedded web server with the command "hugo server --buildDrafts".
See documentation at https://gohugo.io/.

And it would be possible to get straight to the point, but…

First you need to understand and set it up properly once.

The default theme is a draft that will add 3 test posts from themes\default\content and in general asks bricks file.
So let's go to Theme Repository and choose something more cute for our needs. For example, I liked m10c.

git clone https://github.com/vaga/hugo-theme-m10c.git themes/m10c
echo "theme="m10c"" >> hugo.toml

New posts are generated by default in the content directory from a template saved in archetypes, but do not forget to specify the file format, otherwise you will get an error

> hugo new content posts\my-first-post
Error: failed to resolve "posts\\my-first-post" to an archetype template

> hugo new content posts\my-first-post.md
Content "my-blog\\content\\posts\\my-first-post.md" created

The post will not be generated in the blog until the metadata header contains draft = true. We delete it, add something funny and then to taste: you can just run it hugo in the directory with the project and it will generate public with a static site, or you can run hugo serverclick on the suggested URL and immediately view the result in the browser.

Configuring generator and template parameters

Everything basic is configured via config.toml and it's pretty obvious

baseURL = 'https://USERNAME.github.io/'
title = "USERNAME blog"

languageCode="ru-ru"
defaultContentLanguage = "ru"
defaultContentLanguageInSubdir = true

theme="m10c"

# publishdir="_site"

enableRobotsTXT = false

[params]
  author="USERNAME"
  description = 'Whatever Developer, full-stack. Interested in *nix, maker culture, home assistant, photo, nature, birdwatching'
  avatar="https://avatars.githubusercontent.com/u/USERID"

[[params.social]]
  icon = "github"
  name = "My Github"
  url = "https://github.com/USERNAME"
[[params.social]]
  icon = "linkedin"
  name = "linkedin"
  url = "https://www.linkedin.com/in/USERNAME"
[[params.social]]
  icon = "telegram"
  name = "telegram"
  url = "https://t.me/USERNAME"

[menu]
  [[menu.main]]
    identifier = "home"
    name = "Home"
    url = "/"
    weight = 1
  [[menu.main]]
    identifier = "posts"
    name = "Posts"
    url = "/posts/"
    weight = 2
  [[menu.main]]
    identifier = "tags"
    name = "Tags"
    url = "/tags/"
    weight = 3
  [[menu.main]]
    identifier = "about"
    name = "About"
    url = "/about/"
    weight = 4

We change it to suit our accounts.

You can either upload a photo for your avatar directly to the repository, or make a link to a photo from your GitHub profile, or think about some other gravatar.

Let's systematize a little

In the directory we may have

  • _index.md – index file that specifies that we need to generate a list of articles from what is in the current directory and subdirectories. In principle, this is the default behavior for the directory, but you may want to set a title for this page, then the minimum content will be something like this

    ---
    title: "My custom title for this category"
    ---
  • index.md – the main file for this directory (similar to index.html), if it exists, then Hugo will use it for this path and you will have to manually write links to all other articles somewhere

  • all sorts of other things *.md – files from which static pages with your articles will be generated.

Article my-blog\content\posts\article.md will be generated in my-blog\public\posts\article\index.html

And since we generate a directory for each article anyway, to avoid confusion, I prefer to name all posts in the format content\posts\YYYYMMDD-article-name\index.md and put all sorts of screenshots and attachments to them in the directory to the article.
That is, a new article will be generated something like this

hugo new content posts\2024-08-24-blog-like-a-freak\index.md

My article header looks something like this

---
title: 'Бложим как фрики'
description: О мой бложе, что я несу...
date: 2024-08-28T11:46:29+03:00
categories: Blog
tags: ['Blog', 'Hugo', 'Markdown']
layout: post
---

date affects the sort order of articles

Tags and categories are used to generate /tags/ and /categories/ respectively
layout overrides which template from the selected theme is used

And it is worth mentioning the landing page in the root of the site separately. By default, this particular theme creates a list of posts, and all the content from content\_index.md ignored. If we are not satisfied with this behavior of pages with lists of sites, you can m10c\layouts\_default\list.html add section {{ .Content }} after the title. If we want even more customization, we create themes\m10c\layouts\_default\home.html with customization for the root page. For example, you can take a copy of the file from the default theme

{{ define "main" }}
  {{ .Content }}
  {{ range site.RegularPages }}
    <h2><a href="https://habr.com/ru/articles/840218/{{ .RelPermalink }}">{{ .LinkTitle }}</a></h2>
    {{ .Summary }}
  {{ end }}
{{ end }}

Now the page will have an introductory text, and after it the blog posts will be listed with a brief content. But perhaps it will be more convenient, for example, to display the main sections

{{ range .Site.Sections }}
  <h2><a href="https://habr.com/ru/articles/840218/{{ .RelPermalink }}">{{ .LinkTitle }}</a></h2>
{{ end }}

The possibilities for customizing Hugo templates seem endless, the clearest example of this is the documentation from Kubernetes

GitHub

In general, you can host a static primitive on anything, as long as there is enough space, even on an ESP32 with a microSD or on a flash drive plugged into a kinetic. But there is already an accessible, reliable, free and familiar GitHub.

We exclude in .gitignore everything is superfluous

/.hugo_build.lock
/public
/resources/_gen

We initialize the repository, commit our hefty soup

git init
git add .
git commit -m "Initial"

Create a public repository on GitHub and upload to it

git remote add origin git@github.com:USERNAME/my-blog.git
git push -u origin master

GitHub Actions

Well, everything is simple here, we want Hugo to collect a new version of the statics and publish it for every commit to the master. Which we will write in .github\workflows\hugo.yml

name: Deploy Hugo site to Pages

on:
  # Runs on pushes targeting the default branch
  push:
    branches: ["master"]

  # Allows you to run this workflow manually from the Actions tab
  workflow_dispatch:

# Sets permissions of the GITHUB_TOKEN to allow deployment to GitHub Pages
permissions:
  contents: read
  pages: write
  id-token: write

# Allow one concurrent deployment
concurrency:
  group: "pages"
  cancel-in-progress: true

# Default to bash
defaults:
  run:
    shell: bash

jobs:
  # Build job
  build:
    runs-on: ubuntu-latest
    env:
      HUGO_VERSION: 0.133.1
    steps:
      - name: Install Hugo CLI
        run: |
          wget -O ${{ runner.temp }}/hugo.deb https://github.com/gohugoio/hugo/releases/download/v${HUGO_VERSION}/hugo_extended_${HUGO_VERSION}_linux-amd64.deb \
          && sudo dpkg -i ${{ runner.temp }}/hugo.deb
      - name: Checkout
        uses: actions/checkout@v3
        with:
          submodules: recursive
      - name: Setup Pages
        id: pages
        uses: actions/configure-pages@v2
      - name: Build with Hugo
        env:
          # For maximum backward compatibility with Hugo modules
          HUGO_ENVIRONMENT: production
          HUGO_ENV: production
        run: |
          hugo \
            --minify \
            --baseURL "${{ steps.pages.outputs.base_url }}/"
      - name: Upload artifact
        uses: actions/upload-pages-artifact@v1
        with:
          path: ./public

  # Deployment job
  deploy:
    environment:
      name: github-pages
      url: ${{ steps.deployment.outputs.page_url }}
    runs-on: ubuntu-latest
    needs: build
    steps:
      - name: Deploy to GitHub Pages
        id: deployment
        uses: actions/deploy-pages@v1

And since we deploy new content via GitHub Actions, we should also specify GitHub Actions in the repository, in Settings – Pages – Build and deployment – Source

That's it, now you can bring smiles, rage and moral death into the world.

Obsidian

But you still need a more comfortable editor. If you haven't found a suitable one yet, editing raw Markdown is too lazy, and GitHub's own editor doesn't suit you, take Obsidian – a wonderful WYSIWYG editor for Markdown, many people already use it for notes.
Let's make it open the directory with our blog repository as a new Vault and go through the settings

Editor

Strict line breaks = we turn on
Indent using tabs = we turn it off, spaces are our everything

Files and links

Default location for new notes = in the folder specified below
Folder to create new notes in = content/posts

New link format = Relative path to file

Use [[Wikilinks]] – turn it off, we need honest Markdown

Default location for new attachments = Same folder as current file
since each article will still have a separate directory. And all this can be easily transferred anywhere

Templates

We decide whether we will call it manually from the console each time

hugo new content posts\whatever.md

Or, after all, Obsidian will be responsible for the template and then we register the paths to the templates.

In general, it would be good to install some more advanced plugin with templates to generate directly into the desired directory, but at least you can configure it minimally out of the box

Core plugins – Daily notes

New file location = content/posts
Template file location = archetypes/default

Core Plugins – Templates

Let our templates be taken from the directory archetypes

And also change the template itself to something like this

---
title: PAGE TITLE
description: PAGE DESCRIPTION
date: {{date}} {{time:HH:mm:ss Z}}
categories: blog
tags: []
layout: post
---

Obsidian Git

We go to the settings in Community Plugins, enable them, click Browse and look for all sorts of things about Git. We find, for example, Git by Vinzent (Denis Olehov). We install, turn on.

Now with Ctrl+P we can find the commit/push/pull we need right in Obsidian

We commit… all our editor settings are also in the repository and now we can download everything to another PC or phone and slowly, savoring, with a coffee maker, write all sorts of nonsense, so that the fire burns more cheerfully

And with a simple Ctrl+C, Ctrl+V, these articles can then be reposted to Habr and other resources with minimal edits if desired.

If desired, all this can be adapted for maintaining documentation, all kinds of landing pages, a business card site with a CV.

Similar Posts

Leave a Reply

Your email address will not be published. Required fields are marked *