A code formatter for LFE
lfmt is written in Erlang (like LFE itself) and is a general-purpose formatter for the wider BEAM community. While the first engine (fezzik) is intentionally single-language, single-purpose, the forthcoming pe and pc engines are built around user-supplied
formatting-rules files. Given a rule set, lfmt is intended to format
any text file according to those rules.
All engines are pure-Erlang with zero runtime dependencies.
The formatter reads source and pretty-prints it into a consistent, canonical layout — preserving
comments and guaranteeing idempotence: formatting already-formatted code
leaves it unchanged (format(format(X)) == format(X)).
lfmt has a multi-engine design: a single, stable API (lfmt:new/1) sits in
front of pluggable formatting engines, so you can choose the algorithm that
suits you. This release ships the fezzik engine; two further engines are
planned:
| Engine | Status | Notes |
|---|---|---|
fezzik |
available | direct, fast brute-force formatter |
pe |
planned | pretty-expressive (optimal-layout) engine |
pc |
planned | pretty-canny engine |
lfmt is an Erlang library add as a dependency (rebar3) in the usual manner:
{deps, [{lfmt, "~> 0.4"}]}.lfmt provides the formatting capability of the LFE rebar3 plugin (rebar3_lfe) as of version 0.5.5 of that tool.
The simplest form uses the default engine (fezzik); note that this is the only engine which is LFE-only (understandable, given it is a brute-force formatter, not a general-purpose one):
{ok, Formatted} = lfmt:format(Source).To select an engine explicitly, build a reusable formatter with lfmt:new/1:
Fmtr = lfmt:new(#{engine => fezzik}),
{ok, Formatted} = lfmt:format(Fmtr, Source).Source is LFE source as a binary or string, and the result is an iolist.
Because formatted output can contain Unicode codepoints (> 127), convert it to a
binary with unicode:characters_to_binary/1 — not iolist_to_binary/1:
{ok, IoData} = lfmt:format(<<"(defun id (x) x)">>),
Bin = unicode:characters_to_binary(IoData).From LFE:
(case (lfmt:format source)
(`#(ok ,formatted) formatted)
(`#(error ,reason) (error reason)))Selecting an engine that isn't available yet (e.g. pe/pc) is reported
explicitly rather than silently ignored.
Apache-2.0. See LICENSE.
