Each programming language has its own strong points. Choosing the optimal option is the most important factor in building successful software applications. Elixir is a programming language that is well suited for building scalable applications. By using Elixir along with the Erlang VM, you can build applications with very little latency. This article introduces you to the features of the Elixir programming language.
Programming languages play an important role in building successful software applications. Selecting the optimal programming language suitable for the application that you are building is an important task that needs to be carried out carefully. The availability of many options makes the selection process even more difficult.
This article introduces you to a programming language called Elixir, which has been designed for building scalable applications. With the prolific growth in the number of parallel users and the huge volume of data that is getting generated each second, there is a real need for building scalable applications. Elixir’s core philosophy is to enable building applications that scale, and this has been made possible due to the availability of lightweight threads of execution.
Elixir was created by Jose Valim. A wonderful documentary video released by Honeypot about Elixir is available at http://doc.honeypot.io/elixir-documentary-2018/.
The first version of Elixir was released in 2011. The latest stable release of Elixir is version 1.9.4, which was released on November 5, 2019. Elixir comes with the Apache License 2.0. The design of Elixir is influenced by Erlang, Ruby, etc, and the fact that it is used by companies such as Pinterest and Divvy testifies to its power.
The important attributes of Elixir are illustrated in Figure 1. Prominent features such as concurrency, scalability and fault tolerance make Elixir a compelling option as the programming language for your application.
Elixir installation
Elixir can be installed in all major operating systems such as MacOS, UNIX and UNIX-like systems, Windows, etc. For Windows, you can simply download the installer and follow the wizard to get the installation done. In the case of MacOS, follow the instructions given below to install:
brew update brew install elixir
Elixir can be installed in Ubuntu by executing the following commands. The first step is to add the Erlang solutions repository.
$ wget https://packages.erlang-solutions.com/erlang-solutions_2.0_all.deb && sudo dpkg -i erlang-solutions_2.0_all.deb
After this, apt-get can be used to install as shown below:
$ sudo apt-get update $ sudo apt-get install esl-erlang $ sudo apt-get install elixir
The Erlang platform for Elixir is installed using the apt-get install esl-erlang command. Detailed installation instructions along various environments such as Raspberry Pi and Docker are given in the official documentation at https://elixir-lang.org/install.html.
After the successful installation of Elixir, check the installed version with the following command:
$ elixir --version
The Elixir interactive mode
The Elixir programming language provides an interactive mode which can be invoked by running the iex command at the terminal. A screenshot of the Elixir interactive mode environment and version is shown in Figure 2.
The interactive mode can be used to evaluate any expressions similar to Python.
iex(1) > 44 * 2 88 iex(2)>
To come out from the interactive shell, press Ctrl+C twice.
Script execution
To execute the Elixir script, type your code in an editor and save it as .exs. For example:
IO.puts "Welcome to Open Source For You!!"
Save the above code as hello.exs. Then execute with the Elixir command as shown below:
$ elixir hello.exs
Language constructs
Learning to code in Elixir is comparatively simpler. If you are already familiar with programming languages such as Python, you will find learning Elixir is easier.
Elixir has support for the following data types: int, float, bool, atom, strings, list and tuples.
iex> 8 # integer iex> 0x1F # integer iex> 8.0 # float iex> true # boolean iex> :atom # atom / symbol iex> "OSFY" # string iex> [1, 2, 3] # list iex> {1, 2, 3} # tuple
The Elixir atom is similar to that of some other programming languages’ symbols. An atom in elixir is a constant, whose value is its own name. The atoms come handy when you want to enumerate over distinct values.
Elixir has support for anonymous functions. An anonymous function is one with no name. For example:
iex(1)> add = fn a, b -> a + b end #Function<13.126501267/2 in :erl_eval.expr/5> iex(2)> add.(4,4) 8 iex(3)> is_function(add) true iex(4)>
You can observe that in iex(1), we have defined a function with fn and end. Note that there is no name to the function. It has been stored to a variable add. Later, in iex(2), the function has been called using the variable name add. Here, add is not a function name. You can observe a ‘.’ between add and the ‘( ’.
The complete coverage of various language constructs is available in the official documentation.
Elixir processes
The Elixir code runs inside processes, which are isolated from each other. The Elixir’s processes are not the same as the operating system processes. The processes inside Elixir are very lightweight in nature, both in terms of memory and CPU utilisation. Due to this, several hundreds of processes can be executed simultaneously. The Elixir processes can communicate among themselves using message passing. These processes facilitate building distributed applications.
A new process can be spawned with spawn in Elixir, as shown below:
iex(4)> spawn fn -> 1 + 2 end #PID<0.110.0> iex(5)> spawn fn -> 1 + 2 end #PID<0.112.0> iex(6)> spawn fn -> 1 + 2 end #PID<0.114.0>
You will notice that the unnamed function is spawned as various processes that are shown with their PIDs (in iex(4), iex(5) and iex(6)). Primarily, spawn takes a function and executes it in another process.
You can check the status of the process with the following code:
iex(7)> pid = spawn fn -> 1 + 2 end #PID<0.119.0> iex(8)> Process.alive?(pid) false iex(9)>
Messages can be sent and received among these processes as shown below:
iex> send self(), {:hello, "world"} {:hello, "world"}
Elixir input and output
In Elixir, the IO module is used to perform the basic input and output operations. It can use the standard input and output, files or other IO devices.
iex(10)> IO.puts("OSFY") OSFY :ok iex(11)> IO.gets("yes or no? ") yes or no? yes "yes\n" iex(12)>
The basic file IO can be performed by using the following code:
iex(12)> {:ok, file} = File.open("hello", [:write]) {:ok, #PID<0.134.0>} iex(13)> IO.binwrite(file, "OSFY") :ok iex(14)> File.close(file) :ok iex(15)> File.read("hello") {:ok, "OSFY"}
Elixir libraries
One of the major advantages of Elixir is its interoperability with Erlang. Some of the popular libraries are shown in Table 1. Apart from this, the Erlang ecosystem has various packages that are available through the package manager https://hex.pm/.
A simple digraph example with the shortest path is shown in the following code snippet:
digraph = :digraph.new() {:digraph, #Reference <0.2880715758. 4100325377.247127>, #Reference <0.2880715758.4100325377. 247128>, #Reference <0.2880715758.4100325377. 247129>, true} iex(17)> coords = [{0.0, 0.0}, {1.0, 0.0}, {1.0, 1.0}] [{0.0, 0.0}, {1.0, 0.0}, {1.0, 1.0}] iex(18)> [v0, v1, v2] = (for c <- coords, do: :digraph.add_vertex(digraph, c)) [{0.0, 0.0}, {1.0, 0.0}, {1.0, 1.0}] iex(19)> :digraph.add_edge(digraph, v0, v1) [:”$e” | 0] iex(20)> :digraph.add_edge(digraph, v1, v2) [:”$e” | 1] iex(21)> :digraph.get_short_path(digraph, v0, v2) [{0.0, 0.0}, {1.0, 0.0}, {1.0, 1.0}]
To summarise, this article has provided a simple introduction to the Elixir programming language, which is very extensible as it supports the meta-programming concepts. The official documentation has plenty of resources with which you can learn various advanced features such as MIX and OTP. Readers can explore further through various videos, interactive resources, screen casts and books to learn Elixir by navigating to https://elixir-lang.org/learning.html.