Why does (set-auto-mode)
remove the local variable binding and how I can keep the local binding around?
(defvar-local test-var nil)
(setq test-var t)
(message "%s" test-var) ;; t
(set-auto-mode)
(message "%s" test-var) ;; nil
Why does (set-auto-mode)
remove the local variable binding and how I can keep the local binding around?
(defvar-local test-var nil)
(setq test-var t)
(message "%s" test-var) ;; t
(set-auto-mode)
(message "%s" test-var) ;; nil
The first thing that any major mode does is call kill-all-local-variables
.
This function eliminates all the buffer-local variable bindings of
the current buffer except for variables marked as permanent and
local hook functions that have a non-‘nil’ ‘permanent-local-hook’
property (*note Setting Hooks::). As a result, the buffer will see
the default values of most variables.
This function also resets certain other information pertaining to
the buffer: it sets the local keymap to ‘nil’, the syntax table to
the value of ‘(standard-syntax-table)’, the case table to
‘(standard-case-table)’, and the abbrev table to the value of
‘fundamental-mode-abbrev-table’.
The very first thing this function does is run the normal hook
‘change-major-mode-hook’ (see below).
Every major mode command begins by calling this function, which has
the effect of switching to Fundamental mode and erasing most of the
effects of the previous major mode. To ensure that this does its
job, the variables that major modes set should not be marked
permanent.
‘kill-all-local-variables’ returns ‘nil’.
how I can keep the local binding around?
A buffer-local variable is “permanent” if the variable name (a
symbol) has a ‘permanent-local’ property that is non-‘nil’. Such
variables are unaffected by ‘kill-all-local-variables’, and their local
bindings are therefore not cleared by changing major modes. Permanent
locals are appropriate for data pertaining to where the file came from
or how to save it, rather than with how to edit the contents.
E.g. To define a variable which should be permanent-local
:
(defvar VARNAME ...)
(put 'VARNAME 'permanent-local t)
Setting this property for variables which were not intended to be treated that way should be done with due care and consideration for whatever ramifications that will have.