[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
bug#60162: [PATCH] * lisp/cus-edit.el (setopt--set): Warn instead of ras
From: |
Philip Kaludercic |
Subject: |
bug#60162: [PATCH] * lisp/cus-edit.el (setopt--set): Warn instead of rasing an error |
Date: |
Sat, 17 Dec 2022 18:00:43 +0000 |
Drew Adams <drew.adams@oracle.com> writes:
>> Setopt checks the :type of a user option, and raises an user-error if
>> the value doesn't match the type. This can be annoying during
>> initialisation, because minor mistakes interrupt everything and you are
>> let with a partially loaded configuration.
>>
>> I'd propose replacing the `user-error' with a `warn', that would still
>> indicate mistakes, but continue loading the init.el.
>
> I don't have Emacs 29, so I don't know what
> `setopt' is/does. But if it does more or less
> what `customize-set-variable` does then:
It is a macro that allows customising user options like setq
+++
** New macro 'setopt'.
This is like 'setq', but is meant to be used for user options instead
of plain variables, and uses 'custom-set'/'set-default' to set them.
> Can `setopt' be used interactively?
No, for it is a macro.
> `customize-set-variable' raises an error when
> used interactively, if the type doesn't match.
> It does that in the `interactive' form, with
> `custom-prompt-variable'.
>
> But `customize-set-variable' _doesn't_ raise
> an error when called from Lisp with a type
> mismatch (the type check is done only in
> `interactive').
Yes, take a look at the changed definitions:
--8<---------------cut here---------------start------------->8---
;;;###autoload
(defmacro setopt (&rest pairs)
"Set VARIABLE/VALUE pairs, and return the final VALUE.
This is like `setq', but is meant for user options instead of
plain variables. This means that `setopt' will execute any
`custom-set' form associated with VARIABLE.
\(fn [VARIABLE VALUE]...)"
(declare (debug setq))
(unless (zerop (mod (length pairs) 2))
(error "PAIRS must have an even number of variable/value members"))
(let ((expr nil))
(while pairs
(unless (symbolp (car pairs))
(error "Attempting to set a non-symbol: %s" (car pairs)))
(push `(setopt--set ',(car pairs) ,(cadr pairs))
expr)
(setq pairs (cddr pairs)))
(macroexp-progn (nreverse expr))))
;;;###autoload
(defun setopt--set (variable value)
(custom-load-symbol variable)
;; Check that the type is correct.
(when-let ((type (get variable 'custom-type)))
(unless (widget-apply (widget-convert type) :match value)
(warn "Value `%S' does not match type %s" value type)))
(put variable 'custom-check-value (list value))
(funcall (or (get variable 'custom-set) #'set-default) variable value))
--8<---------------cut here---------------end--------------->8---
You see that `customize-set-variable' isn't used at all, to prevent
modifying the user theme. The error/warning is raised by `setopt--set'.
> Since you mention "initialisation" I guess
> this is about calls from Lisp.
> ___
>
> [If `setopt' does what `customize-set-variable'
> does, why was it added? If not, what's its
> particular use case? Just curious; I can always
> wait to find out what Emacs 29 presents...]
As mentioned above, it allows user options to be set like variables
using setq. That means no quoting of user option names and multiple
options can be set in a single call.