EFLS / zetteldeft

A Zettelkasten system! Or rather, some functions on top of the emacs deft package.
https://efls.github.io/zetteldeft
GNU General Public License v3.0
394 stars 42 forks source link

How to create obsidian-style links #104

Open mediapathic opened 3 years ago

mediapathic commented 3 years ago

Obsidian is an increasingly popular markdown editor. I used it for a while, and I have a bunch of files that use its link method, which is essentially full filename and no UID required. I wrote some code to insert links in this style:

(defun my-zetteldeft-find-file-filename-insert (file)
  "Find deft file FILE and insert a link with filename."
  (interactive (list
                (completing-read "File to insert full title from: "
                                 (deft-find-all-files-no-prefix))))
  (let ((deft-use-filename-as-title t))
  (insert zetteldeft-link-indicator
          (substring (file-name-sans-extension file) 1 nil)
          zetteldeft-link-suffix
          )))

I also have set

(setq zetteldeft-link-indicator "[[")
(setq zetteldeft-link-suffix "]]")

I have yet to find a way to actually follow these as links; I am using zetteldeft-search-at-point which works well enough for both use cases of filename and uid, but if anyone has suggestions for treating these as proper links, I would appreciate it.

I post this here mostly to help anyone who like me was struggling with links like this, and also @EFLS I will be happy to make a PR for this if you'd like, though I expect if you want to include this just copying and pasting will be easier :)

EFLS commented 3 years ago

Hi @mediapathic

use [the Obsidian] link method, which is essentially full filename and no UID required

I'm unfamiliar with Obsidian, but this way of working seems inconvenient when you decide to rename files, no?

I have yet to find a way to actually follow these as links; I am using zetteldeft-search-at-point which works well enough for both use cases of filename and uid, but if anyone has suggestions for treating these as proper links, I would appreciate it.

You could write a new function that resembles the -search-at-point one, but calls zetteldeft--search-filename rather than --search-global.

That would look like this:

(defun efls/zetteldeft-search-file-at-point ()
  "Search via `deft' with `thing-at-point' as filter.
Thing can be a double-bracketed link, a hashtag, or a word.
Searches filenames only. When a single file is found, it is opened."
  (interactive)
  (let ((string (zetteldeft--get-thing-at-point)))
   (if string
       (zetteldeft--search-filename string nil)
     (user-error "No search term at point"))))

One potential issue is that zetteldeft--get-thing-at-point might filter too much of the filename. However, if your links are always between [[ ]], it should work.

EFLS commented 3 years ago

If you find a setup that works let me know and/or submit a note to or PR for zd-tutorial!

mediapathic commented 3 years ago

I'm unfamiliar with Obsidian, but this way of working seems inconvenient when you decide to rename files, no?

It is indeed. One of the major selling points of Obsidian is that it has internal detection and automatic update of all links across your files when a file is renamed (it's really quite amazing). So, this works great, but after working in Obsidian for a long time and then moving to emacs... I have a lot of files without UIDs in the filename.

I also have been taking notes in plain text form for a long, long time before I learned about the zettelkasten method, so I have lots of old files from vimwiki, log files named things like "2013-04-01.md", etc. As I find these I am very slowly adding UIDs to the ones that are actually useful, but for now it is very helpful to be able to link to even badly-formed files.

I have yet to find a way to actually follow these as links; I am using zetteldeft-search-at-point which works well enough for both use cases of filename and uid, but if anyone has suggestions for treating these as proper links, I would appreciate it.

You could write a new function that resembles the -search-at-point one, but calls zetteldeft--search-filename rather than --search-global.

That would look like this:

(defun efls/zetteldeft-search-file-at-point ()
  "Search via `deft' with `thing-at-point' as filter.
Thing can be a double-bracketed link, a hashtag, or a word.
Searches filenames only. When a single file is found, it is opened."
  (interactive)
  (let ((string (zetteldeft--get-thing-at-point)))
   (if string
       (zetteldeft--search-filename string nil)
     (user-error "No search term at point"))))

One potential issue is that zetteldeft--get-thing-at-point might filter too much of the filename. However, if your links are always between [[ ]], it should work.

Initial, brief testing indicates that not only does this work, it actually solves my other problem I mentioned in #99 . This function seems to directly open both md-style and org-style links (assuming I set the filename as the link text, which is my usual practice) in both markdown and org files. This little chunk of code solves a problem I have been beating my head against for days now! If I didn't already owe you a beverage of your choice for writing zetteldeft, now I owe you at least two.

Thank you, even moreso than usual.

AtomicNess123 commented 2 years ago

I'm unfamiliar with Obsidian, but this way of working seems inconvenient when you decide to rename files, no?

It is indeed. One of the major selling points of Obsidian is that it has internal detection and automatic update of all links across your files when a file is renamed (it's really quite amazing). So, this works great, but after working in Obsidian for a long time and then moving to emacs... I have a lot of files without UIDs in the filename.

I also have been taking notes in plain text form for a long, long time before I learned about the zettelkasten method, so I have lots of old files from vimwiki, log files named things like "2013-04-01.md", etc. As I find these I am very slowly adding UIDs to the ones that are actually useful, but for now it is very helpful to be able to link to even badly-formed files.

I have yet to find a way to actually follow these as links; I am using zetteldeft-search-at-point which works well enough for both use cases of filename and uid, but if anyone has suggestions for treating these as proper links, I would appreciate it.

You could write a new function that resembles the -search-at-point one, but calls zetteldeft--search-filename rather than --search-global. That would look like this:

(defun efls/zetteldeft-search-file-at-point ()
  "Search via `deft' with `thing-at-point' as filter.
Thing can be a double-bracketed link, a hashtag, or a word.
Searches filenames only. When a single file is found, it is opened."
  (interactive)
  (let ((string (zetteldeft--get-thing-at-point)))
   (if string
       (zetteldeft--search-filename string nil)
     (user-error "No search term at point"))))

One potential issue is that zetteldeft--get-thing-at-point might filter too much of the filename. However, if your links are always between [[ ]], it should work.

Initial, brief testing indicates that not only does this work, it actually solves my other problem I mentioned in #99 . This function seems to directly open both md-style and org-style links (assuming I set the filename as the link text, which is my usual practice) in both markdown and org files. This little chunk of code solves a problem I have been beating my head against for days now! If I didn't already owe you a beverage of your choice for writing zetteldeft, now I owe you at least two.

Thank you, even moreso than usual.

In Zetteldeft, when you update a file, is there a way to update all links in associated files to it?

EFLS commented 2 years ago

Links are resolved via the unique ID. So long as you don't change the ID in the filename, there's no need to update any links.