0

According to the write-file-functions doc-string, "[t]his variable's value is permanent if it is given a local binding."

  • Step 1: Start from emacs -q using Emacs 25.2.1.

  • Step 2: Switch to the *scratch* buffer.

  • Step 3: Type the following in the *scratch* buffer, so that it gets modified and so that we can later evaluate what we typed.

    (add-hook 'write-file-functions (lambda () (message "hello-world")) 'append 'local)

  • Step 4: Evaluate the statement that we typed in Step 3 above -- e.g., C-x C-e

  • Step 5: M-x save-buffer and save it anywhere that is appropriate. I chose to call the file foo and I saved it as ~/Desktop/foo

  • Step 6: M-x describe-variable RET write-file-functions RET; or, C-h v and then the name of the variable we are looking up.

    write-file-functions is a variable defined in ‘files.el’.

    Its value is nil

I expected the write-file-functions hook to maintain the original value because it is permanent when given a local binding. Why is my assumption incorrect?

lawlist
  • 19,106
  • 5
  • 38
  • 120

2 Answers2

1

No explanation, but here are some observations:

  1. I can reproduce this with emacs -Q.

  2. In the help to this var is stated: This variable may be risky if used as a file-local variable.
    This line is added dynamically, it is not stated in the source files.el

  3. You are saving a buffer without a file (*scratch*) to a file. The buffer *scratch* does not exist afterwards, but you have a new buffer called foo.

    If you redo your (add-hook ...) inside the new buffer foo and then save the foo buffer with the already given name, this write-file-functions variable keeps it value.

  4. Doing the same with a local variable (set (make-local-variable 'foo) "value") keeps the variable value always.

And then, I do not know emacs nor elisp good enough. :(

jue
  • 4,576
  • 8
  • 21
1

C-hv write-file-functions

write-file-functions is a variable defined in ‘files.el’.

This variable’s value is permanent if it is given a local binding.
This variable may be risky if used as a file-local variable.

Documentation:
List of functions to be called before saving a buffer to a file.
Only used by ‘save-buffer’.

If one of them returns non-nil, the file is considered already written and the rest are not called.

These hooks are considered to pertain to the visited file. So any buffer-local binding of this variable is discarded if you change the visited file name with M-x set-visited-file-name, but not when you change the major mode.

This hook is not run if any of the functions in ‘write-contents-functions’ returns non-nil. Both hooks pertain to how to save a buffer to file, for instance, choosing a suitable coding system and setting mode bits. (See Info node ‘(elisp)Saving Buffers’.) To perform various checks or updates before the buffer is saved, use ‘before-save-hook’.

phils
  • 50,977
  • 3
  • 79
  • 122