Заметки на полях: Изучай Erlang во имя добра!

Фред Хеберт - широко известный в Erlang сообществе программист. Он не только написал дюжину полезных утилит и приложений, но и замечательную книгу “Изучай Erlang во имя добра!”, которая, к тому же, доступна онлайн совершенно бесплатно. Она в основном предназначена для тех, кто только начинает изучать Erlang. Но и более опытные разработчики с большой вероятностью найдут что-то новое в последних главах книги (CommonTest, Mnesia, Distributed Erlang).

Вот лишь часть того, что я почерпнул из данной книги:

  1. используйте ctrl-a / ctrl-e в командной строке для перехода в начало / конец строки;
  2. ;(,) и andalso(orelse) различаются в работе при построении защитных выражений (guards). Например, when C1 ; C2 не упадет с ошибкой, если первое условие (C1) покрашится, а вычислит второе (C2);
  3. старайтесь избегать “true” веток в условных операторах, если есть возможность покрыть все варианты (пример: X >= 0, X < 0);
  4. Björn Gustavsson из команды Erlang OTP рекомендует использовать gb_sets почти во всех случаях, ordsets, когда вам нужно простое представление и sets, когда требуется строгое сравнение =:= ;
  5. references используются, в том числе, потому что Pid может поменяться пока мы дожидаемся ответа на сообщение (процесс упал и был перезапущен супервизором);
  6. [ETS] ordered_set проигрывает по скорости рандомного чтения set, поэтому должен использоваться только для range queries;
  7. [EUnit] ?_assert исполняется не сразу, а после генерации теста.

{% blockquote %} Симметричная мультипроцессорность появилась в Erlang не сразу, а была добавлена в 2000 годах (ее можно отключить с помощью erl -smp disable) {% endblockquote %}

Distributed Erlang

  1. узлы в Erlang общаются по TCP соединению, и, если у вас большое сообщение, остальные сообщения будут ждать очень долго. Хуже того, heartbeat сообщения могут не дойти до узла и Erlang посчитает, что узел умер;
  2. большое количество связей (link) между узлами не есть хорошо, так как приведет к всплеску количества сообщений при падении одного из них;
  3. 4369 порт закреплен за epmd. range для портов узлов можно установить через inet_dist_listen_min(max);
  4. в консоли можно использовать net_kernel:connect для связи с узлом;
  5. {global, Name} медленно разрешает конфликты имен (3 стратегии) и потерю связи с узлами. Он подходит для небольшого количества регистраций, которые нечасто меняются с течением времени;
  6. распределенные приложения OTP (OTP Distributed Applications) делают упор на то, что ошибки в основном происходят по вине аппаратного обеспечения, а не разделения сети. Если у вас по другому - OTP не для вас. Они (приложения) служат для организации failover и backover;
  7. если планируется использовать горячую замену кода (hot code reloading), то записи (records) лучше не выставлять наружу (только в рамках модуля). Иначе - боль.

{% blockquote %} Версии Erlang >= R15B01 позволяют использовать реестры помимо local и global - {via, МодульРеестра, Имя} {% endblockquote %}

Mnesia

  1. хорошей идеей будет добавить префикс к названию таблиц в mnesia (так как они шарятся по всему кластеру);
  2. при написании большого приложения лучше разделить логику приложения и код mnesia (чтобы, к примеру, иметь возможность заменить транзакции на синхронные);
  3. tv:start() - GUI для просмотра таблиц.

Полезные ссылки:

Anton Kaliaev

Software engineer, blogger, public speaker, traveler

Ulyanovsk, Russia http://homeonrails.com