1

When working with phone calls and tickets, I use Emacs in Org mode to pre-create the entry with the heading containing the current date and time. For obvious reasons, if not constantly using a new file (which would make history searches more difficult), I end up with a very long flat list of call headings and their respective contents.

I now want to change that, so that I get a top-level header with the year, a second-level header with the month and then a third-level header with the actual call entry.

In my trials, I manage to get the results when using the first entry inside the call file, but as soon as I get the second (third, fourth), the indentation is getting deeper with each entry. I also experimented with "post-editing" the automation (e.g. (org-insert-subheading t) (beginning-of-line) (delete-char 1) (end-of-line)), but I find that very messy to the point that items like (org-insert-heading) would have no meaning anymore.

The result shall look somewhat like this:

* <2019>
** <12>
*** call <date&time_of_call>
*** call <date&time_of_call>
* <2020>
** <01>
*** call <date&time_of_call>
*** call <date&time_of_call>
** <02>
*** call <date&time_of_call>
*** call <date&time_of_call>
...

My code so far looks like this (I call eltest with a key shortcut):

(defvar sFilePath "~/Documents/Emacs/"
  "Path to directory.")

(defvar sTestEntryYear "<%Y>"
  "Year format string for entry headings.")
(defvar sTestEntryMonth "<%m>"
  "Month format string for entry headings.")
(defvar sTestEntry "<%a, %Y-%m-%d %H:%M:%S>"
  "Date & time format string for entry headings.")

(defun insert_test_template ()
  "Insert the test template"
  (interactive)
      ((lambda ()
     (org-insert-subheading t)
     (insert (concat "Calls " sNow " Call|WalkUp: ProblemDescription\n\n"))
     (insert "template goes on here\n")
     (insert "RESULT\n")
     (insert "-> "))))

(defun eltest ()
  "Add a new call entry."
  (interactive)
  (switch-to-buffer (find-file (concat sFilePath "Test.org")))
  (widen)
  (let ((sThisYear (format-time-string sTestEntryYear)) (sThisMonth (format-time-string sTestEntryMonth)) (sNow (format-time-string sTestEntry)))
    (end-of-buffer)
    (unless (org-goto-local-search-headings sThisYear nil t)
      ((lambda ()
     (org-insert-heading nil nil t)
     (insert (concat sThisYear "\n")))))
    (end-of-buffer)
    (unless (org-goto-local-search-headings sThisMonth nil t)
      ((lambda ()
     (org-insert-subheading t)
     (insert (concat sThisMonth "\n")))))
    (end-of-buffer)
    (unless (org-goto-local-search-headings sNow nil t)
      ((lambda ()
     (insert_test_template))))
    (while (progn
         (previous-line 1)
         (not (looking-at "^- Name  : $"))))
    (org-show-entry)
    (end-of-line)))
Phoenix
  • 351
  • 1
  • 9
  • 1
    Have you looked at datetrees? – NickD Jun 03 '20 at 22:08
  • 1
    Not yet due to me not knowing about its existence. Don't get me wrong, I do use the manual inside Emacs as well, but when one does not know what to look for, it becomes quite daunting to find stuff. I will see, if I can make sense of it for my purpose. Thanks so far! – Phoenix Jun 04 '20 at 04:42

1 Answers1

2

What you're asking for looks like Org Capture Templates.

(define-key global-map "\C-cc" 'org-capture)

(setq org-capture-templates
'(("c" "Calls arranged in a date tree" entry
    (file+datetree "~/calls.org" "Calls and Meetings")
    "* %^{type|Call|WalkUp|Meeting}: %^{problem} %T
     + %?

     +  RESULT
        + "
    :clock-in t :clock-resume t)))

To use the template with the given key binding, you hit C-c c c as soon as you get a call or a walk-up. The template prompts you for the type, then lets you enter a problem description. You are placed into a capture buffer with the text insert point at the location of the %? in the template - in this case I made it a list that you can add lines to with M-RET.

To file the event from the capture buffer, you hit C-c C-c, or C-c C-k to abort.

The result is very similar to what you asked for:

* Calls and Meetings
** 2020
*** 2020-06 June
**** 2020-06-04 Thursday
***** DONE Call: Stuff got broken <2020-06-04 Thu 09:08>
      :LOGBOOK:
      - State "DONE"       from "STARTED"    [2020-06-04 Thu 09:08]
      - State "STARTED"    from              [2020-06-04 Thu 09:01]
      CLOCK: [2020-06-04 Thu 09:01]--[2020-06-04 Thu 09:08] =>  0:07
      :END:
         + I resolved the issue by fixing the widget.
         + RESULT
           + FIXED!

The template additionally starts a clock which gives you time tracking, but you can eliminate that if you'd like.

Refs:

gregoryg
  • 925
  • 6
  • 8
  • 1
    As with all major new functions I discover in Emacs, this is entirely mind-blowing and jaw-dropping. Thank you very much for the example. It is so much easier to learn such complex features seeing even a single, proper example. The manual and a lot of online resources unfortunately lack such things a lot of times leaving me stranded and reeling to work it out with painstaking trial and error. Therefore: Thank you very much! You got my vote (and would get another, if I could). – Phoenix Jun 04 '20 at 17:39
  • I saw your plea in the comment - glad it blows your mind. I learn new things nearly every week after 25+ years of Emacs. The clocking stuff is amazing when combined with Org Agenda, which is a whole universe in itself! – gregoryg Jun 04 '20 at 17:57