4 ms·
Microservices makes sense, I suppose, but the cases in which distributed services and isolated processes are critical just aren't comment enough in my experienc
by rpazyaquian 10y ago
Microservices makes sense, I suppose, but the cases in which distributed services and isolated processes are critical just aren't comment enough in my experience to require sticking specifically to a SOA-like architecture for everything. Especially in a web app like something you'd make in Rails, which already handles exceptions pretty well and rarely require concurrency.
The idea of composing individual applications and programs sounds very powerful, and I like the idea of using it as a way to compose programs written in different languages together (a Rails server talking to a Clojure ML service that uses Rust bindings to do hardcore number crunching, for example). That could be interesting. I don't know what I'd use it for, though.
- andruby 10y ago> Especially in a web app like something you'd make in Rails, which [..] rarely requires concurrency. What? If you don't need concurrency in a web app that means that your app can only serve one client at a time and other clients have to wait in line. That won't scale to more than a couple concurrent users. You're right that microservices don't make sense for every web app. Especially when you're still figuring out product-market fit. But once you achieve a certain scale (both in number of users and number of developers) microservices/SOA starts to make a lot more sense. And that's an area where the Erlang VM really shines. Erlang's concurrency model is awesome and fits really well with the hardware evolution to more cores: lightweight processes, immutability, message passing, location transparency, etc.
- rpazyaquian 10y agoI wouldn't be surprised if I've just been insulated from thinking about concurrency with Rails/have never worked on a Rails project that had to think about concurrency in any significant way. Which is a little disappointing, I do want to work on interesting problems instead of being a CRUD monkey forever... I do think Elixir and Phoenix have a lot of value because Phoenix has the "get shit done" factor of Rails and yet still allows for your application to scale once you've entered the market, and you don't have to drop everything and move to a more scalable language/architecture and slow down. Plus, Elixir's features and syntax make it a lot more accessible than Erlang.
- sotojuan 10y ago> Especially in a web app like something you'd make in Rails, which already handles exceptions pretty well and rarely require concurrency. That's interesting considering the reason Phoenix was made is because the author was having a lot of trouble doing concurrency in Ruby.
- sanderjd 10y agoI think something that confuses the issue here is that while most applications are a great fit for monolithic Rails (or similar), the applications that many of us here seek out to work on are those that are larger (in scale or in functionality) and more complex. I'm not sure how you could check this, but I suspect that people working on bigger applications where SOA thrives are over-represented here. Most of the debate between "you're not gonna need that!" and "I have needed that!" just stems from people attempting to project their own experiences onto everyone.
- the_gastropod 10y agoConsider background jobs using Resque or Sidekiq. Those are a kind of concurrency. These kinds of libraries are unnecessary in Elixir, where you can spin up another process to handle this kind of "background" work outside of the normal request/response flow.
- mperham 10y agoHow do you process a million jobs in parallel across many machines? How do you schedule a job to run in a week? I'm the author of Sidekiq and not trying to debate; I'm simply ignorant of how Erlang, BEAM and the ecosystem solve these common problems, which usually persist no matter which language you use.
- querulous 10y ago(caveat: in practice you'd do this differently, making sure applications were prestarted/preregistered on remote nodes, ensuring your network was already connected and wrapping most of these calls in nicer function calls but for the sake of illustration i've described the naive way to do this) %% ping a remote node to connect to it pong = net_adm:ping('foo@127.0.0.1'), %% start my application on the remote node _ = spawn('foo@127.0.0.1', application, start, [my_app]), %% my_app is a gen_server, an otp process that abstracts %% async request/response and makes it look more like %% synchronous function calls %% this example assumes the gen_server accepts the JobArgs %% and immediately returns 'ok' as acknowledgement, but does %% the work asynchronously ok = gen_server:call({my_app, 'foo@127.0.0.1'}, {do_some_work, JobArgs}) if you wanted to distribute a number of jobs over a number of nodes you'd just repeat this process for each node and distribute your jobs however you choose, either by round robin or something more complicated like rendezvous hashing or something this example assumes you're uninterested in the responses, but if you wanted to receive the results you could either send a pid (process identifier) along with the request that would be setup to collect the results and do any further processing or you could spawn a local process that made the actual call and blocked until it received the results as for scheduling a job a week in the future, the naive way would be to setup a timer that, when it expires, spawns a process that can execute an arbitrary function. no one would do this, normally, however. you'd probably want to use something like sidekiq that can store the job off node and poll regularly to see if there's any jobs you should run