Introduction to Elixir

Elixir

Elixir is a dynamic, functional language designed for building scalable and maintainable applications.

 Elixir is influenced by

Ruby syntax intelligent sugar
Erlang semantics BEAM, concurrency model
Lisp extensibility metaprogramming, macros

Elixir and Erlang

The syntax is the most obvious difference between Erlang et Elixir but not the only difference.

 

Both languages shares a common ground: same VM, same OTP library, ... but Elixir also aims to improve some of the Erlang flaws.

The problem

Years ago...

But one day "free lunch is over"

https://en.wikipedia.org/wiki/Herb_Sutter#The_Free_Lunch_Is_Over

Concurrency

Concurrency is the composition of independently executing computations.

Why concurrency?

  • Using all cores
  • Using all computers
  • Solve async problems

Classical solution

  • Low level concurrency control
  • Shared memory communication

Problems

  • Deadlock
  • Inanition
  • Not using all cores
  • Race condition

Low level methods

  • Threads
  • Mutexes
  • Critical sections

Locks

  • Difficult to write
  • Difficult to reason
  • Difficult to mantein
  • Difficult to test

High level methods

  • CSP
  • Actors
  • Transactional memory

The actor model

  • Carl Hewitt's model for the foundation of computation
  • everything is an actor
  • actors communicate by messages
  • actors can create other actors
  • and change behaviour according to messages

Whatsapp

  • 900 mill. Users
  • 19Billion messages in & 40B out per day
  • 350.000 msg/sec average
  • 2 mill. connections/node
  • 50 engineers

Backend for multiplayer videogames

Call of duty black ops, best selling videogame.

Pinterest

"We’re converting our notifications system from Java to Elixir. The Java version used an Actor system and weighed in at around 10,000 lines of code. The new Elixir system has shrunk this to around 1000 lines. The Elixir based system is also faster and more consistent than the Java one and runs on half the number of servers."

Bet365 and Erlang

"Our code base is vastly simplified now, and we have less issues with reliability. We are an incredibly peaky business and we find that at the peak of trading we are able to provide our customer with a much more predictable quality product using Erlang,"

What is Elixir/Erlang good for?

  • Chat servers (WhatsApp, ejabberd)

  • Game servers (Wooga)

  • Web frameworks (Phoenix)

  • Distributed databases (Riak and CouchDB)

  • Real-time bidding servers

  • Long-running services/daemons

  • Command-line applications

Erlang

Agner erlang: was a Danish mathematician, statistician and engineer, who invented the fields of traffic engineering and queueing theory.

Creators of Erlang

Erlang

Erlang the movie

Erlang

  • Functional, no mutability
  • Actors (message passing)
  • Light processes
  • Open source since 1998

Elixir

Created by Jose Valim

Why should I care about elixir?

Reasons

  • Superb standard library

  • Added namespaces

  • Added Structs

  • Allowed variable rebinding

  • Added Pipe-operator |>

  • Added polymorphism

  • Added Lisp-style macros

  • Changed syntax

|> — The Pipe Operator

people = DB.find_customers
orders = Orders.for_customers(people)
tax    = sales_tax(orders, 2013)
filing = prepare_filing(tax)

|> — The Pipe Operator

prepare_filing(sales_tax(Orders.-
for_customers(DB.find_customers), 2013))

|> — The Pipe Operator

filing = DB.find_customers
           |> Orders.for_customers
           |> sales_tax(2013)
           |> prepare_filing

Pattern matching

iex> a = 1
1
iex> 1 = a
1
iex> { m, n } = { 2, 3 }
{2, 3}
iex> [ e, f, g ] = [ 4, 5, 6 ]
[4, 5, 6]
iex> "Elixir" <> rest = "Elixir Rocks!"
"Elixir Rocks!"
iex> rest
" Rocks!"
iex> [head | tail] = [1, 2, 3]
[1, 2, 3]
iex> head
1
iex> tail
[2, 3]

Recursion and Pattern matching

defmodule Fib do
  def fib(0), do: 0
  def fib(1), do: 1
  def fib(n), do: fib(n-1) + fib(n-2)
end

Recursion and Pattern matching

defmodule MyList do
  def sum([], total), do: total
  def sum([head | tail], total), do: sum(tail, head+total)
end

MyList.sum([1,2,3,4,5], 0)

Pattern matching

handle_open = fn
  ({:ok, file}) -> "First line: #{IO.read(file, :line)}"
  {_, error} -> "Error: #{:file.format_error(error)}"
end

IO.puts handle_open.(File.open("file.ex"))

Immutability

iex> name = "elixir"
"elixir"
iex> String.capitalize name
"Elixir"
iex> name
"elixir"

“In a functional language, we always transform data. We never modify it in place”

Quote from “Programming Elixir”.

Immutability

m = %{ ​a:​ 1, ​b:​ 2, ​c:​ 3 }
​%{a: 1, b: 2, c: 3}

​iex>​ m1 = %{ m | ​b:​ ​"​​two"​, ​c:​ ​"​​three"​ }
​%{a: 1, b: "two", c: "three”}

​​iex>​ m2 = %{ m1 | ​a:​ ​"​​one"​ }
​%{a: "one", b: "two", c: "three"}

Tooling

1.   Mix

A task runner. It is used to start servers, install dependencies, run tests,...

2.   Hex

Package manager allowing to download Erlang and Elixir packages

3.  Iex

Read eval print loop

Hot reload

Nothing to do, just compile and use your new .ex

 

you don't need to reboot your app,

static typing would have been complicated with this

Observer

> :observer.start

A very useful debug console

Other

Dialyzer: let you do a static analysis
Reltool: tool to make erlang releases
(used by rebar)

Erlang.mk: Alternative to rebar based on a makefile

WombatOAM: commercial product for system supervision

 

Concurrent Programming

Primitive

OTP
Tasks and Agents

Processes versus threads

  • Processes share nothing with each other
  • In the vm not the os, like green threads but
  • more lightweigth than threads
  • more numerous
  • more control: stack, heap and gc per process

Message send and message receive are decoupled

  • avoids common source of deadlock
  • directly supports processes distributed across a network
  • supports more complex message handling
  • can simulate synchrony through send/receive protocol
Technical requirement Server A Server B
Http Server Nginx Elixir
Request Processing Ruby on rails/Node Elixir
Long running requests Go Elixir
Server-Wide State Redis Elixir
Persistable data Redis & Mongo Elixir
Background jobs Cron, bash scripts Elixir
Server crash recovery Upstart Elixir

Twilio

Dokku

Thank you

elixir

By gabrielc

elixir

  • 490