I've been dipping back ito the world of free software, and have been having a huge amount of fun getting back into emacs. I'm using it more of an operating system than I ever did before, as a way to navigate the world using a text interface. I'd never thought I'd be done with the terminal, but this is the first time that I've got something better and more powerful.

Since I do a lot of server wrangling and web development, lets look at how to setup emacs to do JavaScript development. My setup is a Pixelbook, and I run three virtual desktops. The first is a full screen Chrome window with multiple tabs, and the second and third are emacs frames. I flip back and forth between them as needed.

First install emacs. You need emacs > 25 to use magit, so its probable that you'll need to upgrade the emacs in your system. If you are using linux I'll let you sort that out directly, but below are the instructions for OSX.

Installing on debian

The latest emacs (26 at the time of this writing) is on buster, so upgrade to that.

sudo apt-get install emacs

Documentation is not available in the free part of debian. Don't ask me, something complicated. In order to get the info pages, you need to install the package emacs-common-non-dfsg which is in the non-free part.

Start up emacs and then you can do C-x C-f /sudo::/etc/apt/sources.list to open up the sources file as root! That's pretty neat, part of the Tramp system which lets you use local buffers to edit things that are "remote", in this case as another user but also on different hosts.

Add non-free to the end of first line to have access to the other set of packages. Then do M-x shell to startup a bash shell, and you can install the rest of it from there:

sudo apt-get install emacs-common-non-dfsg install-info

You may need to run install-info to get emacs to recognize other stuff in the /usr/share/info directory.

Using homebrew to install emacs on OSX

brew cask install emacs

If you are on OSX you'll also need to install some certs, and defined in this wonderful walkthrough. Simply:

brew install libressl

And then in .emacs add

(require 'gnutls)
(add-to-list 'gnutls-trustfiles "/usr/local/etc/openssl/cert.pem")

Cleaning up backup files

One thing that's annoying is having the Emacs Backup Files everywhere. Lets stick everything in ~/.saves so we don't need to see it.

   backup-by-copying t      ; don't clobber symlinks
    '(("." . "~/.saves/"))    ; don't litter my fs tree
   delete-old-versions t
   kept-new-versions 6
   kept-old-versions 2
   version-control t)

Changing the capslock key to control

Go into System Preferences... -> Keyboard and select Modifier Keys. Switch caps lock key to be control. Totally worth it, but you still need to do a META dance with the options key, instead of the more obvious command key.

Another nice thing is to map your command-key to META, which is much more natural. Put this in .emacs

    (setq mac-option-key-is-meta nil)
    (setq mac-command-key-is-meta t)
    (setq mac-command-modifier 'meta)
    (setq mac-option-modifier nil)

Emacs super basics

Emacs is something much more than an editor. It's an environment within which you can interact with your computer that could replace many of the tools that you use now. I normally use Terminal for example to interact with things and open up other programs to do specific tasks. Emacs could replace terminal, as well as all of the programs that are used to get into the nitty gritty of making computers do what you want. I recommend the Mastering Emacs book as a great way to get started in your emacs journey.

Misc but important

ESC ESC ESCget you out of most messes
C-g C-g C-galso get you out
C-x C-xexit emacs
C-x C-zminimize emacs
C-x C-=Embiggen font
C-x C--Miniturize font


C-x C-fopen a file
C-x C-ssave a file

Moving around

C-fforward character
M-fforward word
M-eforward sentence
C-eforard line
C-bbackward character
M-bbackward word
M-abackward sentence
C-abackward line
M-<beginning of document
M->end of document

Interative search is started with C-s


C-x-1makes the current window full screen
C-x-2split horizontally
C-x-3split vertically
C-x-oswitch focus


C-x r mSet a bookmark
C-x r lList bookmarks
C-x r bJump to bookmark

Adding a new package registry

M-x customize and search for package archives. Insert a new one named 'stable melpa' and add You can paste into emacs using C-y.

Also add

I also like to set visual-line-mode globally to true.

Then Apply and Save, or do C-x C-f

Refresh the package list using M-x package-refresh-contents

If you get an gpg error

Go to customize again and change package-check-signature to nil. Apply and save. Then M-x package-install RET gnu-elpa-keyring-update RET. Then go back to customize and revert package-check-signature to allow-unsigned

Changing themes and fonts

Use M-x customize-themes to change your theme. I also like to have a much larger font, which you can adjust using M-x customize-face and setting the default size to something like 140.

2 spaced tabs

Open up your .emacs file and add:

(setq-default indent-tabs-mode nil)

(setq tab-stop-list (number-sequence 2 120 2))

Use C-space to start a selection, the arrow keys to move around to select it all. Then type M-x eval-region to run the lisp.

Install use-package

M-x package-install RET use-package RET

Install helm

Install M-x package-install helm-ls-git which should install helm as well. Another nice helm package is helm-ag which will grep over your files to look for specific values. Then in your .emacs put

(require 'helm-config)
(require 'helm-ls-git)

(global-set-key (kbd "C-x C-d") 'helm-browse-project)
(global-set-key (kbd "C-x f") 'helm-ag)

Once you load everything, using C-x C-d will let you open up files in a project which is defined as the files in the current git repository. C-x f will let you use ag to file files (this overrides the fill-column command which I don't end up using).

I encourage you to read through the documentation.

Install flycheck and company

To install, M-x package-install RET flycheck and M-x package-install RET company And then in .emacs:

(add-hook 'after-init-hook #'global-flycheck-mode)
(add-hook 'after-init-hook 'global-company-mode)

Once this is done, you need to install the specific linter for the languages you are interested in. For example:

npm i -g eslint

Install emmet

To install M-x package-install emmet-mode

(add-hook 'sgml-mode-hook 'emmet-mode) ;; Auto-start on any markup modes
(add-hook 'css-mode-hook  'emmet-mode) ;; enable Emmet's css abbreviation.
(setq emmet-move-cursor-between-quotes t)

Install web-mode

I find webmode handles indention better for files that have embedded submodes, such as javascript inside of an HTML file.

(require 'web-mode)
(add-to-list 'auto-mode-alist '("\\.phtml\\'" . web-mode))
(add-to-list 'auto-mode-alist '("\\.tpl\\.php\\'" . web-mode))
(add-to-list 'auto-mode-alist '("\\.[agj]sp\\'" . web-mode))
(add-to-list 'auto-mode-alist '("\\.as[cp]x\\'" . web-mode))
(add-to-list 'auto-mode-alist '("\\.erb\\'" . web-mode))
(add-to-list 'auto-mode-alist '("\\.mustache\\'" . web-mode))
(add-to-list 'auto-mode-alist '("\\.djhtml\\'" . web-mode))
(add-to-list 'auto-mode-alist '("\\.html?\\'" . web-mode))

Install lsp-mode

This is the big one. gives you a list of all of the languages supported and what needs to be installed, but lets focus on javascript for now.

M-x package-install RET lsp-ui RET

M-x package-install RET company-lsp RET

M-x package-install RET helm-lsp RET

Then in .emacs

(use-package lsp-mode
  :hook (XXX-mode . lsp)
  :commands lsp)

;; optionally
(use-package lsp-ui :commands lsp-ui-mode)
(use-package company-lsp :commands company-lsp)
(use-package helm-lsp :commands helm-lsp-workspace-symbol)
(use-package lsp-treemacs :commands lsp-treemacs-errors-list)

And then install some of the language servers. In the case of javascript

npm i -g typescript-language-server; npm i -g typescript

Install magit

M-x package-install RET magit RET

Inside of .emacs add:

(global-set-key (kbd "C-x g") 'magit-status)

Magit is amazingly powerful, and I'm still trying to learn it.

Probably the best way to get into it is to first run C-x g (or M-x magit-status) and then use C-h m, which will show you the documentation for the current mode, in this case magit. This is a good way to poke around, though it makes sense to check out the manual which is pretty extensive.

Usage example

After I checkout my repo, I bookmark the base folder using C-x r m. Then I can go there faster without having to navigate through the filesystem.

I start up a shell using M-x shell to run commands. You can M-x rename-buffer to give it a name, and then be able to start up additional shells if needed. Depending upon what you are doing, C-x 2 splits horizontally so that can be nice to see the output of anything you need.

C-x C-d will locate files within that project, which is generally a good substitute for the find in project function that I normally use to move around.


IPFS and Fuse the worlds data in your filesystem



Simple CORS workaround for local development Keep is Simple




Emacs Tramp tricks Replacing terminals with emacs



Developing React Inside Docker Clean up after your mess