
Altair – A declarative statistical visualization library for Python - dragonsh
https://github.com/altair-viz/altair
======
dragonsh
We used altair to develop an analytics dashboard as part of our single page
application (SPA). We developed a web component encapsulating vega-lite JS
library and used that component to assemble the dashboard which is part of the
application. Altair based backend can use custom renderer to generate target
response for analytics API requests. [1]

Most of the commercial and open source solutions including Tableau, Apache
Superset, Metabase were very complicated to provide a seamless integrated
dashboard with our Single Page Application using the same authenticaton and
authorization layer. Most of these solutions recommend using iFrame. With
altair we could directly generate the target vega-lite json for our web
component and it work seamless.

Also for some static reports we could generate output in other formats from
altair directly. Altair being in Python (Apache Superset was a big contender),
it was easy enough to integrate into our backend as one of the analytics
services provider. Given vega-lite and vega grammar is standardized, we are
exploring to build real-time dashboard analytics application for large multi-
screen display in a control room kind of an environment.

Before altair our backend was generating data directly consumed by chartjs web
component.

[1] [https://altair-
viz.github.io/user_guide/custom_renderers.htm...](https://altair-
viz.github.io/user_guide/custom_renderers.html)

~~~
Sherl
Would you recommend this to integrate with FastAPI or dash/plotly for similar
application?

~~~
dragonsh
We have tried dash/plotly and moved to altair. Reason is we can generate vega-
lite specification and send it to web-component based on API Request (we did
it with flask and bottle).

In general with FastAPI you can integrate altair to generate your vega-lite
json as a response to an API request taking care of authentication and
authorization in FastAPI (either with JWT token or other schemes like oauth2).

------
sandGorgon
FYI - Altair is available on Google Colab notebooks without any hacks or
modification.

[https://stackoverflow.com/a/56081568/112050](https://stackoverflow.com/a/56081568/112050)

~~~
s1t5
Yes, makes sense. Jake VanderPlas (who is the author of the post that you
linked to) is the main developer of altair and currently works at Google on
Google Colab. He also has a good introductory book on Python for data science
and his conference talks have a very nice style to them - the guy is just a
great teacher.

------
cgufus
I especially liked the example of the interactive cross-filter:
[https://altair-
viz.github.io/gallery/interactive_layered_cro...](https://altair-
viz.github.io/gallery/interactive_layered_crossfilter.html)

However I didn't get around to learning the principles to use it regularly.
And I fear if you have a certain chart in your head with some special stuff
you end up tinkering around eventually get a lot of code.

------
teruakohatu
I am definitely going to give it a try but I wish statistical/scientific
plotting libraries' documentation would include example comparisons with
matplotlib and ggplot2. I usually just want to know how much easier/prettier
will library X be to use compared to those two.

~~~
phonebucket
> I usually just want to know how much easier/prettier will library X be to
> use compared to those two.

Don't the examples in the README provide a good enough intro?

If you are familiar with matplotlib and ggplot, you'd have a good idea how to
reproduce those examples in those frameworks. If you are not familiar with
them, then what good is the comparison?

~~~
ErikBjare
If you are not familiar with them, the comparison is useful to help you decide
which one to choose?

------
h8hawk
Python's ploting problem is not imperative vs declarative. The main ugliness
is basically "* * kwargs" every where. Every time it force you look at
document to just find name of parameter you are looking for. Another common
problem is Configs pass as string rather than enum.

~~~
uryga
are you arguing against keyword arguments in general, or against

    
    
      def foo(a, b, **kwargs): 
        """
        Refer to `bar` for the full list of allowed kwargs.
        """
        ...
    

i don't mind the former, but the latter always feels annoying. iirc matplotlib
severely suffers from this

~~~
ImaCake
Yeah, it is often a mystery just what options I have available to use in
matplotlib, and it can be tricky to find which one is the one I _actually_
want!

------
tkinz27
Data scientists at my previous company switched to
[https://github.com/has2k1/plotnine](https://github.com/has2k1/plotnine) when
we made a big push to python. Bit closer api to ggplot than Altair.

------
wodenokoto
With ggplot2 you can add any compatible ggplot object to your plot with a
simple `+`.

It looks like with altair you can only "add" things that are already a method
on your altair object. How does 3rd party geoms and similar work?

------
dwiel
I gave altair a try but I found the data format requirements a pain that got
in the way of the nice plotting API. For example, I wanted to plot n lines,
stored in a (timestamps, n) shaped matrix. First I had to convert this into a
format: (index, line_name, value) where index is the timestamps index in the
original matrix, line_name is a unique name given to each line/column, and
finally the value. There is a pandas method that helps with this conversion,
but it just added one extra confusing step to what I was hoping to be a quick
and intuitive plotting tool.

Their write up on the data format is here: [https://altair-
viz.github.io/user_guide/data.html#long-form-...](https://altair-
viz.github.io/user_guide/data.html#long-form-vs-wide-form-data)

~~~
activatedgeek
Wouldn't any plotting library suffer from this challenge anyways?

One would first make a relevant data transform and then send it to whatever
plotting library. I suspect anything further would limit the flexibility of
the plotting library. To make sure I have minimal pain with data transforms, I
first store/transform data exactly like I would in a real transactional
database. Beyond that it just becomes a matter a joins and
filters/projections.

------
kpgiskpg
I've always hated matplotlib, even though it gets the job done. The graphs are
ugly by default, and the API would be unusable if it weren't for
StackOverflow. Maybe I just need to sit down and learn it really well.

Anyway, this seems cool.

~~~
dlkf
> even though it gets the job done

How is this an addendum, rather than the main point? I will always take a
flexible library that allows me to "get the job done" over a declarative
framework that will do something similar to—but not exactly—what I need.

~~~
tryptophan
I've come to the same conclusion.

GGplot2 is _very_ nice to use and an incredible library...as long as you want
to do something the package author approves of. Want to change some behavior
about how bins are generated because the default behavior lies? Too bad.

Matplotlib is ugly, but it doesn't make decisions for you, and once you
understand it, you can do anything with it.

------
f00_
Hope I get to use this in a project one day!

Declarative systems always seem to feel good (SQL and React come to mind)

Vega-lite is the underlying standard (A Grammar of Interactive Graphics ):
[https://vega.github.io/vega-lite/](https://vega.github.io/vega-lite/)

I used altair in a hackathon interview and got the job:
[https://github.com/DustinAlandzes/drchrono-
hackathon/blob/ma...](https://github.com/DustinAlandzes/drchrono-
hackathon/blob/master/drchrono/views.py#L218)

sadly not hosted

------
prepend
I’ve been trying to find a “tableau to d3” product that just spits out
html+css+JavaScript that can run anywhere.

Altair isn’t quite that, but it’s the closest I’ve seen. I wish python had
ggplot2 with its html widgets, but this will do.

I’ve been really impressed with the browser compatibility in that I’ve yet to
find a bug despite lots of weird mobile users. That and the team adds
functionality quickly so almost as soon as I’m annoyed at not ability to add
captions, it’s made available.

------
nicolaskruchten
Altair and Vega-Lite are awesome!

I'll shamelessly plug Plotly Express
([https://plotly.express/](https://plotly.express/)) here as something that
works in a similar way, i.e. generates JSON figure descriptions rendered in
Javascript, with an even more minimal API, that now accepts both long _and
wide_ data :)

------
phunge
Altair is amazing. I've been using matplotlib going on 12 years now -- Altair
didn't feel more productive at first (more typing), but the longer you work
with it, the more you realize how the API is a cohesive system. This leads to
a more iterative workflow and eventually to better visualizations.

------
kfk
Altair and Vega offer a great declarative way to build interactive charts with
a grammar of graphics. As with other options in this area like Tableau they
are not as good with tabular reports (tables). I think they are still greatly
worth it.

------
cjf4
This is easily my favorite Python visualization tool. The declarative nature
is intuitive, and the way it integrates with vegalite provides a lot of
flexibility. The docs are also great.

If you are missing ggplot2 in Python, I’d say look here first.

------
boromi
would it be possible to link this up with multiple user selectible legend that
then update a table? What I'm thinking is a table with multipl entires, where
the legend on the right of the plot serves specify characterstics in the
table. E.g. gender, age group, and then these selections would plot them but
also update the table below them?

~~~
sterlinm
Yes it's theoretically possible. I created an example of linking a table to a
scatter plot brush selection. That said, I have never been able to get
altair/vega-lite to generate a nicely formatted table to my satisfaction. I
mostly end up connecting a simpler altair chart without interactions to a
dataframe and hook them together using something like ipywidgets, Panel, or
streamlit. It would be really nice though to be able to get the table linked
to native altair interactions like selection and brushing.

[https://altair-
viz.github.io/gallery/scatter_linked_table.ht...](https://altair-
viz.github.io/gallery/scatter_linked_table.html)

~~~
boromi
Thanks. Yeah that's not quite what I was hoping for, I was actually thinking
something closer like the following:
[https://www.m43lenses.com/](https://www.m43lenses.com/)

~~~
sterlinm
ipywidgets + altair could mimic that pretty easily I think since with that
example you just want to filter with a bunch of checkmarks/radios/dropdowns on
a sidebar and then display a chart and table based on those filters.

The place where you start to run into problems is if you want to filter the
table based on interactions with the chart. If you're going to use dropdowns
and checkboxes to filter the dataframe and the chart then you have a lot of
good options.

~~~
boromi
Thanks, I'll check out ipywidgets.

So basically use ipwidgets to create the checkmarks/radio/dropdowns. Then hook
the database up to altair. I'll play tommorow with altair and ipywidgets and
see how I can cook this up.

"filter the table based on interactions with the chart" For me all I'd need is
a the corresponding datapoint selected to highlight the row.

------
vpj
We started using custom charts with Altair instead of Tensorboard and it has
been amazing. Thanks!

