
Elixir v1.6 released: code formatter, dynamic supervisors, and more - josevalim
https://elixir-lang.org/blog/2018/01/17/elixir-v1-6-0-released/
======
losvedir
I'm really excited about the code formatter. I'm glad more and more projects
are following Go's lead on this.

How was the default style decided? And very importantly, what's the forum for
users to bikeshed endlessly about how it should be different?

More seriously, as someone who's literally updating a bit of code to use a
:simple_one_for_one supervisor right now - is the new DynamicSupervisor more
about naming, so people understand it better, than semantics? I was under the
impression that :simple_one_for_one, :rest_for_one, etc, were all standard
erlang OTP supervisor strategies and that Elixir mostly deferred to them. Is
it still using the same erlang semantics under the hood?

Oh, and edited to add: does that mean using `:simple_one_for_one` with a
`Supervisor` is now deprecated? If so, what's involved in transitioning to the
new approach?

~~~
napsterbr
While it's clear that a std formatter is a big win (I absolutely _love_ elm-
format), I'm somewhat afraid of this sort of change. Stuff like line length
isn't only a personal preference, changing the width e.g. from 80 to 100 would
seriously "break" my IDE window layout. At the same point, making it
configurable would decrease the benefit of OneTrueStandard. Definitely a tough
decision either way.

~~~
nickjj
I think having something is way better than nothing.

I too like 80 max chars since it lets me fit 3 side by side code windows. From
what I gathered this is configurable at a project level.

To me it seems like a huge step up from having to use a tricked out
rubocop/flake8 config to detect issues while you have to manually fix them.

Just knowing I never have to deal with formatting again because Jose and gang
put a crazy amount of effort into ensuring it does the right thing is really
nice.

~~~
eikenberry
80 character max also fits nicely with the 4-6 inch column width for optimal
readability.

------
dgllghr
It might be a small thing, but I am most excited about @defguard. I find that
splitting a function to match on different inputs and using guards creates
elegant, clear, and maintainable code, but if a guard statement is too large,
that effect is diminished and I fall back to `if` or `case`. @defguard allows
me to stick to the more elegant (in my opinion) solution.

~~~
davidkuhta
For those interested in some of the thought-process of defguard check out
Chris Peele's gist of his development process:

[https://gist.github.com/christhekeele/76c3e37cb9082274f52f79...](https://gist.github.com/christhekeele/76c3e37cb9082274f52f79fa94bab6fe)

While not the final spec per his PR, a really good look at the internals
nonetheless.

~~~
christhekeele
You can follow my development even further—the lingering question in that gist
is how to expand the guard code to see if it is valid in a guard.

I tried my hand at a pure-Elixir guard expansion in an earlier PR, documenting
my thoughts as I went: [https://github.com/elixir-
lang/elixir/pull/5854](https://github.com/elixir-lang/elixir/pull/5854)

After José gave me some direction in response to that, I produced the ultimate
PR: [https://github.com/elixir-
lang/elixir/pull/5857](https://github.com/elixir-lang/elixir/pull/5857)

It simply relies on calling the :elixir_expand.expand function that the
compiler uses, with a guard context—so the defguard implementation is always
up-to-date with what the compiler allows in guards. Waaay more elegant than
munging AST myself.

Funnily enough, the tests I wrote for defguard actually uncovered some missing
assertions in that function. Some invalid expressions would make it past that
step and return a different error much deeper in. It's kinda cool I indirectly
contributed to the compiler.

I took on the feature mostly because over 4 years ago I'd made a gist to do
exactly that, minus the validation, and when I found the issue on github for
it, it gave me a lot of pleasant closure to get it merged in!
[https://gist.github.com/christhekeele/8284977/revisions#diff...](https://gist.github.com/christhekeele/8284977/revisions#diff-
ba11d4e6b23e5ea4fc590c7da3988661R65)

------
ninjakeyboard
Some extra stuff I've been working on to supplement the the formatter in your
workflow a bit:

Pre commit hook: [https://github.com/jasongoodwin/elixir-mix-format-pre-
commit...](https://github.com/jasongoodwin/elixir-mix-format-pre-commit-hook)

Emacs format current file: [https://github.com/jasongoodwin/emacs-elixir-
formatter](https://github.com/jasongoodwin/emacs-elixir-formatter)

Generally the formatter is good, but we've noticed a couple cases where it
would be nice to override

EG:

it would be nice to have the join and on statements on the same line so you
can see as the reader what relates to what

    
    
      u in Db.User,
      distinct: u.id,
      join: c in Db.Comment,
      on: u.id == c.user_id,
      join: p in Db.Profile,
      on: u.profile_id == u.id,
      join: x in Db.SomethingElse,
      on: x.profile_id == u.id,
      join: y in Db.AnotherThing,
      on: y.profile_id == u.id,

...

I can see why it's like that, but it would be nice to be able to override it.

Also the formatter requires () so you end up with ecto code differing from the
styles recommend in the docs

    
    
      schema "thingy" do
        field(:name, :string)
        field(:abbreviation, :string)
      end

instead of

    
    
      schema "thingy" do
        field    :name,         :string
        field    :abbreviation, :string
      end
    

Anyway, still useful and good for the team.

~~~
jurre
> it would be nice to override

One of the big advantages I have experienced from the Golang formatter is that
you cannot configure it, period. This took me a little bit off getting over
myself, but eventually the fact that every single Golang codebase adheres to
these rules is so nice. Plus you don't have to think about it, ever.

In this case I think it would be best if Ecto just recommends the new default
style in their docs.

~~~
ninjakeyboard
That's fair - thanks for the comment. It makes sense - then there are no
opinions or variation so "this is the way" and all code looks like that.

------
rehemiau
For people wondering about what Elixir and the BEAM are offering, for a quick
overview of the best features of this stack see [this talk](
[https://www.youtube.com/watch?v=pO4_Wlq8JeI](https://www.youtube.com/watch?v=pO4_Wlq8JeI)
).

If anyone starts learning Elixir now: I can recommend using VSCode with
ElixirLS extension. Also: pragprog books, Sasa Juric's book. If you like video
tutorials I've heard good things about PragDave's course.

~~~
gekkonier
I guess you mean Elixir in action - its manning and not pragprog.

~~~
rehemiau
Yes, and I do recommend all of pragprog elixir books and manning's elixir on
action.

------
jeffreysmith
defguard/defguardp is a really welcome addition that should improve lots of
normal code. Planning on using it in a refactor _today_. Great to see
improvements like this.

------
qaq
Just in time for a start of a new proj. Huge thanx to everyone who contributed
the maturity of tooling and attention to developer productivity is amazing and
puts many established languages to shame.

------
jmcgough
Been looking forward to this since your keynote at ElixirConf. Love the
direction the language is evolving towards, and the emphasis on improving ease
of use and better tooling.

------
richjdsmith
This is fantastic! Easily most excited for the code formatter - it should make
it easier for new users of the language to pick it up based on seeing others
code.

------
grillwork
thanks for everything you do jose, looking forward to getting our hands on it.

------
nurettin
I wonder why go doesn't have it's elixir, yet.

~~~
chipotle_coyote
I'm not entirely sure what that would exactly _mean,_ but I can think of two
answers, one philosophical and one technical:

(1) Philosophically, Erlang borrows a lot from Prolog while Elixir borrows a
lot from Ruby. For some programmers (dilettantes like myself included), that
relative familiarity is a fairly big win. Go doesn't have the same "weird
syntax" drawback; it's pretty easy for anyone familiar with C-like languages
to pick up the basics virtually on sight.

(2) Technically, Elixir is another language for the Erlang VM, like Scala and
Clojure are other languages for the Java VM. But Go doesn't _have_ a VM; its
compiler produces native code. So there's no way to produce something that's
strictly comparable. You could write a preprocessor that translates an
entirely new syntax into Go, but that wouldn't be Go's Elixir, it would be
Go's CoffeeScript.

~~~
richjdsmith
> Go's CoffeeScript

As someone terrified of lower level languages (I'm a somewhat JR dev, used to
working with fun things like Python, Ruby, Elixir and JS) this would kind of
be really nice. Mostly maps.

~~~
pmontra
There are some languages that transpile to Go:

Have: [http://havelang.org/](http://havelang.org/) with generics

Godzilla:
[https://github.com/jingweno/godzilla](https://github.com/jingweno/godzilla)
ES2015 to Go

I didn't try any of them, nor Go itself.

------
gabrielc
good news, elixir is a such a joy to use.

------
sioa
Sorry for asking here, but if I wanted to learn Elixir, do I need to know
Erlang?

~~~
rehemiau
No. You can start learning elixir and you'll learn about how the BEAM works on
the way. You'll also eventually learn about Erlang/OTP libraries and probably
that's when you'll start reading basic erlang code but that should come
(mostly) naturally. I included some tips in another comment here.

~~~
sioa
Ah thanks.

------
simooooo
Is this code formatter roughly equivalent to format document in c#/VS?

