Project

vega

The project is in a healthy, maintained state
Interactive charts for Ruby, powered by Vega and Vega-Lite
2005
2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
 Dependencies
 Project Readme

Vega.rb

Interactive charts for Ruby, powered by Vega and Vega-Lite

See it in action

Works with Rails, iRuby, and other frameworks

Build Status

Installation

Add this line to your application’s Gemfile:

gem "vega"

Then follow the instructions for how you plan to use it:

  • Importmap (Rails 7+ default)
  • Bun, esbuild, or Webpack
  • Sprockets
  • iRuby
  • Other

Importmap

Add to config/importmap.rb:

pin "vega", to: "vega.js"
pin "vega-lite", to: "vega-lite.js"
pin "vega-embed", to: "vega-embed.js"

And add to app/javascript/application.js:

import "vega"
import "vega-lite"
import "vega-embed"

window.dispatchEvent(new Event("vega:load"))

Bun, esbuild, or Webpack

Run:

bun add vega vega-lite vega-embed
# or
yarn add vega vega-lite vega-embed

And add to app/javascript/application.js:

import embed from "vega-embed"

window.vegaEmbed = embed
window.dispatchEvent(new Event("vega:load"))

Sprockets

Add to app/assets/javascripts/application.js:

//= require vega
//= require vega-lite
//= require vega-embed

iRuby

No additional set up is needed.

Other

For Sinatra and other web frameworks, download Vega, Vega-Lite, and Vega-Embed and include them on pages with charts:

<script src="vega.js"></script>
<script src="vega-lite.js"></script>
<script src="vega-embed.js"></script>

Getting Started

Vega is a visualization grammar, and Vega-Lite is a high-level grammar built on top of it. We recommend using Vega-Lite by default and moving to Vega for advanced use cases.

Create visualizations by chaining together methods:

Vega.lite.data(data).mark("bar").height(200)

There are methods for each of the top-level properties. The docs are a great source of examples:

Example

Create a bar chart

Vega.lite
  .data([{city: "A", sales: 28}, {city: "B", sales: 55}, {city: "C", sales: 43}])
  .mark(type: "bar", tooltip: true)
  .encoding(
    x: {field: "city", type: "nominal"},
    y: {field: "sales", type: "quantitative"}
  )

The chart will automatically render in iRuby. For Rails, render it in your view:

<%= Vega.lite.data(...) %>

Vega-Lite

Start a Vega-Lite chart with:

Vega.lite

Data

Docs

Data can be an array

data([{x: "A", y: 1}, {x: "B", y: 2}])

Or a URL

data("https://www.example.com/data.json")

Or a Rover data frame

data(df)

Or a data generator

data(sequence: {start: 0, stop: 10, step: 1, as: "x"})

Transforms

Docs

transform(bin: true, field: "a", as: "binned a")

Marks

Docs

Bar chart

mark("bar")

Line chart

mark("line")

Pie chart

mark("pie")

Area chart

mark("area")

Enable tooltips

mark(type: "bar", tooltip: true)

Encoding

Docs

encoding(x: {field: "a", type: "ordinal"})

Projection

Docs

projection(type: "albersUsa")

View Composition

Docs

Faceting

facet(row: {field: "x"})

Layering

layer(view)

Concatenation

hconcat(view)
vconcat(view)
concat(view)

Repeating

repeat(row: ["a", "b", "c"])

Resolving

resolve(scale: {color: "independent"})

Selections

Docs

selection(x: {type: "single"})

Parameters

Docs

params(name: "cornerRadius", value: 5)

Config

Docs

Set the font

config(font: "Helvetica")

Top-Level Properties

Docs

Set width and height

width(500).height(300)

Set the background color

background("#000")

Set padding

padding(5)
# or
padding(left: 5, top: 5, right: 5, bottom: 5)

Embed Options

Docs

Set embed options

embed_options(actions: true)

Vega

You can also use Vega directly. In this case, you don’t need to include Vega-Lite in the JavaScript files.

Start a Vega chart with:

Vega.start

Spec

You can also create a specification by hand

spec = {
  "$schema" => "https://vega.github.io/schema/vega-lite/v5.json",
  "data" => {"url" => "https://www.example.com"},
  # ...
}

And render it in Rails

<%= vega_chart spec %>

Or display it in iRuby

Vega.display(spec)

Get the spec for a chart

chart.spec

Exporting Charts (experimental)

Export charts to PNG, SVG, or PDF. This requires Node.js and npm 7+. Run:

yarn add vega-cli vega-lite

For PNG, use:

File.binwrite("chart.png", chart.to_png)

For SVG, use:

File.binwrite("chart.svg", chart.to_svg)

For PDF, use:

File.binwrite("chart.pdf", chart.to_pdf)

Content Security Policy (CSP)

Styles and Frames

Enable unsafe inline styles and blob frames on actions that have charts

class ChartsController < ApplicationController
  content_security_policy only: :index do |policy|
    policy.style_src :self, :unsafe_inline
    policy.frame_src :blob
  end
end

Nonce

Automatically add a nonce when configured in Rails with:

<%= vega_chart chart %>

Interpreter

By default, the Vega parser uses the Function constructor, which can cause issues with CSP.

For Importmap, add to config/importmap.rb:

pin "vega-interpreter", to: "vega-interpreter.js"

And add to app/javascript/application.js:

import "vega-interpreter"

For Bun, run:

bun add vega-interpreter

For esbuild or Webpack, run:

yarn add vega-interpreter

For Sprockets, add to app/assets/javascripts/application.js:

//= require vega-interpreter

And set embed options for your charts

embed_options(ast: true)

History

View the changelog

Contributing

Everyone is encouraged to help improve this project. Here are a few ways you can help:

To get started with development:

git clone https://github.com/ankane/vega-ruby.git
cd vega-ruby
bundle install
bundle exec rake test

Resources for contributors: