New to elixir, need some directions input

Hi everyone,

I am new to elixir (bought Udemy - Stephen Grider’s course)… half way … but still consider really new.

I have a few questions, wonder you could provide your suggestions/inputs.

  1. Is concurrent really important for web development - single page application? Which I can use vue.js or react.js + laravel or django? So how does elixir win here? If it’s really important… why ruby/django/php are dominating the web?
  2. If it’s concurrent, how does it differ with Golang? Not trying to create a language war. But Golang has a lot of companies/users using it. That really really confused me whether should I go with Golang or Elixir?
  3. Based on what I understand, if it’s a single server, Golang is much much faster than Elixir. As Golang compiles to native code vs Elixir on a vm… the question is does it matter to web development or Elixir? As the speed, i have seen blogs where experts claim they could downsize the number of servers + faster executions too.
  4. Since elixir which is powered by erlang is more towards distributed stuff… and since i am just building a single page app with some REST end points (not real time e.g. chat stuff)… I still don’t see why elixir is suitable here? Does that mean I should elixir only for real time stuff… basic web apps e.g. CRM, CMS, better go with Golang, or Django?
  5. I am not a functional language expert… does functional language can apply to all possible projects? or only suited for certain domain?
  6. Can Elixir use to build scraper, bots, console programs (non web stuff)?
  7. Lastly, let’s say I want to build an online cinema ticketing system or air flight system where I can build a choose your seats on real time basis, is Phoenix/Elixir suitable for this? I believe I still need to use react.js or vue.js to render the front end right?

Any tips? Thanks.

3 Likes

It’s not really about winning or not. Concurrent and parallel processing of request will simply be sounder going forward, and will scale better more readily, as it actually uses all your cores without having to juggle several VMs.

To preface this, I’d like to say that Go is perfectly fine to use for a lot of use-cases, web-stuff included.

However, even though you can run things in parallel in many languages and on many platforms, the difference lies in the frameworks surrounding that. Erlang and Elixir have OTP, which is a framework for expressing what are called “processes” (lightweight processes, not OS processes). These are the units that run alongside each other and they are all separate from each other, with their own garbage collector and whatnot.

What that means in practice is that by default you have isolated errors in one process from errors in another and working within the OTP framework means that you will continue to have that situation.

One of the big upsides to using OTP for me is that I can declare what kind of behaviour a process should have and not worry about how it should pass events back and forth. I get that out of the box and it allows me to concentrate only on the parts of the different processes that differ, much like how we want to generalize things like looping to only specify what is different about a particular loop. This includes things like specifying what state the process should be in when it starts and by extension what state it should have when it is restarted.

In addition to declaring process behaviour we can also declare which processes should be started alongside each other, as well as how they should react when a process crashes, which means that we can now specify how different parts of the system relate to each other. There is a great talk by Fred Hebert about this here. He outlines why this matters and how it all fits into “Why Erlang?” (and by extension, “Why Elixir?”).

I wouldn’t agree that you don’t get a lot of benefits even if you’re using only one node/server. The process isolation and declarative framework for processes is enough in my book to be a huge difference.

You can use it in any domain.

You can build pretty much anything in it, though I would never reach for it first if I had something computationally intensive to solve. It’ll be especially suited for anything where you may want to split out certain behaviour and processing out to separate processes. That could be file processing, etc., but it’s much easier to see why servers of any kind would fit that mold, which is why that’s usually what people go for.

Elixir has made it slightly easier to make a CLI application, but I wouldn’t argue that it has any real advantages on that end.

Building the backend stuff is absolutely great in Elixir, yes (which includes the web service as well). ElixirScript (which is Elixir compiled to JavaScript) had a new release a while ago. I haven’t checked it out too much, though, so I can’t recommend it. You can simply serve JS from your server, though, or something that compiles down to JS.

To give some kind of context for how some of the things I’ve referenced matter:

We recently built a layer in our game backend that deals with Lua programs wanting to connect and use our backend for messaging amongst each other to share information, access backend services, etc., and even start affecting the backend systems. First of all, this is stupidly easy because all you need is to connect them via websockets and you can be confident that doing that doesn’t affect the rest of your system.

It’s also not a very scary prospect to allow them to execute commands within the system, as long as you interpret those commands and then you spin the commands/actions/tasks out into their own processes that can either fail or succeed; but you don’t care, because they are isolated. If there are errors that are fatal to those tasks, depending on the type, you can simply ignore them and spin up new tasks, or retry. You specify this behaviour yourself, because you are at liberty to do so.

In a lot of other languages you’d probably not want to build that layer at all, but because it’s Erlang (so it’s of the same character as Elixir), we can pretty much connect anything to our backend and feel safe while doing so. We can concentrate on defining desired behaviour and build that layer together with everything else; not like it’s some special snowflake that will have to be run in a special way, but like it’s a real citizen inside our system.

Erlang and Elixir make for excellent command and control systems. I honestly can’t think of a language that could do it better.

2 Likes

My quick answers, cannot get too in-depth right now. :slight_smile:

Yes, accessing the database, scaling up, proper synchronization, very useful here because of OTP. Ruby/django/php are older, Elixir is essentially brand new in the scheme of things (although it is built on an old language that was far more difficult for most people to use, Elixir gives a new face on Erlang).

The OTP system handles concurrency and failure properly. Golang, for example, can still crash hard, bringing everything down, OTP/Erlang/Elixir expect and handle all forms of failures, including hardware as you can distribute it among servers as well.

Golang is faster on things like math sure, the BEAM is not designed for math efficiency (because even those can sometimes fail, like dividing by zero), the BEAM is optimized for network throughput and failure handling. BEAM itself can still push and saturate a network better than even many optimized C++ systems, and far better than naive ones. If you need to do math or cpu heavy things then the BEAM has communication methods of Nodes, Ports, and NIFs that let you interact with native code. In reality I’ve only needed to use such things a few times, lastly was almost a decade ago (I was doing a lot of higher dimensional matrix math there). The reason the BEAM is so much faster than golang on web serving, even though golang is faster on low-level operations like math is purely because the BEAM can handle network processing faster than any other generic system and faster than even many dedicated systems, consequently golang you would be hard pressed to optimize well enough to get even near the BEAMs ability to push the network, and you still do not have everything else the BEAM gives you like failure handling, migration of processes between servers, etc… etc… Adding those features on golang significantly slow it down far beyond the BEAM.

Distributed includes not just across servers but it also means distributed across cores, or even just distributed via pre-emptive processes on a single core. With something like Django, being written in Python with the GIL, a single bad scenario in processing something holds up the entire web server, every request gets frozen until it calls out to something that releases the GIL, it finishes, or it crashes (which can crash the entire server in certain cases that python cannot catch). Golang has similar issues but without a GIL, if you have a small 8-core server (or 128-core, or whatever), it may be able to spawn a thread per core, but if there is a heavy page (lots of matrix math for example!) it can still freeze processing of other connections if there is at least one connection per core worth of that heavy processing. Again with the beam you do not have to worry about it, it preemptively reschedules its processes so everything gets fair time, even with the server absolutely swamped (say you got hit be reddit) it will still be able to serve people.

It is just a style of programming, if you are not already programming in a similar style in other languages than you have bugs waiting in those other languages, this just helps enforce it, which removes entire classes of bugs.

Yep, it is a full language. If you want anything to do with heavy IO like networking you’d be hard pressed to find a better language, hence why it is so well suited for the web, since the web is just heavy network communication.

Perfectly so. And you can use whatever you want on the front-end, raw vanilla HTML/javascript, your-javascript-framework-of-choice, whatever.

2 Likes

I’m an newbie too on elixir. My background and hobby is Django, I code WordPress (PHP) as my daily job, and I also learn Go & Rails just for curiosity. Since you mention them several times, maybe I can share my opinion too :

It’s really depend on what you want to build. I think Go is good for API or system/low-level, but not very great for full stack web framework. In elixir, we have phoenix for that job. That doesn’t mean, Go cannot do what phoenix do, it’s just much harder and takes more effort to do so.

If you want to build like CMS, CRM, blog, membership site, or any basic web apps, then use Phoenix. But if you want to build API server or system app, then use Go.

If you ask my honest opinion, why I migrate to phoenix, here my 2 cents :

  1. Django is really good, complete and mature framework, but it’s kinda slow
  2. Rails is too many magic that I didnt understand, also slow
  3. Go & PHP syntax is hard on the eyes, it’s ugly. I really don’t like it (it’s more about taste I think).

Elixir syntax is easy on the eyes, it’s also very fast. And Phoenix offered fullstack-like MVC framework, which is I already familiar with.

I think elixir/phoenix is just as productive and useable (if not better) as any other framework you mention.

Please excuse my English anyway :smiley:

2 Likes

Thanks everyone for replying back. Really appreciate this.

I have a few more questions.

  1. as for this “core”

“Concurrent and parallel processing of request will simply be sounder going forward, and will scale better more readily, as it actually uses all your cores without having to juggle several VMs.”
“Distributed includes not just across servers but it also means distributed across cores, or even just distributed via pre-emptive processes on a single core.”

Question: It seems like erlang/elixir works better with dedicated server hardware. Could it work with cloud providers e.g. AWS, Azure, Aliyun or DigitalOcean. Example, creating a droplet in DigitalOcean with 2 CPUs. And this CPUs aren’t really direct CPUs, but virtual CPUs. Basically can it work well with virtual machines with lower specs - memory, vCPU?

Then how about working Amazon Elastic Beanstalk?

  1. as for this “math”

“Golang is faster on things like math sure, the BEAM is not designed for math efficiency (because even those can sometimes fail, like dividing by zero), the BEAM is optimized for network throughput and failure handling.”
“If you need to do math or cpu heavy things then the BEAM has communication methods of Nodes, Ports, and NIFs that let you interact with native code”

Question: I am not sure the “math” context here.

Let’s say I am building an online invoicing web app, with VAT/GST formulate pre-built-in.
Or I am building a mini clone of Instagram
Or I am building a clone of Uber
Or a mini CRM system

Does the above considered “heavy maths” where BEAM may not be suitable? This confuses me a lot. How do you classify maths that probably Erlang/Elixir will fail to live up the expectations?

I presume heavy stuff like games, probably won’t fit the bill.

Plus it’s mentioned that could use BEAM to interact with native code? Do you mean Erlang/Elixir —> interacts —> Go lang???

  1. As for this “Django being slow”

“Django is really good, complete and mature framework, but it’s kinda slow”

Question: As you know Instagram is still using Django till today. As Instagram is a big company and quite a successful one, any reasons why they aren’t planning to go with concurrent platform like Elixir/Erlang? As far I read online, Elixir/Erlang can actually reduce the number of servers/cores required compare to Python/Django? Thus, don’t see why any of the giants aren’t moving to Erlang/Elixir.

  1. As for “phoenix”

“Phoenix offered fullstack-like MVC framework, which is I already familiar with.”

Question: I used Django (not too hardcore) and also Laravel PHP framework which offers/covers extensive functionalities. Does Phoenix come to that level? I was reading online (if not mistaken Rob Conery) that wanted to build a shopping cart or ecommerce using Phoenix. But later quit due to some limitations of Phoenix.

https://github.com/robconery/peach (any reasons why Phoenix didn’t quite fit)

Sorry, I didn’t come here for any language/framework wars. Really want to enter phoenix/elixir world :slight_smile:

  1. As for this

“But if you want to build API server or system app, then use Go.”

Question: So you mean Go is more suitable to build REST endpoints e.g. Instagram or Twilio API (example).

Does that mean Elixir/Erlang is more suitable to build monolith applications instead of REST + React.js?

Any help? Thanks.

Ehh, I’d still use phoenix for that, it would scale significantly better than Go would if things ever grow. Plus it is much easier, shorter, and more readable code.

Works fine on those as single-units. If you want to scale up then just have some method for them to communicate between each other so they can spool up their network mesh. But yes, the BEAM works quite well on very low-end hardware and/or virtual hardware. It was designed for phone-relay-routers way back in the day after all. ^.^

My app at work serving a few dozen people at work concurrently eats about 120megs of ram, and that is with heavy websocket work, some database caching held in memory, etc…

Not a clue what that is. ^.^

I do not use Amazon things at all personally as I can spool up another container on one of my dedicated machines at a significantly smaller cost than the huge charges amazon charges. ^.^

Generic example of any kind of low-level processing that spins the CPU faster than I/O. The BEAM is optimized for I/O, like networking, however you can write and bind in code from other languages then call them with ease to do such CPU bound work if really necessary. If you are writing a CMS or something you will not at all have CPU bound work so you can ignore that.

Network bound.

Network bound with some database graph lookups that will be pretty hefty (PostgreSQL works perfect for this if set up properly).

Network bound.

None are CPU bound, go gains you nothing except larger and more unreadable code while not handling failure conditions as well. ^.^

Sure if you want. Erlang/Elixir can call out to anything. If you had something CPU bound you can call out those parts to Go or C++ or Rust or whatever, anything.

Way way way too much legacy code that likely has multiple caching layers in front of each part of it to bring it up to a speed that works half-decently. Too much work to rewrite, not worth the cost.

Well WhatsApp runs on the BEAM and they are the largest messaging platform in the world. :wink:

Other big things are multiple databases are written on the BEAM (Riak, CouchDB, etc…), other messaging platforms (ejabber, etc…), etc… etc…

Phoenix is a server, not a framework, you are mixing apples and oranges. ^.^

Uh, that sounds like someone is high on something… Phoenix is a server, you can write anything on it, it is not bound to any specific framework (rather you write frameworks ‘on’ it, if you even want them).

Yeah he does not know of what he speaks. ^.^
He cites using maru, but maru is just another plug thing, like phoenix. The webserver in phoenix/maru is ‘cowboy’, there are ‘plugs’ that are built on it to integrate with. Phoenix is just a set of helper plugs, like maru is (except maru only handles REST, Phoenix handles REST, websockets, etc… etc…), you can use as many or as little of them in phoenix as you want. You can use phoenix and maru together if you want, they are all just plugs.

Not really. It would not scale as well, no communication of backend data as well, larger code, more unmaintanable code, not as crash-proof, etc… etc…

Not more suitable or not, it is a server, not a framework, you can build anything on it, whether REST+React.js or industrial applications or a little API connection or a massive distributed websocket chat room with a million users in it. It is a server, not a framework, you can build anything web’y (and far more) on the BEAM with ease. :wink:

2 Likes

Yes I aware that, but instagram also invested a lot of money & infrastructure to make it happen. Not just “vanilla” django that we use today. And I don’t think they would migrate to elixir/phoenix (at least not very soon), because migrate such a huge app is very expensive. Just like facebook, they still use a lot of PHP because of legacy reason, not because PHP is great or something.

I cannot answer this question, since I also still learning the phoenix, and I never tried laravel. But, as far as I know… Phoenix is just like any other MVC framework out there (in terms of workflow and features), but it’s a way way faster. You can compare it directly to Rails I think.

In Go, there are a lots of microframework with exceptional speed & performance (like this one: GitHub - kataras/iris: The fastest HTTP/2 Go Web Framework. New, modern and easy to learn. Fast development with Code you control. Unbeatable cost-performance ratio 🚀), if you prefer simpler solution rather than fullstack MVC. But as I said before, you can also use phoenix to get the jobe done :smiley:

1 Like

Thanks guys :slight_smile: I will continue my journey with elixir/phoenix then :slight_smile:

I’ll KIV Golang

You are on the right path buddy. Keep powerfull with Elixir/Phoenix! :wink:

1 Like

This is only in a multithreading Django server. For example at work we use uWSGI that uses multiple independent processes, there are no GIL issues then.

1 Like

You can use multiple processes, but how much memory that uses? Let’s be optimistic and say that with CoW it will be ~100MB per concurrent request. A single Elixir process starts at ~2kB and grows as needed (for that request only). Furthermore, thanks to how Elixir uses memory, as soon as the request finishes, the entire memory of that request is reclaimed without running the GC.

Another issue with multiple processes is that if you want to share anything between them, you need to employ something like Redis. With a single process, an in-memory data/resource sharing is perfectly enough, unless you’re scaling into multiple servers (in Elixir this is usually realised through ets tables).

3 Likes

Yes, I know these things, I was just commenting on the GIL. Though 100 MB per request is a bit ridiculous don’t you think? :wink:

It’s not per request, but per process, which allows you to run a concurrent request. The request itself probably takes far less. That doesn’t change the fact that on a 512MB server, you probably won’t be able to start more than 3-4 processes.

Of course GIL does not apply for IO operations, so with good luck, those 3-4 processes will allow you probably to handle 10 requests concurrently. With the same memory, phoenix will be able to handle much, much more.

2 Likes

Phoenix has framework in its name http://www.phoenixframework.org/. The webserver would be Cowboy.

That’s not very nice. There has been a lot of talk about marketing and adoption on this forum, the right approach to adoption is not to call people names because they do not share your opinion.

2 Likes

I’ve heard it being called a server a few times as well (can’t remember where now though). I agree with you that it is a framework - plus that’s how it is officially referred to on the homepage:

A productive web framework that does not compromise speed and maintainability.

I agree that we should be as nice as we can about anyone who crops up in conversation - even if they are not a member here. The only real exception would be if someone was widely regarded as highly contemptible (and I can only think of two people that fit that bill in the whole wide programming world) but even then I think it’s preferable to get our points across with diplomacy :lol:

Having said that I do think that ODL1’s comment was a little tongue in cheek as indicated by the cat smily thingy - well I hope so anyway :101:

1 Like

I use uWSGI on some of my servers as well, you have to synchronize communication through the database then (which a few of my things did not even need ^.^). :slight_smile:

For note, on my largest server, a 24 core, 64 gigs ram, 1gb uplink, I had a few erlang servers on it (handling the largest of loads other than nginx itself) and they barely hit a gig of ram total (this was handling anywhere from 200-20000 at peak json HTTP connections per second).

The java servers on the other hand hemorrhaged memory. Had a few python ones as well but they were light load, <1 connection a second on average, they still hit pretty high on memory especially considering their light load…

Er, yes, that is my usual tongue-in-cheek/sarcastic/being-cute emoticon. :slight_smile:
It is hard to hold down my INTJ-speech-impulses at times. :slight_smile:

Ah I meant server as in it does its own hosting and does not state what a website should look like or how it acts (as django does), it can be built to be anything. :slight_smile:

1 Like

https://smashingboxes.com/blog/choosing-your-future-tech-stack-clojure-vs-elixir-vs-go/

Conlusion :slight_smile:

ELIXIR IS THE MOST FUN TO PROGRAM

PS
Go is mostly used for cloud software like Docker, DigitalOcean, Kubernetes …
I think it also would be nice to have some knowledge of GO lang.

2 Likes

Go to a decent degree is google’s manifestation of NIH syndrome :slight_smile:

3 Likes

Maybe yes but Google also giving a lot to open source community :slight_smile:

1 Like

Yep but there are mainly two drivers for this developer mindshare and driving people toward google payed service e.g. k8s GAE etc. We are all benefiting from this though so can’t complain :slight_smile:

1 Like