
Phoenix LiveDashboard - feross
https://github.com/phoenixframework/phoenix_live_dashboard
======
mikl
LiveView is such a game changer for Phoenix (and thus Elixir). From being
“just another web framework” (albeit a very nice one), LiveView enables a
whole different paradigm for web applications. As a developer, it’s like
having superpowers. What would have taken days to build with an SPA or similar
“fat client” JavaScript can be done in hours with LiveView.

~~~
elamje
I think very highly of elixir and Jose. After 3 months of using .NET Blazor in
production, I can say that LiveView and Blazor have some trade offs that
people don’t talk about.

For those that don’t know what they are, they basically keep a websocket
connection open between the client and server to allow the client to call
Elixir and C# functions instead of javascript frameworks that call some rest
api endpoint. You can write HTML click listeners that are in the server
language rather than js.

It’s powerful, but there is a latency trade off since most UI events end up
being handled by the server, the client might notice this latency in the UI.
Blazor specifically has issues with connectivity, which means your client is
completely locked out of the UI until a manual refresh.

It’s true that this is certainly a paradigm shift, and maybe just a stepping
stone to web assembly web apps written in a server language.

I haven’t used LiveView, but I can imagine it’s better than .NET at scaling
since it runs on BEAM rather than the CLR, which means it’s likely the better
choice if you will need to maintain a lot of client connections in your app.

~~~
fahrradflucht
What I don't understand with these technologies, is how you do continuous
deployment without breaking all running client sessions evertime.

~~~
dnsbty
With Erlang releases (compiled code with the Erlang runtime included) you can
do hot code swapping to change the code while it’s still running.

And iirc I believe LiveView will have all the state necessary client-side to
be able to reconstruct the session when reconnecting the socket. I’m not near
my development machine to make sure on that one though.

~~~
te_chris
We store our sessions in Redis and don't do hot code swapping but deploys do
still mostly just work and live channels normally reconnect without any
noticeable downtime. We run everything on GKE so a deploy is just rolling
container swaps.

Liveview is built on top of channels, so worth reading up about them:
[https://hexdocs.pm/phoenix/channels.html](https://hexdocs.pm/phoenix/channels.html)

------
tomconroy
Better link is Jose's tweet about it:
[https://twitter.com/josevalim/status/1250846714665357315](https://twitter.com/josevalim/status/1250846714665357315)

~~~
brightball
Having this built in is absolutely awesome...

------
rubiquity
It’s awesome for Phoenix users to have this built right into their apps. I
know it isn’t a full replacement for Splunk or what have you, but it’s a step
in the right direction to have this at your finger tips. The SaaSification of
operational tools isn’t great from a cost or waste perspective given that most
vendors are likely overprovisioned and under utilized. You also can’t beat the
user experience of staying in your language and framework’s ecosystem. Well
done.

------
cercatrova
I like Elixir and all of its infrastructure and libraries, like BEAM and
Phoenix, but I could never get used to not having static types. What's the
best way to have static types in Elixir?

I have seen in Elixir an implementation of functional programming concepts
that might prove useful:
[https://github.com/witchcrafters/witchcraft](https://github.com/witchcrafters/witchcraft).
It hasn't been updated since last year so I'm not sure if it still works.

These days I've just started using Rust and actix-web instead, seems a lot
faster due to no VM, with static typing, and moreover, algebraic data types. I
wonder if I could use another language without ADTs anymore.

~~~
skrebbel
Same. I suffer through it, because the rest is pretty neat.

There is no best way. Fortunately the Elixir core libraries are annotated with
typespecs, which gets you like 30% there. But dialyzer sucks, and the typespec
syntax itself, as well as its expressiveness, leave a lot to be desired. It's
clearly an afterthought.

One day I'm gonna make a TypeScript for Elixir.

Note: There's eg Gleam a statically typed language for BEAM, but it's quite
unlike Elixir and it has a much smaller community. [https://github.com/gleam-
lang/gleam](https://github.com/gleam-lang/gleam). I doubt using eg Phoenix on
Gleam is possible, or if it is, whether it's fun. It looks promising though,
especially if you're into Ocaml/Haskell-style "hard" FP.

~~~
lpil
Hi! I'm the author of Gleam, thanks for your interest.

For how young we are I think we're doing a good job of building a community,
there are more familiar faces in IRC and on GitHub every day.

My goal is for Gleam to be easier to use than Elixir, and in many ways we are
taking inspiration from Elm which excels here. Hopefully in the future Gleam
will meet your needs! :)

~~~
hopia
Gleam seems like effort in the right place, I'm looking forward to seeing it
in the wild!

Since we got you here, can you tell us what's your plan with static type
checking for message passing semantics? From what I understand, that's the
hard part about producing a static type checker for BEAM systems.

As for things like _gen_server_ , is the idea currently that you simply give
type definitions to callbacks, allowing the gen_server to model its state with
types?

At first glance, I also don't understand yet how parametric polymorphism
works. Is it implemented at language level?

------
namelosw
Phoenix is amazing. Having shallow experience in Rails, I found I can be
productive in day 1. It just works, and solid, and fast.

Yet there are more brilliant things ahead like OTP and LiveView.

There are many other outstanding functional languages, and I like some of them
more than Elixir, but none of them have any framework as solid and
straightforward as Phoenix.

------
krat0sprakhar
Wow, this looks amazing - I'm so jealous of the elixir / pheonix ecosystem!
The built in telemetry is the killer feature IMO as generally one would have
to use an external system such as NewRelic etc to get this info.

Awesome work by the folks behind it - now I just need a project idea for which
I can try this out :)

~~~
nickjj
Not to knock the live dashboard but from what I read on IRC you will still
likely need to use New Relic or other tools to look at logs and explore the
state of your system from the past to help track down errors or analyze /
filter those logs from the past.

The live dashboard only captures information at the moment. There is no
persistence or advanced filtering capabilities. Meaning, if you received an
error notification 5 minutes ago but didn't already have the dashboard open,
you couldn't just load live dashboard and check it out there. You would have
to troll through your own logs or use a 3rd party logging tool just like
before.

Where live dashboard seems to shine is if you already have it open beforehand,
you can see various metrics about your app in real time. Although other
logging tools are pretty close to real-time too.

But it is cool that something like this is included by default. I hope future
releases expand on what it allows you to do.

------
fataliss
I really miss working with Phoenix/Elixir. While switching to the latest
hottest tech rarely make sense, I really feel that the Phoenix core team has
its head in the right place and when I see the features they put out it really
makes me want to switch every project to it.

~~~
djm_
>latest hottest tech rarely make sense

I would agree! But I'd also say that I believe Elixir has moved past this part
of the curve and is seeing serious adoption amongst companies.

I first got interested in 2014 and back then it was definitely still early
days. 6 years later and I'm still yet to regret the decision to invest time
Elixir and BEAM ecosystem.

------
peteforde
Congrats to the Phoenix team on another milestone win. Your rising tide is
lifting many boats.

For those of you working in Rails, you will be excited to know that we have
StimulusReflex:

[https://docs.stimulusreflex.com/](https://docs.stimulusreflex.com/)

SR was inspired by LiveView. It's built on ActionCable, CableReady and
morphdom. It is _fast_ like a demon and works well with AnyCable. You can see
demos here:

[http://expo.stimulusreflex.com/demos/tabular](http://expo.stimulusreflex.com/demos/tabular)

~~~
theonething
Neat! How does this compare with Turbolinks?

~~~
peteforde
It's not an OR, it's an AND.

StimulusReflex is built on top of Stimulus, which is designed to work arm-in-
arm with Turbolinks. We think that the combination of Rails + Stimulus +
Turbolinks + StimulusReflex + solid Russian doll caching is the greatest thing
since sliced bread.

~~~
porker
It would be great to have a higher-level explanation that included this. I
read through the first 4-5 pages of the docs and saw it mentioned these, but
didn't pick up (until the code examples) that it used them.

I'm not a Rails programmer, but I'm keen to learn about all the different
approaches being used & tried, to see what I can make fit with my language.

~~~
peteforde
Help! I'm the guy who writes those docs. I want them to be better. Nothing
strikes terror like "I read through the first 4-5 pages of the docs and saw it
mentioned these, but didn't pick up that it used them."

To me, that's like "When I ordered beef, I didn't know you meant a cow!" lol

Seriously, help me help you. Where did I fuck this up?

The very first paragraph of the Quick Start page:

"A great user experience can be created with Rails alone. Tools such as UJS
remote elements, Stimulus, and Turbolinks are incredibly powerful when
combined. Could you build your application using these tools without
introducing StimulusReflex?"

[https://docs.stimulusreflex.com/quickstart](https://docs.stimulusreflex.com/quickstart)

What is the thing you could have read and understood right away? I really
appreciate whatever you can suggest.

------
kuzee
Elixir/Phoenix developers will get a lot of mileage out of the ability to
quickly collect and inspect stats like this. This is really great and solves
~50% of the use cases for an outside error monitoring service while also
making debugging specific instances easier.

------
systemd0wn
It looks like Plangora made a youtube video recently.
[https://www.youtube.com/watch?v=Nqr5ly35tu8](https://www.youtube.com/watch?v=Nqr5ly35tu8)

------
eqmvii
This is really cool! I'd love to get this into some apps, and the LiveView
dependency might be a nice excuse to sneak that in at the same time...

------
PopeDotNinja
The looks pretty neat. Is this a pretty wrapper for the Erlang Observer, or is
it more than that?

~~~
sb8244
This is more than that. The actual metrics come from erlang functions and
aren't tied to observer.
[https://github.com/phoenixframework/phoenix_live_dashboard/b...](https://github.com/phoenixframework/phoenix_live_dashboard/blob/master/lib/phoenix/live_dashboard/system_info.ex#L135)

Hook into telemetry is also really cool because any library can be
instrumented.

The multi node cluster aspect allows easier monitoring of the full cluster

------
valuearb
What if you live slightly outside of Phoenix? Can you still use the dashboard?

~~~
pselbert
Searching for things related to Phoenix is a constant problem. Even Phoenix
Elixir will sometimes give you results for random bars in Arizona.

~~~
bigbassroller
Try “Elixir Phoenix” and the topic.

------
taspeotis
Is Erlang's BEAM VM really slow compared to other virtual machines, or is it
Phoenix? It seems to be a bit of a laggard on benchmarks [1] and there's been
this thread going on for years [2] which hasn't reached a conclusion.

[1]
[https://www.techempower.com/benchmarks/#section=data-r18&hw=...](https://www.techempower.com/benchmarks/#section=data-r18&hw=ph&test=plaintext&l=zg24n1-f)

[2] [https://elixirforum.com/t/techempower-
benchmarks/171](https://elixirforum.com/t/techempower-benchmarks/171)

EDIT: Thanks everyone for the responses.

~~~
derefr
BEAM is by default tuned for throughput over latency, but also for soft-
realtime responsiveness over throughput. The right benchmark for BEAM
performance isn’t how fast it can do a single-threaded or even multi-threaded
CPU-bound task; but rather the 99th percentile packet-to-pcket latency +
makespan + memory-requirement volatility of a C10M workload. In other words:
if the VM were hosting a million VoIP calls, how many frames would it deliver
“on time” such that the client wouldn’t discard them?

(This is not to say you can’t tune BEAM to the needs of other workloads; those
are just the defaults. Though, _because_ that is the default assumed workload,
it’s also the one most optimization effort goes into.)

BEAM is also pure-functional in a way that a lot of VMs hosting pure-
functional _languages_ aren’t; things like mutable atomic memory handles were
only introduced recently, and there’s no plan to rewrite core operations in
terms of them, because these primitives are less _predictable_ in their time
costs than equivalent functional primitives.

You can go fast under BEAM, but the people who want to do so, often decide
that it’s too hard to go fast while _also_ retaining soft-real-time guarantees
they began using a BEAM language to attain; so they instead use one of BEAM’s
many IPC bridges to hook up a fast native “port program” written in another
language to the BEAM node, ensuring that any hiccups or crashes in the native
code are isolated to its own address space and execution threads.

This last consideration means that very few people are really driving BEAM’s
performance forward, because so many instead take the “escape hatch” of low-
overhead IPC.

Taken as whole systems, though, you’ll find BEAM in a lot of services that go
very fast indeed—you just won’t usually find BEAM itself handling the
performance-critical part!

~~~
taspeotis
Thank you for the explanation of BEAM + its objectives and internals.

> It's incredibly good at multiprocessing, which is really useful in the
> websphere

So on that benchmark I linked, if you switched to the latency tab Phoenix
clocks in at 14.6ms average latency with a standard deviation of 23ms and a
max of 460.7ms. The best looking ASP.NET Core result from a standard deviation
and max point of view is 1.5ms average latency, 1.4ms standard deviation and
49ms max.

So again it's hard for me to tell whether it's BEAM or Phoenix that's
responsible for the relative performance hit.

~~~
derefr
Very likely Phoenix (Phoenix is “more” software than ASP.Net is; a better
comparison might be to Erlang’s cowboy library); but also very likely that the
author of that benchmark didn’t really tune BEAM. By default, BEAM has runtime
tracing hooks enabled; native code compilation (HiPE) disabled; no core
pinning; low enough process-heap-size upon spawn that an immediate grow is
usually necessary; and a slew of other things.

There’s also the fact that Elixir and even Erlang don’t take full advantage of
the possibilities of BEAM-bytecode whole-program optimization. For example,
any list you walk using Erlang’s lists module or Elixir’s Enum module is going
to generate a back-and-forth of remote (symbolic) calls, rather than resulting
in the body of that function of lists/Enum being inlined and fused into the
caller. Which in turn means, even if you use HiPE, you’ll be thunking in and
out of native code so much that the overhead will eat any potential benefit;
_and_ each side will be opaque to the static analysis of the other, so even a
wholesale native recompilation of the runtime won’t save you. (Same with
gen_servers: remote callbacks through library code, rather than fused module-
local receive statements; ergo, 10x optimization opportunity lost.)

You’ll see real optimization in code generated by e.g. Erlang’s lexer-
generator library leex; or in specific parts of each language’s stdlib, like
Elixir’s Unicode-handling functions. But such optimized code emission is thin-
on-the-ground compared to “naive” coding in Erlang/Elixir. (And I don’t blame
the language devs: the languages are fast enough for almost everything people
try to do; and for the rest, you can ignore the language-as-framework and
write entirely self-contained modules that only rely on BEAM primitives.)

