I have created a mini-roam in org-mode with custom links. My two link types are: `page` and `journal`:
;;; open journal file
;; by inserting `journal:2022-05-12' for instance.
(org-add-link-type "journal" 'org-open-journal-file)
(defun org-open-journal-file (journal-filename-sans-ext)
"Open journal file corresponding to JOURNAL-FILENAME-SANS-EXT."
(find-file-other-window (concat org-journal-dir "/" journal-filename-sans-ext ".org")))
;;; open file in `~/Dropbox/org/pages'
;; by inserting `page:Fitness' for instance.
(org-add-link-type "page" 'org-open-page-file)
(defun org-open-page-file (page-filename-sans-ext)
"Open page file corresponding to PAGE-FILE-SANS-EXT."
(find-file-other-window (concat org-directory "/pages/" page-filename-sans-ext ".org")))
With the code below I can create a link to pages in my `pages/` folder or create a new page.
## How can I show backlinks to these custom org-links?
Now when I open a file in my `pages/` folder, I'd like to see a list of
pages that link to this page.
There are many solutions that require me to add a custom property `ID`
or `CUSTOM_ID`, but I don't want to add IDs to nodes. Just link to `pages`
(aka files) and show links to them.
Anyone know of a solution?
## Code
;;; Get all file names in pages/ folder
(defun ugt-get-filenames-in-pages-folder nil
(interactive)
(let* ((pages-path (concat org-directory "/pages/")))
(cl-flet ((transform-filename (fname)
(capitalize (replace-regexp-in-string "[-]+" " "
(file-name-sans-extension fname)))))
(mapcar #'transform-filename (directory-files pages-path nil ".*\\.org$")))))
;;; Create page or link to page
(defun ugt-org-insert-page-link (&optional arg)
"Insert page link and add page name to description to hide the \"page\" prefix.
Or: Search and insert a file link.
"
(interactive "P")
;; Check if reagion is active
(let* ((page-name
(cond (arg ;; prefix argument given
;; use word under cursor
(prog1 (thing-at-point 'word 'no-properties)
(search-backward-regexp "\\b")
(kill-word 1)))
;; is region selected? use that
((use-region-p)
(replace-regexp-in-string "[- .,;\n\t]+$" "" ;; remove trailing whitespaces
(buffer-substring-no-properties (region-beginning) (region-end))))
(t
(replace-regexp-in-string "[-]+"
" "
(completing-read "Enter page name or select from list: "
(ugt-get-filenames-in-pages-folder) nil 'confirm)))))
(fname (downcase
(replace-regexp-in-string "[ \n\t]+" "-" ;; replace whitespaces by dashses
page-name)))
(fname-with-extension (concat fname ".org"))
(fname-with-path (concat org-directory "/pages/" fname-with-extension)))
(cond ((not (file-exists-p fname-with-path))
(with-current-buffer (find-file-noselect fname-with-path)
(let*
((title (concat "#+title: " (capitalize page-name)))
(date (concat "#+date: "
(shell-command-to-string "echo -n $(date +'%A, %d. %B %Y at %T')")))
(startup "#+startup: showall inlineimages"))
(insert (concat title "\n" date "\n" startup "\n"))
(save-buffer)))
(message "Created new page `%s'" (capitalize page-name)))
(t
(message "Linked to page `%s'" page-name)))
(if (string= (buffer-file-name) fname-with-path)
(message "Trying to link to current file.")
(org-insert-link
nil
;; link location
;;(concat counsel--fzf-dir "/" file)
(concat "page:" fname)
;; description
(capitalize page-name)))))