I would like to set the environment variables for a spawned subprocess only.
They are controlled by process-environment. The documentation says:
binding that variable with let is also reasonable practice.
In this example I try to unset HOME with:
(defun f()
(let ((old-home (getenv "HOME")))
(let* ((process-environment process-environment)
(process-environment (setenv-internal process-environment "HOME" nil nil)))
(start-process "proc" nil "notepad"))
(string= old-home (getenv "HOME"))))
(f)
(f) returns nil and process-environment is permanently changed (outside the let*).
Another thing, that happens when debugging, is that concurrent processes using HOME (for example Emacs autosave hooks) might fail crashing the debug session.
An alterative would be to use two setenvs before and after start-process. It still would not solve the conflict with concurrent processes (and does not explain how to use process-environment inside a let).