Utiliser spacemacs aux côtés d’emacs: comment garder un fichier .emacs.d séparé


32

Je voudrais essayer spacemacs. Mais je ne souhaite pas pour l'instant passer de la configuration habituelle à emacs. J'aimerais donc que la configuration qui se trouve actuellement dans mon .emacs.drépertoire soit dans un répertoire et que la configuration équivalente pour spacemacs se trouve dans un autre répertoire. Peu importe le nom de chaque répertoire.

Est-ce possible, à court de chroots / LD_PRELOAD / autre telle ruse? Comment puis-je le faire?


2
Voir aussi la réponse de Dan à une question similaire que j'avais concernant l'installation d'un minuteur avec des options au démarrage d'Emacs: emacs.stackexchange.com/questions/3588/… J'utilise depuis une légère variation de cette réponse.
lawlist

1
Dans la catégorie «autres astuces», vous pourriez peut-être créer un lien symbolique spacemacspointant sur l'exécutable emacs et utiliser la valeur de (car command-line-args)pour décider du fichier init à exécuter. Ceci suppose, bien sûr, que vous utilisez un système Unix autre que OS X. (La manière dont les bundles d'application fonctionnent sur OS X rend cette astuce difficile à réaliser.)
Harald Hanche-Olsen le

1
Voir une autre approche ici: emacs.stackexchange.com/q/4253/780
glucas

2
Je reviens à peine pour dire, environ 18 mois plus tard, que c'est toujours la raison pour laquelle je n'ai pas appris les astronautes. J'ai eu quelques problèmes avec la réponse acceptée alors, juste essayé à nouveau, toujours vrai. Après l’ajout de la couche org, "la définition de la fonction de Symbol est vide: boucle" tout à l’heure. Je ne sais pas si cela fait partie de la cause, mais c'est exactement le problème: pour un projet "batteries incluses", il semble étrange de devoir bricoler quelque chose juste pour le démarrer, puis se demander si ma configuration est prise en charge? Peut-être injuste mais cela me fait perdre confiance. Peut-être que dans 18 mois, tout sera réglé ...
Croad Langshan Le

Réponses:


20

Une option consiste à spécifier la configuration que vous souhaitez charger dans un ~/.emacsfichier. Quand Emacs démarre, il recherchera un tel fichier avant de regarder dedans ~/.emacs.d/. Pour plus de détails, vous pouvez en savoir plus sur le fichier Init dans le manuel Emacs.

Ainsi, par exemple, vous pouvez créer un ~/.spacemacs.det conserver votre existant ~/.emacs.dtel quel. Créez ensuite un ~/.emacsfichier pour charger celui que vous souhaitez utiliser:

(setq use-spacemacs t)   ; or nil 

(when use-spacemacs
  (setq user-emacs-directory "~/.spacemacs.d/"))   ; defaults to ~/.emacs.d/

(load (expand-file-name "init.el" user-emacs-directory))

Si vous le souhaitez, vous pouvez trouver des moyens de changer de configuration sans modifier le fichier .emacs. Par exemple, demandez à vos .emacs de vérifier certaines variables d’environnement que vous définissez dans votre shell ou dans un script que vous utilisez pour démarrer spacemacs:

(setq use-spacemacs (getenv "USE_SPACEMACS"))

1
Il doit sûrement y avoir un moyen de savoir si vous utilisez spacemacs ou non? Par exemple, en vérifiant (avec fboundp) une fonction ou une commande unique à spacemacs?
Harald Hanche-Olsen

2
Bien sûr, mais ce n’était pas la question telle que je l’ai comprise. Spacemacs n’est qu’une configuration emacs et le PO veut savoir comment gérer plusieurs répertoires de configuration indépendants d’emacs.
glucas

1
@ HaraldHanche-Olsen qui m'a surpris aussi quand je l'ai téléchargé, mais quand j'y ai réfléchi, cela prenait tout son sens. Je pense que la raison en est que, pour la plupart des systèmes, il semble nécessaire de créer un "produit" poli comme un spacemac, il est donc nécessaire d'exploiter un langage système de niveau inférieur - mais dans emacs, il y a beaucoup d'extensibilité (merci, elisp) que ce n'est pas nécessaire.
Croad Langshan

1
J'ai accepté cela, mais je ne l'avais pas réellement essayé. Maintenant que j'ai, cela ne fonctionne pas tout à fait tel quel: Erreur de fichier: Impossible d'ouvrir le fichier de chargement, /home/me/.emacs.d/core/core-load-paths.el - J'avais besoin de (setq user-emacs-directory "~/.spacemacs.d/")cela pour cela travail (dans une prognbranche de votre conditionnel). Pouvez-vous ajouter cela à votre réponse pour que je puisse l'accepter à nouveau?
Croad Langshan

2
@glucas je suis sur win10, pour une raison quelconque, HOME a été assigné à c: / users / nate. Suppression de la variable environnementale et tout a bien fonctionné.
Nathaniel Saxe le

12

Comme il y a plus à faire sur init que le simple chargement d'un fichier et que, d'autre part, créer des liens symboliques .emacs.dou modifier les HOMEmodifications de mon environnement d'exécution, j'ai opté pour une variante de ce que @glucas avait proposé. J'ai utilisé le code de startup.elet ajouté le correctif de # 15539 pour utiliser une variable d'environnement permettant de basculer entre différents répertoires d'initialisation. Si aucun n'est donné, la valeur par défaut est utilisée.

Il y avait un problème avec spacemacs: asyncne sait pas à propos du répertoire init modifié et ne peut donc pas trouver certains fichiers nécessaires. Mais ceci a été résolu récemment dans spacemacs: Erreur lors de l’utilisation d’un répertoire de configuration autre que .emacs.d · Issue # 3390

Voici donc mon ~/.emacsqui devrait se comporter comme le code init initial mais avec un répertoire init configurable:

;;; .emacs --- let the user choose the emacs environment to use

;;; Commentary:
;;; This code mimics the behaviour of `startup.el' to let the
;;; usage of the custom init directory behave just like the
;;; one and only "~/.emacs.d".
;;;
;;; By setting the environment variable `EMACS_USER_DIRECTORY'
;;; the user-emacs-directory can be chosen and if there is an
;;; `init.el' the configuration from that directory will be used.
;;; If the environment variable is not set or there is no `init.el'
;;; the default configuration directory `~/.emacs.d/' will be used.
;;;
;;; The variable `server-name' will be set to the name of the directory
;;; chosen as start path.  So if the server will be started, it can be
;;; reached with 'emacsclient -s servername'.
;;;
;;; This now works with a current version of spacemacs but does not
;;; work with `async-start' in general, if the code executed with `async'
;;; uses `user-init-dir' or makes other assumptions about the emacs
;;; start-directory.

;;; Code:
(let* ((user-init-dir-default
    (file-name-as-directory (concat "~" init-file-user "/.emacs.d")))
       (user-init-dir
    (file-name-as-directory (or (getenv "EMACS_USER_DIRECTORY")
                    user-init-dir-default)))
       (user-init-file-1
    (expand-file-name "init" user-init-dir)))
  (setq user-emacs-directory user-init-dir)
  (with-eval-after-load "server"
    (setq server-name
      (let ((server--name (file-name-nondirectory
                   (directory-file-name user-emacs-directory))))
        (if (equal server--name ".emacs.d")
        "server"
          server--name))))
  (setq user-init-file t)
  (load user-init-file-1 t t)
  (when (eq user-init-file t)
    (setq user-emacs-directory user-init-dir-default)
    (load (expand-file-name "init" user-init-dir-default) t t)))

(provide '.emacs)
;;; .emacs ends here

Il y a aussi un ajout intéressant qui le fait fonctionner comme un démon sans effort supplémentaire: le nom du serveur sera défini sur le nom du répertoire init. Alors maintenant, vous pouvez démarrer un deuxième démon emacs avec un spacemacs vanille

EMACS_USER_DIRECTORY=~/.emacsenv.d/spacemacs emacs --daemon

et toujours utiliser emacsclient

emacsclient -s spacemacs -c -e '(message "Hello spacemacs")'

Mon cas d'utilisation est très simple et je suis stupéfait d'être le seul: j'ai un démon emacs qui tourne toujours et je l'utilise depuis gui et sur console (avec ssh par exemple). Dans cet Emacs, je prépare toute ma documentation et mon journal de travail, il doit donc être là tout le temps. Mais ensuite, je veux essayer spacemacs ou l'un des autres packages de distribution et même le configurer, jusqu'à ce que je puisse abandonner ma configuration actuelle ou utiliser certaines des idées intelligentes. Et comme d'autres, je voulais créer une configuration de base simple pour mes collègues - et la documenter avec org-mode dans mon instance en cours d'exécution.

Comme le seul problème que je connaisse est asyncqu’il ne connait pas le répertoire d’initialisation modifié, je pense au meilleur moyen d’ajouter une configuration à des asyncvariables qui devraient être injectées par défaut, de sorte qu’il n’est pas nécessaire de corriger tous les correctifs. invocations d’ async-startespace comme les astronautes.


C'est vraiment charmant et a fonctionné à merveille ... jusqu'à ce que j'en aie besoin async. :-( Depuis que vous avez posté depuis quelques mois, avez-vous une solution de contournement?
Trey

Malheureusement non - mais pour spacemacs, il est fixe et pour les asynchrones généraux, je ne sais pas vraiment s'il doit y avoir aucun changement, car async-startdémarre emacs sans rien et si vous voulez utiliser une variable, vous devez la transmettre. être agréable et pratique, si async peut être configuré avec une liste de variables, qui sera utilisé à chaque invocation de async-start.
Uwe Koloska

1
Avec cette approche, il se peut que d’autres variables soient initialisées à partir du répertoire utilisateur-emacs par défaut avant le chargement de votre fichier .emacs. Par exemple, je devais ajouter (setq custom-theme-directory user-emacs-directory)ici.
glucas

1
Je ne sais pas où cette variable est définie, car lorsque je l'examine dans un test minimal, j'obtiens: Sa valeur est "~ / .emacs.d /". La valeur d'origine était "~ / .emacsenv.d / init-test /". Elle a donc la bonne valeur, mais elle a été écrasée.
Uwe Koloska

1
En fait, j'ai fini par utiliser cette réponse longtemps après avoir posé la question. Je n'ai pas changé la réponse acceptée parce que c'est trop long et parce que je n'ai pas vraiment prêté beaucoup d'attention à la mise en œuvre! Cette réponse m'a toutefois été très utile.
Croad Langshan

5

Il est expliqué ici et un PR est en cours pour l'ajouter à la documentation:

mkdir ~/spacemacs
git clone git@github.com:syl20bnr/spacemacs.git ~/spacemacs/.emacs.d
HOME=~/spacemacs emacs```

6
Oui, je change parfois de pays pour essayer une autre configuration. L'inconvénient est que HOME est utilisé pour d'autres tâches que vous préférez ne pas affecter.
glucas

3

Cela a déjà été répondu et accepté, mais si vous avez envie d'essayer de nouvelles façons de faire les choses de manière réversible (au-delà de la configuration emacs), je vous recommanderais de passer une demi-heure à vous familiariser avec GNU Stow. C'est en quelque sorte ln -ssur les stéroïdes, et il pourrait y avoir plusieurs approches pour l'utiliser. Vous pouvez avoir la configuration complète dans un seul sous-répertoire (y compris les configurations offlineimap, emacs, etc.) - ce serait une approche basée sur l'environnement - ou avoir un sous-répertoire distinct pour chaque application que vous possédez. Schizophrénie sucrée.

Exemple: liste relative à emacs de mon ~ / Stow:

-> % ls ~/Stow | grep emacs
emacs 
emacs_from_scratch
spacemacs
hoodoo@T450s 2:46 [~]

Il y a une configuration initiale que j'ai réussi à rendre utilisable, une configuration «je reste avec les valeurs par défaut» et une «je vais rouler la mienne». Je peux simplement activer et désactiver chacun de ces éléments et les avoir toujours disponibles. Chaque sous-répertoire peut avoir un arbre entier par rapport à mon ~ / et il est très pratique de le mélanger.


J'utilise déjà stow comme cela se produit. Mais comment l'utilisez-vous pour cela? Vous surveillez simplement votre fichier .emacs.d en faisant un lien symbolique avec celui que vous souhaitez utiliser, à l’aide de stow? Avez-vous déjà couru les deux en même temps? Si oui, je suppose que les deux émacs pensent qu'ils "possèdent" .emacs.d. Je me demande si cela pourrait causer des problèmes avec des choses qui sauvent des choses là-bas, comme je ne sais pas dire recentf, savehist, autosave, etc., surtout quand les deux copies d’emacs fonctionnent avec des configurations radicalement différentes?
Croad Langshan

Non, je modifie simplement les configurations selon les besoins.
Roman Grazhdan

2

J'ai vérifié le patch utilisé par @Uwe Koloska. Ce n'était pas inclus dans la branche principale. Je suis plutôt d’accord, je pense que le problème devrait être résolu en dehors d’emacs en utilisant le shell et laisser emacs n’en sait rien.

Peut-être que cette fonctionnalité serait plus logique du point de vue de l'utilisateur, l'utilisation d'un drapeau serait moins compliquée pour certains utilisateurs.

Dans mon cas d'utilisation, je souhaite conserver mon installation Emacs et Spacemacs afin que ma variante des deux solutions ci-dessus fonctionne de la manière suivante.

script shell

Tout d’abord le script de lancement de spacemacs:

#!/bin/sh

export EMACS_USER_DIR=~/spacemacs/emacs.d

exec emacs "$@"

Ce script s'appelle spacemacset est installé dans le /usr/local/bindossier.

fichier .emacs

Ensuite, j'ai besoin d'un .emacsfichier dans mon dossier personnel qui traiterait correctement la variable d'environnement EMACS_USER_DIR.

(defvar user-custom-dir (getenv "EMACS_USER_DIR"))

(when (/= (length user-custom-dir) 0)
  (setq user-emacs-directory (file-name-as-directory user-custom-dir)))

(load (expand-file-name "init.el" user-emacs-directory))

Je ne suis pas du tout habitué à elisp, alors je suis venu ici, des personnes plus expérimentées pourraient probablement proposer quelque chose de mieux. Mais bon, ça marche.

Eye-candy

Alors pourquoi ne pas ajouter une icône:

icône

[Desktop Entry]
Name=Spacemacs
GenericName=Text Editor
Comment=Edit text
MimeType=text/english;text/plain;text/x-makefile;text/x-c++hdr;text/x-c++src;text/x-chdr;text/x-csrc;text/x-java;text/x-moc;text/x-pascal;text/x-tcl;text/x-tex;application/x-shellscript;text/x-c;text/x-c++;
Exec=spacemacs %F
Icon=/home/marcs/.icons/spacemacs.svg
Type=Application
Terminal=false
Categories=Development;TextEditor;
StartupWMClass=Emacs
Keywords=Text;Editor;

3
Votre script doit utiliser exec emacs "$@".
Uwe Koloska

Oui, merci pour le tuyau, juste corrigé.
Marcs

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.