#+TITLE: Static blog with org-mode
#+AUTHOR: Yann Esposito
#+EMAIL: yann.esposito@gmail.com
#+KEYWORDS: programming, blog

[[https://her.esy.fun][her.esy.fun]]

This is a new take on my personal blog.
With a lot more minimalism in mind.

Fully done with [[https://orgmode.org][=org-mode=]].

* Code magic

Here is how I publish this website in emacs using org-mode.
I just eval that code and then do a simple `org-publish` for the blog.

And that's it.

#+begin_src elisp :results none
    (require 'org)
    (require 'ox-publish)
    (require 'ox-html)
    (require 'org-element)
    (require 'ox-rss)

    (defun org-blog-prepare (project-plist)
      "With help from `https://github.com/howardabrams/dot-files'.
              Touch `index.org' to rebuilt it.
              Argument `PROJECT-PLIST' contains information about the current project."
      (let* ((base-directory (plist-get project-plist :base-directory))
             (buffer (find-file-noselect (expand-file-name "index.org" base-directory) t)))
        (with-current-buffer buffer
          (set-buffer-modified-p t)
          (save-buffer 0))
        (kill-buffer buffer)))

    (defvar org-blog-head
      "<link rel=\"stylesheet\" type=\"text/css\" href=\"/assets/css/minimalist.css\"/>
       <link rel=\"shortcut icon\" type=\"image/x-icon\" href=\"/favicon.ico\">")

    (defun org-blog-preamble (_plist)
      "Pre-amble for whole blog."
      "<strong><code>Programming Heresy</code></strong>")

    (defun org-blog-postamble (_plist)
      "Post-amble for whole blog."
      "<hr/>
         <a href=\"/\">Home</a> -
         <a href=\"/archive.html\">Posts</a>")

    (defun org-blog-sitemap-format-entry (entry _style project)
      "Return string for each ENTRY in PROJECT."
      (when (s-starts-with-p "posts/" entry)
        (format (concat "@@html:<span class=\"archive-item\">"
                        "<span class=\"archive-date\">"
                        "@@ %s @@html:</span>@@ [[file:%s][%s]] @@html:</span>@@")
                (format-time-string "%Y-%m-%d"
                                    (org-publish-find-date entry project))
                entry
                (org-publish-find-title entry project))))

  (defun org-blog-sitemap-function (title list)
    "Return sitemap using TITLE and LIST returned by `org-blog-sitemap-format-entry'."
    (concat "#+TITLE: " title "\n\n"
            "\n#+begin_archive\n"
            (mapconcat (lambda (li)
                         (format "@@html:<li>@@ %s @@html:</li>@@" (car li)))
                       (seq-filter #'car (cdr list))
                       "\n")
            "\n#+end_archive\n"))

  (setq rootdir (projectile-project-root))

  (setq org-publish-project-alist
          `(("orgfiles"
             :base-directory (concat rootdir "/src/")
             :exclude ".*drafts/.*"
             :base-extension "org"

             :publishing-directory (concat rootdir "/_site/")

             :recursive t
             :preparation-function org-blog-prepare
             :publishing-function org-html-publish-to-html

             :with-toc nil
             :with-title t
             :with-date t
             :section-numbers nil
             :html-doctype "html5"
             :html-html5-fancy t
             :html-head-include-default-style nil
             :html-head-include-scripts nil
             :htmlized-source t
             :html-head-extra ,org-blog-head
             :html-preamble org-blog-preamble
             :html-postamble org-blog-postamble

             :auto-sitemap t
             :sitemap-filename "archive.org"
             :sitemap-title "Blog Posts"
             :sitemap-style list
             :sitemap-sort-files anti-chronologically
             :sitemap-format-entry org-blog-sitemap-format-entry
             :sitemap-function org-blog-sitemap-function)

            ("assets"
             :base-directory (concat rootdir "/src/assets/")
             :base-extension ".*"
             :publishing-directory (concat rootdir "/_site/assets/")
             :publishing-function org-publish-attachment
             :recursive t)

            ("rss"
             :base-directory (concat rootdir "/src/")
             :base-extension "org"
             :html-link-home "https://her.esy.fun/"
             :html-link-use-abs-url t
             :rss-extension "xml"
             :publishing-directory (concat rootdir "/")
             :publishing-function (org-rss-publish-to-rss)
             :exclude ".*"
             :include ("archive.org")
             :section-numbers nil
             :table-of-contents nil)

            ("blog" :components ("orgfiles" "assets" "rss"))))
#+end_src
