SW engineering, engineering management and the business of software

subscribe for more
stuff like this:

Formatting Embedded Elixir (.leex and .eex) Files in Visual Studio Code with Prettier

Formatting .ex and .exs files in VS Code is fairly straight forward with the ElixirLS plugin.

However that currently doesn’t deal with embedded elixir files (.eex and .leex)

There are a couple ways to do this.

htmlbeautifier

My first go at this was a VS code plugin called Elixir Templates Formatter. This plugin and the two or three others that share the same icon use htmlbeautifier under the hood, which is typically installed via ruby’s gem package manager.

This was easy to install and worked for me for a while, but three issues popped up:

  • It was so slow, that occasionally, I would make a change, save, make second change, save and the formatter would then write the formatted first change over the second change.
  • On particularly complex files, the formatter might crash. The file might not save or in some cases, the file would be cleared.
  • These crashes tended to spawn rogue ruby processes that would peg the CPU to 100%, trigger the fans and slow my laptop to a crawl

So unless you like data loss and crippling your development machine, I’d not recommend these plugins.

Prettier

Prettier is a javascript solution that has a plugin architecture. Fortunately, someone wrote an eex plugin for prettier and it works pretty well (pun intended).

The first thing is to install the Prettier VS Code plugin. The one I use currently have over 11 million installs and has the id: esbenp.prettier-vscode.

It is kind of a pain to setup, the first step is to simply install prettier and eex plugin:

npm install --global prettier prettier-plugin-eex

Update: Prettier v2.3.x seems to break with this plugin as of v0.5.0. You can use the following to work around this until the plugin is updated.

npm install --global prettier@2.2.1 prettier-plugin-eex

At this point, you should see both of those packages in your global node_modules directory. You can use this command to list all globally installed node modules: npm list -g --depth 0

We aren’t done yet!

In the root directory of your Phoenix project, create a .prettierignore file, then add the following lines:

deps/
_build/
.elixir_ls
assets
priv

If you want to customize your prettier config, also create a prettier.config.js file. At a minimum, you should have module.exports = {} in that file. See the docs on prettier config files for more info.

Lastly, we have to make changes to VS Code’s settings.json file. You get tho this by doing cmd-shift-P (possibly control-shift-P on your platform) and typing in settings and looking for the “Preferences: Open Settings (JSON)” item.

This should open up settings.json for you right in VS Code.

add the following lines:

"prettier.prettierPath": "/usr/local/lib/node_modules/prettier",
"files.associations": {
  "*.eex": "html-eex",
  "*.leex": "html-eex"
},
"[html-eex]": {
  "editor.defaultFormatter": "esbenp.prettier-vscode"
},

You need to know your npm root path. You can use the command npm root -g to find this. For me, on Mac OS X using homebrew, it’s /usr/local/lib/node_modules. It may be different for your. if so, adjust the prettier.prettierPath value in the config above.

Going thru this:

  • We tell the prettier plugin to look in the assets/node_modules directory to find prettier. Normally the prettier plugin expects to find node_modules at the root level.
  • We tell VS Code to treat .eex and .leex files as html-eex (HTML Embedded Elixir).
  • And lastly we tell VS Code to use prettier to format those files.

Prettier’s defaults look different that htmlbeautifier, so if your files are under source control, it might be worth it to go reformat all of them if you are switching over. Prettier’s defaults take more vertical space, but make it much easier to edit html tag attributes.

Summary

Data loss is very bad. Don’t use htmlbeautifier based plugins to format your .eex and .leex files. Use Prettier. There is some setup you have to do to get it to work.



in lieu of comments, you should follow me on twitter at twitter/amattn and on twitch.tv at twitch.tv/amattn. I'm happy to chat about content here anytime.


the fine print:
aboutarchivetwittertwitchconsulting or speaking inquiries
© matt nunogawa 2010 - 2021 / all rights reserved