В последнее время я проводил несколько экспериментов с docker compose, чтобы развернуть несколько совместных микросервисов. Я вижу множество преимуществ, которые предоставляют микросервисы, и теперь, когда есть хороший набор инструментов для управления ими, я думаю, что не так уж сложно перейти в вагон микросервисов.
Но я тоже экспериментировал с Эликсиром, и мне очень нравятся преимущества, которые дает сам по себе. Учитывая, что он поощряет упаковку вашего кода в несколько разделенных приложений и поддерживает горячее обновление кода, как бы вы смешали докер с эликсиром (или erlang, если на то пошло)?
Например, если я хочу использовать docker, потому что он обеспечивает паритет dev-prod, как в него вписывается elixir? Учитывая, что контейнеры докеров неизменяемы, я теряю возможность обновлять горячий код, верно? А как насчет сине-зеленых развертываний или канареечных выпусков?
Я имею в виду, что я мог бы просто написать микросервисы с помощью Elixir и использовать их, как если бы они были написаны на любом другом языке, полиглотизм в любом случае является одним из преимуществ микросервисов, но тогда я не получаю всех преимуществ от использования платформы OTP, я Предполагаю, что чисто совместные приложения на erlang намного оптимальнее, чем использование промежуточных очередей для связи между микросервисами, написанными на разных (или нет) языках.
Ответы:
Это очень открытый вопрос, но я попытаюсь проиллюстрировать, почему Elixir / Erlang может быть лучшей платформой для разработки распределенных систем (независимо от того, работаете ли вы с микросервисами).
Во-первых, давайте начнем с некоторой предыстории. Виртуальная машина Erlang и ее стандартная библиотека были разработаны заранее для построения распределенных систем, и это действительно заметно. Насколько мне известно, это единственная среда выполнения и виртуальная машина, широко используемая в производственной среде, разработанная заранее для этого варианта использования.
Приложения
Например, вы уже намекнули на «приложения». В Erlang / Elixir код упакован внутри приложений, которые:
Влияние этого дизайна огромно. Это означает, что разработчики Elixir при написании приложений более четко подходят к:
Мало того, инструменты вокруг этой абстракции великолепны. Если у вас есть Эликсир установлен, откройте «Iex» и введите:
:observer.start()
. Помимо отображения информации и графиков о вашей действующей системе, вы можете убивать случайные процессы, видеть их использование памяти, состояние и многое другое. Вот пример запуска этого в приложении Phoenix:Разница здесь в том, что приложения и процессы дают вам абстракцию для размышлений о вашем коде в производственной среде . Многие языки предоставляют пакеты, объекты и модули в основном для организации кода без отражения в системе времени выполнения. Если у вас есть атрибут класса или одноэлементный объект: как вы можете рассуждать о сущностях, которые могут им манипулировать? Если у вас есть утечка памяти или узкое место, как вы можете найти ответственный за это объект?
Если вы спросите кого-нибудь, кто работает в распределенной системе, то это именно то, что им нужно, и с Erlang / Elixir у вас есть это как строительный блок.
Общение
На самом деле все это только начало. При построении распределенной системы вам необходимо выбрать протокол связи и сериализатор данных. Многие люди выбирают HTTP и JSON, которые, если подумать, представляют собой очень подробную и дорогостоящую комбинацию для выполнения того, что на самом деле является вызовом RPC.
С Erlang / Elixir у вас уже есть протокол связи и механизм сериализации из коробки. Если вы хотите, чтобы две машины взаимодействовали друг с другом, вам нужно только дать им имена, убедиться, что у них один и тот же секрет, и все готово.
Джейми рассказал об этом на Erlang Factory 2015 и о том, как они смогли использовать это для создания игровой платформы: https://www.youtube.com/watch?v=_i6n-eWiVn4
Если вы хотите использовать HTTP и JSON, это тоже нормально, и такие библиотеки, как Plug, и фреймворки, такие как Phoenix, также гарантируют вам продуктивность.
Microservices
Пока я не говорил о микросервисах. Это потому, что до этого момента они не имели значения. Вы уже проектируете свою систему и узлы вокруг очень крошечных изолированных процессов. Если хотите, назовите их наносервисами!
Мало того, они также упакованы в приложения, которые группируют их как объекты, которые можно запускать и останавливать как единое целое. Если у вас есть приложения A, B и C, а затем вы хотите развернуть их как [A, B] + [C] или [A] + [B] + [C], у вас будет очень мало проблем с этим из-за к присущему им дизайну. Или, что еще лучше, если вы не хотите заранее усложнять развертывание микросервисов в своей системе, вы можете просто развернуть их целиком на одном узле.
И, в конце концов, если вы работаете все это с помощью Erlang распределенного протокола, вы можете запустить их в различных узлах и они будут в состоянии достигнуть другой до тех пор , как вы обратитесь к ним
{:node@network, :name}
вместо:name
.Я мог бы пойти дальше, но надеюсь, что убедил вас на этом этапе. :)
источник