;; -*- lexical-binding: t -*- ;;; Vars and setup (jao-load-path "org-static-blog") (when (> emacs-major-version 26) (use-package htmlize :ensure t)) (defvar jao-blog-base-dir "~/doc/jao.io") (defun jao-blog-dir (p) (expand-file-name p jao-blog-base-dir)) (setq jao-org-blog-tag-files (seq-difference (directory-files (jao-blog-dir "blog") nil "tag-.*") "tag-norss.html") jao-org-blog-tags (mapcar (lambda (f) (string-match "tag-\\(.+\\)\\.html" f) (format "%s" f (match-string 1 f))) jao-org-blog-tag-files) jao-org-blog-tag-rss (mapcar (lambda (f) (string-match "\\(.+\\)-rss\\.xml" f) (format "%s" f (match-string 1 f))) (directory-files (jao-blog-dir "blog") nil ".*-rss.xml")) jao-org-blog-tag-names (mapcar (lambda (f) (string-match "tag-\\(.+\\)\\.html" f) (match-string 1 f)) jao-org-blog-tag-files)) ;;; Header (setq org-static-blog-page-header (concat "\n" "\n" "\n" "\n" "\n" "\n" "\n" "\n") org-static-blog-page-preamble (concat "
" " programming (and other) musings" "
" " about" " | hacking" " | archive" " |
" " tags" "
" (mapconcat #'identity jao-org-blog-tags "") "
" "
" " |
" " rss" "
" (mapconcat #'identity jao-org-blog-tag-rss "") "
" "
" "
" "
")) ;;; Footer (setq org-static-blog-page-postamble (with-temp-buffer (insert-file-contents "~/.emacs.d/commons.html") (buffer-string))) ;;; Package (use-package org-static-blog :ensure t :init (setq org-static-blog-use-preview t org-static-blog-preview-link-p t org-static-blog-preview-start "" org-static-blog-preview-end "" org-static-blog-preview-date-first-p t org-static-blog-index-length 30 org-static-blog-preview-convert-titles t org-static-blog-preview-ellipsis "more ..." org-static-blog-enable-tags t org-static-blog-tags-file "tags.html" org-static-blog-rss-file "rss.xml" org-static-blog-publish-url "https://jao.io/blog/" org-static-blog-publish-title "programming (and other) musings" org-static-blog-posts-directory (jao-blog-dir "posts/") org-static-blog-drafts-directory (jao-blog-dir "pages/") org-static-blog-publish-directory (jao-blog-dir "blog/") org-static-blog-rss-extra "" ; "mail@jao.io\n" org-static-blog-rss-max-entries 30 org-static-blog-rss-excluded-tag "norss" org-static-blog-enable-tag-rss t org-export-with-toc nil org-export-with-section-numbers nil) :config (defun jao-org-static-post-path (pf dt) (cond ((string-match-p "pages/.*\\|in-no-particular-order" pf) (file-name-nondirectory pf)) ((string-match-p "drafts/.*" pf) pf) ((string-match-p "^[[:digit:]]+-.*" pf) pf) (t (concat (format-time-string "%Y-%m-%d-" dt) (file-name-nondirectory pf))))) (advice-add 'org-static-blog-generate-post-path :override #'jao-org-static-post-path) :bind (:map org-mode-map (("C-c B" . jao-transient-org-blog)))) ;;; New entries (defun jao-org-blog-publish-file (fname) (interactive (list (read-file-name "Publish: " nil (buffer-file-name) t (buffer-file-name)))) (let ((geiser-active-implementations '(guile)) (geiser-default-implementation 'guile) (whitespace-style nil)) (org-static-blog-publish-file fname))) (defconst jao-org-static-blog--prev-beg "#+html: ") (defconst jao-org-static-blog--prev-end "#+html: ") (defun jao-org-static-blog-create-new-post (&optional draft) (interactive) (let* ((title (read-string "Title: ")) (file (replace-regexp-in-string "\s" "-" (downcase title))) (tags (completing-read-multiple "Tags: " jao-org-blog-tag-names))) (find-file (expand-file-name (concat file ".org") (if draft org-static-blog-drafts-directory org-static-blog-posts-directory))) (insert "#+title: " title "\n" "#+date: " (format-time-string "<%Y-%m-%d %H:%M>") "\n" "#+filetags: " (mapconcat #'identity tags " ") "\n\n") (when (member "books" tags) (insert jao-org-static-blog--prev-beg "\n\n[[../img/" file ".jpg]]\n\n")) (save-excursion (insert jao-org-static-blog--prev-end "\n")))) ;;; Drafts (defun jao-org-static-blog-update-date () (interactive) (when (y-or-n-p "Update date? ") (goto-char (point-min)) (when (re-search-forward "^#\\+date: " nil t) (delete-line) (insert (format-time-string "<%Y-%m-%d %H:%M>")) (save-buffer)))) (defun jao-org-static-blog-create-new-draft () (interactive) (jao-org-static-blog-create-new-post t)) (defun jao-org-static-blog-publish-draft () (interactive) (let* ((from (read-file-name "Post: " org-static-blog-drafts-directory nil t)) (to (expand-file-name (file-name-nondirectory from) org-static-blog-posts-directory))) (rename-file from to) (when-let* ((b (get-buffer from))) (kill-buffer b)) (find-file to) (jao-org-static-blog-update-date) (when (y-or-n-p "Generate HTML? ") (jao-org-blog-publish)))) (defun jao-org-static-blog-edit-draft () (interactive) (find-file (read-file-name "Edit: " org-static-blog-drafts-directory nil t))) ;;; Publish (defun jao-org-blog-publish (&optional force) (interactive "P") (let ((geiser-active-implementations '(guile)) (geiser-default-implementation 'guile) (whitespace-style nil)) (org-static-blog-publish force))) (defun jao-org-blog-republish () (interactive) (jao-org-blog-publish t)) ;;; Transient (defun jao-org-static-prev-begin () (interactive) (insert jao-org-static-blog--prev-beg)) (defun jao-org-static-prev-end () (interactive) (insert jao-org-static-blog--prev-end)) (transient-define-prefix jao-transient-org-blog () [["Insert blog snippet" ("s" "preview begin" jao-org-static-prev-begin) ("S" "preview end" jao-org-static-prev-end) ("T" "update date" jao-org-static-blog-update-date)] ["Edit blog" ("n" "create post" jao-org-static-blog-create-new-post) ("d" "create draft" jao-org-static-blog-create-new-draft) ("e" "edit draft" jao-org-static-blog-edit-draft)] ["Publish blog" ("D" "publish draft" jao-org-static-blog-publish-draft) ("f" "publish single file" jao-org-blog-publish-file) ("p" "publish all" jao-org-blog-publish) ("r" "republish" jao-org-blog-republish)]]) ;;; . (provide 'jao-custom-blog)