mirror of
https://github.com/org-roam/org-roam
synced 2025-09-02 14:53:31 -05:00
Simplify org-roam-insert and org-roam-find-file (#62)
* Simplify org-roam-insert and org-roam-find-file See #59. * Add docs for org-roam automatic filenaming * Update installation instructions
This commit is contained in:
135
org-roam.el
135
org-roam.el
@@ -33,26 +33,8 @@ Valid values are
|
||||
(const right))
|
||||
:group 'org-roam)
|
||||
|
||||
(defcustom org-roam-link-representation 'id
|
||||
"The value used to represent an org-roam link.
|
||||
|
||||
Valid values are
|
||||
* file,
|
||||
* title."
|
||||
:type '(choice (const id)
|
||||
(const title))
|
||||
:group 'org-roam)
|
||||
|
||||
(defcustom org-roam-timestamped-files nil
|
||||
"Whether to use timestamps to generate unique filenames."
|
||||
:type 'boolean
|
||||
:group 'org-roam)
|
||||
|
||||
(defcustom org-roam-timestamp-format "%Y-%m-%d%H%M%S"
|
||||
"The timestamp format to use filenames.")
|
||||
|
||||
(defcustom org-roam-link-id-format "§%s"
|
||||
"The format string used when inserting org-roam links that use id."
|
||||
(defcustom org-roam-file-format "%Y%m%d%H%M%S"
|
||||
"The timestamp format to use filenames."
|
||||
:type 'string
|
||||
:group 'org-roam)
|
||||
|
||||
@@ -61,6 +43,9 @@ Valid values are
|
||||
:type 'string
|
||||
:group 'org-roam)
|
||||
|
||||
(defcustom org-roam-use-timestamp-as-filename t
|
||||
"Whether to use timestamp as a file name. If not true, prompt for a file name each time.")
|
||||
|
||||
(defcustom org-roam-autopopulate-title t "Whether to autopopulate the title."
|
||||
:type 'boolean
|
||||
:group 'org-roam)
|
||||
@@ -133,13 +118,13 @@ If called interactively, then PARENTS is non-nil."
|
||||
(f-child-of-p (file-truename (buffer-file-name (current-buffer)))
|
||||
org-roam-directory)))
|
||||
|
||||
(defun org-roam--get-title (file)
|
||||
"Return title of `FILE'.
|
||||
|
||||
It first tries the cache. If the cache does not contain the file,
|
||||
it will return the title by loading the file."
|
||||
(defun org-roam--get-title-from-cache (file)
|
||||
"Return title of `FILE' from the cache."
|
||||
(or (gethash file org-roam-titles-cache)
|
||||
(org-roam--extract-file-title file)))
|
||||
(progn
|
||||
(unless org-roam-cache-initialized
|
||||
(user-error "The Org-Roam caches aren't built! Please run org-roam--build-cache-async"))
|
||||
nil)))
|
||||
|
||||
(defun org-roam--find-files (dir)
|
||||
"Return all org-roam files in `DIR'."
|
||||
@@ -177,20 +162,15 @@ If `ABSOLUTE', return the absolute file-path. Else, return the relative file-pat
|
||||
(file-relative-name absolute-file-path
|
||||
(file-truename org-roam-directory)))))
|
||||
|
||||
(defun org-roam--get-id (file-path)
|
||||
"Convert `FILE-PATH' to the org-roam id."
|
||||
(file-name-sans-extension
|
||||
(file-relative-name
|
||||
(file-truename file-path)
|
||||
(file-truename org-roam-directory))))
|
||||
(defun org-roam--get-title-or-slug (file-path)
|
||||
"Convert `FILE-PATH' to the file title, if it exists. Else, return the path."
|
||||
(or (org-roam--get-title-from-cache file-path)
|
||||
(-> file-path
|
||||
(file-relative-name (file-truename org-roam-directory))
|
||||
(file-name-sans-extension))))
|
||||
|
||||
(defun org-roam--get-title-or-id (file-path)
|
||||
"Convert `FILE-PATH' to the file title, if it exists. Else, return the id."
|
||||
(or (org-roam--get-title file-path)
|
||||
(org-roam--get-id file-path)))
|
||||
|
||||
(defun org-roam--title-to-id (title)
|
||||
"Convert TITLE to id."
|
||||
(defun org-roam--title-to-slug (title)
|
||||
"Convert TITLE to a filename-suitable slug."
|
||||
(let* ((s (s-downcase title))
|
||||
(s (replace-regexp-in-string "[^a-zA-Z0-9_ ]" "" s))
|
||||
(s (s-split " " s))
|
||||
@@ -232,9 +212,20 @@ If not provided, derive the title from the file name."
|
||||
(org-roam--make-file file-path))
|
||||
(find-file file-path)))
|
||||
|
||||
(defun org-roam--get-new-id ()
|
||||
"Return a new ID, generated from the current time."
|
||||
(format-time-string org-roam-timestamp-format (current-time)))
|
||||
(defun org-roam--get-new-id (&optional title)
|
||||
"Return a new ID, generated from the current time.
|
||||
|
||||
Optionally pass it the title, for a smart file name."
|
||||
(if org-roam-use-timestamp-as-filename
|
||||
(format-time-string org-roam-file-format (current-time))
|
||||
(let* ((slug (read-string "Enter ID (without extension): "
|
||||
(if title
|
||||
(org-roam--title-to-slug title)
|
||||
"")))
|
||||
(file-path (org-roam--get-file-path slug t)))
|
||||
(if (file-exists-p file-path)
|
||||
(user-error "There's already a file at %s")
|
||||
slug))))
|
||||
|
||||
(defun org-roam-new-file ()
|
||||
"Quickly create a new file, using the current timestamp."
|
||||
@@ -243,58 +234,34 @@ If not provided, derive the title from the file name."
|
||||
|
||||
;;; Inserting org-roam links
|
||||
(defun org-roam-insert ()
|
||||
"Insert an org-roam link."
|
||||
"Find an org-roam file, and insert a relative org link to it at point."
|
||||
(interactive)
|
||||
(pcase org-roam-link-representation
|
||||
('id (org-roam--insert-id))
|
||||
('title (org-roam--insert-title))))
|
||||
|
||||
(defun org-roam--insert-title ()
|
||||
"Find `ID', and insert a relative org link to it at point."
|
||||
(let* ((completions (mapcar (lambda (file)
|
||||
(list (org-roam--get-title-or-id file)
|
||||
(org-roam--get-id file)))
|
||||
(list (org-roam--get-title-or-slug file)
|
||||
file))
|
||||
(org-roam--find-all-files)))
|
||||
(title (completing-read "File: " completions))
|
||||
(id (cadr (assoc title completions))))
|
||||
(when (not id)
|
||||
(if org-roam-timestamped-files
|
||||
(setq id (org-roam--get-new-id)))
|
||||
(read-string "Enter new file id: " (org-roam--title-to-id title)))
|
||||
(let ((file-path (org-roam--get-file-path id)))
|
||||
(unless (file-exists-p file-path)
|
||||
(org-roam--make-file file-path title))
|
||||
(insert (format "[[%s][%s]]"
|
||||
(concat "file:" file-path)
|
||||
(format org-roam-link-title-format title))))))
|
||||
|
||||
(defun org-roam--insert-id ()
|
||||
"Find `ID', and insert a relative org link to it at point."
|
||||
(let* ((id (completing-read "File: " (mapcar #'org-roam--get-id (org-roam--find-all-files))))
|
||||
(file-path (org-roam--get-file-path id)))
|
||||
(file-path (or (cadr (assoc title completions))
|
||||
(org-roam--get-new-id title))))
|
||||
(unless (file-exists-p file-path)
|
||||
(org-roam--make-file file-path))
|
||||
(org-roam--make-file file-path title))
|
||||
(insert (format "[[%s][%s]]"
|
||||
(concat "file:" file-path)
|
||||
(format org-roam-link-id-format id)))))
|
||||
(format org-roam-link-title-format title)))))
|
||||
|
||||
;;; Finding org-roam files
|
||||
(defun org-roam-find-file ()
|
||||
"Find and open an org-roam file."
|
||||
(interactive)
|
||||
(let* ((completions (mapcar (lambda (file)
|
||||
(list (org-roam--get-title-or-id file) file))
|
||||
(list (org-roam--get-title-or-slug file) file))
|
||||
(org-roam--find-all-files)))
|
||||
(title-or-id (completing-read "File: " completions))
|
||||
(file-path (cadr (assoc title-or-id completions))))
|
||||
(unless file-path
|
||||
(let ((id (if org-roam-timestamped-files
|
||||
(org-roam--get-new-id)
|
||||
(read-string "Enter new file id: "
|
||||
(org-roam--title-to-id title-or-id)))))
|
||||
(setq file-path (org-roam--get-file-path id t))))
|
||||
(title-or-slug (completing-read "File: " completions))
|
||||
(file-path (or (cadr (assoc title-or-slug completions))
|
||||
(org-roam--get-file-path
|
||||
(org-roam--get-new-id title-or-slug) t))))
|
||||
(unless (file-exists-p file-path)
|
||||
(org-roam--make-file file-path title-or-id))
|
||||
(org-roam--make-file file-path title-or-slug))
|
||||
(find-file file-path)))
|
||||
|
||||
;;; Building the org-roam cache (asynchronously)
|
||||
@@ -536,7 +503,7 @@ This is equivalent to removing the node from the graph."
|
||||
(defun org-roam-update (file-path)
|
||||
"Show the backlinks for given org file for file at `FILE-PATH'."
|
||||
(org-roam--ensure-cache-built)
|
||||
(let ((buffer-title (org-roam--get-title-or-id file-path)))
|
||||
(let ((buffer-title (org-roam--get-title-or-slug file-path)))
|
||||
(with-current-buffer org-roam-buffer
|
||||
(let ((inhibit-read-only t))
|
||||
(erase-buffer)
|
||||
@@ -553,7 +520,7 @@ This is equivalent to removing the node from the graph."
|
||||
(maphash (lambda (file-from contents)
|
||||
(insert (format "** [[file:%s][%s]]\n"
|
||||
file-from
|
||||
(org-roam--get-title-or-id file-from)))
|
||||
(org-roam--get-title-or-slug file-from)))
|
||||
(dolist (content contents)
|
||||
(insert (concat (propertize (s-trim (s-replace "\n" " " content))
|
||||
'font-lock-face 'org-block)
|
||||
@@ -657,15 +624,15 @@ This needs to be quick/infrequent, because this is run at
|
||||
(mapcar (lambda (file)
|
||||
(insert
|
||||
(format " \"%s\" [URL=\"roam://%s\"];\n"
|
||||
(org-roam--get-id file)
|
||||
(org-roam--get-title-or-slug file)
|
||||
file)))
|
||||
(org-roam--find-all-files))
|
||||
(maphash
|
||||
(lambda (from-link to-links)
|
||||
(dolist (to-link to-links)
|
||||
(insert (format " \"%s\" -> \"%s\";\n"
|
||||
(org-roam--get-id from-link)
|
||||
(org-roam--get-id to-link))))
|
||||
(org-roam--get-title-or-slug from-link)
|
||||
(org-roam--get-title-or-slug to-link))))
|
||||
)
|
||||
org-roam-forward-links-cache)
|
||||
(insert "}")
|
||||
|
Reference in New Issue
Block a user