chartkick 3.3.1 → 4.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +31 -2
- data/LICENSE.txt +1 -1
- data/README.md +78 -39
- data/lib/chartkick.rb +2 -26
- data/lib/chartkick/enumerable.rb +25 -0
- data/lib/chartkick/helper.rb +43 -28
- data/lib/chartkick/version.rb +1 -1
- data/licenses/LICENSE-chart.js.txt +9 -0
- data/licenses/LICENSE-chartjs-adapter-date-fns.txt +9 -0
- data/licenses/LICENSE-chartkick.js.txt +22 -0
- data/licenses/LICENSE-date-fns.txt +20 -0
- data/vendor/assets/javascripts/Chart.bundle.js +2 -20755
- data/vendor/assets/javascripts/chart.js +12486 -0
- data/vendor/assets/javascripts/chartjs-adapter-date-fns.bundle.js +6313 -0
- data/vendor/assets/javascripts/chartkick.js +340 -257
- metadata +16 -52
- data/CONTRIBUTING.md +0 -46
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: d9ca3fe125f71ef5a1a21a191a03244b9235396f4c72f4d8e742f7d1a3feaa98
|
4
|
+
data.tar.gz: d7da49117fa84b8525bf76acc421b22e71a0a38a2f2e798c182f96f0d6780a60
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: b00a3accac3e738dc1d0fa7480d162002f5302a8e725d28bfcd3c455514fa79080559b01cfc8a897c44a8d551fdfad3b80fb39a98a9b69671ec8dfa9c2d082e4
|
7
|
+
data.tar.gz: 5a1ccaf63c5bbd240e6ef7a14e240992387cc16c7ce43e6c1b3eab8cb1b632046adbea632db17a96194a21e6e7ce2427d1997ca5734541d51b3c6d2e506a3a8f
|
data/CHANGELOG.md
CHANGED
@@ -1,7 +1,36 @@
|
|
1
|
+
## 4.0.0 (2021-04-04)
|
2
|
+
|
3
|
+
- Added support for Chart.js 3
|
4
|
+
- Added `loading` option
|
5
|
+
- Made charts deferrable by default
|
6
|
+
- Set `nonce` automatically when present
|
7
|
+
- Prefer `empty` over `messages: {empty: ...}`
|
8
|
+
- Removed support for Ruby < 2.6 and Rails < 5.2
|
9
|
+
|
10
|
+
Breaking changes
|
11
|
+
|
12
|
+
- Removed support for Chart.js 2
|
13
|
+
|
14
|
+
## 3.4.2 (2020-10-20)
|
15
|
+
|
16
|
+
- Updated Chart.js to 2.9.4
|
17
|
+
|
18
|
+
## 3.4.1 (2020-10-06)
|
19
|
+
|
20
|
+
- Relaxed validation for `width` and `height` options
|
21
|
+
|
22
|
+
## 3.4.0 (2020-08-04)
|
23
|
+
|
24
|
+
- Fixed CSS injection with `width` and `height` options - [more info](https://github.com/ankane/chartkick/issues/546)
|
25
|
+
|
26
|
+
## 3.3.2 (2020-07-23)
|
27
|
+
|
28
|
+
- Updated Chartkick.js to 3.2.1
|
29
|
+
|
1
30
|
## 3.3.1 (2019-12-26)
|
2
31
|
|
3
32
|
- Updated Chart.js to 2.9.3
|
4
|
-
- Fixed
|
33
|
+
- Fixed deprecation warnings in Ruby 2.7
|
5
34
|
|
6
35
|
## 3.3.0 (2019-11-09)
|
7
36
|
|
@@ -19,7 +48,7 @@
|
|
19
48
|
|
20
49
|
## 3.2.0 (2019-06-04)
|
21
50
|
|
22
|
-
- Fixed XSS vulnerability -
|
51
|
+
- Fixed XSS vulnerability - [more info](https://github.com/ankane/chartkick/issues/488)
|
23
52
|
|
24
53
|
## 3.1.0 (2019-05-26)
|
25
54
|
|
data/LICENSE.txt
CHANGED
data/README.md
CHANGED
@@ -4,13 +4,17 @@ Create beautiful JavaScript charts with one line of Ruby. No more fighting with
|
|
4
4
|
|
5
5
|
[See it in action](https://chartkick.com)
|
6
6
|
|
7
|
-
|
7
|
+
**Chartkick 4.0 was recently released** - see [how to upgrade](#upgrading)
|
8
|
+
|
9
|
+
:fire: For admin charts and dashboards, check out [Blazer](https://github.com/ankane/blazer/), and for advanced visualizations, check out [Vega](https://github.com/ankane/vega)
|
8
10
|
|
9
11
|
:two_hearts: A perfect companion to [Groupdate](https://github.com/ankane/groupdate), [Hightop](https://github.com/ankane/hightop), and [ActiveMedian](https://github.com/ankane/active_median)
|
10
12
|
|
13
|
+
[](https://github.com/ankane/chartkick/actions)
|
14
|
+
|
11
15
|
## Quick Start
|
12
16
|
|
13
|
-
Add this line to your application
|
17
|
+
Add this line to your application’s Gemfile:
|
14
18
|
|
15
19
|
```ruby
|
16
20
|
gem "chartkick"
|
@@ -19,14 +23,13 @@ gem "chartkick"
|
|
19
23
|
For Rails 6 / Webpacker, run:
|
20
24
|
|
21
25
|
```sh
|
22
|
-
yarn add chartkick
|
26
|
+
yarn add chartkick
|
23
27
|
```
|
24
28
|
|
25
29
|
And in `app/javascript/packs/application.js`, add:
|
26
30
|
|
27
31
|
```js
|
28
|
-
require("chartkick")
|
29
|
-
require("chart.js")
|
32
|
+
require("chartkick/chart.js")
|
30
33
|
```
|
31
34
|
|
32
35
|
For Rails 5 / Sprockets, in `app/assets/javascripts/application.js`, add:
|
@@ -36,7 +39,7 @@ For Rails 5 / Sprockets, in `app/assets/javascripts/application.js`, add:
|
|
36
39
|
//= require Chart.bundle
|
37
40
|
```
|
38
41
|
|
39
|
-
This sets up Chartkick with Chart.js. For other charting libraries, see [detailed instructions](#installation).
|
42
|
+
This sets up Chartkick with [Chart.js](https://www.chartjs.org/). For other charting libraries, see [detailed instructions](#installation).
|
40
43
|
|
41
44
|
## Charts
|
42
45
|
|
@@ -206,12 +209,6 @@ Specify legend position
|
|
206
209
|
<%= line_chart data, legend: "bottom" %>
|
207
210
|
```
|
208
211
|
|
209
|
-
Defer chart creation until after the page loads
|
210
|
-
|
211
|
-
```erb
|
212
|
-
<%= line_chart data, defer: true %>
|
213
|
-
```
|
214
|
-
|
215
212
|
Donut chart
|
216
213
|
|
217
214
|
```erb
|
@@ -260,16 +257,22 @@ Show insignificant zeros, useful for currency - *Chart.js, Highcharts*
|
|
260
257
|
<%= line_chart data, round: 2, zeros: true %>
|
261
258
|
```
|
262
259
|
|
263
|
-
Friendly byte sizes
|
260
|
+
Friendly byte sizes
|
264
261
|
|
265
262
|
```erb
|
266
263
|
<%= line_chart data, bytes: true %>
|
267
264
|
```
|
268
265
|
|
266
|
+
Show a message when data is loading
|
267
|
+
|
268
|
+
```erb
|
269
|
+
<%= line_chart data, loading: "Loading..." %>
|
270
|
+
```
|
271
|
+
|
269
272
|
Show a message when data is empty
|
270
273
|
|
271
274
|
```erb
|
272
|
-
<%= line_chart data,
|
275
|
+
<%= line_chart data, empty: "No data" %>
|
273
276
|
```
|
274
277
|
|
275
278
|
Refresh data from a remote source every `n` seconds
|
@@ -308,7 +311,7 @@ Chartkick.options = {
|
|
308
311
|
Customize the html
|
309
312
|
|
310
313
|
```ruby
|
311
|
-
Chartkick.options[:html] = '<div id="%{id}" style="height: %{height};"
|
314
|
+
Chartkick.options[:html] = '<div id="%{id}" style="height: %{height};">%{loading}</div>'
|
312
315
|
```
|
313
316
|
|
314
317
|
You capture the JavaScript in a content block with:
|
@@ -323,7 +326,7 @@ Then, in your layout, use:
|
|
323
326
|
<%= yield :charts_js %>
|
324
327
|
```
|
325
328
|
|
326
|
-
|
329
|
+
For Padrino, use `yield_content` instead of `yield`.
|
327
330
|
|
328
331
|
This is great for including all of your JavaScript at the bottom of the page.
|
329
332
|
|
@@ -370,9 +373,7 @@ If you want to use the charting library directly, get the code with:
|
|
370
373
|
<%= line_chart data, code: true %>
|
371
374
|
```
|
372
375
|
|
373
|
-
The code will be logged to the JavaScript console.
|
374
|
-
|
375
|
-
> JavaScript functions cannot be logged, so it may not be identical.
|
376
|
+
The code will be logged to the JavaScript console. JavaScript functions cannot be logged, so it may not be identical.
|
376
377
|
|
377
378
|
### Download Charts
|
378
379
|
|
@@ -384,7 +385,7 @@ Give users the ability to download charts. It all happens in the browser - no se
|
|
384
385
|
<%= line_chart data, download: true %>
|
385
386
|
```
|
386
387
|
|
387
|
-
|
388
|
+
Safari will open the image in a new window instead of downloading.
|
388
389
|
|
389
390
|
Set the filename
|
390
391
|
|
@@ -418,21 +419,20 @@ Next, choose your charting library.
|
|
418
419
|
- [Google Charts](#google-charts)
|
419
420
|
- [Highcharts](#highcharts)
|
420
421
|
|
421
|
-
|
422
|
+
In the instructions below, `application.js` must be included **before** the charts in your views, unless using the `:content_for` option.
|
422
423
|
|
423
424
|
### Chart.js
|
424
425
|
|
425
426
|
For Rails 6 / Webpacker, run:
|
426
427
|
|
427
428
|
```sh
|
428
|
-
yarn add chartkick
|
429
|
+
yarn add chartkick
|
429
430
|
```
|
430
431
|
|
431
432
|
And in `app/javascript/packs/application.js`, add:
|
432
433
|
|
433
434
|
```js
|
434
|
-
require("chartkick")
|
435
|
-
require("chart.js")
|
435
|
+
require("chartkick/chart.js")
|
436
436
|
```
|
437
437
|
|
438
438
|
For Rails 5 / Sprockets, in `app/assets/javascripts/application.js`, add:
|
@@ -487,7 +487,7 @@ yarn add chartkick highcharts
|
|
487
487
|
And in `app/javascript/packs/application.js`, add:
|
488
488
|
|
489
489
|
```js
|
490
|
-
require("chartkick
|
490
|
+
require("chartkick/highcharts")
|
491
491
|
```
|
492
492
|
|
493
493
|
For Rails 5 / Sprockets, download [highcharts.js](https://code.highcharts.com/highcharts.js) into `vendor/assets/javascripts` (or use `yarn add highcharts` in Rails 5.1+), and in `app/assets/javascripts/application.js`, add:
|
@@ -505,6 +505,27 @@ Download [chartkick.js](https://raw.githubusercontent.com/ankane/chartkick/maste
|
|
505
505
|
<script src="chartkick.js"></script>
|
506
506
|
```
|
507
507
|
|
508
|
+
Then include the charting library.
|
509
|
+
|
510
|
+
Chart.js - download [Chart.js](https://unpkg.com/chart.js@3/dist/chart.js) and the [date-fns adapter bundle](https://unpkg.com/chartjs-adapter-date-fns@2.0.0/dist/chartjs-adapter-date-fns.bundle.js)
|
511
|
+
|
512
|
+
```html
|
513
|
+
<script src="chart.js"></script>
|
514
|
+
<script src="chartjs-adapter-date-fns.bundle.js"></script>
|
515
|
+
```
|
516
|
+
|
517
|
+
Google Charts
|
518
|
+
|
519
|
+
```html
|
520
|
+
<script src="https://www.gstatic.com/charts/loader.js"></script>
|
521
|
+
```
|
522
|
+
|
523
|
+
Highcharts - download [highcharts.js](https://code.highcharts.com/highcharts.js)
|
524
|
+
|
525
|
+
```html
|
526
|
+
<script src="highcharts.js"></script>
|
527
|
+
```
|
528
|
+
|
508
529
|
### Multiple Libraries
|
509
530
|
|
510
531
|
If more than one charting library is loaded, choose between them with:
|
@@ -562,6 +583,12 @@ Redraw the chart with:
|
|
562
583
|
chart.redraw()
|
563
584
|
```
|
564
585
|
|
586
|
+
Destroy the chart with:
|
587
|
+
|
588
|
+
```javascript
|
589
|
+
chart.destroy()
|
590
|
+
```
|
591
|
+
|
565
592
|
Loop over charts with:
|
566
593
|
|
567
594
|
```javascript
|
@@ -587,23 +614,28 @@ Check out [chartkick.js](https://github.com/ankane/chartkick.js)
|
|
587
614
|
|
588
615
|
## Upgrading
|
589
616
|
|
590
|
-
###
|
617
|
+
### 4.0
|
591
618
|
|
592
|
-
|
619
|
+
If you use Sprockets, update the gem and you’re good to go!
|
593
620
|
|
594
|
-
|
595
|
-
- Removed chartkick.js from asset precompile (no longer needed)
|
596
|
-
- Removed `xtype` option - numeric axes are automatically detected
|
597
|
-
- Removed `window.Chartkick = {...}` way to set config - use `Chartkick.configure` instead
|
598
|
-
- Removed support for the Google Charts jsapi loader - use loader.js instead
|
621
|
+
If you use Webpacker, run:
|
599
622
|
|
600
|
-
|
623
|
+
```sh
|
624
|
+
yarn upgrade chartkick --latest
|
625
|
+
```
|
601
626
|
|
602
|
-
|
627
|
+
If you use Chart.js with Webpacker, in `app/javascript/packs/application.js`, change:
|
603
628
|
|
604
|
-
|
605
|
-
|
606
|
-
|
629
|
+
```js
|
630
|
+
require("chartkick")
|
631
|
+
require("chart.js")
|
632
|
+
```
|
633
|
+
|
634
|
+
to:
|
635
|
+
|
636
|
+
```js
|
637
|
+
require("chartkick/chart.js")
|
638
|
+
```
|
607
639
|
|
608
640
|
## Credits
|
609
641
|
|
@@ -613,8 +645,6 @@ Chartkick uses [iso8601.js](https://github.com/Do/iso8601.js) to parse dates and
|
|
613
645
|
|
614
646
|
View the [changelog](https://github.com/ankane/chartkick/blob/master/CHANGELOG.md)
|
615
647
|
|
616
|
-
Chartkick follows [Semantic Versioning](https://semver.org/)
|
617
|
-
|
618
648
|
## Contributing
|
619
649
|
|
620
650
|
Everyone is encouraged to help improve this project. Here are a few ways you can help:
|
@@ -623,3 +653,12 @@ Everyone is encouraged to help improve this project. Here are a few ways you can
|
|
623
653
|
- Fix bugs and [submit pull requests](https://github.com/ankane/chartkick/pulls)
|
624
654
|
- Write, clarify, or fix documentation
|
625
655
|
- Suggest or add new features
|
656
|
+
|
657
|
+
To get started with development:
|
658
|
+
|
659
|
+
```sh
|
660
|
+
git clone https://github.com/ankane/chartkick.git
|
661
|
+
cd chartkick
|
662
|
+
bundle install
|
663
|
+
bundle exec rake test
|
664
|
+
```
|
data/lib/chartkick.rb
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
# modules
|
2
|
+
require "chartkick/enumerable"
|
1
3
|
require "chartkick/helper"
|
2
4
|
require "chartkick/version"
|
3
5
|
|
@@ -18,29 +20,3 @@ module Chartkick
|
|
18
20
|
end
|
19
21
|
self.options = {}
|
20
22
|
end
|
21
|
-
|
22
|
-
# for multiple series
|
23
|
-
# use Enumerable so it can be called on arrays
|
24
|
-
module Enumerable
|
25
|
-
def chart_json
|
26
|
-
if is_a?(Hash)
|
27
|
-
if (key = keys.first) && key.is_a?(Array) && key.size == 2
|
28
|
-
group_by { |k, _v| k[0] }.map do |name, data|
|
29
|
-
{name: name, data: data.map { |k, v| [k[1], v] }}
|
30
|
-
end
|
31
|
-
else
|
32
|
-
to_a
|
33
|
-
end
|
34
|
-
elsif is_a?(Array)
|
35
|
-
map do |v|
|
36
|
-
if v.is_a?(Hash) && v[:data].is_a?(Hash)
|
37
|
-
v = v.dup
|
38
|
-
v[:data] = v[:data].to_a
|
39
|
-
end
|
40
|
-
v
|
41
|
-
end
|
42
|
-
else
|
43
|
-
self
|
44
|
-
end.to_json
|
45
|
-
end
|
46
|
-
end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
# for both multiple series and
|
2
|
+
# making sure hash order is preserved in JavaScript
|
3
|
+
module Enumerable
|
4
|
+
def chart_json
|
5
|
+
if is_a?(Hash)
|
6
|
+
if (key = keys.first) && key.is_a?(Array) && key.size == 2
|
7
|
+
group_by { |k, _v| k[0] }.map do |name, data|
|
8
|
+
{name: name, data: data.map { |k, v| [k[1], v] }}
|
9
|
+
end
|
10
|
+
else
|
11
|
+
to_a
|
12
|
+
end
|
13
|
+
elsif is_a?(Array)
|
14
|
+
map do |v|
|
15
|
+
if v.is_a?(Hash) && v[:data].is_a?(Hash)
|
16
|
+
v = v.dup
|
17
|
+
v[:data] = v[:data].to_a
|
18
|
+
end
|
19
|
+
v
|
20
|
+
end
|
21
|
+
else
|
22
|
+
self
|
23
|
+
end.to_json
|
24
|
+
end
|
25
|
+
end
|
data/lib/chartkick/helper.rb
CHANGED
@@ -37,17 +37,16 @@ module Chartkick
|
|
37
37
|
|
38
38
|
private
|
39
39
|
|
40
|
-
def chartkick_chart(klass, data_source, **options)
|
40
|
+
def chartkick_chart(klass, data_source, nonce: true, **options)
|
41
41
|
@chartkick_chart_id ||= 0
|
42
42
|
options = chartkick_deep_merge(Chartkick.options, options)
|
43
43
|
element_id = options.delete(:id) || "chart-#{@chartkick_chart_id += 1}"
|
44
|
-
height = options.delete(:height) || "300px"
|
45
|
-
width = options.delete(:width) || "100%"
|
44
|
+
height = (options.delete(:height) || "300px").to_s
|
45
|
+
width = (options.delete(:width) || "100%").to_s
|
46
46
|
defer = !!options.delete(:defer)
|
47
47
|
# content_for: nil must override default
|
48
48
|
content_for = options.key?(:content_for) ? options.delete(:content_for) : Chartkick.content_for
|
49
49
|
|
50
|
-
nonce = options.delete(:nonce)
|
51
50
|
if nonce == true
|
52
51
|
# Secure Headers also defines content_security_policy_nonce but it takes an argument
|
53
52
|
# Rails 5.2 overrides this method, but earlier versions do not
|
@@ -57,6 +56,8 @@ module Chartkick
|
|
57
56
|
elsif respond_to?(:content_security_policy_script_nonce)
|
58
57
|
# Secure Headers
|
59
58
|
nonce = content_security_policy_script_nonce
|
59
|
+
else
|
60
|
+
nonce = nil
|
60
61
|
end
|
61
62
|
end
|
62
63
|
nonce_html = nonce ? " nonce=\"#{ERB::Util.html_escape(nonce)}\"" : nil
|
@@ -65,12 +66,26 @@ module Chartkick
|
|
65
66
|
html_vars = {
|
66
67
|
id: element_id,
|
67
68
|
height: height,
|
68
|
-
width: width
|
69
|
+
width: width,
|
70
|
+
# don't delete loading option since it needs to be passed to JS
|
71
|
+
loading: options[:loading] || "Loading..."
|
69
72
|
}
|
73
|
+
|
74
|
+
[:height, :width].each do |k|
|
75
|
+
# limit to alphanumeric and % for simplicity
|
76
|
+
# this prevents things like calc() but safety is the priority
|
77
|
+
# dot does not need escaped in square brackets
|
78
|
+
raise ArgumentError, "Invalid #{k}" unless html_vars[k] =~ /\A[a-zA-Z0-9%.]*\z/
|
79
|
+
end
|
80
|
+
|
70
81
|
html_vars.each_key do |k|
|
82
|
+
# escape all variables
|
83
|
+
# we already limit height and width above, but escape for safety as fail-safe
|
84
|
+
# to prevent XSS injection in worse-case scenario
|
71
85
|
html_vars[k] = ERB::Util.html_escape(html_vars[k])
|
72
86
|
end
|
73
|
-
|
87
|
+
|
88
|
+
html = (options.delete(:html) || %(<div id="%{id}" style="height: %{height}; width: %{width}; text-align: center; color: #999; line-height: %{height}; font-size: 14px; font-family: 'Lucida Grande', 'Lucida Sans Unicode', Verdana, Arial, Helvetica, sans-serif;">%{loading}</div>)) % html_vars
|
74
89
|
|
75
90
|
# js vars
|
76
91
|
js_vars = {
|
@@ -84,28 +99,28 @@ module Chartkick
|
|
84
99
|
end
|
85
100
|
createjs = "new Chartkick[%{type}](%{id}, %{data}, %{options});" % js_vars
|
86
101
|
|
87
|
-
if defer
|
88
|
-
|
89
|
-
<
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
102
|
+
warn "[chartkick] The defer option is no longer needed and can be removed" if defer
|
103
|
+
|
104
|
+
# Turbolinks preview restores the DOM except for painted <canvas>
|
105
|
+
# since it uses cloneNode(true) - https://developer.mozilla.org/en-US/docs/Web/API/Node/
|
106
|
+
#
|
107
|
+
# don't rerun JS on preview to prevent
|
108
|
+
# 1. animation
|
109
|
+
# 2. loading data from URL
|
110
|
+
js = <<~JS
|
111
|
+
<script#{nonce_html}>
|
112
|
+
(function() {
|
113
|
+
if (document.documentElement.hasAttribute("data-turbolinks-preview")) return;
|
114
|
+
|
115
|
+
var createChart = function() { #{createjs} };
|
116
|
+
if ("Chartkick" in window) {
|
117
|
+
createChart();
|
118
|
+
} else {
|
119
|
+
window.addEventListener("chartkick:load", createChart, true);
|
120
|
+
}
|
121
|
+
})();
|
122
|
+
</script>
|
123
|
+
JS
|
109
124
|
|
110
125
|
if content_for
|
111
126
|
content_for(content_for) { js.respond_to?(:html_safe) ? js.html_safe : js }
|