Як я можу оцінити elisp у файлі органода, коли він відкритий?


13

У мене є код elisp, який я хотів би запускати у файлах orgmode, коли вони завантажуються (різні для різних файлів та визначені в самому файлі). Чи є спосіб це зробити? Я нічого не бачив у http://orgmode.org/manual/In_002dbuffer-settings.html

Якщо я можу додати щось до ініціалізації emacs, яка запускає спеціально названий блок коду кожного разу, коли файл orgmode завантажується, це може бути рішенням, але я не знаю, як це зробити, і в ідеалі є щось вбудоване.


1
Можливо, файлові локальні змінні?
Дан

Це працює! Ви хочете зробити це у відповідь, який я можу прийняти?
серв

Надалі думка, що це дуже брудне середовище для редагування, тому хорошим рішенням буде локальна змінна файлу, що працює з іменованим кодовим блоком.
AVV

Загорніть його в прогну чи лямбда, можливо?
День

3
Ви також можете використовувати, # -*- eval: (lisp code here) -*-але ви також повинні бути обізнані про небезпеку. Навіть якщо ви не ділитесь цими документами ні з ким іншим, тлумачення Emacs Lisp означатиме, що зміни можуть випадково призвести до втрати даних. Також гачок режиму звучить як кращий варіант, якщо ви хочете запустити один і той же код для більш ніж одного файлу.
wvxvw

Відповіді:


9

Це рішення не потребує змін init.el(з незначними змінами). Хоча це передбачає локальні оцінки файлів - але це саме те, про що вимагала ОП. Перевагами рішення є:

  • запитує підтвердження для оцінки коду
  • Код elisp можна редагувати і тестувати в середовищі org-babel
  • оскільки рішення не потребує змін init.elу файлі органода, може бути надано (довіреним) користувачам

Я перефразую рішення тут.

Додайте src-блок десь у вашому файлі:

#+NAME: startup
#+BEGIN_SRC emacs-lisp
(your-code-here)
#+END_SRC

Потім поставте це в кінці свого файлу orgmode:

# Local Variables:
# eval: (progn (org-babel-goto-named-src-block "startup") (org-babel-execute-src-block) (outline-hide-sublevels 1))
# End:

Я додав, (outline-hide-sublevels 1)тому що мені подобається ховати src-блок всередині заголовка і хочу, щоб підрівні приховувалися під час запуску. Без цього твердження суборівні будуть розширені на (org-babel-goto-named-src-block "startup").

За допомогою цього рішення, emacs запитає дозволу на виконання (1-й: застосувати локальні змінні; 2-й: виконати "startup" -src-блок). Оскільки у моєму файлі багато src-блоків, я встановив ще один файл-локальна змінна org-confirm-babel-evaluate, наприклад, такий:

# Local Variables:
# org-confirm-babel-evaluate: nil
# eval: (progn (org-babel-goto-named-src-block "startup") (org-babel-execute-src-block) (outline-hide-sublevels 1))
# End:

Попередження: З цим доповненням, emacs підкаже лише один раз про дозвіл на виконання - всі src-блоки в цьому файлі тепер можуть бути виконані без додаткового підтвердження. Як вже вказували інші, така поведінка може бути небезпечною, і ви повинні бути дуже обережними з цим налаштуванням.

Тим НЕ менше, я б стверджувати , що це рішення (особливо перша версія) є більш безпечним , ніж один даними Джо Corneli , тому що принаймні у вас буде запропоновані для підтвердження для виконання. Рішення Джо буде оцінювати спеціальний блок без підтвердження, якщо він знайдеться у файлі. Зловмисникові, звичайно, доведеться відгадати назву спеціального блоку ...

Я використовую такий підхід для написання великих документів, які потребують, наприклад, адаптації до механізмів організації експорту.


5

org-mode... Окрім будь-яких гачків, які його батьківський режим, outline-modeможливо, запускався, цей режим працює гаком org-mode-hook, як останній крок під час ініціалізації.

Отже, у вашому init.el:

(defun function-that-finds-and-evaluates-special-block ()
;; DWIM :-)
)
(add-hook 'org-mode-hook 'function-that-finds-and-evaluates-special-block)

Мені це здається більш розумним, ніж файли-файли для цього завдання. Але, можливо, мені чогось не вистачає.
Дрю

@Joe Corneli І що тоді ви додали до фактичного файлу org?
лампа розжарювання

Нічого особливого, крім «спеціального блоку».
Джо Корнелі

3

Так як ви просите

(різні для різних файлів та визначені у самому файлі)

то спробуйте це рішення .


Хочете пояснити, чому голосування "за"?
Користувач Emacs

Це тому, що відповіді, які є лише посиланнями на інші відповіді, не враховують. Якщо говорити, можливо, це питання є дурнем того, з ким ви пов’язані?
Лінус Арвер

1

Я погоджуюся з пропозицією @Joe Corneli щодо використання гачка.

Мені здається, що ви можете використовувати закладки тут: покладіть на гачок певний стрибок закладок. Перевагою закладки до кодового блоку є те, що він, як правило, переміщується автоматично (наприклад, у міру зміни вмісту файлу), тому про розміщення блоку, як правило, слід дбати про автоматичне.

[Але мені незрозуміло, чому ви маєте код у файлах режиму Org, а не в іншому місці. Ми сприймаємо це як дане, відповідно до постановки проблеми, але мені цікаво, чому ви це робите. Повідомлення нас про дизайн у цьому відношенні може призвести до кращої допомоги.]


0

Я намагався вдосконалити код від Джо Корнелі:

Це вам потрібно у вашому файлі init.el:

  (defun tdh/eval-startblock ()
    (if (member "startblock" (org-babel-src-block-names))
      (save-excursion
        (org-babel-goto-named-src-block "startblock")
        (org-babel-execute-src-block))
      nil
      )
    )
  (add-hook 'org-mode-hook 'tdh/eval-startblock)

Кожен раз, коли ви відкриваєте буфер в органічному режимі, він шукатиме вихідний блок з ім'ям startblock, якщо такий знайдеться, він виконає його.

У файлах, які перебувають в органічному режимі, ви можете вставити:

#+NAME: startblock
#+BEGIN_SRC emacs-lisp
  ;; Any code you want
#+END_SRC
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.