Compare commits

...
717 Commits
Author SHA1 Message Date
Hugh Miles 84ee6d5084 Lyft additional endpoints 2018-02-07 12:32:10 -08:00
Maxime Beauchemin 5d4d7febb9 Reverts apache/incubator-superset#4244 (#4303)
(cherry picked from commit f8dcbf70c5)
2018-01-31 08:17:49 -08:00
Hugh Miles cbedb8b814 fixed conflicts 2018-01-29 14:50:55 -08:00
Hugh A. Miles II 073d56cb33 Added Path, Polygon, and Arcs to deckGL example dashboard (#4242)
* Added Path, Polygon, and Arcs to deckGL example dashboard

* reorder task

* formatting...

* fix flights reference

* cleanup on aisle 9
2018-01-29 11:51:36 -08:00
Maxime Beauchemin e4a95f9428 Use the query_obj as the basis for the cache key (#4260)
* Use the query_obj as the basis for the cache key

When we recently moved from hashing form_data to define the cache_key
towards using the rendered query instead,
it made is such that non deterministic form
control values like relative times specified in "from" and "until" time
bound resulted in making those miss cache 100% of the time.

Here we move away from using the rendered query and using the query_obj
instead.

* Deprecating using form_data in templates
2018-01-28 09:46:13 -08:00
Riccardo Magliocchetti 1b06140bde Bump sqlalchemy to 1.2.2 (#4299)
* Bump sqlalchemy to 1.2.2

Fix #4196

* Bump sqlalchemy-utils to 0.32.21
2018-01-28 09:32:41 -08:00
Maxime Beauchemin f8dcbf70c5 Reverts apache/incubator-superset#4244 (#4303) 2018-01-26 18:09:09 -08:00
michellethomas b9299d61ac Fixing json decode error on druiddatasourcemodelview/api/read (#4291) 2018-01-25 17:12:34 -08:00
Hugh A. Miles II 2384ad4eb5 [geo] Add JS controls to remaining layers (#4272)
* Update viz.py

* added JS controls

* add JS to grid layout

* add JS to hexagon layer

* added JS controls to screengrid

* update to js_data_mutator controls

* remove .map()
2018-01-25 14:07:34 -08:00
Hugh A. Miles II 3fac9367fb Added remaining JS controls to DeckGL layers 2018-01-24 17:13:08 -08:00
Hugh Miles 63cbcb80c3 fastforward to apache/master 2018-01-24 17:05:57 -08:00
Maxime Beauchemin 2b66eadee2 Set point size control's default for deck_scatter viz (#4261) 2018-01-24 16:49:37 -08:00
Maxime Beauchemin 94d9337e0b deck_multi to pass down filters to layers (#4270)
Filters applied to deck_multi will be passed down to layers as.

If the column isn't set as "filterable", the filter is ignored.

Also note that Dashboard configuration in regards to
"filter_immune_slices" and such will be disregarded in this context as
it isn't the dashboard controller passing down the filter and that
context is not easily accessible here.
2018-01-24 16:26:31 -08:00
Maxime Beauchemin a0621e10a8 Handle 'pd.Timestamp' when jsonifying (#4275) 2018-01-24 16:09:22 -08:00
Maxime Beauchemin b72d5b03dc Prevent FilterBox extra query (#4276)
closes https://github.com/apache/incubator-superset/issues/4249
2018-01-24 16:09:03 -08:00
Maxime Beauchemin 914480ad3c Fix SUPERSET_WEBSERVER_TIMEOUT in VisualizeModal (#4277)
* Fix SUPERSET_WEBSERVER_TIMEOUT in VisualizeModal

* Fix test

* lint
2018-01-24 16:08:48 -08:00
Maxime Beauchemin ff2f85f39b [geo] JS function to receive the whole data array instead of individual object (#4262)
Moving from having the user define an interceptor function that operates
on one object at a time.

By passing the entire array, it's possible to do multiple pass where
needed. A common pattern might be to figure out the max value in order
to define a scaler function. That's only possible if dealing with the
whole array.
2018-01-24 13:16:14 -08:00
Maxime Beauchemin 9cf16a4ff2 Fix click on now in DateFilterControl (#4265)
When clicking on `now` or the infinity sign, the popover closes but the
value doesn't show in the label as expected.
2018-01-24 13:15:44 -08:00
Maxime Beauchemin b90c410c01 [explore] fix empty query message in 'View Query' (#4273) 2018-01-24 13:14:38 -08:00
Xiao Hanyu 77d1e5d046 Always use fluid container for navbar. (#4279)
As in https://github.com/apache/incubator-superset/pull/4147 removes the
final non fluid container navbar, I think there's no need to keep this
line of code. Just use navbar with fluid container, always.
2018-01-24 08:55:57 -08:00
Marcus Levine 4bc5fe5495 [BUGFIX]: Check datatype of results before converting to DataFrame (#4108)
* conditional check on datatype of results before converting to df

fix type checking

fix conditional checks

remove trailing whitespace and fix df_data fallback def

actually remove trailing whitespace

generalized type check to check all columns for dict

refactor dict col check

* move df conversion to helper and add unit test

add missing newlines

another missing newline

fix quotes

more quote fixes
2018-01-23 20:58:06 -08:00
timifasubaa 2c72a7ae4f Use json for imports and exports, not pickle (#4243)
* make superset imports and exports use json, not pickle

* fix tests
2018-01-23 20:55:27 -08:00
Maxime Beauchemin 4b11f45f72 Using a NullPool for external connections by default (#4251)
Currently, even though `get_sqla_engine` calls get memoized, engines are
still short lived since they are attached to an models.Database ORM
object. All engines created through this method have the scope of a web
request.

Knowing that the SQLAlchemy objects are short lived means that
a related connection pool would also be short lived and mostly useless.
I think it's pretty rare that connections get reused within the context
of a view or Celery worker task.

We've noticed on Redshift that Superset was leaving many connections
opened (hundreds). This is probably due to a combination of the current
process not garbage collecting connections properly, and perhaps the
absence of connection timeout on the redshift side of things. This
could also be related to the fact that we experience web requests timeouts
(enforced by gunicorn) and that process-killing may not allow SQLAlchemy
to clean up connections as they occur (which this PR may not help
fixing...)

For all these reasons, it seems like the right thing to do to use
NullPool for external connection (but not for our connection to the metadata
db!).

Opening the PR for conversation. Putting this query into our staging
today to run some tests.
2018-01-23 15:13:50 -08:00
Maxime Beauchemin 04ae004f43 Set 'Range Filter' default to false (#4264)
It got set to true mistakenly.
2018-01-23 11:23:41 -08:00
Andres Botero 29ef8c4af8 Fix heatmap tooltip disappears under the slice's header (#4268) 2018-01-23 10:16:14 -08:00
Maxime Beauchemin 718230cdf2 Bump flower==0.9.2 (#4263) 2018-01-23 10:15:10 -08:00
Maxime Beauchemin 36956a5d24 Using a NullPool for external connections by default
Currently, even though `get_sqla_engine` calls get memoized, engines are
still short lived since they are attached to an models.Database ORM
object. All engines created through this method have the scope of a web
request.

Knowing that the SQLAlchemy objects are short lived means that
a related connection pool would also be short lived and mostly useless.
I think it's pretty rare that connections get reused within the context
of a view or Celery worker task.

We've noticed on Redshift that Superset was leaving many connections
opened (hundreds). This is probably due to a combination of the current
process not garbage collecting connections properly, and perhaps the
absence of connection timeout on the redshift side of things. This
could also be related to the fact that we experience web requests timeouts
(enforced by gunicorn) and that process-killing may not allow SQLAlchemy
to clean up connections as they occur (which this PR may not help
fixing...)

For all these reasons, it seems like the right thing to do to use
NullPool for external connection (but not for our connection to the metadata
db!).

Opening the PR for conversation. Putting this query into our staging
today to run some tests.
2018-01-22 16:59:18 -08:00
John Bodley 8175e19f72 [cache] Fixing json.dumps for timestamp (#4240) 2018-01-19 12:10:39 -08:00
Grace Guo 7b76356182 [Sql Lab] Fix query results display at the bottom of screen (#4246) 2018-01-19 10:19:54 -08:00
Grace Guo 1c56319be4 [Sql Lab] Fix Autorefresh component pulling not stopped. (#4244) 2018-01-19 08:57:23 -08:00
Maxime Beauchemin 36caca3244 Fix 'argument to reversed() must be a sequence' (#4237)
When passing empty/null location data out of certain rows in the spatial
control, Superset raises an error when trying to reverse the tuple.
2018-01-18 15:22:22 -08:00
Hugh A. Miles II 1c76d583b3 Added DeckGL.Polygon Layer w/ JS controls (#4227)
* Working polygon layer for deckGL

* add js controls

* add thumbnail

* better description

* refactor to leverage line_column controls

* templates: open code and documentation on a new tab (#4217)

As they are external resources.

* Fix tutorial doesn't match the current interface #4138 (#4215)

* [bugfix] markup and iframe viz raise 'Empty query' (#4225)

closes https://github.com/apache/incubator-superset/issues/4222

Related to: https://github.com/apache/incubator-superset/pull/4016

* [bugfix] time_pivot entry got missing in merge conflict (#4221)

PR here https://github.com/apache/incubator-superset/pull/3518 missed a
line of code while merging conflicts with time_pivot viz

* Improve deck.gl GeoJSON visualization (#4220)

* Improve geoJSON

* Addressing comments

* lint

* refactor to leverage line_column controls

* refactor to use DeckPathViz

* oops
2018-01-18 13:47:04 -08:00
Hugh A. Miles II ee77f11b27 remove setting spatial in DeckPathViz class (#4235) 2018-01-18 13:47:04 -08:00
michellethomas 3b40e90b40 Don't cache if there's no cache key (#4229) 2018-01-18 13:47:04 -08:00
Peter Lubell-Doughtie 6cd83c3025 add Ona as a user (#4234) 2018-01-18 13:47:03 -08:00
Maxime Beauchemin af941736a4 Improve deck.gl GeoJSON visualization (#4220)
* Improve geoJSON

* Addressing comments

* lint
2018-01-18 13:47:03 -08:00
Maxime Beauchemin e502c22c70 [bugfix] time_pivot entry got missing in merge conflict (#4221)
PR here https://github.com/apache/incubator-superset/pull/3518 missed a
line of code while merging conflicts with time_pivot viz
2018-01-18 13:47:03 -08:00
Maxime Beauchemin 46411bc4ad [bugfix] markup and iframe viz raise 'Empty query' (#4225)
closes https://github.com/apache/incubator-superset/issues/4222

Related to: https://github.com/apache/incubator-superset/pull/4016
2018-01-18 13:47:03 -08:00
Yongjie Zhao 32e06616d9 Fix tutorial doesn't match the current interface #4138 (#4215) 2018-01-18 13:47:03 -08:00
Riccardo Magliocchetti b3bc1429ac templates: open code and documentation on a new tab (#4217)
As they are external resources.
2018-01-18 13:47:03 -08:00
michellethomas 9b3eef893a Adding limit to time_table viz to get druid query to work (#4207) 2018-01-18 13:47:03 -08:00
Maxime Beauchemin 151657ba3e [line chart] fix time shift color (#4202) 2018-01-18 13:47:03 -08:00
Hugh A. Miles II 5079b2aa95 Added DeckGL.Polygon Layer w/ JS controls (#4227)
* Working polygon layer for deckGL

* add js controls

* add thumbnail

* better description

* refactor to leverage line_column controls

* templates: open code and documentation on a new tab (#4217)

As they are external resources.

* Fix tutorial doesn't match the current interface #4138 (#4215)

* [bugfix] markup and iframe viz raise 'Empty query' (#4225)

closes https://github.com/apache/incubator-superset/issues/4222

Related to: https://github.com/apache/incubator-superset/pull/4016

* [bugfix] time_pivot entry got missing in merge conflict (#4221)

PR here https://github.com/apache/incubator-superset/pull/3518 missed a
line of code while merging conflicts with time_pivot viz

* Improve deck.gl GeoJSON visualization (#4220)

* Improve geoJSON

* Addressing comments

* lint

* refactor to leverage line_column controls

* refactor to use DeckPathViz

* oops
2018-01-18 13:28:46 -08:00
Hugh A. Miles II cab8e7d22d remove setting spatial in DeckPathViz class (#4235) 2018-01-18 12:03:46 -08:00
michellethomas 85d137b20a Don't cache if there's no cache key (#4229) 2018-01-18 08:28:26 -08:00
Peter Lubell-Doughtie a942f81dfd add Ona as a user (#4234) 2018-01-18 08:27:56 -08:00
Maxime Beauchemin 01043c9bf4 Improve deck.gl GeoJSON visualization (#4220)
* Improve geoJSON

* Addressing comments

* lint
2018-01-17 14:01:32 -08:00
Maxime Beauchemin a9610e2886 [bugfix] time_pivot entry got missing in merge conflict (#4221)
PR here https://github.com/apache/incubator-superset/pull/3518 missed a
line of code while merging conflicts with time_pivot viz
2018-01-17 13:54:45 -08:00
Maxime Beauchemin 5897d85f7a [bugfix] markup and iframe viz raise 'Empty query' (#4225)
closes https://github.com/apache/incubator-superset/issues/4222

Related to: https://github.com/apache/incubator-superset/pull/4016
2018-01-17 13:54:10 -08:00
Yongjie Zhao 0367dce38b Fix tutorial doesn't match the current interface #4138 (#4215) 2018-01-16 21:18:00 -08:00
Riccardo Magliocchetti 1ca1395382 templates: open code and documentation on a new tab (#4217)
As they are external resources.
2018-01-16 21:17:27 -08:00
michellethomas 2607e4be4d Adding limit to time_table viz to get druid query to work (#4207) 2018-01-16 10:27:35 -08:00
Maxime Beauchemin 04680e5ff1 [line chart] fix time shift color (#4202) 2018-01-12 15:10:17 -08:00
Hugh Miles 23cc83f300 fix mergeconflicts 2018-01-12 13:45:17 -08:00
John Bodley a7a6678d5c [cache] Using the query as the basis of the cache key (#4016) 2018-01-12 12:05:12 -08:00
Maxime Beauchemin 8069d6221d [druid] fix 2 phases queries that specify 'Sort By' on 'Series limit' (#4203) 2018-01-12 11:29:24 -08:00
Maxime Beauchemin 269f55c29a [bugfix] dealing with DBAPIs that return unserilizable types (#4200)
Funky datatypes in some databases like BLOBs will have the DBAPI return
python types that can't be serialized to JSON out of the box.

Currently, when this happens SQL Lab fails in a bad way with a gigantic
HTML error message.

This allows specifying a pessimistic JSON serializer handler that will
simply show "Unserializable [type]"
2018-01-12 11:11:31 -08:00
Hugh A. Miles II bca27b436b [Geo] Added DeckGL Arc Layer and Refactor on BaseDeckGL class (#4134)
* Added DeckGL.arc layer

* added color controls

* added stroke_width control

* added process spatial key methods

* change exception to ValueError

* put location into tuple

* reference global spatial keys array

* linting

* refactor on process_spatial_data_obj

* rm whitespace

* refactor arc.get_data

* Revert "refactor arc.get_data"

This reverts commit 8d01b2a22e.

* add spatial controls array

* refactor on spatial keys again :)

* return altered df

* Working refactor with deckGL Arcs

* working arcs refactor :)

* refactored all other deckGL viz types
2018-01-12 11:06:11 -08:00
Benedict Jin aecaa85905 Hanization (#4126)
* Hanization

* Hanization step two

* 1. Update mo & json file; 2. Remove necessary msgid & msgstr; 3. Fix error python-format; 4. Other improvements

* Hanization step three

* Hanization step four (49%)

* Translate chart options

* Translate Search

* Translate view results Data preview new table name 10 seconds 30 seconds 1 minute 5 minutes

* Hanization & update mo/json files

* Update filter translation

* Hanization step 5th (60%)

* Hanization step 6th (70%)

* Hanization step 7th (80%)

* Hanization step 8th (83%)
2018-01-12 08:11:37 -08:00
bolkedebruin 7e36488f03 Superset was using undefined metrics for specifying limits (#4114)
in case a form did not specify a metric (e.g. mapbox). If it is
not available it now defaults to the first dimension instead.

This fixes issue #3604
2018-01-11 21:45:34 -08:00
Maxime Beauchemin 87c3e831a8 Using user-defined Javascript to customize geospatial visualization (#4173)
* Using JS to customize spatial viz and tooltips

* Add missing deck_multi.png

* Improve GeoJSON layer with JS support and extra controls

* Addressing comments
2018-01-11 15:42:44 -08:00
Maxime Beauchemin ee63ebc8ec [datasource editor] click checkbox creates metrics instantly (#4183)
* [datasource editor] click checkbox creates metrics instantly

* Fix tests
2018-01-11 15:42:19 -08:00
Maxime Beauchemin 5916291901 [explore] fix json highlighting for Druid queries (#4201) 2018-01-11 15:41:28 -08:00
Maxime Beauchemin 4b0f252170 Sort out dependencies in travis/tox (#4186)
* Make travis a bit more lean

* Bump npm to 5.6.0
2018-01-10 21:46:10 -08:00
Beto Dealmeida 9176a4072b Enable SQL syntax highlighting in View Query (#4184)
* Enable SQL syntax highlighting in View Query

* Enable SQL syntax highlighting in View Query
2018-01-10 20:49:28 -08:00
John Bodley 0cb7c5e4a6 [annotations] Fixing migration for annotation layers (#4187) 2018-01-10 08:50:05 -08:00
Yongjie Zhao e182f7f962 fix since or until is empty value #4170 (#4176) 2018-01-09 16:54:18 -08:00
Hugh Miles 6e820b8355 rm merge arrows 2018-01-09 16:04:24 -08:00
Hugh Miles 8db14c47e7 fixed permissions 2018-01-09 15:44:00 -08:00
Hugh Miles 58ff72776d updated cherry-pick for lyft-endpoints 2018-01-09 14:12:22 -08:00
fabianmenges 23c98294bd Moving the custom_password_store out of Database class (#4182) 2018-01-09 13:14:20 -08:00
John Bodley 22bdd9e324 [security] Adding all derived FAB UserModelView views to admin only (#4180) 2018-01-09 13:05:37 -08:00
Maxime Beauchemin b72bf98f68 Using JS to customize spatial viz and tooltips
(cherry picked from commit df22f29aa49f8e5991e19430aeed816ab08d2dd3)
2018-01-09 09:01:59 -08:00
Hugh Miles 32b466184e Moved lyft specific endpoints into its own file
(cherry picked from commit a2630b41c8d7da859a39fe5f9f5e51e66e9e97b9)
2018-01-09 08:57:21 -08:00
Maxime Beauchemin bfdfd66160 Simplify login form for oauth
(cherry picked from commit 89ba06d9a6)
2018-01-09 08:57:10 -08:00
Maxime Beauchemin a4c1d6d5c0 0.23.0rc1 2018-01-09 08:51:11 -08:00
Maxime Beauchemin b159e51787 Don't use fully qualified column names in metric definitions (#4101)
When generating an auto SUM() metric on a column, Superset currently
will go `SUM(table_name.column_name)`. This is an issue when moving to
point to another table. It's common to work on some temporary table or
work table and eventually need to point Superset to an alternate table.
2018-01-08 22:03:37 -08:00
John Bodley d57012067b [FAB] configuring updating of permissions (#4172) 2018-01-08 14:39:18 -08:00
timifasubaa 9364fb5b79 Allow alpha role import csv (#4164)
* allow alphas upload csv

* nits
2018-01-08 13:36:30 -08:00
Maxime Beauchemin c49fb0aa9b Make Welcome page into a simple React app (#4147)
* Make Welcome page into a simple React app

This removes a dependency on datatables, we should be able to get rid
of it as we re-write the Table and PivotTable viz

* tests/lint

* Bump node version to latest
2018-01-07 22:13:06 -08:00
Grace Guo b9af019567 Fix chart rendering error in time series table (#4156) 2018-01-06 16:49:59 -08:00
Grace Guo e7f8143c3b [Bug] Closing change datasource modal throws JS error (#4157) 2018-01-05 14:21:52 -08:00
Alexander Tronchin-James c9e47f0bb3 Check for non-None database before using. (#4162)
Some valid sqlalchemy uri's return a URL object with database=None, which causes the following error:
```
2018-01-05 17:59:47,560:ERROR:root:argument of type 'NoneType' is not iterable
Traceback (most recent call last):
  File "/opt/incubator-superset/superset/sql_lab.py", line 186, in execute_sql
    user_name=user_name,
  File "/opt/incubator-superset/superset/utils.py", line 124, in __call__
    return self.func(*args, **kwargs)
  File "/opt/incubator-superset/superset/models/core.py", line 644, in get_sqla_engine
    url = self.db_engine_spec.adjust_database_uri(url, schema)
  File "/opt/incubator-superset/superset/db_engine_specs.py", line 505, in adjust_database_uri
    if '/' in database:
TypeError: argument of type 'NoneType' is not iterable
```
This patch corrects that problem.
2018-01-05 13:54:17 -08:00
Beto Dealmeida 686023c8dd Druid support via SQLAlchemy (#4163)
* Use druiddb

* Remove auto formatting

* Show prequeries

* Fix subtle bug with lists

* Move arguments to query object

* Fix druid run_query
2018-01-05 13:52:58 -08:00
Benedict Jin d997a450cf Fix invaild gitter url (#4125) 2018-01-04 14:45:58 -08:00
zhao yongjie 9e053923d4 Adding Apache Kylin datasource for documentation (#4148) 2018-01-03 20:24:15 -08:00
Leonardo Rochael Almeida ef06a9d497 Create DATA_DIR after importing config (#4143)
Delay creating DATA_DIR until config is fully imported.

This allows superset_config.py to override DATA_DIR before superset
attempts to create it in a potentially unwriteable location.
2018-01-03 09:54:59 -08:00
Maxime Beauchemin 37205099db Fix USA's state geojson for 'Country Map' visualization (#4121)
* Fix USA's state geojson for 'Country Map' visualization

Turns out the ISO codes were missing from the geojson file, this adds it
and uses human-readable indents.

* using proper ISO codes

* Linting

New linting rules started applying, I'm guessing a new version of
pylint?
2018-01-02 20:21:33 -08:00
timifasubaa e498f2fcb6 fix variable name (#4139) 2018-01-02 14:32:24 -08:00
Jeff Niu f7c55270db Remedy for dual axis annotation (#4130) 2018-01-02 14:31:16 -08:00
Maxime Beauchemin 0a6208296e [explore] add datasource metadata (#4104) 2018-01-02 08:41:27 -08:00
Hugh A. Miles II bf4d3a0dff better thumbnail for deck_geojson (#4135) 2017-12-28 13:38:07 -08:00
Hugh A. Miles II b227612f6e Added guard statement for spatial controls (#4124) 2017-12-26 12:27:27 -08:00
Maxime Beauchemin 45686a1af6 Multi layers DECK.GL visualization (#4096)
* Multi layers DECK.GL viz

* Fix tests

* rebasing

* Fix error handling in chartActions

* Addressing comments
2017-12-26 10:47:29 -08:00
Benedict Jin 82ed4878c4 Fix rst grammar problems (#4116) 2017-12-25 23:39:28 -08:00
James Pesculis 6e1ec8347d Update UserInfo.jsx and set additional properties for react-gravatar (#4118) 2017-12-25 23:29:27 -08:00
Hugh A. Miles II f905726c24 [geo] Added DeckGL GeoJson layer (#4097)
* added deckgl geojson layer

* linting

* fixed comments

* addressed comments

* added override with controls.color_picker > 0

* set var properly

* set colors if property doesnt exist at all

* refacator on property mapping
2017-12-22 14:40:08 -08:00
Maxime Beauchemin 69195f8d2d Introduce Javascript controls (#4076)
* Introduce Javascript controls

This allows power-users to perform intricate transformations on data and
objects using javascript code.

The operations allowed are "sanboxed" or limited using node's vm
`runInNewContext`
https://nodejs.org/api/vm.html#vm_vm_runinnewcontext_code_sandbox_options

For now I'm only enabling in the line chart visualization, but the plan
would be to go towards offering more power to people who can write some
JS moving forward.

* Not applied
2017-12-20 21:24:35 -08:00
Nicolas Bonnotte b4909f2d03 [Bugfix] Issues with merge_extra_filters (#4042) (#4091) 2017-12-20 16:22:43 -08:00
Maxime Beauchemin 44e753d94d [sql lab] deeper support for templating (#3996)
* [sql lab] deeper support for templating

* Fixing py tests

* Fix typo
2017-12-19 15:55:58 -08:00
Maxime Beauchemin e4903e6dc6 [geo] add support for deck.gl's path layer (#4067)
* [geo] add support for deck.gl's path layer

Works with json and polyline data.

* Lint
2017-12-19 12:38:03 -08:00
Maxime Beauchemin d4e8d57fc4 Using TextAreaControl for WHERE and HAVING clause section (#4090) 2017-12-19 12:11:35 -08:00
kuriancheeramelil 281ae45495 Fix for SQL editor throwing can't deserialize google.cloud.bigquery._helpers.Row with BigQuery (#4071)
* fix for SQL editor throwing cant deserialize google.cloud.bigquery._helpers.Row with BigQuery

* linted code

* disable pylint import error of bigquery row

* fixed spacing issue before inline-comment
2017-12-18 21:22:34 -08:00
fabianmenges ff4f9b4527 Bugfix: Druid having filters are broken (#4089) 2017-12-18 17:06:12 -08:00
fabianmenges 86f9087ea2 Event annotation should have min width (#4083) 2017-12-18 15:37:05 -08:00
Maxime Beauchemin 7cd9b85831 [bugfix] iframe and markup are broken (#4082)
fixes https://github.com/apache/incubator-superset/issues/4080
2017-12-18 14:42:18 -08:00
fabianmenges 71e1eea9f4 DB migration of annotation_layers on slice objects and slimming down annotation object. (#4072) 2017-12-18 13:11:06 -08:00
Jeff Niu 1e79e9cd2a [Bugfix] Issues with table filtering (#4073)
* Fixing some issues with table filtering

* Added some comments
2017-12-17 15:43:34 -08:00
Jeff Niu af7cdeba4d [Feature] enhanced memoized on get_sqla_engine and other functions (#3530)
* added watch to memoized

* added unit tests for memoized

* code style changes
2017-12-17 10:35:00 -08:00
fabianmenges 500e6256c0 Full Annotation Framework (#3518)
* Adding full Annotation Framework

* Viz types

* Re organizing native annotations

* liniting

* Bug fix

* Handle no data

* Cleanup

* Refactor slice form_data to data
2017-12-16 16:10:45 -08:00
Nic e79d05fd77 #4058 Fix Oracle timestamps (Oracle "ORA-00907: missing right parenthesis" error) (#4065) 2017-12-15 21:31:09 -08:00
Maxime Beauchemin fc85756c20 [geo] turn off renderTrigger on viewport control (#4066)
For context, the viewport gets updated dynamically from the user
actions on the map. This is done on a timer every second or so to keep
the form data updated with the viewport settings.

With renderTrigger=true on that control that generates re-renders which
introduces glitches while zooming/panning. So turning it off as we don't
really expect users to input viewport info directly in the control
anyways.
2017-12-15 14:59:54 -08:00
John Bodley 6081f7161a [health] Adding DB check to /health (#4062) 2017-12-15 14:59:41 -08:00
Maxime Beauchemin c21513fb8c Adding rowcount label to explore view header (#4059) 2017-12-15 11:47:44 -08:00
Maxime Beauchemin ec752b1378 [geo] provide more flexible Spatial controls (#4032)
Before this PR the only way to query lat/long is in the shape of 2
columns that contains lat and long.

Now we're adding 2 more options:
* a single column that has lat and long with a delimiter in between
* support for geohashes - geohashes are cool
2017-12-15 11:47:27 -08:00
Maxime Beauchemin cf1d9ce1e6 Add db_engine_spec for Druid (#4063)
The `druiddb` pypi package provides a dbapi and sqlalchemy dialect for
Druid. This PR hooks adds some superset-specific conf.
2017-12-15 11:47:00 -08:00
Maxime Beauchemin 6188d60fec Bump dev version on trunk (#4048) 2017-12-12 21:29:19 -08:00
Maxime Beauchemin dfc28f37eb Changelog for 0.21.0 (#4045)
* Changelog for 0.21.0

* more entries
2017-12-12 21:29:01 -08:00
Maxime Beauchemin 23c834f04e Fix the pypi build (#4047) 2017-12-12 18:12:26 -08:00
Hugh A. Miles II c84211ec44 Change reference for slices to chart (#4049)
* change reference for slices to chart

* change profile page reference

* change reference for Associated Slices

* change back to single quotes

* fix other single quotes

* linting

* last one

* fix test
2017-12-12 18:02:17 -08:00
Jeff Niu 7d374428d3 [Bugfix] _add_filters_from_pre_query doesn't handle dim specs (#3974)
* Fixed _add_filters_from_pre_query for dimension specs

* add_filters_from_pre_query ignores extraction functions
2017-12-11 12:35:25 -08:00
John Bodley 3a2974f589 [API] Deprecate /update_role/ API endpoint (#4041) 2017-12-10 21:14:15 -08:00
timifasubaa 3ed8f5fc23 resolve python2 str() issue (#4030)
* make string conversion use utf8

* Update viz.py

* make utf-8 consistent with other usages

* Update viz.py

* Update viz.py
2017-12-09 14:23:24 -08:00
Grace Guo 61755f0b7d apply custom css for dashboard initially load (#4031) 2017-12-07 16:56:40 -08:00
fabianmenges 0a3d2fccd4 [BUGFIX]: Fixing dttm_sql_literal to use python_date_format when specified. (#3891) 2017-12-07 16:38:22 -08:00
Maxime Beauchemin 0b40c8a26f Add fastdom js dependency (#3947)
The nvd3 docs say that it if the fastdom library is present it makes use
of it.

"Including Fastdom in your project can greatly increase the performance
of the line chart (particularly in Firefox and Internet Explorer) by
batching DOM read and write operations to avoid layout thrashing. NVD3
will take advantage of Fastdom if present."
2017-12-07 16:36:46 -08:00
Beto Dealmeida 81df7087db Remove unused callbacks when setting state (#4015) 2017-12-06 21:56:28 -08:00
Jeff Niu cb7c5aa70c Fixed finding postaggregations (#4017) 2017-12-06 21:55:43 -08:00
Maxime Beauchemin 5bc581fd44 New time_pivot visualization (#3941)
* New time_pivot visualization

* Minor tweaks

* Addressing comments
2017-12-06 21:50:33 -08:00
Maxime Beauchemin 5ee70b244b Add type MONEY as numeric type (#3959)
fixes https://github.com/apache/incubator-superset/issues/3953
2017-12-06 21:49:42 -08:00
Maxime Beauchemin a26cf001c4 Add row_limit to heatmap controls (#3969) 2017-12-06 21:49:27 -08:00
Dmitry Goryunov e02d35ed5c Add support of another DatabaseError format (#4019) 2017-12-06 21:49:03 -08:00
rumbin e98a1c3537 asciifying http header for csv download; fixes #3952 (#3975)
* asciifying http header for csv download; fixes #3952

* fixed order of imports and added unidecode to requirements in setup.py
2017-12-05 12:04:58 -08:00
timifasubaa 4404751a1d Add has_access to import_dashboard (#4001)
* Add has_access to import_dashboard

* Update core.py

* Update core.py
2017-12-05 12:03:13 -08:00
Maxime Beauchemin defe6789c0 [sql lab] fix position of 'save query' Popover (#3999)
* [sql lab] fix position of 'save query' Popover

The "Save Query" popover renders on the upper left corner as opposed to
where it should (relative to the Save Query button). After a bit of
research, it seems like Popover won't render in the right place when
parents are absolute.

I'm guessing this stopped working properly when I added the resizable
panes.

Anyhow, the solution here is to use a modal instead.

* Fixing tests
2017-12-05 11:37:13 -08:00
Beto Dealmeida 823f306f24 Call props.onChange only when closing filter (#4003) 2017-12-05 11:17:12 -08:00
fabianmenges 72627b1761 Adding YAML Import-Export for Datasources to CLI (#3978)
* Adding import and export for databases

* Linting
2017-12-05 11:14:52 -08:00
Alan Cruickshank 1702b020be Rollback bulk-delete of table columns (#4009)
Fix likely required upstream in FAB before we can properly enable this.
2017-12-05 11:14:21 -08:00
Grace Guo 89f6ccc1c6 Add Datasource Name filter under slice list view (#4000) 2017-12-04 13:45:36 -08:00
Maxime Beauchemin eff5952641 Alternate PR to #3970 (#3997) 2017-12-04 08:19:51 -08:00
rumbin f10395b2f7 [doc] added setting X-Forwarded-Proto to https behind reverse proxy with ssl encryption; fixes #3655 (#3976) 2017-12-03 22:00:58 -08:00
Maxime Beauchemin b2647567c0 Create CODE_OF_CONDUCT.md (#3991) 2017-12-02 14:57:54 -08:00
Grace Guo 028456572b [Dashboard] fix a filter refresh bug and add Test (#3967) 2017-12-01 10:58:55 -08:00
Maxime Beauchemin 84a7730f47 [docs] making it clear sqlite shouldn't be used in a cluster (#3965) 2017-11-30 22:06:16 -08:00
Chris Williams 76a2f95231 [time series table] visual improvements (#3957)
* [time series table] visual improvements

* [time series table] don't set cell color if text color isn't set
2017-11-30 20:48:17 -08:00
michellethomas 9904593dc3 Improving speed of dashboard import (#3958)
* Improve dashboard import

* Updating tests for Slice.import_obj
2017-11-30 20:47:22 -08:00
Jeff Niu 8f00e9e30b [Bugfix] Druid run_query dimensions part 3 + Unit tests (#3949)
* Fixed and added tests for druid run query

* Fixes style and python3
2017-11-30 20:32:53 -08:00
Maxime Beauchemin 16ab696d7c [country_map] use Albers USA projection (#3946)
* [country_map] use Albers USA projection

* Minor touchups

* Adding color scheme
2017-11-30 14:09:53 -08:00
Maxime Beauchemin 1ce14df43d fix 'superset db history' (#3948)
* fix 'superset db history'

Related Error msg when running `superset db history`:
"NameError: Can't invoke function 'get_bind', as the proxy object has not
yet been established for the Alembic 'Operations' class.  Try placing
this code inside a callable."

* Lint
2017-11-29 20:52:56 -08:00
michellethomas 34d6618b2e Allow underscores in slugs (#3951)
* Allow underscores in slugs

* Switching regex to use shorter \w
2017-11-29 14:55:13 -08:00
Riccardo Magliocchetti abdd1d537f config: bring back sqlite default database (#3955)
That became postgres in 268edcf

Fix #3954
2017-11-29 10:03:01 -08:00
Maxime Beauchemin d9fda346cb Add an "Edit Mode" to Dashboard view (#3940)
* Add a togglable edit mode to dashboard

* Submenu for controls

* Allowing 'Save as' outside of editMode

* Set editMode to false as default
2017-11-28 09:10:21 -08:00
Jeff Niu 6cbe0e6096 Fixed branching condition with dimension spec (#3920) 2017-11-27 21:12:20 -08:00
timifasubaa 268edcfedd Import CSV (#3643)
* add upload csv button to sources dropdown

* upload csv to non-hive datasources

* upload csv to hive datasource

* update FAQ page

* add tests

* fix linting errors and merge conflicts

* Update .travis.yml

* Update tox.ini
2017-11-27 21:07:12 -08:00
Maxime Beauchemin c5ddf57124 Fix call in Chart (#3945) 2017-11-27 21:06:47 -08:00
kkalyan f9202ba179 minor filter select enhancements (#3933)
* `values_for_column` configurable row limit

* `FilterControl` cancels active ajax request if any
2017-11-27 21:05:53 -08:00
Alan Cruickshank 17635e1a2b Make Table Columns & Metrics Bulk-deletable (#3929) 2017-11-25 23:05:51 -08:00
John Bodley 285197926e [travis] Standardizing before_install (#3922) 2017-11-21 22:10:17 -08:00
Jeff Niu 5466fab2a0 Switched to span instead of textarea for copytoclipboard (#3923) 2017-11-21 22:09:41 -08:00
Jeff Niu ed85032277 Moved percent metrics to its own row (#3924) 2017-11-21 22:08:15 -08:00
Maxime Beauchemin 680e1cbb42 Revert "Filter out unavailable databases (#3875)" (#3918)
This reverts commit ae2205aeb5.
2017-11-21 12:58:47 -08:00
Maxime Beauchemin 2d37dec5ff [bugfix] remove quotes from Postgres time grains (#3913) 2017-11-21 11:24:17 -08:00
Maxime Beauchemin 3f4c306bd6 Fix left padding in dashboard widgets (#3915) 2017-11-21 10:24:28 -08:00
Maxime Beauchemin ac432495d7 [cosmetic] remove border from table viz (#3916) 2017-11-21 10:23:48 -08:00
michellethomas 12fb7c1a62 When checking if you should renderTriggered make sure key exists in controls (#3912) 2017-11-21 10:22:55 -08:00
Yu Xiao feb15a30a2 fix the schema-fetching problem for impala in sql_lab (#3906)
* fix the schema-fetching problem for impala in sql_lab

* delete redundant print

* remove blank lines...

* minior corrections
2017-11-21 09:28:31 -08:00
Alan Cruickshank eb0f3970cf Add UK Metropolitan Districts and Isle of Man (#3911) 2017-11-20 18:06:58 -08:00
Maxime Beauchemin b82d15af76 Bumping webpack related deps (#3904) 2017-11-20 15:27:02 -08:00
Maxime Beauchemin 32b38ee2d6 [bugfix] allow limiting word cloud (#3902) 2017-11-20 10:32:14 -08:00
Maxime Beauchemin 1d702f2142 Fixes default hanlding in Altered slice tag (#3903) 2017-11-20 08:43:38 -08:00
bolkedebruin 4ae77ba8af Workaround pandas bug in datetimes with time zones (#3910)
A bug in to_dict(orient="records") in pandas/core/frame.py prevents
datetimes with time zones to be worked with. This works around the
issue in superset by re-implementing the logic of pandas in the
correct way. Until pandas fixes the issue this code should stay.

https://github.com/pandas-dev/pandas/issues/18372

This closes #1929
2017-11-20 08:33:18 -08:00
John Bodley 3c72e1f8fb [3541] Augmenting datasources uniqueness constraints (#3583) 2017-11-19 20:09:18 -08:00
John Bodley 4bfe08d7c3 [druid] Fixing issue 3894 multi-processing w/ Gunicorn (#3895) 2017-11-18 21:40:40 -08:00
John Bodley 3a7ed8d194 [druid] Catch IOError when fetching Druid datasource time boundary (#3897) 2017-11-17 20:20:47 -08:00
John Bodley 4d204b3b36 [druid] Renaming refresh_async method (#3899) 2017-11-17 20:11:44 -08:00
Alan Cruickshank 39ee33aeff Add datasource to the SliceAddView modal (#3884) (#3900) 2017-11-17 20:11:23 -08:00
Grace Guo 831cd21737 [dashboard bug]Instant control should take effect instantly (#3890)
in explore view, controls like color cheme, legend, rich tooltip, etc., change these controls should see effect instantly, without click Run Query.
2017-11-17 16:34:53 -08:00
Maxime Beauchemin a82bb588f4 Allow users to specify label->color mapping (#3879)
Users can define `label_colors` in a dashboard's JSON metadata that
enforces a label to color mapping.

This also makes the function that maps labels to colors case insensitive.
2017-11-17 15:56:04 -08:00
michellethomas a84bd5225c Only refreshing non instant filters on apply (#3893) 2017-11-17 12:52:48 -08:00
John Bodley f0acc11249 [druid] Fix datasource column enumeration (#3896) 2017-11-16 22:41:54 -08:00
Grace Guo fa35d7d2f4 fix input height to match with react-select (#3852) 2017-11-16 11:50:32 -08:00
Maxime Beauchemin e65aba3c46 Fixing the build's linting errors (#3887)
master has new linting rules, PRs got merged with lint that was ok at
branching but not ok in masert anymore
2017-11-16 11:18:33 -08:00
Maxime Beauchemin fab7b1083b A better looking favicon (#3851) 2017-11-16 10:14:54 -08:00
Maxime Beauchemin d9161fb76a Fix slug function (#3876) 2017-11-16 09:47:00 -08:00
Maxime Beauchemin 85b18ff5e7 [table] show 'Time' column header instead of '__timestamp' (#3880) 2017-11-16 09:33:42 -08:00
Maxime Beauchemin 3a8af5d0b0 DECKGL integration - Phase 1 (#3771)
* DECKGL integration

Adding a new set of geospatial visualizations building on top of the
awesome deck.gl library. https://github.com/uber/deck.gl

While the end goal it to expose all types of layers and let users bind
their data to control most props exposed by the deck.gl API, this
PR focusses on a first set of visualizations and props:

* ScatterLayer
* HexagonLayer
* GridLayer
* ScreenGridLayer

* Addressing comments

* lint

* Linting

* Addressing chri's comments
2017-11-16 00:30:02 -08:00
Maxime Beauchemin 1c545d3a2d Further refactoring around dashboards (#3843)
I was wondering what was left to do in order to remove Dashboard.jsx
and superset.js, and it looks like they can just be pulled out.

I am so happy to get rid of what used to be the messiest JS files in the
whole repo.

Thanks @graceguo!
2017-11-16 00:27:15 -08:00
Grace Guo 120a5d08f9 [dashboard bug] Fix standalone slice (#3877) 2017-11-15 12:38:07 -08:00
Riccardo Magliocchetti b586cb0ba7 Add mailing list and move screenshot at the end of README (#3872)
* README: add the mailing list

And mark the google group as deprecated

* README: move the screenshots at the end

So hopefully it'll be easier to find the resources
2017-11-15 08:40:18 -08:00
Dmitry Goryunov ae2205aeb5 Filter out unavailable databases (#3875) 2017-11-15 08:39:43 -08:00
John Bodley 2e25fc4161 [issue] Resolving issue 2530 (#3865) 2017-11-14 21:13:00 -08:00
John Bodley ba89b2d091 [cache] Fixing cache key w/ merged extra filters (#3809) 2017-11-14 21:12:26 -08:00
michellethomas aee8438924 Fixing an issue with stripping filter values (#3869) 2017-11-14 19:22:03 -08:00
John Bodley a6ba841e57 [flake8] Updaing CONTRIBUTING.md (#3862) 2017-11-14 18:17:53 -08:00
Grace Guo 8643228b51 [Dashboard bug] Fix merged filter param name (#3866)
front-end merge time filter params, and update query with param name 'extra_filters'
2017-11-14 12:28:55 -08:00
Grace Guo de869973c7 Fix cachedDttm prop type (#3858) 2017-11-14 08:14:59 -08:00
John Bodley ac57780607 [flake8] Resolving Q??? errors (#3847) 2017-11-13 21:06:51 -08:00
Mike Schiller 630604bc6b adding support for getting list of foreign tables for PostgreSQL (#3856)
* adding support for getting list of foreign tables for PostgreSQL

* need extra newline to pass lint
2017-11-13 21:05:22 -08:00
Grace Guo eb5d220b5e [Dashboard bug] Slice doesn't show loading icon when loading (#3834) 2017-11-13 16:07:15 -08:00
Grace Guo 3f076b00cd [Dashboard bug]Fix userId prop in Explore view Save_Modal (#3857)
For userId, the attribute name in bootstrap data is user_id
2017-11-13 16:06:45 -08:00
Maxime Beauchemin 514f9452f3 [sql lab] minor cosmetic touchups on Run / Save buttons (#3850) 2017-11-13 12:39:28 -08:00
Maxime Beauchemin 068c343be0 [sqllab] fix wrong error msg (#3849)
I was getting some "Could not connect to server" when there was
a proper json payload with an `error` key, the change here makes sure to
prioritize those messages over the generic one.
2017-11-12 21:24:20 -08:00
Maxime Beauchemin 500455fc72 Add CHANGELOG.md entries for 0.20.0 to 0.20.5 (#3842) 2017-11-12 11:28:37 -08:00
John Bodley 1b4f128f55 [flake8] Resolving F5?? errors (#3846) 2017-11-12 11:09:22 -08:00
Grace Guo 1a3a8daf49 [Dashboard bug] should reset chartAlert when start new query (#3841) 2017-11-11 22:38:40 -08:00
王洁玉 7fce8eab3a Update setup.py (#3510) 2017-11-11 21:51:53 -08:00
Grace Guo b4c9402737 [Dashboard bug] Fix Cache status and dttm information display for each slice (#3833) 2017-11-11 21:51:25 -08:00
Grace Guo 8459347bdc [Dashboard bug] should reset chartAlert when start new query (#3837) 2017-11-11 21:45:29 -08:00
Riccardo Magliocchetti f7bf17290c run_tests.sh: call coveralls only on CI (#3836) 2017-11-11 21:44:55 -08:00
John Bodley d908e48d61 [slice] Removing deprecated argument (#3838) 2017-11-11 21:44:24 -08:00
John Bodley a3a4687ebf [viz] Fix payload force logic (#3839) 2017-11-11 21:43:55 -08:00
Jeff Niu 4d48d5d854 [Explore] Altered Slice Tag (#3668)
* Added altered tag to explore slice view and fixes #3616

* unit tests

* Moved getDiffs logic into AlteredSliceTag

* code style fixs
2017-11-10 21:33:31 -08:00
Maxime Beauchemin 83e6807fa0 [docs] add StatsD setup instructions (#3813) 2017-11-10 17:54:56 -08:00
John Bodley ba96984048 [flake8] Resolving E3?? errors (#3814) 2017-11-10 17:52:34 -08:00
Maxime Beauchemin 591e5ec32e Bump celery to 4.1.0 (#3831)
* Bump celery to 4.1.0

* Also bumping boto3 to allow for celery 4 on SQS
2017-11-10 16:28:56 -08:00
John Bodley 690de862e8 [flake8] Resolve E1?? errors (#3805) 2017-11-10 12:06:22 -08:00
John Bodley 35810ce2bf [docstring] Refining warm_up_cache comment (#3815) 2017-11-10 08:05:20 -08:00
Grace Guo 6c52f2ff72 First time fetching chart should not force refresh. (#3822) 2017-11-09 21:48:05 -08:00
Alan Cruickshank d663bea5e6 Basic German Translation (#3740)
Not complete but most of the core interface
2017-11-09 20:45:37 -08:00
John Bodley 1ea4521d0c [flake8] Resolving E7?? errors (#3816) 2017-11-09 20:23:59 -08:00
John Bodley c4153c0bbe [flake8] Resolving E4?? errors (#3817) 2017-11-09 20:23:47 -08:00
Hugh A. Miles II ae8b249dc2 Added /healthcheck endpoint for integrations with envoy (#3819)
* fixed mergeconflicts

* fixed mergeconflicts forreal this time

* added healthcheck test
2017-11-09 20:23:28 -08:00
Prasanna Swaminathan 9500f0aae3 Fix typo in installation.rst (#3818)
`superser runserver` should be `superset runserver`
2017-11-09 20:22:45 -08:00
Maxime Beauchemin be3da6396f Fix misleading SQL Lab timeout error message (#3825) 2017-11-09 19:09:16 -08:00
Grace Guo 330926c167 fix error message format when long query timeout (#3823) 2017-11-09 19:07:49 -08:00
michellethomas cbcc00c929 Make overflow important to allow scrolling on dashboard (#3810) 2017-11-08 20:35:45 -08:00
John Bodley d03b74f754 [flake8] Resolving F4?? errors (#3811) 2017-11-08 20:34:33 -08:00
John Bodley ec21d5af21 [flake8] Resolving E2?? errors (#3812) 2017-11-08 20:34:23 -08:00
michellethomas 70c7315ae0 Making time table viz scrollable (#3808) 2017-11-08 16:18:59 -08:00
Grace Guo 4fa1f0ab17 Dashboard refactory (#3581)
Create Chart component for all chart fetching and rendering, and apply redux architecture in dashboard view.
2017-11-08 10:46:21 -08:00
Maxime Beauchemin 39e502faae Stamping version to 0.21.0dev (#3801)
Making it clear that master has a `dev`-suffixed version. Proper release
number will be created in release branches.

There are constraints as to what npm and setuptools will accept as a
proper version number and N.N.Ndev seems to work so I'm rolling with it

Open to suggestion as to how to tag `master`
2017-11-08 09:47:41 -08:00
Ishpreet Singh 0280bc52e0 Allowing Leading and Trailing spaces in connection (#3433) 2017-11-07 22:13:18 -08:00
Jeff Niu dee47864c4 Fixed single extraction dimension error (#3796) 2017-11-07 21:35:56 -08:00
John Bodley 17623f71d4 [flake8] Resolving C??? errors (#3787) 2017-11-07 21:32:45 -08:00
Magicansk 7453131858 Update messages.json (#3716)
* Update messages.json

* Update messages.json
2017-11-07 20:28:47 -08:00
John Bodley e822fb50d8 [flake8] Resolving W??? errors (#3784) 2017-11-07 20:25:10 -08:00
John Bodley e2bca47421 [flake8] Resolve I??? errors (#3797) 2017-11-07 20:23:40 -08:00
Maxime Beauchemin 7987cb794b Add Lyft and Twitter to list of companies (#3789) 2017-11-07 17:07:14 -08:00
Chris Williams 7483e2c942 [time table] use sparkData values in tooltip (#3794) 2017-11-07 15:52:51 -08:00
michellethomas e6129eb492 Adding back iso and correctly filtering iso from contrib total (#3793) 2017-11-07 13:34:31 -08:00
michellethomas b10aca2de1 Removing iso from data (#3788) 2017-11-06 23:29:02 -08:00
John Bodley 02cbad59de [flake8] Resolving F8?? errors (#3778) 2017-11-06 21:15:36 -08:00
Stephanie Rivera ccb87d337c Rename files to allow RPM build (#3785)
I was having issues getting an RPM to build. My error was

Processing files: superset-0.20.1-1.noarch
error: File must begin with "/": Lockup
error: File must begin with "/": With
error: File must begin with "/": Text.svg
error: File must begin with "/": Lockup
error: File must begin with "/": With
error: File must begin with "/": Text@2x.png
error: File must begin with "/": Lockup
error: File must begin with "/": Without
error: File must begin with "/": Text@1x.svg
error: File must begin with "/": Lockup
error: File must begin with "/": Without
error: File must begin with "/": Text@2x.png
error: File must begin with "/": Mark.png
error: File must begin with "/": Mark@1x.svg

for ref https://github.com/pypa/setuptools/issues/767
File renaming fixes this issue
2017-11-06 17:13:53 -08:00
John Bodley 63a49983eb [falke8] Resolving F6?? errors (#3783) 2017-11-06 16:56:03 -08:00
Maxime Beauchemin 81dd622fdb [explore] using verbose_name in 'Time Column' control (#3529) 2017-11-06 15:21:34 -08:00
Jeff Niu 9a49b1c41d [Performance] VirtualizedSelect for SelectControl and FilterBox (#3654)
* Added virtualized select to SelectControl, allow onPaste to create new options

* Added unit tests

* Added virtualized/paste select to filterbox
2017-11-06 15:20:13 -08:00
Alejandro Fernandez b059506afa DI-1113. ADDENDUM. Authentication: Enable user impersonation for Superset to HiveServer2 using hive.server2.proxy.user (a.fernandez) (#3697) 2017-11-06 10:20:38 -08:00
John Bodley 13c17e1526 [flake8] Enabling flake8 linting (#3776) 2017-11-04 22:50:42 -07:00
John Bodley 8e3217a921 [sql-lab] Fixing Run Query tooltip (#3774) 2017-11-04 00:10:47 -07:00
michellethomas aed7c7436a Fix dashboard export download (#3773) 2017-11-04 00:10:02 -07:00
Chris Williams 7f3edad119 [time table] add tooltip to sparkline (#3767)
* [time table] add tooltip to sparkline

* [time table] open link in new tab

* [time table] add back Mustache
2017-11-03 12:37:15 -07:00
Stephanie Rivera 7fd9c82ae8 Update to reflect new version of cryptography (#3748)
update to 1.9

I have built and pip installed with latest cryptography.
2017-11-02 13:51:17 -07:00
Riccardo Magliocchetti f3c7052f30 docs: reword the FAQ regarding table changes (#3763)
So we stop confusing people that thinks we do DDL.

Fix #3761
2017-11-02 13:50:11 -07:00
Dmitry Goryunov 326d90a5e4 add stackoverflow tag (#3764) 2017-11-02 13:49:47 -07:00
Maxime Beauchemin cccc47311b Add dummy file to fix symlink (#3759)
In `assets/static` we have a symlink pointing to `docs/_build/html`
which is .gitignored and missing in the repo since we don't want the
html-generated docs in the repo, meaning the symlink is broken

Having the symlink broken creates issues with pip-compile somehow.

Adding a dummy file here addresses that
2017-11-02 10:17:28 -07:00
Grace Guo 5c03167948 fix https://github.com/apache/incubator-superset/pull/3726 (#3751) 2017-11-01 21:07:44 -07:00
Alan Cruickshank 87b6d76c32 Consolidate all translation config (#3750)
Move all translation config to superset/translations
2017-11-01 20:13:22 -07:00
Maxime Beauchemin abfa03474c Bumping react-select to rc10 (#3726) 2017-10-31 22:03:18 -07:00
mxmzdlv 5bc734b2e5 Fix has_table method (#3741)
Dialect's has_table method requires connection as the first argument, not engine (https://github.com/zzzeek/sqlalchemy/blob/master/lib/sqlalchemy/engine/interfaces.py#L454). Instead, we can use engine's has_table method that handles the connection for us (https://github.com/zzzeek/sqlalchemy/blob/master/lib/sqlalchemy/engine/base.py#L2141). Alternatively, we could call engine.dialect.has_table(engine.connect(), ...).
2017-10-30 21:04:23 -07:00
Ryan Harmuth 814b70ffd8 Escape columns names for time grains - postgres (#3736) 2017-10-30 21:02:46 -07:00
Baldo Alessandro 1e18bfdea4 Fix 3657 (#3739)
* Reorders MANIFEST.in

* Includes the translations dir in MANIFEST
2017-10-30 11:26:42 -07:00
michellethomas 200b66d088 Using indexOf instead of includes for isXAxisString (#3733) 2017-10-27 16:00:44 -07:00
Grace Guo cbd01074ba bump react-bootstrap version (#3723)
1. avoid exports is not defined error
2. per jordan's suggestion, update .babelrc only use airbnb presets
2017-10-26 23:10:00 -07:00
Maxime Beauchemin 1582fa1964 Add CRUD action to refresh table metadata (#3721)
A shortcut to make it easy to refresh a table's schema
2017-10-26 16:17:56 -07:00
Maxime Beauchemin a9b6d11ade Validate JSON in slice's params on save (#3720)
fixes https://github.com/apache/incubator-superset/issues/3507

This prevents malformed JSON from getting saved in a slice's params. It
also prevents the issue described in #3507 from happening though as a
result malformed slices will render using default control values.
2017-10-26 16:16:21 -07:00
Maxime Beauchemin c4b6324e74 Fix box_plot NaN issue (#3722)
fixes https://github.com/apache/incubator-superset/issues/3712
2017-10-26 12:00:22 -07:00
Magicansk 9432ea80be Update messages.po (#3715)
[Chinese Translation]
2017-10-25 23:26:38 +00:00
Rogan f412b4c158 Missing the data of one province and two regions of China (#3686) 2017-10-25 22:27:18 +00:00
Rogan 547a3bf4e7 Fix the ISO code description of region/province/department (#3685)
* Fix the ISO code description of region/province/department

*  Missing the data of one province and two regions of China

* Revert " Missing the data of one province and two regions of China"

This reverts commit abff4555cd.
2017-10-25 00:58:54 +00:00
Maxime Beauchemin e97dc9d3cb Set logging level to debug for DummyStatsLogger (#3662) 2017-10-25 00:50:15 +00:00
Jeff Niu efae14592e fixes for bugs in #3689 (#3692) 2017-10-24 21:58:15 +00:00
Angus Ma 1d06495629 add VIPKID to the orgs. (#3703) 2017-10-24 21:30:54 +00:00
Jeff Niu ffdfdb94ab changed metric heading from h1 to h3 (#3696) 2017-10-24 21:30:31 +00:00
Yu Xiao 8d7e97a26e [translation] added japanese support (#3713)
* [translation] added japanese support

* fix
2017-10-24 21:29:00 +00:00
Maxime Beauchemin f8b8f6a343 [minor] fix label showing description in time_table's URL (#3663) 2017-10-24 21:27:53 +00:00
Grace Guo 4967342362 fix the slice permission issue after user click-edit new slice title (#3711) 2017-10-24 11:19:51 -07:00
John Bodley 9893847991 [form-data] Quoting form data (#3701) 2017-10-24 10:08:08 -07:00
Grace Guo 18e9640d99 fixing the datasource inconsistence but in visualize flow (#3698)
datasource in landing explore view is not the datasource created in sal lab.
2017-10-23 20:29:49 -07:00
Maxime Beauchemin 58ea736ed6 [cleanup] removing print() artefacts (#3683) 2017-10-23 15:48:47 -07:00
Jay Lindquist b4bdc45a6b Add support for IE 11 for markup slices (#3702)
* Add srcdoc-polyfill tosupport Internet Explorer iframes in markup slices. Add allow-top-navigation and allow-popups to support links within iframes

* Remove jquery from markup.js
2017-10-23 15:35:15 -07:00
michellethomas fa07b8d51b defaultSort should be false when no sort is necessary (#3693) 2017-10-23 11:17:28 -07:00
Jeff Niu e121a8585e [Feature] Percentage columns in Table Viz (#3586)
* Added percent metric options to table viz

* Added unit tests for TableViz

* fixed code for python3

* bump travis
2017-10-16 20:16:20 -07:00
Alejandro Fernandez adef519583 DI-1113. Authentication: Enable user impersonation for Superset to HiveServer2 using hive.server2.proxy.user (a.fernandez) (#3652) 2017-10-16 20:15:16 -07:00
Maxime Beauchemin 08f09b4761 [minor] fix padding in Time Table (#3664)
When in dashboard view, the Time Table needs some paddding
2017-10-16 17:01:35 -07:00
Jeff Niu 2a89c90e0b unit tests for OptionDescription component (#3678) 2017-10-16 16:31:43 -07:00
michellethomas ce5fa379ec Avoid dividing by zero for sparkline in time table viz (#3679) 2017-10-16 16:31:07 -07:00
timifasubaa d4d4a9b1f1 Sqllab error troubleshooting (#3680)
* provide troubleshooting link

* add option to append error troubleshooting link beneath sqllab error
2017-10-16 16:30:08 -07:00
Maxime Beauchemin d0b5b449b2 Add a ColorPickerControl (#3653)
* Add a ColorPickerControl

* Tests
2017-10-15 23:38:38 -07:00
Jeff Niu bad6938d1a [New Viz] Partition Diagram (#3642)
* Added Partition Visualization

* added unit tests
2017-10-12 21:54:59 -07:00
timifasubaa 48e28eff9b Add description for running specific test (#3665) 2017-10-12 20:53:37 -07:00
michellethomas f87163413b Making the sort order for metrics pull from fd for time table viz (#3661) 2017-10-12 17:51:26 -07:00
Ali Cirik 52a9f2742b Make columns that return an exception on click unsortable. (#3417) 2017-10-11 22:36:12 -07:00
michellethomas 7f07fbefbc Adding sort time table (#3651)
* Updating time_table component to sort

* Removing old sort
2017-10-11 21:25:17 -07:00
Ganesh Krishnan 93660c6838 added aihello as superset user. (#3647) 2017-10-11 21:17:54 -07:00
Maxime Beauchemin 3ebadbcda9 Fix #3612 - reverse sign in difference calculation (#3646) 2017-10-11 21:14:39 -07:00
Denny Biasiolli 3df3e0d681 Fixing some warnings during tests (#3648)
* ColorSchemeControl: fixing bad use of PropTypes

Accessing PropTypes via the main React package is deprecated, and will be
removed in React v16.0. Use the latest available v15.* prop-types package from
npm instead. For info on usage, compatibility, migration and more, see
https://fb.me/prop-types-docs

* Control: adding PropTypes.func in types allowed inside `value` prop

This removes a warning during yarn tests

Fix #3589

* tests(QueryStateLabel): removing missing prop warning

```
Warning: Failed prop type: The prop `query` is marked as required in
`QueryStateLabel`, but its value is `undefined`.
    in QueryStateLabel
```

* SaveQuery: removing invalid prop `target` supplied to `Overlay`.

This removes a warning during yarn tests:

```
Warning: Failed prop type: Invalid prop `target` supplied to `Overlay`.
```

* RunQueryActionButton: removing `isRequired` from queryState props

This removes a warning during yarn tests:
```
Warning: Failed prop type: The prop `queryState` is marked as required in
`RunQueryActionButton`, but its value is `null`.
```
2017-10-11 21:07:52 -07:00
Jeff Niu 4a3c09187a [Translations] Restored lost French translations (#3645)
* Added some missing translations

squash

* Restored previous French translations
2017-10-10 17:52:39 -07:00
Maxime Beauchemin 76f8d33d81 [sql lab] fix impersonation + template issue (#3644)
When the database impersonation flag is on, a query using a template
fails. It has to do with templating using a database connection without
a username being specified by the caller, along with the fact that the
work is taking place on a worker, outside a web request, where
referencing g.user raises this exception.
2017-10-10 17:52:22 -07:00
Maxime Beauchemin 6cc6637454 Pin moment.js library since 2.19.0 creates problem (#3641)
The 2.19.0 released today (2017-10-10) creates issues with the
DateFilterControl somehow. Pining lib to latest known version.
2017-10-10 15:53:03 -07:00
Maxime Beauchemin d7f8a7fde3 [time_table] adding support for URLs / links (#3600)
Using Mustache templating and providing {{ metric }} as well as
{{ ...formData }} as context.
2017-10-10 11:54:21 -07:00
michellethomas 80eb9c2c64 Set tooltip to show extent of sparkData (#3626)
* Set tooltip to show extent of sparkData

* Using d3format instead of round
2017-10-10 11:53:53 -07:00
Grace Guo bd45e3b19a add explicit message display for 'Fetching Annotation Layer' error (#3631) 2017-10-10 11:49:53 -07:00
Maxime Beauchemin b866b33dee [bugfix] Template rendering failed: '_AppCtxGlobals' object has no attribute 'user' (#3637)
Somehow the nature of `g` in Flask has changed where `g.user` used to
be provided outside the web request scope and its not anymore.

The fix here should address that.
2017-10-10 11:46:28 -07:00
Grace Guo 8994bdacbd fix long title text wrapping in editable-title component (#3638)
fix https://github.com/apache/incubator-superset/issues/3628
2017-10-10 11:45:48 -07:00
Maxime Beauchemin f3b403d346 [minor] proper tooltip on ControlHeader's instant re-render trigger (#3625) 2017-10-09 23:28:14 -07:00
Yu Xiao 5ad4167512 add annotation option and a linear color map for heatmap viz. (#3634)
* add annotation option and a linear color map for heatmap viz.

* error fixes.

* fixes for requested changes
2017-10-09 23:17:51 -07:00
Maxime Beauchemin ca67a7a4e9 [bugfix] empty From date filter NoneType error (#3633)
Error "AttributeError: 'NoneType' object has no attribute 'split'" is
fired.
2017-10-09 20:59:11 -07:00
Riccardo Magliocchetti 64ef8b14b4 remove unused imports (#3621)
* superset: remove unused imports

Spotted by pyflakes

* superset: removed unused get_session
2017-10-08 21:04:09 -07:00
Jeff Niu 912c6f6231 fixing date/time filter keys (#3611) 2017-10-07 13:07:23 -07:00
Maxime Beauchemin 6f1351fbbb [bugfix] #3593 'Chart Options' panel is missing (#3606) 2017-10-06 00:43:55 -07:00
Maxime Beauchemin f75dc0271d Removing git artifact (#3601) 2017-10-05 09:25:05 -07:00
Maxime Beauchemin 1fb8716231 [hotfix] fixing issues around new time_table viz (#3599) 2017-10-04 16:22:11 -07:00
Maxime Beauchemin ed212440b5 [hofix] work around circular deps (#3598)
* [hofix] work around circular deps

* lint
2017-10-04 14:48:32 -07:00
Maxime Beauchemin 1528288b59 [time table] fix reversed ratio (#3597) 2017-10-04 13:11:02 -07:00
Jeff Niu 7c936e7f60 [Feature/Bugfix] Datepicker and time granularity options to dashboard filters (#3508)
* Feature: added datepicker and time granularity options to dashboard filter

* Added option for Druid datasource time filters

* added more checkbox control over dashboard time filters
2017-10-04 12:43:29 -07:00
Denny Biasiolli ff268a7526 updating react-alert dependency to v2.3.0 (#3596)
it was downgraded in commit 7045018d86.
The old version used React.PropTypes and it was deprecated.
This version is compatible with React 15+.

Fix #3588
2017-10-04 12:08:06 -07:00
Maxime Beauchemin e9804aedff [translations] generating missing strings (#3577) 2017-10-04 12:07:46 -07:00
Jeff Niu e95132ddc3 [Bugfix/Feature] Fixed slice render staggering on dashboard first load (#3478)
* Feature: disable dashboard refresh staggering

* Removed refresh staggering everywhere except during periodic render
2017-10-04 10:23:17 -07:00
Maxime Beauchemin bb0f69d074 New "Time Series - Table" visualization (#3543)
* [WiP] adding a new "Time Series - Table" viz

* Adding drag-n-drop to collection

* Using keys in arrays

* tests
2017-10-04 10:17:33 -07:00
Maxime Beauchemin 645de384e3 [sql lab] fix numeric sort in data table (#3587)
Currently numerical values sort as alpha, this addresses the issue.
2017-10-04 10:17:01 -07:00
fabianmenges 15ecdeb3ba Fxing bug in label generation for multiple groupbys (#3594) 2017-10-04 09:40:30 -07:00
Naoya Kanai 04ea3addc4 update immutable.js to v3.8.2 (MIT license) (#3591) 2017-10-04 09:07:12 -07:00
Jeff Niu 7e64f2e988 [Feature] Copy-to-clipboard button in View Query (#3571)
* added copy-to-clipboard button to explore/view query

* modified CopyToClipboard to deselect current before copying
2017-10-03 22:34:40 -07:00
Jeff Niu 40fbf1c761 Allow users to see query string when query returns no data (#3585) 2017-10-03 22:32:17 -07:00
fabianmenges a85968eadb [Bugfix]: Explore view does not respect custom timeout. (#3582) 2017-10-03 22:20:32 -07:00
Jeff Niu efc63669a6 Fixed creating new filter options in FilterBox (#3584) 2017-10-03 22:20:10 -07:00
Jeff Niu 076f9cd095 Added custom pasteSelect to handle paste events (#3562) 2017-10-03 15:58:18 -07:00
Maxime Beauchemin fdbc936dc9 Bumping React to 15.6.2 (MIT license) (#3569)
I think that leaves only immutable.js with the ASF-incompatible PATENTS clause

I asked for a 3.8.x MIT release of the immutable lib here:
https://github.com/facebook/immutable-js/issues/1309
2017-10-03 15:57:42 -07:00
Maxime Beauchemin 18e459e19e v0.20.1 (#3576) 2017-10-03 00:04:43 -07:00
michellethomas 064363df78 After saving slice fixing redirect (#3572) 2017-10-02 18:19:52 -07:00
Jeff Niu f8cc05b54e Added label+percent and label+value display options to pie chart (#3565) 2017-10-02 15:53:11 -07:00
Denny Biasiolli 9baca6758d Removing yarn warnings during install (#3567)
* removing deprecated babel-preset-es2015 in favor of babel-preset-env

This removes this yarn warning during install:

```
warning babel-preset-es2015@6.24.1:
Thanks for using Babel: we recommend using babel-preset-env now:
please read babeljs.io/env to update!
```

* updating sinon to 4.0.0

This removes wrench from its dependencies and this yarn warning during install:

```
warning wrench@1.3.9: wrench.js is deprecated!
You should check out fs-extra (https://github.com/jprichardson/node-fs-extra)
for any operations you were using wrench for.
Thanks for all the usage over the years.
```
2017-10-02 15:25:37 -07:00
Maxime Beauchemin b39d165913 [nvd3] fix single metric showing up in legend (#3563) 2017-10-02 10:42:16 -07:00
Kan Ouivirach bc3ad64619 Add Pronto Tools to user list (#3558) 2017-10-02 08:41:04 -07:00
Gábor Hermann 0bd2ac5353 Minor documentation fix (#3553) 2017-09-29 16:47:18 -07:00
Maxime Beauchemin 03e2af8bd9 CHANGELOG for 0.20.0 (#3545) 2017-09-28 14:42:57 -07:00
timifasubaa 82b85d1d6c Explore update button labels (#3534)
* resolve ui ambiguity

* resolve button name ambiguity

* update test
2017-09-28 14:40:11 -07:00
Maxime Beauchemin 17c7ca239a Fixing missing messages.json file (#3547) 2017-09-28 12:24:00 -07:00
Grace Guo ef59b6b650 try to fix problem that chrome window not opening after ajax requrest (#3528) 2017-09-27 21:22:22 -07:00
Grace Guo d1a7a7b85c Time Series Annotation Layers (#3521)
* Adding annotations to backend

* Auto fetching Annotations on the backend

* Closing the loop

* Adding missing files

* annotation layers UI

for https://github.com/apache/incubator-superset/issues/3502

* a few fixes per code review.

- add annotation input sanity check before add and before update.
- make SelectAsyncControl component statelesis, and generic
- add annotation description in d3 tool tip
- use less variable to replace hard-coded color
2017-09-27 20:40:07 -07:00
Maxime Beauchemin 3d72eb475a [explore] fix cached tooltip (#3526) 2017-09-27 20:39:29 -07:00
Maxime Beauchemin b50489eb96 v0.20.0 (#3544) 2017-09-27 20:38:50 -07:00
Riccardo Magliocchetti 8773e32cd6 setup: bump pandas to 0.20.3 (#3506) 2017-09-27 19:50:06 -07:00
Riccardo Magliocchetti f438ccbcb1 Add support for column specific fillna to viz (#3066)
Fix #3029
2017-09-27 17:51:04 -07:00
Riccardo Magliocchetti f829b486d1 docs: QUERY_TIMEOUT_THRESHOLD is gone (#3537) 2017-09-27 08:20:59 -07:00
Maxime Beauchemin 06e52e600e [style] no bold on dashboard widget headers (#3531) 2017-09-26 16:04:09 -07:00
michellethomas f0636b8748 Break word on InfoTooltip (#3532)
* Break word on InfoTooltip

* Moving style object to separate const
2017-09-26 16:03:39 -07:00
Jeff Niu c629282ec4 Feature: Paired t-test table visualization (#3473)
* Feature: paired t-test table viz

* Added unit tests for viz
2017-09-26 15:11:35 -07:00
Jeff Niu 7d934e7246 Feature: query string API endpoint (#3513)
* exposed API endpoint to get querystring for a slice

* Added unit tests for endpoint

* fixed test case for python3

* moved get querystring logic into its own func

* renamed query string endpoint
2017-09-26 09:03:03 -07:00
fabianmenges 8efcaeb768 Feature: Display the verbose name for metrics within Charts and legend. (#3504) 2017-09-25 20:21:44 -07:00
Jeff Niu cf0b670932 Druid refresh metadata performance improvements (#3527)
* parallelized refresh druid metadata

* fixed code style errors

* fixed code for python3

* added option to only scan for new druid datasources

* Increased code coverage
2017-09-25 18:00:46 -07:00
Grace Guo 3949d39478 Allow user update slice title in visualize flow (#3466)
* 1. after user make sql query and visualize, allow user click title to update slice title, and create a new slice at the same time.
2. don't save new title if it is empty. Will still show old title.

* change saveSlice call response and update explore view
2017-09-25 11:38:29 -07:00
Grace Guo 5718d6bbaf allow user update slice name in dashboard view (#3467)
- if current user is allowed to edit dashboard, we will allow this user to edit slice name.
- show different tooltip given allowed/not-allowed to update slice name.
- user will click slice name and update.
- after user submit edit, if he doesn't have right to alter slice, server-side will return error message to client-side. Slice name will not be changed or saved.
- will show notification after save slice name.
2017-09-25 11:37:12 -07:00
Jeff Niu f3146ef6f9 Add Table performance improvements (#3509)
* Improved performance of 'Add table' function

* got rid of pvt function call

* changes metric obj to key on metric_name
2017-09-25 11:35:09 -07:00
michellethomas 255ea69977 Add metric warning (#3499)
* Adding warning text to metrics

* Adding javascript tests

* Fixing downgrade script for warning_text

* Adding merge migration
2017-09-22 09:49:13 -07:00
Grace Guo 9af34ba51c js translation -- performance improvment (#3390)
* Chinese page

* Using react-intl-universal to improve multi language in react page

* Using react-intl-universal to improve multi language in react page

* react_intl_universal

* change

* change

* change

* change

* change

* change

* change

* merge

* multiple page in js

* merge

* merge

* merge

* merge

* Js Translations

* JS Translation

* JS Translations

* Js translation

* JS translations

* JS translations

* Js translaion

* JS en Translation

* JS Translation

* upgrade document

Fixing the damn build (#3179)

* Fixing the build

* Going deeper

[bugfix] only filterable columns should show up in FilterBox list (#3105)

* [bugfix] only filterable columns should show up in FilterBox list

* Touchups

Datasource cannot be empty (#3035)

add title description to model view (#3045)

* add title description to model view

* add missing import

Add 'show/hide totals' option to pivot table vis (#3101)

[bugfix] numeric value for date fields in table viz (#3036)

Bug was present only when using the NOT GROUPED BY option

fixes https://github.com/ApacheInfra/superset/issues/3027

fix hive.fetch_logs (#2968)

add Zalando to the list of organizations (#3171)

docs: fixup installation examples code indentation (#3169)

[bugfix] fix bar order (#3180)

[bugfix] visualize flow error: 'Metric x is not valid' (#3181)

The metric name in the frontend doesn't match the one generated on the
backend. It turns out the explore view will default to the first
metric so specifying one isn't needed.

Fix the segment interval for pulling metadata (#3174)

The end of the interval would be on the truncated today date, which
means that you will exclude today. If your realtime ingestion job
runs shorter than a day, the metadata cannot be pulled from the
druid cluster.

Bump cryptography to 1.9 (#3065)

As 1.7.2 doesn't compile here with openssl 1.1.0f

Escaping the user's SQL in the explore view (#3186)

* Escaping the user's SQL in the explore view

When executing SQL from SQL Lab, we use a lower level API to the
database which doesn't require escaping the SQL. When going through
the explore view, the stack chain leading to the same method may need
escaping depending on how the DBAPI driver is written, and that is the
case for Presto (and perhaps other drivers).

* Using regex to avoid doubling doubles

[sqllab] improve Hive support (#3187)

* [sqllab] improve Hive support

* Fix "Transport not open" bug
* Getting progress bar to show
* Bump pyhive to 0.4.0
* Getting [Track Job] button to show

* Fix testzz

Add BigQuery engine specifications (#3193)

As contributed by @mxmzdlv on issue #945

[bugfix] fix merge conflict that broke Hive support (#3196)

Adding 'apache' to docs (#3194)

[druid] Allow custom druid postaggregators (#3146)

* [druid] Allow custom druid postaggregators

Also, fix the postaggregation for approxHistogram quantiles so it adds
the dependent field and that can show up in the graphs/tables.

In general, postAggregators add significant power, we should probably
support including custom postAggregators. Plywood has standard
postAggregators here, and a customAggregator escape hatch that allows
you to define custom postAggregators.

This commit adds a similar capability for Superset and a additional
field/fields/fieldName breakdown of the typical naming for dependent
aggregations, which should make it significantly easier to develop
approxHistogram and custom postAggregation-required dashboards.

* [druid] Minor style cleanup in tests file.

* [druid] Apply code review suggestions

* break out CustomPostAggregator into separate class. This just cleans
  up the creation of the postaggregator a little bit.
* minor style issues.
* move the function around so the git diff is more readable

add combine config for metrics in pivot table (#3086)

* add combine config for metrics in pivot table

* change method to stack/unstack

* update backendSync

Autofocus search input in VizTypeControl modal onEnter (#2929)

Speed up JS build time (#3203)

Also bumping a few related libs

JS Translation

JS translations

js translation

fix issue 3204 (#3205)

[bugfix] capture Hive job_id pre-url transformation (#3213)

js translation

fix issue 3204 (#3205)

[bugfix] capture Hive job_id pre-url transformation (#3213)

[docs] update url in CONTRIBUTING.md (#3212)

[sqllab/cosmetics] add margin-top for labels in query history (#3222)

[explore] nvd3 sort values in rich tooltip (#3197)

[sqllab] fix UI shows 'The query returned no results' momentarily (#3214)

this is visible when running async queries between the fetching and
success state as the rows are getting cached in the component

[explore] DatasourceControl to pick datasource in modal (#3210)

* [explore] DatasourceControl to pick datasource in modal

Makes it easier to change datasource, also makes it such that the list
of all datasources doesn't need to be loaded upfront.

* Adding more metadata

* Js translation

* js tran

* js trans

* js trans

* js tran

* js trans

* js trans

* js tran

* js translation

* js trans

* js translation

* try load language pack async

* Backend translations things

* create language pack inside common data

* performance improvement for js i18n.

- js bundle should not contain localized content
- we populate translation content from server-side, in boostrap.common.language_pack
- in client-side, use promise to wrap around translation content. text will be translated after translation content arrived/parsed.
- fix linting

* fix Timer unit test

* 1. add global hook for all tests, to make translation pack avaialble before each test starts.
2. fix unit test for Timer component
3. remove noused method get_locale, and modules
4. fix page reload after user change page language

* parse and build i18n dictionary as a module

* fix sync-backend task, which should run without DOM
2017-09-20 12:37:33 -07:00
timifasubaa 1cf634afa2 Remove repeated line (#3491)
* add lanscape?

* Revert "add lanscape?"

This reverts commit b3d6e80af4.

* remove unused line
2017-09-19 21:30:48 -07:00
timifasubaa d7fc364ff4 Fix idna requirement (#3497)
There is often conflicting versions of idna. This fixes is to 2.5.
2017-09-19 21:30:18 -07:00
timifasubaa aebd089ca5 update contributing.md (#3495)
Uses pip instead to setup superset.
2017-09-19 21:30:01 -07:00
Maxime Beauchemin ae7f163372 Removing super() call from refactor (#3500) 2017-09-19 16:41:09 -07:00
Maxime Beauchemin ed9f56448f Adding missing future imports (#3493) 2017-09-19 11:20:22 -07:00
Maxime Beauchemin ccd5fd44cf Removing dependency on pythrifthiveapi (#3494)
Since the latest pyhive, we don't need pythrifthiveapi as they ship with
the latest version.

There's actually a conflict between the new pyhive and pythrifthiveapi
and this fixes it.
2017-09-19 11:19:49 -07:00
Maxime Beauchemin c5252d0f43 [heatmap] account for bounds = 0 (#3474)
* [heatmap] account for bounds = 0

* Fix sorting

* linting
2017-09-18 21:32:39 -07:00
timifasubaa ede1432936 Improve code quality (#3480)
* add lanscape?

* add code climate badges

* pylint first pass

* Try out yapf

* merge

* merge

* lint

* more yapf

* removed unnecessary corrections
2017-09-18 20:40:27 -07:00
fabianmenges c3c9ceb1cc Feature/Fix: Get a full times_series for your filter instead of Topn for each point in time (#3434) 2017-09-18 10:48:05 -07:00
datinho 6fe93e18c7 Getting datatype with its dialect (#3486) 2017-09-18 09:55:41 -07:00
Dmitry Goryunov c988080990 Feature: "Impersonate user" setting on Datasource (#3404)
* Add "Impersonate user" setting to Datasource

* Add tests

* Use g.user.username for all the sync cases

* use uri.username instead of uri.user

* Small refactoring
2017-09-18 09:52:29 -07:00
JulieRossi a26e65f418 Create CsvResponse to manage csv exports encoding (#3484) 2017-09-18 09:51:13 -07:00
Maxime Beauchemin e66f68d36c Better installation docs (#3469) 2017-09-18 09:49:48 -07:00
Riccardo Magliocchetti cb4d934ba5 viz: fix reversed stats_logger label (#3475) 2017-09-18 09:45:49 -07:00
Riccardo Magliocchetti 6962c76412 docs: athena can be installed from pypi (#3477)
As sqlalchemy support has been merged and available in a release
since a few.
2017-09-18 09:45:00 -07:00
Riccardo Magliocchetti b0d25a154a Miscvizcleanups (#3476)
* viz: remove unused countries import

* viz: simplify code in BaseViz.query_obj
2017-09-18 09:44:19 -07:00
fabianmenges e22aecb0d1 Adding hook for CSRF exempting flask views. (#3435) 2017-09-14 20:54:18 -07:00
Jeff Carey 32bd827b25 bugfix/3321 Ensure text appears on buttons inside tables (#3409) 2017-09-14 20:28:01 -07:00
Stephanie Rivera e399a8c613 Simple grammar and update to link (#3415) 2017-09-14 17:41:01 -07:00
JulieRossi b90d8e32f1 config: allow changing default options for writting csv (#3441) 2017-09-14 17:40:15 -07:00
Xiao Hanyu c81026ddb1 Add shopee to user list. (#3425)
Shopee (https://shopee.sg) use superset for data analytics, visualisation and reporting.
2017-09-14 17:12:54 -07:00
Jeff Niu dd72048320 Fixed filter removal bug (#3458)
* Fixed bugs when removing filter, switching operators, and switching columns

* Fixed lint errors for code style

* Added more unit tests for FilterControl

* Code format changes to meet standards
2017-09-14 17:10:38 -07:00
Grace Guo ad604aed09 fix encoding error in sql lab logging (#3424) 2017-09-14 11:18:34 -07:00
timifasubaa 31b7b9a6a0 Sqllab dont send empty queries to db (#3459)
* add lanscape?

* prevent empty queries from being sent to db

* Revert "add lanscape?"

This reverts commit b3d6e80af4.

* improve code style

* nit

* unnit

* renit
2017-09-14 09:50:06 -07:00
Jeff Niu 745784fc97 Fixed dashboard filters carrying over to explore slice (#3461) 2017-09-14 09:44:00 -07:00
fabianmenges fdee06bbf2 Adding hook for external password store for databases (#3436) 2017-09-13 20:59:03 -07:00
Maxime Beauchemin 816c517f0f Allow specifying sort criteria on Table viz (#3460)
* Allow to specify sort criteria on table viz

* Better handling of ordering
2017-09-13 20:18:47 -07:00
Maxime Beauchemin 49f24d128b [heatmap] numerous improvements (#3456)
* [heatmap] numerous improvements

* flexibility as to how to sort X and Y axis (alpha/value, desc/asc)
* option to show a legend
* fixed margins, maximize real estate
* allowed users to define bounds

* Tunning
2017-09-13 16:13:45 -07:00
Grace Guo 8223729e1e fix https://github.com/apache/incubator-superset/issues/3430 (#3431) 2017-09-12 12:06:38 -07:00
Grace Guo 2d6b9422c6 fix https://github.com/apache/incubator-superset/issues/3422 (#3440) 2017-09-12 12:06:22 -07:00
fabianmenges 3c0e85e2c0 Adding order_desc flag to explore endpoint (#3439) 2017-09-12 09:48:43 -07:00
fabianmenges 490c707eb6 Handling pandas ExtensionDtypes (#2937) 2017-09-12 09:36:28 -07:00
Maxime Beauchemin 7c1b56f3a9 [postgres] adding support to serialized timedelta (#3444) 2017-09-12 09:06:53 -07:00
Maxime Beauchemin 3e9f797949 [explore] show validation error on control panel header (#3453)
* [explore] show validation error on control panel header

* Linting
2017-09-12 09:06:29 -07:00
Maxime Beauchemin f3de758363 [heatmap] fix default sorting (#3450)
Currently the heatmap axis are sorted randomly, this PR makes it such
that it's properly sorted.

Also allowing for specifying the left and bottom margins
2017-09-12 09:06:03 -07:00
Maxime Beauchemin 90e46cb39c Fix off-by-one error with linear color scales (#3452)
* Fix off-by-one error with linear color scales

* linting
2017-09-12 09:05:26 -07:00
Maxime Beauchemin fe77534c03 [explore] checkbox control won't uncheck (#3454) 2017-09-12 09:05:07 -07:00
fabianmenges 1f135e41cd Ignore intellij files (#3446) 2017-09-12 09:04:48 -07:00
Maxime Beauchemin 147c12dddf Fixing the build (#3445)
* Bumping npm

* Fixing the build

This addresses long standing issues and hacks around react-map-gl
that have been creating all sorts of build issues over time.

It appears that recent changes broke things further.

This PR upgrades to the latest `react-map-gl` and removes related hacks.
2017-09-11 16:30:39 -07:00
Riccardo Magliocchetti 3dfdde130a setup: Bump sqlalchemy-utils to 0.32.16 (#3405)
Now sqlalchemy-utils will make explicit that we are trying
decoding the secret with the wrong key instead of a generic
UnicodeDecodeError.

Fix #2600
2017-09-01 08:30:48 -07:00
Maxime Beauchemin 255a36c280 [hotfix] user dashboard says '150 weeks' (#3403) 2017-08-31 15:00:21 -07:00
Maxime Beauchemin 66f646ac66 [hotfix] fix slices where since/until = None (#3401) 2017-08-30 20:26:58 -07:00
Maxime Beauchemin e53f3032bb [dashboard] adding an option to duplicate slices when "Saving AS" (#3391)
* [dashboard] adding an option to duplicate slices when "Saving AS"

* Fix tests
2017-08-30 14:09:29 -07:00
Maxime Beauchemin 3b4cd812ae Fix copypasta control label error 'Until' -> 'Since' (#3399) 2017-08-30 14:05:21 -07:00
Maxime Beauchemin ac5da46fb2 [line chart] add 'min_periods' control related to rolling windows (#3397)
* [line chart] add 'min_periods' control related to rolling windows

* Linting js
2017-08-30 13:32:07 -07:00
Maxime Beauchemin 497a6f1df9 [hive] fix date casting in explore view (#3394) 2017-08-30 11:56:43 -07:00
Maxime Beauchemin 1fd08a5912 [hotfix] backward compatibility on date expressions (#3396)
Previously all 'since' date expression evaluated in the future like
`30 days` would be reassigned to the past (now - `30 days`). It would
extend to fixed dates which is a bad thing and was removed.

Now we have reports and dashboards in the wild that use things like `30
days` and we'd like to not break those as we roll out the next version.

This fix should allow for that.
2017-08-30 11:18:23 -07:00
Patryk 9676f02497 Add Capital Service to organizations list (#3395) 2017-08-30 09:36:54 -07:00
mxmzdlv 42dd64e413 Fix datatable scroll height when using filter or pagination (#3377) 2017-08-29 21:10:48 -07:00
Grace Guo c3ab796734 fix date picker Select alignment (#3392) 2017-08-29 19:08:54 -07:00
Maxime Beauchemin a782d623f0 Build optimizations (#3378)
Bumping some version, removing unused libs, ...
2017-08-28 16:16:52 -07:00
Maxime Beauchemin 48b88e5241 [dashboard] load list of slices at modal enter time (#3379) 2017-08-28 14:31:43 -07:00
Maxime Beauchemin a47a512808 [explore] Improved time filters controls (#3371)
* Improved time filters controls

* lint

* Fix coverage

* Allow empty dates
2017-08-28 09:16:23 -07:00
Maxime Beauchemin aff7a82664 [sql lab] using react-split-pane (#3363)
* [sql lab] using react-split-pane

* padding
2017-08-27 15:01:24 -07:00
Maxime Beauchemin 2d237fe2ef v1.9.1 (#3376) 2017-08-26 15:07:17 -07:00
mxmzdlv c944c61747 Apply advanced analytics processing to comparison time series (#3373) 2017-08-25 11:08:15 -07:00
Maxime Beauchemin 0c8b24378d [webpack] add a 'npm run dev-fast' command that is much faster (#3362)
The tradeoff is that the sourcemap isn't as reliable.
2017-08-24 19:23:23 -07:00
Boris Hajduk 90ba6ee6a0 bugfix for addTotalValues with negative values (#3366) 2017-08-24 15:37:58 -07:00
timifasubaa 8d877e8a35 [explore] Fix and test slice id logging issue (#3339)
* [explore] fixed padding bug on filter section

* fix slice_id logging issue

* [superset-sqllab] fix slice_id population in appropriate column

* [explore-logging] test the slice_id logging fix

* fix travis errors

* fix nits pointed out in PR comments

* cleanup tests

* made python more beautiful

* made python even more beautiful

* made python even more more beautiful

* made python even more more more beautiful

* fix lint error

* make exception handling more specific

* fixed silly error

* fixed argument indentation
2017-08-24 09:11:41 -07:00
Maxime Beauchemin c5b1eb7f5b Bump fab to 1.9.4 (#3364)
Important bug/security fixes detailed here:
https://github.com/dpgaspar/Flask-AppBuilder/blob/master/docs/versions.rst
2017-08-24 08:08:29 -07:00
Maxime Beauchemin 46d60880eb Revert "[sql lab] Make sql editor resizable (#3242)" (#3360)
This reverts commit 75e69f02e8.
2017-08-23 14:40:08 -07:00
Maxime Beauchemin 0c36827368 [dist_bar] break down control groups (#3357) 2017-08-22 21:11:48 -07:00
timifasubaa 2b1bb35c5c delete unused csv file (#3356) 2017-08-22 21:11:26 -07:00
Maxime Beauchemin d3824bbb38 [hotfix] react-select dropdown autocomplete are invisible (#3358) 2017-08-22 20:56:25 -07:00
Maxime Beauchemin 670ba5d32e Collapsible Control sections (#3354)
The left panel of the explore view has become crowded and overwhelming
overtime. This PR adds functionality to collapse the control sections,
and sets most sections to be collapse by default as the explore view
opens up.

* breakdown `Query` section for most viz
* bring filters to the top, under Query section
* collapse most sections by default
* removed confusing outdated description for Filter section
2017-08-22 16:10:55 -07:00
Maxime Beauchemin 64c91ec9e3 [bugfix] Y bounds in line chart (#3353)
Also fixing tick labels showing NaN in the `dist_bar` viz
2017-08-22 16:10:42 -07:00
Maxime Beauchemin 1fda6f0745 [css] react-select only in theme (#3351) 2017-08-21 17:36:54 -07:00
Grace Guo f8e596b9d8 fix multi-value react select style (#3352) 2017-08-21 17:36:33 -07:00
Maxime Beauchemin 254645773c Better looking checkboxes (#3345)
Also showing icon only on hover on control headers
2017-08-21 13:47:50 -07:00
Maxime Beauchemin e79adbbc5f [hotfix] self-immune filter_box fix (#3338) 2017-08-18 17:43:11 -07:00
Dmitry Goryunov 75e69f02e8 [sql lab] Make sql editor resizable (#3242)
* Update to the version of react-ace with the fixed sizing issues

* Make ace editor resizable

* Use small util method for offset calculation instead of $

* Test ResizableAceEditor

* Make the right pane of the Sql Lab scrollable

* Add default and min height to the ResizableAceEditor

* Implement SplitPane

* Make Splitter fullscreen

* React on resize of the window

* Implement min and max

* Get rid of a magic number + add margin

* Handle resize event with delay + cleanup the code

* Make ResultSet adjustable

* Make QueryHistory adjustable

* Remove ResizableAceEditor

* Make linter happy

* Test SplitPane

* Init sizes properly
2017-08-18 17:15:25 -07:00
Maxime Beauchemin 6fc837db51 [sql lab] improve error messages (#3308)
* [sql lab] improve error messages

Some error messages in non-async mode were showing as JSON or sometimes
as tuples. This fixes that.

* linting
2017-08-18 15:50:07 -07:00
Maxime Beauchemin 2923a125db Syncing the timeout param from backend (#3329)
* Syncing the timeout param from backend

* Linting
2017-08-18 15:49:47 -07:00
Maxime Beauchemin 527572c3eb [dashboard] re-enabling cascading filters (#3335)
* [dashboard] re-enabling cascading filters

https://github.com/apache/incubator-superset/pull/3183 disabled the
ability of a filterbox to get filtered by another filterbox

* linting
2017-08-18 15:49:29 -07:00
Maxime Beauchemin a7ba6e4a5d [nvd3] fix bubble axis (#3332)
number of issues are addressed here:
* x axis formatting doesn't apply in bubble chart
* adding option to show/hide bounds of x and y axis
* with a flaky 'auto' margin mode, allow user to specify hard values or
  auto
* x label font-size was different than y axis
* show more options and reorg Control panels for Axes in `line` viz
2017-08-18 11:56:34 -07:00
Maxime Beauchemin e31ad22f50 [hotfix] hotfixing the hotfix (#3333) 2017-08-17 23:18:41 -07:00
Rogan 813ed6018d Unnecessary to specify order_columns for DatasourceModelView (#3331) 2017-08-17 22:18:32 -07:00
Grace Guo 0454ef3726 disable immediately re-render for color scheme change (#3328)
for chart type: bubble, area, treemap and country map, color scheme change cannot take effect immediately. So have to disable immediately re-render function and hide lightening icon for these chart type.
2017-08-17 21:38:34 -07:00
Maxime Beauchemin afedcdf0d8 [hotfix] dashboard widget resize is broken (#3330)
blame https://github.com/apache/incubator-superset/pull/3315
2017-08-17 21:20:51 -07:00
Riccardo Magliocchetti 9f3aeb22d9 docs: add references to Flask-Appbuilder Security documentation (#3322)
And a specific link to an oauth example configuration.
2017-08-17 11:48:22 -07:00
Maxime Beauchemin 59268e978a Use react-alert for backend message flashing (#3315) 2017-08-16 23:00:23 -07:00
Grace Guo b9a2fa4015 Allow for multiple color schemes (#3295)
* Allow for multiple color schemes

1. create ColorSchemeControl component
2. using the same new control component for linear colors

* add color spectum for linear color scheme

* remove dup css

* fix controls setting for linear color scheme

* minor fix by code review comment
2017-08-16 22:20:11 -07:00
Invenis 3c8577b853 French translation (#3313) 2017-08-16 20:29:18 -07:00
Maxime Beauchemin 0aa3d2a818 [hive] improve error messages (#3305)
* [hive] improve error messages

* Addressing comments
2017-08-16 17:40:28 -07:00
Maxime Beauchemin fbd0d46e8a Fix styles in Separator widget (#3309)
Style wasn't working right for separator widget since the iframe sandboxing of
the markup widget. This addresses this small issue and also now allows
for html in the separator widget
2017-08-16 17:40:06 -07:00
Maxime Beauchemin c4e056929d [sql lab] run button shortcut tooltip (#3310) 2017-08-16 17:39:48 -07:00
Maxime Beauchemin 84e59a11f1 [bugfix] Presto KeyError 'errorLocation' (#3291) 2017-08-16 13:25:09 -07:00
Maxime Beauchemin 9fcd5d67e4 [sql lab] add pending to the list of searchable statuses (#3292) 2017-08-16 13:24:43 -07:00
Maxime Beauchemin ccf505a480 [mapbox] fix viewport alterations (#3293)
* [mapbox] fix viewport alterations

Since explorev2 it appears that altering the viewport hasn't been
changing the controls as it used to. This PR addresses it.

* lint
2017-08-16 11:23:01 -07:00
Rogan d1d1c49009 Fix raise error when query datasource (#3298)
* Catching the 'NoResultFound' exception when the datasource does't exist

* change one() to first()

* revert modify

* remove import
2017-08-16 10:18:43 -07:00
Maxime Beauchemin 232a5c392e [docs] document how to compile/publish docs (#3296) 2017-08-15 16:37:40 -07:00
Maxime Beauchemin 9c6248f3ba [dashboard] add link to export CSV from dashboard (#3280)
* [dashboard] add link to export CSV from dashboard

fixes #1304

* Fix tests
2017-08-14 18:25:36 -07:00
Maxime Beauchemin 6841697917 FAQ entry for backend support (#3282)
so that I can close:
https://github.com/apache/incubator-superset/pull/1470/files
2017-08-14 17:57:09 -07:00
Maxime Beauchemin 81817309d3 [sql lab] fix sluggish backspace in editor (#3286)
Somehow Ace's "changeSelection" event is triggered when hitting
backspace (and shouldn't!).

changeSelection on our side triggers enough work to make the
holding backspace sluggish and laggy.

This fix ignores selection with a length of 1, avoiding mutating the
state altogether when hitting/holding backspace.
2017-08-14 17:55:30 -07:00
Grace Guo 025ef5a0f1 Fix Chart Error Message Display (#3287) 2017-08-14 12:24:35 -07:00
Maxime Beauchemin 9a4e4d0443 [dashboard] fix standalone mode that hides the navbar (#3284) 2017-08-14 12:24:05 -07:00
Grace Guo c9c6bcaabe Improve superset list view content layout (#3031)
* improve superset list view page layout

- less header spaces and stacks
- move pagination down to bottom
- apply material design style to 'add' action button
- will apply to all superset list view, like slices list, security tab lists etc.

* improve superset list view page layout

- less header spaces and stacks
- move pagination down to bottom
- apply material design style to 'add' action button
- will apply to all superset list view, like slices list, security tab lists etc.

* improve superset list view page layout

- less header spaces and stacks
- move pagination down to bottom
- apply material design style to 'add' action button
- will apply to all superset list view, like slices list, security tab lists etc.

* improve superset list view page layout

- less header spaces and stacks
- move pagination down to bottom
- apply material design style to 'add' action button
- will apply to all superset list view, like slices list, security tab lists etc.

* improve superset list view page layout

- less header spaces and stacks
- move pagination down to bottom
- apply material design style to 'add' action button
- will apply to all superset list view, like slices list, security tab lists etc.

* remove tabs from indentation

* fix merge conflicts

* adjust css after code merge
2017-08-11 15:34:29 -07:00
Maxime Beauchemin 144f516700 [markup] fix CSS, remove scrollbar (#3281) 2017-08-11 08:26:47 -07:00
Emanuele Cesena c17ffc1e9c Fix returned time parse_human_datetime (#2033)
parse_human_datetime parses date-only strings, e.g. "today", returning the correct date but time set at 9am. This is an internal implementation in parsedatetime. This patch resets to midnight. If time is specified and parsed, it is correctly returned.
2017-08-10 23:04:49 -07:00
Rogan 0d4137d21e Add translatable columns in label_columns of the view (#3032)
* add translatable columns in label_columns of the view

* display the verbose_name of columns in list view, just like in the metrics list

* Revert "display the verbose_name of columns in list view, just like in the metrics list"

This reverts commit f815d3b3ed.
2017-08-10 22:28:06 -07:00
Maxime Beauchemin 0c5db55d55 [security] prevent XSS markup viz (#3211)
* Prevent XSS in Markup viz

We protect the browser by sandboxing the user code inside an iframe

* Helvetica
2017-08-10 21:38:33 -07:00
Rogan bd4a4c2753 add _() to Exception messages (#3034)
* add `_()` to Exception messages

* fix error
2017-08-10 20:57:05 -07:00
Rogan f399fcd624 display the verbose_name of columns in list view, just like in the metrics list (#3275) 2017-08-10 20:52:24 -07:00
Rogan 08e40e2d78 add placeholder to Select components (#3274) 2017-08-10 20:51:36 -07:00
Luis Rodriguez 2898f9d379 Added Konfio to 'Who uses Superset' list. (#3277) 2017-08-10 20:50:49 -07:00
Alex Guziel dfea8df7c9 Fix celery worker (#3278) 2017-08-10 20:50:21 -07:00
Rogan a5320a0f37 [add] Save filters to dashboard (#3183)
* [add] Save filters to dashboard

* format code

* fix CI error

* add semicolon  semi

* fix none object

* add test data
optimize the js code
fix the compatibility issue

* fix urllib to urllib.parse

* add space

* update test case

* remove  'return'

* fix error

* update test case
2017-08-10 20:49:49 -07:00
Grace Guo b68084b9ac Explore view save modal spec (#3110)
* split reducer logic for ExploreViewContainer

* fix saveModal component and unit tests

* revert changes in SaveModal_spec.
will make another commit just to improve test coverage for SaveModal component.

* improve test coverage for explore view components:
- SaveModal component
- URLShortLinkButton

* remove comment-out code

* [bugfix] wrong 'Cant have overlap between Series and Breakdowns' (#3254)

* [explore] make edit datasource a basic link (#3244)

* Relying on FAB for font-awesome.min.css (#3261)

* Modernize SQLA pessimistic handling (#3256)

Looks like SQLAlchemy has redefined the best practice around
pessimistic connection handling.

* [webpack] break CSS and JS files while webpackin' (#3262)

* [webpack] break CSS and JS files while webpackin'

* cleaning up some templates

* Fix pylint issue

* import logging (#3264)

* [bugfix] preserve order in groupby (#3268)

Recently in
https://github.com/apache/incubator-superset/commit/4c3313b01cb508ced8519a68f6479db423974929
I introduced an issue where the order of groupby fields might change.

This addresses this issue and will preserve ordering.

* Explicitly add Flask as dependancy (#3252)

* Use sane Celery defaults to prevent tasks from being delayed (#3267)

* Improve the chart type of Visualize in sqllab (#3241)

* Improve the chart type of Visualize in sqllab & Add some css & Fix the link address in the navbar

* add vizTypes filter

* Set default ports Druid (#3266)

For Druid set the default port for the broker and coordinator.

* [explore] Split large reducer logic in ExploreViewContainer (#3088)

* split reducer logic for ExploreViewContainer

* fix saveModal component and unit tests

* revert changes in SaveModal_spec.
will make another commit just to improve test coverage for SaveModal component.

* remove comment-out code

* fix merge confilicts
2017-08-10 17:04:44 -07:00
timifasubaa 3b24d7df83 [explore] fixed padding bug on filter section (#3279) 2017-08-10 16:48:30 -07:00
Grace Guo b3107bb603 [explore] Split large reducer logic in ExploreViewContainer (#3088)
* split reducer logic for ExploreViewContainer

* fix saveModal component and unit tests

* revert changes in SaveModal_spec.
will make another commit just to improve test coverage for SaveModal component.

* remove comment-out code

* fix merge confilicts
2017-08-10 14:21:45 -07:00
Alex Guziel 08b7e891a7 Use sane Celery defaults to prevent tasks from being delayed (#3267) 2017-08-09 22:34:39 -07:00
Maxime Beauchemin 57421d14d0 [bugfix] preserve order in groupby (#3268)
Recently in
https://github.com/apache/incubator-superset/commit/4c3313b01cb508ced8519a68f6479db423974929
I introduced an issue where the order of groupby fields might change.

This addresses this issue and will preserve ordering.
2017-08-09 18:06:18 -07:00
Fokko Driesprong 0cf0860a3d Set default ports Druid (#3266)
For Druid set the default port for the broker and coordinator.
2017-08-09 17:25:00 -07:00
Maxime Beauchemin 327c052456 [webpack] break CSS and JS files while webpackin' (#3262)
* [webpack] break CSS and JS files while webpackin'

* cleaning up some templates

* Fix pylint issue
2017-08-09 09:52:43 -07:00
eeve 033ba2cb66 Improve the chart type of Visualize in sqllab (#3241)
* Improve the chart type of Visualize in sqllab & Add some css & Fix the link address in the navbar

* add vizTypes filter
2017-08-09 09:12:21 -07:00
Maxime Beauchemin cc36428260 Modernize SQLA pessimistic handling (#3256)
Looks like SQLAlchemy has redefined the best practice around
pessimistic connection handling.
2017-08-09 09:10:12 -07:00
Fokko Driesprong 6da68ab271 Explicitly add Flask as dependancy (#3252) 2017-08-09 09:09:02 -07:00
Maxime Beauchemin be01851ef7 Relying on FAB for font-awesome.min.css (#3261) 2017-08-09 09:04:29 -07:00
cclauss 20915457ff import logging (#3264) 2017-08-09 08:18:10 -07:00
Maxime Beauchemin 2385cd445b [explore] make edit datasource a basic link (#3244) 2017-08-08 12:29:24 -07:00
Maxime Beauchemin 0429e842b5 [bugfix] wrong 'Cant have overlap between Series and Breakdowns' (#3254) 2017-08-07 21:47:42 -07:00
Pedro Valentim Silva Leite f68189b54e Fix Yahoo's website link (#3249) 2017-08-07 08:31:49 -07:00
Zeeshan Ahmed dcf83031d1 Fix typo (#3246) 2017-08-06 20:27:54 -07:00
Riccardo Magliocchetti ef7e9dd336 docs: use yarn in making your own build (#3235) 2017-08-04 09:31:36 -07:00
Riccardo Magliocchetti ae0655028f explore: redraw chart on width change too (#3067)
Fix #3028
2017-08-04 09:15:08 -07:00
Maxime Beauchemin 166c576c94 Add basic Impala engine spec (#3225)
From:
https://www.cloudera.com/documentation/enterprise/5-8-x/topics/impala_datetime_functions.html
2017-08-04 09:10:32 -07:00
Rich @ RadICS 7190cf8e77 Treemap vis verbose metric name (#3237)
* Change hardcoded references to 'User' security model to allow custom class override

* verbose metric name in treemap

* Linting
2017-08-04 09:07:03 -07:00
Shao-Yen "Fred" Cheng 2ef9bfed20 [bug fix] Fix to #3137 and #3239 (#3240)
* #3137 add the leftover code from #3138 for fixing issue #3137

* #3239 Use slice id as the key instead of sliceName
2017-08-04 09:05:50 -07:00
Rich @ RadICS 0191fa58c8 SUPERSET_HOME enviroment variable (#3238)
* Change hardcoded references to 'User' security model to allow custom class override

* Add SUPERSET_HOME environment variable
2017-08-04 08:51:40 -07:00
Maxime Beauchemin 4c3313b01c Handle Time at query_obj generation time (#3236)
As opposed to in the within itself
2017-08-03 15:42:26 -07:00
Maxime Beauchemin 5278b53218 [pivot] add support for in Pivot on Druid (#3230) 2017-08-03 00:04:16 -07:00
Maxime Beauchemin 4ea770068b Allowing to integrate time as a groupby value (#3229) 2017-08-02 21:33:27 -07:00
Maxime Beauchemin 91bd38a851 0.19.0 (#3227) 2017-08-02 16:56:46 -07:00
Rich @ RadICS 163f4e359c Allow 'refresh_immune_slices' (#2974)
* Allow 'refresh_immune_slices'

* Changed param name, added note in FAQ

* Linting
2017-08-02 08:46:19 -07:00
Riccardo Magliocchetti 90592d3e3d sql_lab: re-raise exception in get_sql_results (#3111)
As caller expect it to raise an exception instead of returning
None.

Refs #3075
2017-08-01 22:38:52 -07:00
Maxime Beauchemin 62fcdf2a92 [explore] DatasourceControl to pick datasource in modal (#3210)
* [explore] DatasourceControl to pick datasource in modal

Makes it easier to change datasource, also makes it such that the list
of all datasources doesn't need to be loaded upfront.

* Adding more metadata
2017-08-01 12:08:00 -07:00
Maxime Beauchemin 48821b5101 [sqllab] fix UI shows 'The query returned no results' momentarily (#3214)
this is visible when running async queries between the fetching and
success state as the rows are getting cached in the component
2017-08-01 10:26:13 -07:00
Maxime Beauchemin 3b129253a3 [explore] nvd3 sort values in rich tooltip (#3197) 2017-08-01 10:25:52 -07:00
Maxime Beauchemin 48760849ec [sqllab/cosmetics] add margin-top for labels in query history (#3222) 2017-08-01 10:25:13 -07:00
Xingze Zhang 9c1ca07c40 [docs] update url in CONTRIBUTING.md (#3212) 2017-08-01 08:54:35 -07:00
Maxime Beauchemin 774ad45efb [bugfix] capture Hive job_id pre-url transformation (#3213) 2017-07-31 22:22:08 -07:00
Xingze Zhang 299e9ce6b8 fix issue 3204 (#3205) 2017-07-31 12:24:19 -07:00
Maxime Beauchemin 219f33f0d1 Speed up JS build time (#3203)
Also bumping a few related libs
2017-07-28 17:34:09 -07:00
Andrew Pariser 58a704b84c Autofocus search input in VizTypeControl modal onEnter (#2929) 2017-07-28 14:57:24 -07:00
Rogan b58cfbcb91 add combine config for metrics in pivot table (#3086)
* add combine config for metrics in pivot table

* change method to stack/unstack

* update backendSync
2017-07-28 14:16:38 -07:00
Brian Wolfe 1e325d9645 [druid] Allow custom druid postaggregators (#3146)
* [druid] Allow custom druid postaggregators

Also, fix the postaggregation for approxHistogram quantiles so it adds
the dependent field and that can show up in the graphs/tables.

In general, postAggregators add significant power, we should probably
support including custom postAggregators. Plywood has standard
postAggregators here, and a customAggregator escape hatch that allows
you to define custom postAggregators.

This commit adds a similar capability for Superset and a additional
field/fields/fieldName breakdown of the typical naming for dependent
aggregations, which should make it significantly easier to develop
approxHistogram and custom postAggregation-required dashboards.

* [druid] Minor style cleanup in tests file.

* [druid] Apply code review suggestions

* break out CustomPostAggregator into separate class. This just cleans
  up the creation of the postaggregator a little bit.
* minor style issues.
* move the function around so the git diff is more readable
2017-07-28 11:45:59 -07:00
Maxime Beauchemin ad5a4389a2 Adding 'apache' to docs (#3194) 2017-07-28 11:42:01 -07:00
Maxime Beauchemin e4fba0ffb7 [bugfix] fix merge conflict that broke Hive support (#3196) 2017-07-27 21:34:15 -07:00
Maxime Beauchemin e584a9673f Add BigQuery engine specifications (#3193)
As contributed by @mxmzdlv on issue #945
2017-07-27 14:01:13 -07:00
Maxime Beauchemin b888802e05 [sqllab] improve Hive support (#3187)
* [sqllab] improve Hive support

* Fix "Transport not open" bug
* Getting progress bar to show
* Bump pyhive to 0.4.0
* Getting [Track Job] button to show

* Fix testzz
2017-07-27 14:00:19 -07:00
Maxime Beauchemin 25c599d040 Escaping the user's SQL in the explore view (#3186)
* Escaping the user's SQL in the explore view

When executing SQL from SQL Lab, we use a lower level API to the
database which doesn't require escaping the SQL. When going through
the explore view, the stack chain leading to the same method may need
escaping depending on how the DBAPI driver is written, and that is the
case for Presto (and perhaps other drivers).

* Using regex to avoid doubling doubles
2017-07-27 09:47:31 -07:00
Riccardo Magliocchetti fb866a937b Bump cryptography to 1.9 (#3065)
As 1.7.2 doesn't compile here with openssl 1.1.0f
2017-07-26 14:11:11 -07:00
Fokko Driesprong aa95e03eb9 Fix the segment interval for pulling metadata (#3174)
The end of the interval would be on the truncated today date, which
means that you will exclude today. If your realtime ingestion job
runs shorter than a day, the metadata cannot be pulled from the
druid cluster.
2017-07-26 09:28:08 -07:00
Maxime Beauchemin cf1d0f38ad [bugfix] visualize flow error: 'Metric x is not valid' (#3181)
The metric name in the frontend doesn't match the one generated on the
backend. It turns out the explore view will default to the first
metric so specifying one isn't needed.
2017-07-26 09:22:25 -07:00
Maxime Beauchemin fca982c609 [bugfix] fix bar order (#3180) 2017-07-26 09:22:03 -07:00
Riccardo Magliocchetti 747bf80474 docs: fixup installation examples code indentation (#3169) 2017-07-26 09:20:06 -07:00
Dmitry Goryunov 4f7fd65c8b add Zalando to the list of organizations (#3171) 2017-07-26 08:32:06 -07:00
timfeirg 6045063e78 fix hive.fetch_logs (#2968) 2017-07-25 21:43:19 -07:00
Maxime Beauchemin 0ec9cd4ad2 [bugfix] numeric value for date fields in table viz (#3036)
Bug was present only when using the NOT GROUPED BY option

fixes https://github.com/ApacheInfra/superset/issues/3027
2017-07-25 21:30:40 -07:00
Rich @ RadICS 4268513653 Add 'show/hide totals' option to pivot table vis (#3101) 2017-07-25 21:11:38 -07:00
Rogan 7654eef110 add title description to model view (#3045)
* add title description to model view

* add missing import
2017-07-25 21:06:34 -07:00
Rogan b301ba1f57 Datasource cannot be empty (#3035) 2017-07-25 21:05:31 -07:00
Maxime Beauchemin 95509f2000 [bugfix] only filterable columns should show up in FilterBox list (#3105)
* [bugfix] only filterable columns should show up in FilterBox list

* Touchups
2017-07-25 20:50:41 -07:00
Maxime Beauchemin 49ab09101b Fixing the damn build (#3179)
* Fixing the build

* Going deeper
2017-07-25 13:57:29 -07:00
Chris Williams 40d9e15126 Add event-flow visualization (#3102)
* [event-flow] add event flow visualizaton type from @data-ui/event-flow.

* [event-flow] update vis thumbnail

* [event-flow] update row limit label, remove duplicate chart controls

* [dependencies] add @data-ui/event-flow 0.0.2

* [linting] fix multiple imports

* [deps] bump mapbox-gl and react-map-gl to fix build

* [event-flow] bump to 0.0.3 for es2015 + stage-0 babel presets

* [deps] revert mapbox version bumps

* [event-flow] update png, bump to newest version, address reviewer comments, add min event count form.

* [event-flow] pin version

* [event-flow][spec] add test for coveralls

* [event-flow] revert spec
2017-07-21 16:29:25 -07:00
Maxime Beauchemin a141695b2b Prevent people from deleting datasources that have associate slices (#3163) 2017-07-19 16:24:20 -07:00
Maxime Beauchemin d01e67a159 More logging to csv endpoint (#3164) 2017-07-19 15:59:30 -07:00
Maxime Beauchemin c34df3eea4 [bugfix] SQLA instance has been deleted (#3159)
Related Msg:
sqlalchemy.orm.exc.ObjectDeletedError: Instance '<PermissionView at
0x7f10306b0e90>' has been deleted, or its row is otherwise not present.
2017-07-19 01:35:00 -07:00
luc 56bcbb0f8e add douban to the orgs. (#3157) 2017-07-19 01:18:34 -07:00
Maxime Beauchemin 51f1aa3106 [docs] use yarn in CONTRIBUTING.md (#3150)
* [docs] use yarn in CONTRIBUTING.md

* Updating badges
2017-07-19 01:17:56 -07:00
Maxime Beauchemin d7e419127c [bugfix] fails on None view_menu (#3155)
* [bugfix]  fails on None view_menu

* Update coveralls token
2017-07-18 19:42:20 -07:00
Grace Guo 27fab0d54f allow user press Enter key to end editing title (#3112) 2017-07-17 08:58:10 -07:00
Maxime Beauchemin 091e93c831 [minor] change tooltip on 'Edit slice properties' (#3116)
* [minor] change tooltip on 'Edit slice properties'

* Upgrading npm version for travis

* Bumping node version to most recent
2017-07-16 22:29:30 -07:00
Maxime Beauchemin bb6b2da267 Prevent SQLA warning related to SQLALCHEMY_TRACK_MODIFICATION (#3133) 2017-07-16 22:02:22 -07:00
Shao-Yen "Fred" Cheng 7abe2d5eee [#3137] Use state.datasource.type instead of state.datasource_type when rendering ControlPanelsContainer (#3138) 2017-07-16 21:04:34 -07:00
Maxime Beauchemin 7b015faae9 [heatmap] basic non empty validation (#3119) 2017-07-15 20:07:57 -07:00
Ke Zhu e834154030 Fixes #3134 by correct response content-type of /testconn (#3135) 2017-07-15 09:52:37 -07:00
丁桂涛 256a521bf1 [Celery] fix the celery worker concurrency settings (#3126) 2017-07-14 09:44:41 -07:00
Maxime Beauchemin a626f994bf [CLI] Improve the missing perm creation logic (#3118)
I don't think this worked as intended
2017-07-13 15:53:20 -07:00
Maxime Beauchemin 76dda688b1 Using yarn instead of npm install (#3120) 2017-07-13 15:16:39 -07:00
Grace Guo 163a6a20e5 clarify Superset different timeout config (#3044)
* clarify different timeout configuration for superset
2017-06-30 15:47:37 -07:00
Maxime Beauchemin 3d136aa0a4 Update docs links on README 2017-06-28 06:27:51 -07:00
Grace Guo ff3057de5d fix default checkbox alignment (#3042) 2017-06-26 18:06:12 -07:00
Maxime Beauchemin 7045018d86 New chart type : Chord Diagrams (#3013) 2017-06-26 16:44:47 -07:00
Maxime Beauchemin a55f963e52 [bugfix] issue creating separators & markup slices (#3041) 2017-06-26 11:00:21 -07:00
fabianmenges 8dfe2b70b2 Bug fix: Datasource -> Slice relationship (#3011) 2017-06-22 17:30:09 -07:00
Maxime Beauchemin fdbb569c3e 0.18.5 2017-06-22 15:46:09 -07:00
Maxime Beauchemin cc3e63f1de [docs] adding info on how to create new viz 2017-06-22 12:37:42 -07:00
Grace Guo a48e246aa0 add test coverage for sql lab components (#3022) 2017-06-22 10:31:13 -07:00
Maxime Beauchemin 6eba6cac0b [hotfix] xAxis broken on time series viz 2017-06-21 16:35:50 -07:00
Maxime Beauchemin bd706ebbd1 Fixing image sizes for horizon and country_map 2017-06-21 14:34:56 -07:00
Maxime Beauchemin abbf138cfb Bumping SQLLAB_ASYNC_TIME_LIMIT_SEC default config to 6 hours 2017-06-21 14:16:53 -07:00
Grace Guo de346a3eba CONTRIBUTING: add python unittes setup (#3021) 2017-06-21 12:52:04 -07:00
Maxime Beauchemin 99e1de58bc A set of minor fixes (#3014) 2017-06-21 12:09:49 -07:00
Maxime Beauchemin 5344a80535 Bumping flask-appbuilder to 1.9.1 2017-06-21 11:32:41 -07:00
Maxime Beauchemin 0b09a74d37 Downgrading celery to 3.1.25
https://github.com/celery/celery/issues/3932 is a blocker for Airbnb
2017-06-21 11:29:22 -07:00
Riccardo Magliocchetti e21745ac9d CONTRIBUTING: ask to quote python stacktraces (#3017) 2017-06-21 10:12:34 -07:00
Maxime Beauchemin 593861eac6 [bugfix] fix metrics/metric control default (#3009)
We should pick an arbitrary metric by default. This broke when
improving the metrics selector recently.
2017-06-21 09:31:29 -07:00
Maxime Beauchemin 53dead9c29 Revert "Bumping FAB to 1.9.1"
This reverts commit f64e2ba7d5.
2017-06-20 22:25:58 -07:00
Maxime Beauchemin f64e2ba7d5 Bumping FAB to 1.9.1 2017-06-20 21:52:16 -07:00
Benjamin Yolken 80515d2a92 Revert change in npm run build command (#3012) 2017-06-20 21:34:17 -07:00
Maxime Beauchemin 4d72afb54b Adding missing dependency and linting webpack.js (#3008) 2017-06-20 14:04:36 -07:00
Maxime Beauchemin 06fcaa3095 Stabilizing Celery / SQL Lab (#2981)
* upgrade celery to 4.0.2
* using Redis for unit tests (sqla broker not supported in Celery 4)
* Setting Celery's soft_time_limit based on `SQLLAB_ASYNC_TIME_LIMIT_SEC` config
* Better error handling in async tasks
* Better statsd logging in async tasks
* show [pending/running] query status in Results tab
* systematically using sqla NullPool on worker (async) to limit number
  of database connections
2017-06-20 13:55:03 -07:00
Benjamin Yolken de88764e93 Misc. tweaks to improve webpack performance (#2994)
* Misc. tweaks to improve webpack performance

* Fix code climate style issues
2017-06-20 08:40:33 -07:00
Rogan 9051e1f3e2 translations extracted by pybabel (#2990) 2017-06-19 23:58:39 -07:00
Andrew Chen ba93e6a2d1 Fix importing config from env var (#2983) 2017-06-19 23:51:34 -07:00
Maxime Beauchemin 7e5e229f48 Improving TextAreaControl to support code and modal (#2988) 2017-06-19 22:27:16 -07:00
Maxime Beauchemin b9915e7ecf [pivot viz] fix formatting and verbose names (#2957)
* [pivot viz] fix formatting and verbose names

* Fixing tests
2017-06-19 22:10:54 -07:00
Maxime Beauchemin 3e51c61dbf [explore] improve bubble viz (#2927)
* [explore] improve bubble viz

* allow for custom axis formatters
* reorg the control panels

* Addressing comments
2017-06-19 22:09:09 -07:00
Grace Guo 591e512327 add test coverage for SqlEditorLeftBar (#2984) 2017-06-19 11:39:32 -07:00
Grace Guo fc5db474b7 fix is_owner check (#2985) 2017-06-19 10:57:30 -07:00
Maxime Beauchemin c083aec8e8 [FilterBox] use column verbose names (#2970) 2017-06-17 09:46:27 -07:00
Maxime Beauchemin 1ce3b81d01 Imporving the README 2017-06-16 23:35:46 -07:00
Maxime Beauchemin 89cd10b3ce [bufix] superset views not getting from_dttm-to_dttm in template context (#2978) 2017-06-15 22:49:55 -07:00
Maxime Beauchemin 712297480c [CLI] adding 'superset flower' command (flower is a UI for Celery) (#2963)
* [CLI] adding 'superset flower' command (flower is a UI for Celery)

* Addressing comments
2017-06-15 17:02:17 -07:00
Alanna Scott 6ddccaaa9b tests for saveQuery, fetchQueryResults, runQuery, postStopQuery (#2979) 2017-06-15 15:35:31 -07:00
Grace Guo 1dcf2c4326 fix local state 'columns' (#2896)
* fix local state 'columns'
* fix method name per code review
2017-06-15 15:30:13 -07:00
Alanna Scott f0a8ea644b test props on alert wrapper (#2977) 2017-06-15 14:18:34 -07:00
Grace Guo fb6ef26a24 add test coverage for ResultSet component (#2972)
* add test coverage for ResultSet component
2017-06-15 13:51:09 -07:00
Alanna Scott 00b34d7fbd [js-testing] add tests for explore actions (#2976)
* move to explore folder and delete explorev2 folder

* add tests for fetchDatasourceMetadata

* tests for fetchDatasources, fetchDatasourceMetadata

* use $.ajax for fetch dashboards and write test
2017-06-15 12:26:22 -07:00
Grace Guo 8329ea2b9b Edit Dashboard title and Slice title in place (#2940)
* Edit Dashboard title and Slice title in place

Add EditableTitle component into Dashboard and Explore view to support edit title inline.
2017-06-14 12:52:12 -07:00
Alanna Scott da0a87a735 add test for ControlPanelSection (#2961) 2017-06-14 10:12:29 -07:00
Maxime Beauchemin 7aeca39c46 [js] remove unused npm dependencies (#2952) 2017-06-13 22:08:13 -07:00
Alanna Scott e1751c065c add new slice test (#2939)
* sort explicitly on label

* add simple test for /slicemodelview/add endpoint

* make comments and method names more clear

* fix test name

* be more explicit, test status_code
2017-06-13 09:44:26 -07:00
Alanna Scott e5151cb915 [js] version js file names using webpack chunkhash (#2951)
* get compiled js file names

* make manifest available as template var

* use script src directly to avoid flash of unstyled content in the case of csstheme.js

* linting

* attempt to fix tests

* exception

* print the path when no manifest file found

* handle case when manifest.json is not present for some reason, or in the case of tests
2017-06-13 09:44:00 -07:00
Maxime Beauchemin 24e3c7f89a [dashboard] notify instead of modal onSave (#2941)
* [dashboard] notify instead of modal onSave

* Addressing comments
2017-06-12 21:04:46 -07:00
Maxime Beauchemin 987cb9978d [hotfix] bumping pandas version to 0.20.2 2017-06-13 00:03:33 +00:00
Nishant Bangarwa 274d21795f Fix handling of Chunked requests (#1742)
* Fix handling of Chunked requests

Add fix for handling chunk encoding requests.
If ENABLE_CHUNK_ENCODING is set to true, for requests with transfer
encoding set to true. It will set wsgi.input_terminated to true which
tells werkzeug to ignore content-length and read the stream till the
end.

 break comment in multiple lines

* remove debug print logging
2017-06-12 13:46:14 -07:00
Maxime Beauchemin 0d2c2b0681 [table viz] get metrics to right-align (#2943)
Moved the histogram to be rooted on the right side as well

fixes https://github.com/airbnb/superset/issues/2933
2017-06-12 13:35:00 -07:00
Maxime Beauchemin 1eff48facb Bumping some dependencies (#2945)
Most notably Flask AppBuilder to 1.9.0
2017-06-12 13:21:14 -07:00
timfeirg 17bd7512ff remove reference for CSRF_ENABLED, and use WTF_CSRF_ENABLED instead (#2946) 2017-06-12 13:17:59 -07:00
Maxime Beauchemin 16141ecb94 [explore] improve metric(s) and groupby(s) controls (#2921)
* [explore] improve metric(s) and groupby(s) controls

- surface verbose_name, description & expression in controls
- [table viz] surface verbose name in table header

* Fixing tests

* Addressing comments

* Fixing tests (once more)
2017-06-09 11:29:55 -07:00
Alanna Scott 34f381bc25 v 0.18.5-alpha.3 2017-06-08 11:21:07 -07:00
Alanna Scott 24292dbc11 add new slice form improvements (#2928)
* dont set first datasource as default

* not used

* add a disabled class if datasource is not selected

* sort datasources alphabettically

* make btn disabled is no datasource is selected

* fix linting
2017-06-08 10:49:02 -07:00
Maxime Beauchemin 24a2f5b8f0 [big number] various improvements (#2912)
* [big number] various improvements

* dynamic number of X axis ticks based on width to prevent label overlap
* corrected overflow on the x axis
* improved tooltips (precise arrow and visible data point circle on hover)

* Fixing tooltips in heatmap viz
2017-06-08 08:50:30 -07:00
Maxime Beauchemin 0e6f754af9 Fix #2814 - json serialization edge case (#2924) 2017-06-08 08:49:01 -07:00
Alanna Scott fb85f008fa v 0.18.5-alpha.2 2017-06-07 23:12:16 -07:00
Maxime Beauchemin 85fb4a933d [hotfix] only apply SQLAlchemy limit where needed
Observed issue in dev environment where SQL queries were emitted with
`LIMIT 0`. This fix addresses it.
2017-06-07 22:56:56 -07:00
Alanna Scott d3ace6d63f [js-testing] type checking for dates.js (#2893)
* tests for dates.js

* linting

* test fduration output

* ignore warnings in code climate

* use eslint-2 otherwise defaults to eslint-3

* test eslint 1

* remove channel rule

* disable checks

* checks for eslint engine
2017-06-07 22:27:21 -07:00
Alanna Scott 205eed8350 add more tests for Timer (#2889) 2017-06-07 22:12:07 -07:00
Alanna Scott 5bf40e2256 [slices] add simple new slice form (#2800)
* initial structure for add new slice page

* simplify add slice form

* add a test

* fix long line

* use underscore for template name

* fix controls path

* fix vis types select
2017-06-07 22:08:59 -07:00
Denny Biasiolli 7c28e4eace updating react-alert dependency to v2.0.1 (#2923) 2017-06-07 12:07:15 -07:00
Xiao Hanyu a882f7a55f Ignore pyenv files in .gitignore. (#2906)
Some python developers use Python version manager to create and switch Python
enviroments, pyenv (http://github.com/yyuu/pyenv) is one of the version managers.

When you use `pyenv local x.x.x`, `pyenv` will put a `.python-version` file in
project directory, which, in general, should not be commited to git.
2017-06-06 23:44:57 -07:00
Maxime Beauchemin 9aba77db74 0.18.5-alpha.1 2017-06-06 12:22:27 -07:00
Grace Guo c9e5fbb09b [dashboard]Add timeout message on Dashboard view (#2910)
Same as explore view, if query takes > 45 seconds not returned, we will show Query timeout warning message. Otherwise user will see 504 Gateway timeout error.
2017-06-06 12:05:05 -07:00
Maxime Beauchemin 65f25a1e5a [explore] fix IN filter on numeric field (#2908) 2017-06-05 17:41:08 -07:00
Josh Walters e0dd5d9d1d Removed __time column from druid metadata refresh, added long and double schema support (#2911)
* Removed __time column from load, added long/double schema support

* Format fix
2017-06-05 17:40:47 -07:00
Grace Guo 737db25b6e fix visualize modal checkbox alignment (#2897)
in Visualize Modal, table headers are left-aligned. So columns checkboxes should also be left-aligned.
2017-06-05 10:38:42 -07:00
Maurizio Napolitano bea702269c update for the italian translation (#2902)
* italian translation

* update for the italian translation
2017-06-04 18:03:34 -07:00
Maxime Beauchemin d78da8a9bf [docs faq] how do I add new columns to an existing table (#2888) 2017-06-04 18:02:10 -07:00
Riccardo Magliocchetti ed8153ff8b update contributing a bit re contributing code (#2903)
* CONTRIBUTING: document starter_task label

* CONTRIBUTING: PR should work travis python versions

* CONTRIBUTING: move PR guidelines at the top

* CONTRIBUTING: no need to open a new pr after review
2017-06-04 18:00:33 -07:00
Riccardo Magliocchetti f7ce100180 travis: no need to install python3.5 (#2904)
As we are testing on 3.4 and 2.7.
2017-06-04 17:56:43 -07:00
Maxime Beauchemin 72291d65c9 0.18.4 2017-06-04 17:54:31 -07:00
Grace Guo 0d3f57a78d fix a linting error (#2895) 2017-06-02 15:52:39 -07:00
Alanna Scott 04fb0e2c2d fix js error on explore view (#2894)
* fix js error on explore view

* bump version
2017-06-02 14:36:51 -07:00
Maxime Beauchemin 155fec0a6b Updating CHANGELOG.md to 0.18.3 2017-06-02 13:06:21 -07:00
Maxime Beauchemin d90044cd52 0.18.3 2017-06-02 08:27:56 -07:00
fabianmenges 62bd4eb211 Converting filter argument to number if column is number (#2891) 2017-06-02 08:13:46 -07:00
Alanna Scott 677c427b16 delete DataPreviewModal, it doesn't get used anywhere (#2882) 2017-06-01 14:30:15 -07:00
justinr1234 52b0716571 [bugfix] allow database macro to work when CSRF is diabled (#2884) 2017-06-01 09:41:55 -07:00
Xiao Hanyu 04b662ea11 Fix a type error in rst' sub list. (#2881)
Sub list in rst requires a blank line above and below.

Ref:
- http://docutils.sourceforge.net/docs/ref/rst/restructuredtext.html#bullet-lists
2017-05-31 21:26:17 -07:00
Grace Guo db052b17ea Add visualize advise for long query (#2879)
in SqlLab view, if query takes over 45 seconds, we will show advise to store a summarized data set before user clicks on Visualize button.
This advise will not block Visualize button.

fixes https://github.com/airbnb/superset/issues/2733
2017-05-31 15:50:26 -07:00
Maxime Beauchemin e300273e71 [explore] adding y_axis_bounds to force Y axis bounds (#2878)
* [explore] adding y_axis_bounds to force Y axis

* Handling comments
2017-05-31 14:47:09 -07:00
Maxime Beauchemin c5f2eafc90 [explore] 'Save as' -> 'Save' as it can be used to overwrite (#2875)
* [explore] 'Save as' -> 'Save' as it can be used to overwrite

* Fix tests
2017-05-31 14:31:13 -07:00
Alanna Scott 90e4d6469d [js-testing] more tests for SelectControl (#2877)
* rename spec folder

* remove special handling for viz_type control since it now uses VizTypeControl

* add test for getOptions

* linting

* add test for cwp

* linting
2017-05-31 10:52:02 -07:00
Grace Guo 1e7773eb16 Improve visualize modal test coverage (#2811)
add unit tests for VisualizeModal component
2017-05-30 18:16:22 -07:00
Maxime Beauchemin 3c89c8cc46 0.18.3-alpha.3 2017-05-30 11:24:14 -07:00
Maxime Beauchemin 74086dae2b [bars] fix sort numeric bar on x axis (#2812) 2017-05-30 11:18:25 -07:00
Maxime Beauchemin 66403f1876 [explore] viz type selector as modal (#2787)
* [explore] viz type selector as modal

* Addressing comments

* Adressing comments
2017-05-30 11:05:18 -07:00
Maxime Beauchemin 3a4cd3ae24 Applying specified limit in bubble plot (#2815)
* Applying specified limit in bubble plot

* Keeping bubbles proportinate
2017-05-30 11:04:44 -07:00
Maxime Beauchemin 4ffc1f613e Fix filter values populating for views (#2816) 2017-05-30 10:51:34 -07:00
Maxime Beauchemin dfbba84400 0.18.3-alpha.2 2017-05-30 10:39:17 -07:00
Grace Guo 77864e6cf4 reduce clientside timeout limit (#2820)
it was set to 60 seconds. But it seems gateway will return 504 around 50 seconds.
Will reduce client side timeout limit to 45 seconds.
2017-05-25 16:07:02 -07:00
Maxime Beauchemin 4d12251806 [explore] include ControlHeader as part of Control interface (#2809)
* [explore] include ControlHeader as part of Control interface

* Adressing comments
2017-05-25 11:54:26 -07:00
Alanna Scott 0c9f9b695b [clarity/consistency] rename /explorev2/ -> /explore/ (#2802)
* rename /explorev2/ -> /explore/

* add redirect for existing explorev2 urls

* fix long line

* remove extra line

* fix missed ref in spec
2017-05-24 17:12:28 -07:00
Marek Vavruša a4a2bf7ae9 filter_box: allow creatable entries (#2804)
The reason is that it should be able to create arbitrary filters
over attributes with very high cardinality, where loading all
possible combinations into the filter box is infeasible,
e.g. IPv6 addresses.
2017-05-24 14:41:58 -07:00
Grace Guo d0a04cde49 apply redux for VisualizeModal (#2795)
* redux visualize modal

* redux visualize modal

- apply redux
- add unit test for connect container component
- fix lint error

* redux visualize modal

- apply redux
- add unit test for connect container component
- fix lint error
2017-05-24 11:58:54 -07:00
Maxime Beauchemin 69685b9dcc Fixing country maps (#2801) 2017-05-24 09:27:04 -07:00
ymatagne b308a3eb4e Added Country Map : New Visualization tools (#2708)
* feat(visualization): Create new visualization's tools that display country with geojson file. Currently only  france and Spain are loaded

* refacto(visualization): fix issues created by codeclimate

* refacto(visualization): fix issues created by travis for mysql databases

* refacto(visualization): fix issues created by codeclimate

* refacto(visualization): fix issues created by codeclimate

* refacto(visualization): fix issues created by codeclimate

* refacto(visualization): fix issues created by codeclimate

* fix(visualization): fix issues

* doc(visualization): Init visualization documentation

* doc(visualization): init visualization documentation for country

* fix(visualization): implement iso 3166-2 for id of country

* fix(visualization): implement iso 3166-2 for id of country

* doc(visualization): init visualization documentation for country

* fix(visualization): implement iso 3166-2 for id of country

* feat(country_map): add ukraine map in component

* fix(visualization): Test dont working and add color based on metrics

* refacto(visualization): fix issues for es6 and color component
2017-05-23 10:43:33 -07:00
yamdraco bfa40bd360 [hotfix] 'filter box from and to date filter #2649' (#2785) 2017-05-22 21:15:10 -07:00
ShengyaoQian b0e2904c24 Updating permission when refreshing druid datasource (#2655)
* Updating permission when refreshing druid datasource

* Adding test

* Fix style

* Deletion view_menu after db, table, cluster, ds deletion

* Update table model

* Linting

* Override _delete instead of post_delete

* fix

* lint

* fix multi delete

* fix

* Refactoring

* Amending
2017-05-22 16:41:32 -07:00
Maxime Beauchemin ce506bdf65 Logging a few more actions (#2783)
* Logging a few more actions

* adding statsd dep
2017-05-19 10:25:58 -07:00
Maxime Beauchemin 922cc037bf 0.18.3-alpha.1 2017-05-18 15:59:28 -07:00
Maxime Beauchemin 8252ada1f9 [docs] more details on how filters are applied (#2778) 2017-05-18 15:56:42 -07:00
Maxime Beauchemin a2d2f8bb8c Enable filter value autocomplete in examples (#2781) 2017-05-18 15:56:24 -07:00
Maxime Beauchemin 7c5f61d6a6 Adding some STATSD logging (#2715) 2017-05-18 15:25:09 -07:00
Maxime Beauchemin 841e18a08c [sql lab] make database ordering alphabetical in left panel (#2769) 2017-05-17 21:31:16 -07:00
Maxime Beauchemin dbc7fef7f5 [sql lab] fix user timestamp is off (#2774) 2017-05-17 15:34:19 -07:00
Maxime Beauchemin cbfe3cb2dc 0.18.2 2017-05-16 23:08:56 -07:00
Maxime Beauchemin 5fcd25def1 0.18.1-alpha.2 2017-05-16 21:58:02 -07:00
Maxime Beauchemin fe3f5f69ae [hotfix] 'No numeric types to aggregate' 2017-05-16 21:57:02 -07:00
Maxime Beauchemin 2395fbbdaa Adding end_result_backend_time to Query model (#2766)
This will help us keep track on how long it takes to push the data
into the results backend.
2017-05-16 20:34:38 -07:00
Grace Guo 960b26c7a2 Show clear and actionable query timeout error message (#2763)
* Show clear and actionable query timeout error message

1. Instead of waiting for a long time or server-side response 504 Gateway timeout, explore view now add a query timeout threshold. After timeout it will show specific querytimeout message.
2. fix alert box close button position.

* Show clear and actionable query timeout error message

1. Instead of waiting for a long time or server-side response 504 Gateway timeout, explore view now add a query timeout threshold. After timeout it will show specific querytimeout message.
2. fix alert box close button position.
3. fix a linting error.
2017-05-16 13:12:12 -07:00
Maxime Beauchemin 28ac3504d6 0.18.1-alpha.1 2017-05-16 00:03:47 -07:00
Maxime Beauchemin ecc00bdd26 [explore] a bit less margin in left panel (#2758)
* [explore] a bit less margin in left panel

* fix tests

* forcing react-select 1.0.0-rc.3
2017-05-16 00:02:37 -07:00
eeve e7946451d6 fixed 500 error when export dashboard (#2760)
https://github.com/airbnb/superset/blob/master/superset/views/core.py#L474

http://flask-appbuilder.readthedocs.io/en/latest/actions.html?highlight=action

```
@action("mulexport", __("Export"), __("Export dashboards?"), "fa-database")
    def mulexport(self, items):
        ids = ''.join('&id={}'.format(d.id) for d in items)
```
change to 
```
@action("mulexport", __("Export"), __("Export dashboards?"), "fa-database")
    def mulexport(self, items):
        if not isinstance(items, list):
            items = [items]
        ids = ''.join('&id={}'.format(d.id) for d in items)
```

fixed:
#2184
#2667
2017-05-15 21:33:07 -07:00
Anthony Bush 9b34600c8e Remove duplicate text (#2761) 2017-05-15 21:31:37 -07:00
Maxime Beauchemin 884610861b 0.18.0 2017-05-13 16:33:03 -07:00
yileic d9bd3d6460 fix percentage change viz (#2757) 2017-05-13 15:46:02 -07:00
Maxime Beauchemin 38375be5c3 Fix issues around % signs and Presto (#2755)
* Fix issues around % signs and Presto

* Fix mysql
2017-05-12 09:45:33 -07:00
Rich @ RadICS 91d951ac42 Change hardcoded references to 'User' security model to allow custom class override (#2728) 2017-05-12 09:37:24 -07:00
yileic d79a45ff32 add number format to pivot table (#2703)
* modify pivot table number format

* lint code

* lint code

* lint

* lint

* change variable name

* add number format to pivot table

* clean

* fix code climate
2017-05-11 20:34:07 -07:00
yileic 818251fc85 make margin consistent (#2753) 2017-05-11 20:31:05 -07:00
Maxime Beauchemin 75abd1f44a 0.18.0-alpha.4 2017-05-11 08:26:06 -07:00
Maxime Beauchemin f55df3b18b [sql lab] fix responsivity of grid (#2742)
* [sql lab] fix responsivity of grid

* Lint
2017-05-11 08:24:08 -07:00
Maxime Beauchemin 5dbfdefae8 [sql lab] fix partitionned table has no partitions (#2740) 2017-05-11 08:23:43 -07:00
Maxime Beauchemin e5584440ce Speed up all CRUD list views (#2747)
Load times on list view pages like Slices, Dashboards, Tables and Database
have grown to be terrible over time.

After a bit of digging, I found that the not specifying `search_columns`
in ModelViews actually means "all columns" and that for each filter,
FAB goes and fetches a list of all values to prepopulate the
filter dropdowns. That means that the list of tables would fetch all
slices and all users upfront which is horrible. Worse, database list
view would fetch all queries with is insane.

This picks a subset of columns for search/filters and changes the
default to show only 100 elements per page instead of 500
2017-05-11 08:22:30 -07:00
Grace Guo d5e9d5d045 fix auto select override pre-selected value bug (#2745)
auto select should only apply to cases where select control doesn't have pre-selected value prop. If select control has pre-selected value (passed in from value prop), auto select first avaliable options should not apply.
2017-05-10 17:27:43 -07:00
yileic 3208a014ff fix dual line chart margin (#2737) 2017-05-09 17:44:08 -07:00
Maxime Beauchemin 874c12ad2d 0.18.0-alpha.3 2017-05-09 16:14:16 -07:00
Maxime Beauchemin 22d8075c53 Making the stop button instantaneous (#2738) 2017-05-09 16:10:08 -07:00
Maxime Beauchemin baebba1159 0.18.0-alpha.2 2017-05-09 13:37:25 -07:00
Maxime Beauchemin 04748b4cda [SQL Lab] fix gamma metadata access (#2702) 2017-05-09 13:36:49 -07:00
Maxime Beauchemin a471afe206 [sql lab] improvements to the left panel (#2709)
* [sql lab] improvements to the left panel

* better error handling with error notifications
* table is added instantly with a loading image

* Fixing tests

* Fixed tests
2017-05-09 13:36:10 -07:00
Boris Hajduk 5d0a01d0d0 Decimal is a valid numeric type (#2720)
* Decimal is a valid numeric type

This will allow automatic creation of sum__ and avg__ metrics

* formatting for line length at 80 chars

* Reformating again, for the mandatory 79 chars maximum.
2017-05-08 22:19:52 -07:00
Maxime Beauchemin 9e1272e97c 0.18.0-alpha.1 2017-05-08 18:04:26 -07:00
Maxime Beauchemin aeebd8840d [table] fixing CSS glitches on table view (#2725)
Somehow the CSS trick we use to display histogram-type visual elements
in table views started showing some odd glitches since
what I believe was a not-so-recent version of webkit.

The bug is around the `linear-gradient` call under `background-image`
prop being used to show non-gradient or "hard" colors, while using
transparency.

I was able to find a workaround that addresses things in chrome by using
a fake [minimal] gradient instead of a flat color.
2017-05-08 17:59:23 -07:00
YOU 55d3b012e5 refactor: recentActions ajax call is redundant (#2722) 2017-05-06 21:27:40 -07:00
Maxime Beauchemin a6e1e18244 [sql lab] fix CREATE TABLE AS (#2719) 2017-05-06 21:23:55 -07:00
YOU 46d7a925bb chore: remove unused methods with invalid models.Query usage (#2721)
* fix: models.Query is not defined

* chore: remove unused Query and methods
2017-05-06 21:23:17 -07:00
Maxime Beauchemin 5929ab7689 [dashboard] fix missing datasource issue (#2718)
Addresses a bug that happens when rendering a dashboard for which
a datasource behind one of the slices has been deleted
2017-05-05 16:48:41 -07:00
graceguo-supercat fffb7b500a [sql lab]Add autoSelect (#2713)
In sql editor database dropdown list, we want to auto-select the first available option.
2017-05-05 11:00:06 -07:00
Maxime Beauchemin cb14640a82 Removing uneeded results_backends.py (#2717) 2017-05-04 23:41:10 -07:00
Maxime Beauchemin d65054e015 [sql lab] fix csv export where % in query (#2711)
* [sql lab] fix csv export where  in query

* Prgoress
2017-05-04 16:34:18 -07:00
Maxime Beauchemin 5d5060eca6 Remove unecessary handling of %% (#2714) 2017-05-04 14:11:10 -07:00
Marek Vavruša 9ff351532a Basic integration with ClickHouse (#1844)
* db_engine_specs: added engine spec for clickhouse

* models: group by time without join on subquery

if this is enabled, it will remove the subquery when grouping by time,
and group by time will be rewritten as group by timeslot, ...

this particularly fixes clickhouse backend

* docs: added clickhouse

* models: allow using secondary dttm columns as constraints

* superset/forms: configurable default slice since time

* superset/models: respect dialect quoting

* dttm handling, codeclimate tweaks
2017-05-03 13:57:39 -07:00
Songyan Ho 59a6f447ec Fix missing curUserId from SliderAdder.jsx (#2705) 2017-05-01 21:58:14 -07:00
Maxime Beauchemin 1887b5e934 0.17.6 2017-05-01 13:13:06 -07:00
Maxime Beauchemin 33758bfff5 0.17.6-alpha.2 2017-05-01 09:00:48 -07:00
Alanna Scott 2d5beb1f91 improve csrf expiration error handling (#2695)
* add message

* re run query on result set mount if there is session time out error
2017-05-01 08:59:44 -07:00
Justin Park 5fd0e7d028 [vis] bar values should match y axis format (#2701)
It passes the user yAxis format value to the totalValue function to render the label text accordingly
2017-05-01 08:59:02 -07:00
Songyan Ho ef0c4be067 Fix for referring specific svg (#2612)
* Fix for referring specific svg

* Remove trailing space
2017-04-30 11:08:40 -07:00
Maxime Beauchemin ac3aba7c7d [sql lab] visualization flow: fixing the groupby parameter (#2681) 2017-04-30 11:04:29 -07:00
yileic 0fdb57a181 fix (#2696) 2017-04-30 11:01:34 -07:00
Maxime Beauchemin 3e7b5df287 [explore] fix empty chart when changing viz type (#2698)
* [explore] fix empty chart when changing viz type

* Lint
2017-04-30 10:58:45 -07:00
Denny Biasiolli 3cd16cf368 Fix test's warnings (#2697)
* tests: adding required props to FilterableTable mockedProps

* tests: adding required prop `height` to QuerySearch mockedProps

* tests: adding required prop `height` to ResultSet mockedProps

* tests: adding required prop `height` to SqlEditorLeftBar mockedProps

* tests: fix warning in Timer component
2017-04-30 10:58:09 -07:00
Riccardo Magliocchetti a58adc862e Fix orm query in HiveEngineSpec.handle_cursor (#2699)
Fix #2643
2017-04-30 10:55:56 -07:00
yileic 7d88f80a9b hack to dynamically adjust y axis left margin (#2689)
* hack to dynamic adjust y axis margin

* merge into the previous hack

* render for both hack
2017-04-28 19:56:19 -07:00
yileic 09be02f70a fix x axis label (#2691) 2017-04-28 17:59:09 -07:00
alanmcruickshank 50fcdd3a34 Adding tails.com to inthewild (#2685) 2017-04-28 17:57:32 -07:00
Denny Biasiolli dee36491c5 Fix js warnings (#2693)
* react: using prop-types package to fix deprecated React.PropTypes property warning

https://facebook.github.io/react/warnings/dont-call-proptypes.html

* removing babel devDependency because has been deprecated in favor of babel-cli

this fixes a warning during `npm install`:
```
npm WARN deprecated babel@6.23.0:
In 6.x, the babel package has been deprecated in favor of babel-cli.
Check https://opencollective.com/babel to support the Babel maintainers
```

* js: setting ExploreActionButtons.queryEndpoint PropType as required

because it's required in the child component DisplayQueryButton

* js(tests): using object in expandedSlices prop type of SliceCell tests

* js(tests): adding required props to SqlEditor mockedProps

* js(tests): adding required prop editorHeight to TabbedSqlEditors mockedProps

* js: removing unused moments dependency
2017-04-28 17:56:29 -07:00
yileic 903612ac6c fix (#2692) 2017-04-28 15:16:55 -07:00
yileic ce705054fa fix a bug in 'getMaxLabelSize' and x axis label not shown problem (#2694)
* fix

* fix code climate
2017-04-28 15:14:04 -07:00
graceguo-supercat c589616883 [sql lab] Update event handler name (#2680)
Update SqlEditor database change event handler name to be more specific.
2017-04-28 11:42:48 -07:00
Riccardo Magliocchetti 58309f275f Mark a few more string for translation (#2651)
* Mark some more string for translations

Fix #2629

* Rebuild translations

* Please codeclimate
2017-04-26 21:57:56 -07:00
Tom Paine edf4e4f24e Update README.md (#2676)
Spelling
2017-04-26 21:57:11 -07:00
Maxime Beauchemin b3e0b5b586 Specifying cryptography version in install docs 2017-04-26 14:20:27 -07:00
Maxime Beauchemin 68802989bc Pinning cryptography lib to 1.7.2 2017-04-26 10:32:25 -07:00
Alanna Scott 70887d72e2 0.17.6-alpha.1 2017-04-25 22:13:29 -07:00
Maxime Beauchemin 1922225042 Alternate fix for #2665 (#2671)
* Alternate fix for #2665

* Addressing comments

* Fix doctest
2017-04-25 18:18:17 -07:00
Alanna Scott 0bdc3010d8 [vis] fix pivot table scrolling when using more than 1 groupy col (#2674)
* fix scrolling when more than 1 groupby

* generalize function arguments

* fix pivot table scrolling in js

* add padding rules back

* linting
2017-04-25 16:14:59 -07:00
robert-digit 1df37e6e4d add option for pulling favourited dashboards by username (#2661)
* add option for pulling favourited dashboards by username

add tests

* fix too many lines pep8 error
2017-04-24 20:48:25 -07:00
Alanna Scott e9ed416654 fix csrf error on import_dashboards (#2672) 2017-04-24 18:38:17 -07:00
Maxime Beauchemin 03c42b5b87 Showing slices on datasource edit form (#2645)
* Showing slices on datasource edit form

* fixing build
2017-04-24 17:40:34 -07:00
Maxime Beauchemin e055e6d2c2 Fixing PropTypes warning messages (#2670)
* Fixing PropTypes warning message

React recently started warning on the upcoming deprecation of
React.PropTypes, the new approach is to use the `prop-types`
npm package instead.

* Fixing the tests
2017-04-24 17:39:57 -07:00
Maxime Beauchemin 29780821e8 [druid] fixing the having clause in the explore view (#2648)
* [druid] fixing the having clause in the explore view

* Backend

* Lint

* Fixing tests
2017-04-24 16:31:16 -07:00
Maxime Beauchemin f10ee13901 [druid] fix FilterBox viz gets timestamps as values if granularity <> all (#2647) 2017-04-24 10:27:26 -07:00
Maxime Beauchemin cdfc4a35b2 Optimizing the standalone view (#2663)
The standalone view doesn't need to fetch the datasources asynchronously
to fill in the dataources dropdown, it also doesn't need to render any
of the controls.
2017-04-23 22:13:23 -07:00
yileic eb762c8bfe add the missing right bracket (#2662) 2017-04-22 12:36:47 -07:00
Riccardo Magliocchetti 83abfef830 superset: fix argument swap for SqliteEngineSpec.get_table_names (#2664)
Fix #2660
2017-04-22 12:35:39 -07:00
Maxime Beauchemin 54137ad023 Updating CHANGELOG 2017-04-21 14:15:21 -07:00
491 changed files with 273670 additions and 15801 deletions
+5
View File
@@ -5,6 +5,11 @@ engines:
enabled: false
eslint:
enabled: true
checks:
import/extensions:
enabled: false
import/no-extraneous-dependencies:
enabled: false
config:
config: superset/assets/.eslintrc
pep8:
+1 -1
View File
@@ -1 +1 @@
repo_token: eESbYiv4An6KEvjpmguDs4L7YkubXbqn1
repo_token: 4P9MpvLrZfJKzHdGZsdV3MzO43OZJgYFn
+5
View File
@@ -24,6 +24,8 @@ app.db
*.bak
.idea
*.sqllite
.vscode
.python-version
# Node.js, webpack artifacts
*.entry.js
@@ -32,3 +34,6 @@ node_modules
npm-debug.log
yarn.lock
superset/assets/version_info.json
# IntelliJ
*.iml
-2
View File
@@ -1,2 +0,0 @@
[pycodestyle]
max-line-length = 90
+1 -1
View File
@@ -102,7 +102,7 @@ evaluation=10.0 - ((float(5 * error + warning + refactor + convention) / stateme
good-names=i,j,k,ex,Run,_,d,e,v,o,l,x,ts
# Bad variable names which should always be refused, separated by a comma
bad-names=foo,bar,baz,toto,tutu,tata
bad-names=foo,bar,baz,toto,tutu,tata,d,fd
# Colon-delimited sets of names that determine each other's naming style when
# the name regexes allow several styles.
+6 -13
View File
@@ -1,38 +1,31 @@
language: python
services:
- redis-server
addons:
code_climate:
repo_token: 5f3a06c425eef7be4b43627d7d07a3e46c45bdc07155217825ff7c49cb6a470c
apt:
sources:
- deadsnakes
packages:
- python3.5
cache:
directories:
- $HOME/.wheelhouse/
env:
global:
- TRAVIS_CACHE=$HOME/.travis_cache/
- TRAVIS_NODE_VERSION="6.10.2"
matrix:
- TOX_ENV=flake8
- TOX_ENV=javascript
- TOX_ENV=pylint
- TOX_ENV=py34-postgres
- TOX_ENV=py34-sqlite
- TOX_ENV=py27-mysql
- TOX_ENV=py27-sqlite
before_install:
- npm install -g npm@'>=4.5.0'
before_script:
- mysql -e 'drop database if exists superset; create database superset DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci' -u root
- mysql -u root -e "DROP DATABASE IF EXISTS superset; CREATE DATABASE superset DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci"
- mysql -u root -e "CREATE USER 'mysqluser'@'localhost' IDENTIFIED BY 'mysqluserpassword';"
- mysql -u root -e "GRANT ALL ON superset.* TO 'mysqluser'@'localhost';"
- psql -c 'create database superset;' -U postgres
- psql -c "CREATE USER postgresuser WITH PASSWORD 'pguserpassword';" -U postgres
- psql -U postgres -c "CREATE DATABASE superset;"
- psql -U postgres -c "CREATE USER postgresuser WITH PASSWORD 'pguserpassword';"
- export PATH=${PATH}:/tmp/hive/bin
install:
- pip install --upgrade pip
- pip install tox tox-travis
- rm -rf ~/.nvm && git clone https://github.com/creationix/nvm.git ~/.nvm && (cd ~/.nvm && git checkout `git describe --abbrev=0 --tags`) && source ~/.nvm/nvm.sh && nvm install $TRAVIS_NODE_VERSION
script: tox -e $TOX_ENV
+711
View File
@@ -1,5 +1,716 @@
## Change Log
### 0.22.1
Fixes 0.22.0
### 0.22.0
Bad empty release
### 0.21.2 (2017/12/11 21:18 +00:00)
- [#3974](https://github.com/apache/incubator-superset/pull/3974) [Bugfix] `_add_filters_from_pre_query` doesn't handle dim specs (#3974) (@Mogball)
- [#4041](https://github.com/apache/incubator-superset/pull/4041) [API] Deprecate /update_role/ API endpoint (#4041) (@john-bodley)
- [#4030](https://github.com/apache/incubator-superset/pull/4030) resolve python2 str() issue (#4030) (@timifasubaa)
### 0.21.1
Bad-empty release
### 0.21.0 (2017/12/08 09:11 +00:00)
- [#4031](https://github.com/apache/incubator-superset/pull/4031) apply custom css for dashboard initially load (#4031) (@graceguo-supercat)
- [#3891](https://github.com/apache/incubator-superset/pull/3891) [BUGFIX]: Fixing dttm_sql_literal to use python_date_format when specified. (#3891) (@fabianmenges)
- [#3947](https://github.com/apache/incubator-superset/pull/3947) Add fastdom js dependency (#3947) (@mistercrunch)
- [#4015](https://github.com/apache/incubator-superset/pull/4015) Remove unused callbacks when setting state (#4015) (@betodealmeida)
- [#4017](https://github.com/apache/incubator-superset/pull/4017) Fixed finding postaggregations (#4017) (@Mogball)
- [#3941](https://github.com/apache/incubator-superset/pull/3941) New time_pivot visualization (#3941) (@mistercrunch)
- [#3959](https://github.com/apache/incubator-superset/pull/3959) Add type MONEY as numeric type (#3959) (@mistercrunch)
- [#3969](https://github.com/apache/incubator-superset/pull/3969) Add row_limit to heatmap controls (#3969) (@mistercrunch)
- [#4019](https://github.com/apache/incubator-superset/pull/4019) Add support of another DatabaseError format (#4019) (@dmigo)
- [#3975](https://github.com/apache/incubator-superset/pull/3975) asciifying http header for csv download; fixes #3952 (#3975) (@rumbin)
- [#4001](https://github.com/apache/incubator-superset/pull/4001) Add has_access to import_dashboard (#4001) (@timifasubaa)
- [#3999](https://github.com/apache/incubator-superset/pull/3999) [sql lab] fix position of 'save query' Popover (#3999) (@mistercrunch)
- [#4003](https://github.com/apache/incubator-superset/pull/4003) Call props.onChange only when closing filter (#4003) (@betodealmeida)
- [#3978](https://github.com/apache/incubator-superset/pull/3978) Adding YAML Import-Export for Datasources to CLI (#3978) (@fabianmenges)
- [#4009](https://github.com/apache/incubator-superset/pull/4009) Rollback bulk-delete of table columns (#4009) (@alanmcruickshank)
- [#4000](https://github.com/apache/incubator-superset/pull/4000) Add Datasource Name filter under slice list view (#4000) (@graceguo-supercat)
- [#3997](https://github.com/apache/incubator-superset/pull/3997) Alternate PR to #3970 (#3997) (@mistercrunch)
- [#3976](https://github.com/apache/incubator-superset/pull/3976) [doc] added setting X-Forwarded-Proto to https behind reverse proxy with ssl encryption; fixes #3655 (#3976) (@rumbin)
- [#3991](https://github.com/apache/incubator-superset/pull/3991) Create CODE_OF_CONDUCT.md (#3991) (@mistercrunch)
- [#3967](https://github.com/apache/incubator-superset/pull/3967) [Dashboard] fix a filter refresh bug and add Test (#3967) (@graceguo-supercat)
- [#3965](https://github.com/apache/incubator-superset/pull/3965) [docs] making it clear sqlite shouldn't be used in a cluster (#3965) (@mistercrunch)
- [#3957](https://github.com/apache/incubator-superset/pull/3957) [time series table] visual improvements (#3957) (@williaster)
- [#3958](https://github.com/apache/incubator-superset/pull/3958) Improving speed of dashboard import (#3958) (@michellethomas)
- [#3949](https://github.com/apache/incubator-superset/pull/3949) [Bugfix] Druid `run_query` dimensions part 3 + Unit tests (#3949) (@Mogball)
- [#3946](https://github.com/apache/incubator-superset/pull/3946) [country_map] use Albers USA projection (#3946) (@mistercrunch)
- [#3948](https://github.com/apache/incubator-superset/pull/3948) fix 'superset db history' (#3948) (@mistercrunch)
- [#3951](https://github.com/apache/incubator-superset/pull/3951) Allow underscores in slugs (#3951) (@michellethomas)
- [#3955](https://github.com/apache/incubator-superset/pull/3955) config: bring back sqlite default database (#3955) (@xrmx)
- [#3940](https://github.com/apache/incubator-superset/pull/3940) Add an "Edit Mode" to Dashboard view (#3940) (@mistercrunch)
- [#3920](https://github.com/apache/incubator-superset/pull/3920) Fixed branching condition with dimension spec (#3920) (@Mogball)
- [#3643](https://github.com/apache/incubator-superset/pull/3643) Import CSV (#3643) (@timifasubaa)
- [#3945](https://github.com/apache/incubator-superset/pull/3945) Fix call in Chart (#3945) (@mistercrunch)
- [#3933](https://github.com/apache/incubator-superset/pull/3933) minor filter select enhancements (#3933) (@kkalyan)
- [#3929](https://github.com/apache/incubator-superset/pull/3929) Make Table Columns & Metrics Bulk-deletable (#3929) (@alanmcruickshank)
- [#3922](https://github.com/apache/incubator-superset/pull/3922) [travis] Standardizing before_install (#3922) (@john-bodley)
- [#3923](https://github.com/apache/incubator-superset/pull/3923) Switched to span instead of textarea for copytoclipboard (#3923) (@Mogball)
- [#3924](https://github.com/apache/incubator-superset/pull/3924) Moved percent metrics to its own row (#3924) (@Mogball)
- [#3875](https://github.com/apache/incubator-superset/pull/3875) Revert "Filter out unavailable databases (#3875)" (#3918) (@mistercrunch)
- [#3913](https://github.com/apache/incubator-superset/pull/3913) [bugfix] remove quotes from Postgres time grains (#3913) (@mistercrunch)
- [#3915](https://github.com/apache/incubator-superset/pull/3915) Fix left padding in dashboard widgets (#3915) (@mistercrunch)
- [#3916](https://github.com/apache/incubator-superset/pull/3916) [cosmetic] remove border from table viz (#3916) (@mistercrunch)
- [#3912](https://github.com/apache/incubator-superset/pull/3912) When checking if you should renderTriggered make sure key exists in controls (#3912) (@michellethomas)
- [#3906](https://github.com/apache/incubator-superset/pull/3906) fix the schema-fetching problem for impala in sql_lab (#3906) (@xiaoyugit)
- [#3911](https://github.com/apache/incubator-superset/pull/3911) Add UK Metropolitan Districts and Isle of Man (#3911) (@alanmcruickshank)
- [#3904](https://github.com/apache/incubator-superset/pull/3904) Bumping webpack related deps (#3904) (@mistercrunch)
- [#3902](https://github.com/apache/incubator-superset/pull/3902) [bugfix] allow limiting word cloud (#3902) (@mistercrunch)
### 0.21.0rc2 (2017/11/20 17:18 +00:00)
- [#3903](https://github.com/apache/incubator-superset/pull/3903) Fixes default hanlding in Altered slice tag (#3903) (@mistercrunch)
- [#3910](https://github.com/apache/incubator-superset/pull/3910) Workaround pandas bug in datetimes with time zones (#3910) (@bolkedebruin)
- [#3583](https://github.com/apache/incubator-superset/pull/3583) [3541] Augmenting datasources uniqueness constraints (#3583) (@john-bodley)
- [#3895](https://github.com/apache/incubator-superset/pull/3895) [druid] Fixing issue 3894 multi-processing w/ Gunicorn (#3895) (@john-bodley)
- [#3897](https://github.com/apache/incubator-superset/pull/3897) [druid] Catch IOError when fetching Druid datasource time boundary (#3897) (@john-bodley)
- [#3899](https://github.com/apache/incubator-superset/pull/3899) [druid] Renaming refresh_async method (#3899) (@john-bodley)
- [#3884](https://github.com/apache/incubator-superset/pull/3884) Add datasource to the SliceAddView modal (#3884) (#3900) (@alanmcruickshank)
- [#3890](https://github.com/apache/incubator-superset/pull/3890) [dashboard bug]Instant control should take effect instantly (#3890) (@graceguo-supercat)
- [#3879](https://github.com/apache/incubator-superset/pull/3879) Allow users to specify label->color mapping (#3879) (@mistercrunch)
- [#3893](https://github.com/apache/incubator-superset/pull/3893) Only refreshing non instant filters on apply (#3893) (@michellethomas)
### 0.21.0rc1 (2017/11/17 17:33 +00:00)
- [#3896](https://github.com/apache/incubator-superset/pull/3896) [druid] Fix datasource column enumeration (#3896) (@john-bodley)
- [#3852](https://github.com/apache/incubator-superset/pull/3852) fix input height to match with react-select (#3852) (@graceguo-supercat)
- [#3887](https://github.com/apache/incubator-superset/pull/3887) Fixing the build's linting errors (#3887) (@mistercrunch)
- [#3851](https://github.com/apache/incubator-superset/pull/3851) A better looking favicon (#3851) (@mistercrunch)
- [#3876](https://github.com/apache/incubator-superset/pull/3876) Fix slug function (#3876) (@mistercrunch)
- [#3880](https://github.com/apache/incubator-superset/pull/3880) [table] show 'Time' column header instead of '__timestamp' (#3880) (@mistercrunch)
- [#3771](https://github.com/apache/incubator-superset/pull/3771) DECKGL integration - Phase 1 (#3771) (@mistercrunch)
- [#3843](https://github.com/apache/incubator-superset/pull/3843) Further refactoring around dashboards (#3843) (@mistercrunch)
- [#3877](https://github.com/apache/incubator-superset/pull/3877) [dashboard bug] Fix standalone slice (#3877) (@graceguo-supercat)
- [#3872](https://github.com/apache/incubator-superset/pull/3872) Add mailing list and move screenshot at the end of README (#3872) (@xrmx)
- [#3875](https://github.com/apache/incubator-superset/pull/3875) Filter out unavailable databases (#3875) (@dmigo)
### 0.20.6 (2017/11/15 05:26 +00:00)
- [#3865](https://github.com/apache/incubator-superset/pull/3865) [issue] Resolving issue 2530 (#3865) (@john-bodley)
- [#3809](https://github.com/apache/incubator-superset/pull/3809) [cache] Fixing cache key w/ merged extra filters (#3809) (@john-bodley)
- [#3869](https://github.com/apache/incubator-superset/pull/3869) Fixing an issue with stripping filter values (#3869) (@michellethomas)
- [#3862](https://github.com/apache/incubator-superset/pull/3862) [flake8] Updaing CONTRIBUTING.md (#3862) (@john-bodley)
- [#3866](https://github.com/apache/incubator-superset/pull/3866) [Dashboard bug] Fix merged filter param name (#3866) (@graceguo-supercat)
- [#3858](https://github.com/apache/incubator-superset/pull/3858) Fix cachedDttm prop type (#3858) (@graceguo-supercat)
- [#3847](https://github.com/apache/incubator-superset/pull/3847) [flake8] Resolving Q??? errors (#3847) (@john-bodley)
- [#3856](https://github.com/apache/incubator-superset/pull/3856) adding support for getting list of foreign tables for PostgreSQL (#3856) (@mike-schiller)
- [#3834](https://github.com/apache/incubator-superset/pull/3834) [Dashboard bug] Slice doesn't show loading icon when loading (#3834) (@graceguo-supercat)
- [#3857](https://github.com/apache/incubator-superset/pull/3857) [Dashboard bug]Fix userId prop in Explore view Save_Modal (#3857) (@graceguo-supercat)
- [#3850](https://github.com/apache/incubator-superset/pull/3850) [sql lab] minor cosmetic touchups on Run / Save buttons (#3850) (@mistercrunch)
- [#3849](https://github.com/apache/incubator-superset/pull/3849) [sqllab] fix wrong error msg (#3849) (@mistercrunch)
- [#3842](https://github.com/apache/incubator-superset/pull/3842) Add CHANGELOG.md entries for 0.20.0 to 0.20.5 (#3842) (@mistercrunch)
- [#3846](https://github.com/apache/incubator-superset/pull/3846) [flake8] Resolving F5?? errors (#3846) (@john-bodley)
- [#3841](https://github.com/apache/incubator-superset/pull/3841) [Dashboard bug] should reset chartAlert when start new query (#3841) (@graceguo-supercat)
- [#3510](https://github.com/apache/incubator-superset/pull/3510) Update setup.py (#3510) (@joriewong)
- [#3833](https://github.com/apache/incubator-superset/pull/3833) [Dashboard bug] Fix Cache status and dttm information display for each slice (#3833) (@graceguo-supercat)
- [#3837](https://github.com/apache/incubator-superset/pull/3837) [Dashboard bug] should reset chartAlert when start new query (#3837) (@graceguo-supercat)
- [#3836](https://github.com/apache/incubator-superset/pull/3836) run_tests.sh: call coveralls only on CI (#3836) (@xrmx)
- [#3838](https://github.com/apache/incubator-superset/pull/3838) [slice] Removing deprecated argument (#3838) (@john-bodley)
- [#3839](https://github.com/apache/incubator-superset/pull/3839) [viz] Fix payload force logic (#3839) (@john-bodley)
- [#3668](https://github.com/apache/incubator-superset/pull/3668) [Explore] Altered Slice Tag (#3668) (@Mogball)
- [#3813](https://github.com/apache/incubator-superset/pull/3813) [docs] add StatsD setup instructions (#3813) (@mistercrunch)
- [#3814](https://github.com/apache/incubator-superset/pull/3814) [flake8] Resolving E3?? errors (#3814) (@john-bodley)
- [#3831](https://github.com/apache/incubator-superset/pull/3831) Bump celery to 4.1.0 (#3831) (@mistercrunch)
- [#3805](https://github.com/apache/incubator-superset/pull/3805) [flake8] Resolve E1?? errors (#3805) (@john-bodley)
- [#3815](https://github.com/apache/incubator-superset/pull/3815) [docstring] Refining warm_up_cache comment (#3815) (@john-bodley)
- [#3822](https://github.com/apache/incubator-superset/pull/3822) First time fetching chart should not force refresh. (#3822) (@graceguo-supercat)
- [#3740](https://github.com/apache/incubator-superset/pull/3740) Basic German Translation (#3740) (@alanmcruickshank)
- [#3816](https://github.com/apache/incubator-superset/pull/3816) [flake8] Resolving E7?? errors (#3816) (@john-bodley)
- [#3817](https://github.com/apache/incubator-superset/pull/3817) [flake8] Resolving E4?? errors (#3817) (@john-bodley)
- [#3819](https://github.com/apache/incubator-superset/pull/3819) Added /healthcheck endpoint for integrations with envoy (#3819) (@hughhhh)
- [#3818](https://github.com/apache/incubator-superset/pull/3818) Fix typo in installation.rst (#3818) (@pswaminathan)
- [#3825](https://github.com/apache/incubator-superset/pull/3825) Fix misleading SQL Lab timeout error message (#3825) (@mistercrunch)
- [#3823](https://github.com/apache/incubator-superset/pull/3823) fix error message format when long query timeout (#3823) (@graceguo-supercat)
- [#3810](https://github.com/apache/incubator-superset/pull/3810) Make overflow important to allow scrolling on dashboard (#3810) (@michellethomas)
- [#3811](https://github.com/apache/incubator-superset/pull/3811) [flake8] Resolving F4?? errors (#3811) (@john-bodley)
- [#3812](https://github.com/apache/incubator-superset/pull/3812) [flake8] Resolving E2?? errors (#3812) (@john-bodley)
- [#3808](https://github.com/apache/incubator-superset/pull/3808) Making time table viz scrollable (#3808) (@michellethomas)
- [#3581](https://github.com/apache/incubator-superset/pull/3581) Dashboard refactory (#3581) (@graceguo-supercat)
- [#3801](https://github.com/apache/incubator-superset/pull/3801) Stamping version to 0.21.0dev (#3801) (@mistercrunch)
- [#3433](https://github.com/apache/incubator-superset/pull/3433) Allowing Leading and Trailing spaces in connection (#3433) (@ishpreet-singh)
- [#3796](https://github.com/apache/incubator-superset/pull/3796) Fixed single extraction dimension error (#3796) (@Mogball)
- [#3787](https://github.com/apache/incubator-superset/pull/3787) [flake8] Resolving C??? errors (#3787) (@john-bodley)
- [#3716](https://github.com/apache/incubator-superset/pull/3716) Update messages.json (#3716) (@magicansk)
- [#3784](https://github.com/apache/incubator-superset/pull/3784) [flake8] Resolving W??? errors (#3784) (@john-bodley)
- [#3797](https://github.com/apache/incubator-superset/pull/3797) [flake8] Resolve I??? errors (#3797) (@john-bodley)
- [#3789](https://github.com/apache/incubator-superset/pull/3789) Add Lyft and Twitter to list of companies (#3789) (@mistercrunch)
- [#3794](https://github.com/apache/incubator-superset/pull/3794) [time table] use sparkData values in tooltip (#3794) (@williaster)
- [#3793](https://github.com/apache/incubator-superset/pull/3793) Adding back iso and correctly filtering iso from contrib total (#3793) (@michellethomas)
- [#3788](https://github.com/apache/incubator-superset/pull/3788) Removing iso from data (#3788) (@michellethomas)
- [#3778](https://github.com/apache/incubator-superset/pull/3778) [flake8] Resolving F8?? errors (#3778) (@john-bodley)
- [#3785](https://github.com/apache/incubator-superset/pull/3785) Rename files to allow RPM build (#3785) (@SpyderRivera)
- [#3783](https://github.com/apache/incubator-superset/pull/3783) [falke8] Resolving F6?? errors (#3783) (@john-bodley)
- [#3529](https://github.com/apache/incubator-superset/pull/3529) [explore] using verbose_name in 'Time Column' control (#3529) (@mistercrunch)
- [#3654](https://github.com/apache/incubator-superset/pull/3654) [Performance] VirtualizedSelect for SelectControl and FilterBox (#3654) (@Mogball)
- [#3697](https://github.com/apache/incubator-superset/pull/3697) DI-1113. ADDENDUM. Authentication: Enable user impersonation for Superset to HiveServer2 using hive.server2.proxy.user (a.fernandez) (#3697) (@afernandez)
### 0.20.5 (2017/11/06 07:18 +00:00)
- [#3776](https://github.com/apache/incubator-superset/pull/3776) [flake8] Enabling flake8 linting (#3776) (@john-bodley)
- [#3774](https://github.com/apache/incubator-superset/pull/3774) [sql-lab] Fixing Run Query tooltip (#3774) (@john-bodley)
- [#3773](https://github.com/apache/incubator-superset/pull/3773) Fix dashboard export download (#3773) (@michellethomas)
- [#3767](https://github.com/apache/incubator-superset/pull/3767) [time table] add tooltip to sparkline (#3767) (@williaster)
- [#3748](https://github.com/apache/incubator-superset/pull/3748) Update to reflect new version of cryptography (#3748) (@SpyderRivera)
- [#3763](https://github.com/apache/incubator-superset/pull/3763) docs: reword the FAQ regarding table changes (#3763) (@xrmx)
- [#3764](https://github.com/apache/incubator-superset/pull/3764) add stackoverflow tag (#3764) (@dmigo)
- [#3759](https://github.com/apache/incubator-superset/pull/3759) Add dummy file to fix symlink (#3759) (@mistercrunch)
- [#3751](https://github.com/apache/incubator-superset/pull/3751) fix https://github.com/apache/incubator-superset/pull/3726 (#3751) (@graceguo-supercat)
- [#3750](https://github.com/apache/incubator-superset/pull/3750) Consolidate all translation config (#3750) (@alanmcruickshank)
- [#3726](https://github.com/apache/incubator-superset/pull/3726) Bumping react-select to rc10 (#3726) (@mistercrunch)
- [#3741](https://github.com/apache/incubator-superset/pull/3741) Fix has_table method (#3741) (@mxmzdlv)
- [#3736](https://github.com/apache/incubator-superset/pull/3736) Escape columns names for time grains - postgres (#3736) (@Ryanthegiantlion)
- [#3739](https://github.com/apache/incubator-superset/pull/3739) Fix 3657 (#3739) (@baldoalessandro)
- [#3733](https://github.com/apache/incubator-superset/pull/3733) Using indexOf instead of includes for isXAxisString (#3733) (@michellethomas)
- [#3723](https://github.com/apache/incubator-superset/pull/3723) bump react-bootstrap version (#3723) (@graceguo-supercat)
- [#3721](https://github.com/apache/incubator-superset/pull/3721) Add CRUD action to refresh table metadata (#3721) (@mistercrunch)
- [#3720](https://github.com/apache/incubator-superset/pull/3720) Validate JSON in slice's params on save (#3720) (@mistercrunch)
- [#3722](https://github.com/apache/incubator-superset/pull/3722) Fix box_plot NaN issue (#3722) (@mistercrunch)
- [#3715](https://github.com/apache/incubator-superset/pull/3715) Update messages.po (#3715) (@magicansk)
- [#3686](https://github.com/apache/incubator-superset/pull/3686) Missing the data of one province and two regions of China (#3686) (@roganw)
- [#3685](https://github.com/apache/incubator-superset/pull/3685) Fix the ISO code description of region/province/department (#3685) (@roganw)
- [#3662](https://github.com/apache/incubator-superset/pull/3662) Set logging level to debug for DummyStatsLogger (#3662) (@mistercrunch)
- [#3692](https://github.com/apache/incubator-superset/pull/3692) fixes for bugs in #3689 (#3692) (@Mogball)
- [#3703](https://github.com/apache/incubator-superset/pull/3703) add VIPKID to the orgs. (#3703) (@killpanda)
- [#3696](https://github.com/apache/incubator-superset/pull/3696) changed metric heading from h1 to h3 (#3696) (@Mogball)
- [#3713](https://github.com/apache/incubator-superset/pull/3713) [translation] added japanese support (#3713) (@xiaoyugit)
- [#3663](https://github.com/apache/incubator-superset/pull/3663) [minor] fix label showing description in time_table's URL (#3663) (@mistercrunch)
- [#3711](https://github.com/apache/incubator-superset/pull/3711) fix the slice permission issue after user click-edit new slice title (#3711) (@graceguo-supercat)
- [#3701](https://github.com/apache/incubator-superset/pull/3701) [form-data] Quoting form data (#3701) (@john-bodley)
- [#3698](https://github.com/apache/incubator-superset/pull/3698) fixing the datasource inconsistence but in visualize flow (#3698) (@graceguo-supercat)
- [#3683](https://github.com/apache/incubator-superset/pull/3683) [cleanup] removing print() artefacts (#3683) (@mistercrunch)
- [#3702](https://github.com/apache/incubator-superset/pull/3702) Add support for IE 11 for markup slices (#3702) (@jaylindquist)
- [#3693](https://github.com/apache/incubator-superset/pull/3693) defaultSort should be false when no sort is necessary (#3693) (@michellethomas)
- [#3586](https://github.com/apache/incubator-superset/pull/3586) [Feature] Percentage columns in Table Viz (#3586) (@Mogball)
- [#3652](https://github.com/apache/incubator-superset/pull/3652) DI-1113. Authentication: Enable user impersonation for Superset to HiveServer2 using hive.server2.proxy.user (a.fernandez) (#3652) (@afernandez)
- [#3664](https://github.com/apache/incubator-superset/pull/3664) [minor] fix padding in Time Table (#3664) (@mistercrunch)
- [#3678](https://github.com/apache/incubator-superset/pull/3678) unit tests for OptionDescription component (#3678) (@Mogball)
- [#3679](https://github.com/apache/incubator-superset/pull/3679) Avoid dividing by zero for sparkline in time table viz (#3679) (@michellethomas)
- [#3680](https://github.com/apache/incubator-superset/pull/3680) Sqllab error troubleshooting (#3680) (@timifasubaa)
- [#3653](https://github.com/apache/incubator-superset/pull/3653) Add a ColorPickerControl (#3653) (@mistercrunch)
- [#3642](https://github.com/apache/incubator-superset/pull/3642) [New Viz] Partition Diagram (#3642) (@Mogball)
- [#3665](https://github.com/apache/incubator-superset/pull/3665) Add description for running specific test (#3665) (@timifasubaa)
- [#3661](https://github.com/apache/incubator-superset/pull/3661) Making the sort order for metrics pull from fd for time table viz (#3661) (@michellethomas)
- [#3417](https://github.com/apache/incubator-superset/pull/3417) Make columns that return an exception on click unsortable. (#3417) (@aliavni)
- [#3651](https://github.com/apache/incubator-superset/pull/3651) Adding sort time table (#3651) (@michellethomas)
- [#3647](https://github.com/apache/incubator-superset/pull/3647) added aihello as superset user. (#3647) (@ganeshkrishnan1)
- [#3646](https://github.com/apache/incubator-superset/pull/3646) Fix #3612 - reverse sign in difference calculation (#3646) (@mistercrunch)
- [#3648](https://github.com/apache/incubator-superset/pull/3648) Fixing some warnings during tests (#3648) (@dennybiasiolli)
### 0.20.4 (2017/10/12 04:04 +00:00)
- [#3645](https://github.com/apache/incubator-superset/pull/3645) [Translations] Restored lost French translations (#3645) (@Mogball)
- [#3644](https://github.com/apache/incubator-superset/pull/3644) [sql lab] fix impersonation + template issue (#3644) (@mistercrunch)
- [#3641](https://github.com/apache/incubator-superset/pull/3641) Pin moment.js library since 2.19.0 creates problem (#3641) (@mistercrunch)
- [#3600](https://github.com/apache/incubator-superset/pull/3600) [time_table] adding support for URLs / links (#3600) (@mistercrunch)
- [#3626](https://github.com/apache/incubator-superset/pull/3626) Set tooltip to show extent of sparkData (#3626) (@michellethomas)
- [#3631](https://github.com/apache/incubator-superset/pull/3631) add explicit message display for 'Fetching Annotation Layer' error (#3631) (@graceguo-supercat)
- [#3637](https://github.com/apache/incubator-superset/pull/3637) [bugfix] Template rendering failed: '_AppCtxGlobals' object has no attribute 'user' (#3637) (@mistercrunch)
- [#3638](https://github.com/apache/incubator-superset/pull/3638) fix long title text wrapping in editable-title component (#3638) (@graceguo-supercat)
- [#3625](https://github.com/apache/incubator-superset/pull/3625) [minor] proper tooltip on ControlHeader's instant re-render trigger (#3625) (@mistercrunch)
- [#3634](https://github.com/apache/incubator-superset/pull/3634) add annotation option and a linear color map for heatmap viz. (#3634) (@xiaoyugit)
- [#3633](https://github.com/apache/incubator-superset/pull/3633) [bugfix] empty From date filter NoneType error (#3633) (@mistercrunch)
- [#3621](https://github.com/apache/incubator-superset/pull/3621) remove unused imports (#3621) (@xrmx)
- [#3611](https://github.com/apache/incubator-superset/pull/3611) fixing date/time filter keys (#3611) (@Mogball)
### 0.20.2 (2017/10/06 07:46 +00:00)
- [#3606](https://github.com/apache/incubator-superset/pull/3606) [bugfix] #3593 'Chart Options' panel is missing (#3606) (@mistercrunch)
- [#3601](https://github.com/apache/incubator-superset/pull/3601) Removing git artifact (#3601) (@mistercrunch)
- [#3599](https://github.com/apache/incubator-superset/pull/3599) [hotfix] fixing issues around new time_table viz (#3599) (@mistercrunch)
- [#3598](https://github.com/apache/incubator-superset/pull/3598) [hofix] work around circular deps (#3598) (@mistercrunch)
- [#3597](https://github.com/apache/incubator-superset/pull/3597) [time table] fix reversed ratio (#3597) (@mistercrunch)
- [#3508](https://github.com/apache/incubator-superset/pull/3508) [Feature/Bugfix] Datepicker and time granularity options to dashboard filters (#3508) (@Mogball)
- [#3596](https://github.com/apache/incubator-superset/pull/3596) updating react-alert dependency to v2.3.0 (#3596) (@dennybiasiolli)
- [#3577](https://github.com/apache/incubator-superset/pull/3577) [translations] generating missing strings (#3577) (@mistercrunch)
- [#3478](https://github.com/apache/incubator-superset/pull/3478) [Bugfix/Feature] Fixed slice render staggering on dashboard first load (#3478) (@Mogball)
- [#3543](https://github.com/apache/incubator-superset/pull/3543) New "Time Series - Table" visualization (#3543) (@mistercrunch)
- [#3587](https://github.com/apache/incubator-superset/pull/3587) [sql lab] fix numeric sort in data table (#3587) (@mistercrunch)
- [#3594](https://github.com/apache/incubator-superset/pull/3594) Fxing bug in label generation for multiple groupbys (#3594) (@fabianmenges)
- [#3591](https://github.com/apache/incubator-superset/pull/3591) update immutable.js to v3.8.2 (MIT license) (#3591) (@naoyak)
- [#3571](https://github.com/apache/incubator-superset/pull/3571) [Feature] Copy-to-clipboard button in View Query (#3571) (@Mogball)
- [#3585](https://github.com/apache/incubator-superset/pull/3585) Allow users to see query string when query returns no data (#3585) (@Mogball)
- [#3582](https://github.com/apache/incubator-superset/pull/3582) [Bugfix]: Explore view does not respect custom timeout. (#3582) (@fabianmenges)
- [#3584](https://github.com/apache/incubator-superset/pull/3584) Fixed creating new filter options in FilterBox (#3584) (@Mogball)
- [#3562](https://github.com/apache/incubator-superset/pull/3562) Added custom pasteSelect to handle paste events (#3562) (@Mogball)
- [#3569](https://github.com/apache/incubator-superset/pull/3569) Bumping React to 15.6.2 (MIT license) (#3569) (@mistercrunch)
### 0.20.1 (2017/10/03 07:04 +00:00)
- [#3576](https://github.com/apache/incubator-superset/pull/3576) v0.20.1 (#3576) (@mistercrunch)
- [#3572](https://github.com/apache/incubator-superset/pull/3572) After saving slice fixing redirect (#3572) (@michellethomas)
- [#3565](https://github.com/apache/incubator-superset/pull/3565) Added label+percent and label+value display options to pie chart (#3565) (@Mogball)
- [#3567](https://github.com/apache/incubator-superset/pull/3567) Removing yarn warnings during install (#3567) (@dennybiasiolli)
- [#3563](https://github.com/apache/incubator-superset/pull/3563) [nvd3] fix single metric showing up in legend (#3563) (@mistercrunch)
- [#3558](https://github.com/apache/incubator-superset/pull/3558) Add Pronto Tools to user list (#3558) (@zkan)
- [#3553](https://github.com/apache/incubator-superset/pull/3553) Minor documentation fix (#3553) (@gaborhermann)
- [#3545](https://github.com/apache/incubator-superset/pull/3545) CHANGELOG for 0.20.0 (#3545) (@mistercrunch)
- [#3534](https://github.com/apache/incubator-superset/pull/3534) Explore update button labels (#3534) (@timifasubaa)
- [#3547](https://github.com/apache/incubator-superset/pull/3547) Fixing missing messages.json file (#3547) (@mistercrunch)
### 0.20.0 (2017/09/28 04:26 +00:00)
- [#3528](https://github.com/apache/incubator-superset/pull/3528) try to fix problem that chrome window not opening after ajax requrest (#3528) (@graceguo-supercat)
- [#3521](https://github.com/apache/incubator-superset/pull/3521) Time Series Annotation Layers (#3521) (@graceguo-supercat)
- [#3526](https://github.com/apache/incubator-superset/pull/3526) [explore] fix cached tooltip (#3526) (@mistercrunch)
- [#3544](https://github.com/apache/incubator-superset/pull/3544) v0.20.0 (#3544) (@mistercrunch)
- [#3506](https://github.com/apache/incubator-superset/pull/3506) setup: bump pandas to 0.20.3 (#3506) (@xrmx)
- [#3066](https://github.com/apache/incubator-superset/pull/3066) Add support for column specific fillna to viz (#3066) (@xrmx)
- [#3537](https://github.com/apache/incubator-superset/pull/3537) docs: QUERY_TIMEOUT_THRESHOLD is gone (#3537) (@xrmx)
- [#3531](https://github.com/apache/incubator-superset/pull/3531) [style] no bold on dashboard widget headers (#3531) (@mistercrunch)
- [#3532](https://github.com/apache/incubator-superset/pull/3532) Break word on InfoTooltip (#3532) (@michellethomas)
- [#3473](https://github.com/apache/incubator-superset/pull/3473) Feature: Paired t-test table visualization (#3473) (@Mogball)
- [#3513](https://github.com/apache/incubator-superset/pull/3513) Feature: query string API endpoint (#3513) (@Mogball)
- [#3504](https://github.com/apache/incubator-superset/pull/3504) Feature: Display the verbose name for metrics within Charts and legend. (#3504) (@fabianmenges)
- [#3527](https://github.com/apache/incubator-superset/pull/3527) Druid refresh metadata performance improvements (#3527) (@Mogball)
- [#3466](https://github.com/apache/incubator-superset/pull/3466) Allow user update slice title in visualize flow (#3466) (@graceguo-supercat)
- [#3467](https://github.com/apache/incubator-superset/pull/3467) allow user update slice name in dashboard view (#3467) (@graceguo-supercat)
- [#3509](https://github.com/apache/incubator-superset/pull/3509) Add Table performance improvements (#3509) (@Mogball)
- [#3499](https://github.com/apache/incubator-superset/pull/3499) Add metric warning (#3499) (@michellethomas)
- [#3390](https://github.com/apache/incubator-superset/pull/3390) js translation -- performance improvment (#3390) (@graceguo-supercat)
- [#3491](https://github.com/apache/incubator-superset/pull/3491) Remove repeated line (#3491) (@timifasubaa)
- [#3497](https://github.com/apache/incubator-superset/pull/3497) Fix idna requirement (#3497) (@timifasubaa)
- [#3495](https://github.com/apache/incubator-superset/pull/3495) update contributing.md (#3495) (@timifasubaa)
- [#3500](https://github.com/apache/incubator-superset/pull/3500) Removing super() call from refactor (#3500) (@mistercrunch)
- [#3493](https://github.com/apache/incubator-superset/pull/3493) Adding missing future imports (#3493) (@mistercrunch)
- [#3494](https://github.com/apache/incubator-superset/pull/3494) Removing dependency on pythrifthiveapi (#3494) (@mistercrunch)
- [#3474](https://github.com/apache/incubator-superset/pull/3474) [heatmap] account for bounds = 0 (#3474) (@mistercrunch)
- [#3480](https://github.com/apache/incubator-superset/pull/3480) Improve code quality (#3480) (@timifasubaa)
- [#3434](https://github.com/apache/incubator-superset/pull/3434) Feature/Fix: Get a full times_series for your filter instead of Topn for each point in time (#3434) (@fabianmenges)
- [#3486](https://github.com/apache/incubator-superset/pull/3486) Getting datatype with its dialect (#3486) (@datinho)
- [#3404](https://github.com/apache/incubator-superset/pull/3404) Feature: "Impersonate user" setting on Datasource (#3404) (@dmigo)
- [#3484](https://github.com/apache/incubator-superset/pull/3484) Create CsvResponse to manage csv exports encoding (#3484) (@JulieRossi)
- [#3469](https://github.com/apache/incubator-superset/pull/3469) Better installation docs (#3469) (@mistercrunch)
- [#3475](https://github.com/apache/incubator-superset/pull/3475) viz: fix reversed stats_logger label (#3475) (@xrmx)
- [#3477](https://github.com/apache/incubator-superset/pull/3477) docs: athena can be installed from pypi (#3477) (@xrmx)
- [#3476](https://github.com/apache/incubator-superset/pull/3476) Miscvizcleanups (#3476) (@xrmx)
- [#3435](https://github.com/apache/incubator-superset/pull/3435) Adding hook for CSRF exempting flask views. (#3435) (@fabianmenges)
- [#3409](https://github.com/apache/incubator-superset/pull/3409) bugfix/3321 Ensure text appears on buttons inside tables (#3409) (@jeffcarey)
- [#3415](https://github.com/apache/incubator-superset/pull/3415) Simple grammar and update to link (#3415) (@SpyderRivera)
- [#3441](https://github.com/apache/incubator-superset/pull/3441) config: allow changing default options for writting csv (#3441) (@JulieRossi)
- [#3425](https://github.com/apache/incubator-superset/pull/3425) Add shopee to user list. (#3425) (@xiaohanyu)
- [#3458](https://github.com/apache/incubator-superset/pull/3458) Fixed filter removal bug (#3458) (@Mogball)
- [#3424](https://github.com/apache/incubator-superset/pull/3424) fix encoding error in sql lab logging (#3424) (@graceguo-supercat)
- [#3459](https://github.com/apache/incubator-superset/pull/3459) Sqllab dont send empty queries to db (#3459) (@timifasubaa)
- [#3461](https://github.com/apache/incubator-superset/pull/3461) Fixed dashboard filters carrying over to explore slice (#3461) (@Mogball)
- [#3436](https://github.com/apache/incubator-superset/pull/3436) Adding hook for external password store for databases (#3436) (@fabianmenges)
- [#3460](https://github.com/apache/incubator-superset/pull/3460) Allow specifying sort criteria on Table viz (#3460) (@mistercrunch)
- [#3456](https://github.com/apache/incubator-superset/pull/3456) [heatmap] numerous improvements (#3456) (@mistercrunch)
- [#3431](https://github.com/apache/incubator-superset/pull/3431) fix https://github.com/apache/incubator-superset/issues/3430 (#3431) (@graceguo-supercat)
- [#3440](https://github.com/apache/incubator-superset/pull/3440) fix https://github.com/apache/incubator-superset/issues/3422 (#3440) (@graceguo-supercat)
- [#3439](https://github.com/apache/incubator-superset/pull/3439) Adding order_desc flag to explore endpoint (#3439) (@fabianmenges)
- [#2937](https://github.com/apache/incubator-superset/pull/2937) Handling pandas ExtensionDtypes (#2937) (@fabianmenges)
- [#3444](https://github.com/apache/incubator-superset/pull/3444) [postgres] adding support to serialized timedelta (#3444) (@mistercrunch)
- [#3453](https://github.com/apache/incubator-superset/pull/3453) [explore] show validation error on control panel header (#3453) (@mistercrunch)
- [#3450](https://github.com/apache/incubator-superset/pull/3450) [heatmap] fix default sorting (#3450) (@mistercrunch)
- [#3452](https://github.com/apache/incubator-superset/pull/3452) Fix off-by-one error with linear color scales (#3452) (@mistercrunch)
- [#3454](https://github.com/apache/incubator-superset/pull/3454) [explore] checkbox control won't uncheck (#3454) (@mistercrunch)
- [#3446](https://github.com/apache/incubator-superset/pull/3446) Ignore intellij files (#3446) (@fabianmenges)
- [#3445](https://github.com/apache/incubator-superset/pull/3445) Fixing the build (#3445) (@mistercrunch)
- [#3405](https://github.com/apache/incubator-superset/pull/3405) setup: Bump sqlalchemy-utils to 0.32.16 (#3405) (@xrmx)
- [#3403](https://github.com/apache/incubator-superset/pull/3403) [hotfix] user dashboard says '150 weeks' (#3403) (@mistercrunch)
- [#3401](https://github.com/apache/incubator-superset/pull/3401) [hotfix] fix slices where since/until = None (#3401) (@mistercrunch)
- [#3391](https://github.com/apache/incubator-superset/pull/3391) [dashboard] adding an option to duplicate slices when "Saving AS" (#3391) (@mistercrunch)
- [#3399](https://github.com/apache/incubator-superset/pull/3399) Fix copypasta control label error 'Until' -> 'Since' (#3399) (@mistercrunch)
- [#3397](https://github.com/apache/incubator-superset/pull/3397) [line chart] add 'min_periods' control related to rolling windows (#3397) (@mistercrunch)
- [#3394](https://github.com/apache/incubator-superset/pull/3394) [hive] fix date casting in explore view (#3394) (@mistercrunch)
- [#3396](https://github.com/apache/incubator-superset/pull/3396) [hotfix] backward compatibility on date expressions (#3396) (@mistercrunch)
- [#3395](https://github.com/apache/incubator-superset/pull/3395) Add Capital Service to organizations list (#3395) (@pkonarzewski)
- [#3377](https://github.com/apache/incubator-superset/pull/3377) Fix datatable scroll height when using filter or pagination (#3377) (@mxmzdlv)
- [#3392](https://github.com/apache/incubator-superset/pull/3392) fix date picker Select alignment (#3392) (@graceguo-supercat)
- [#3378](https://github.com/apache/incubator-superset/pull/3378) Build optimizations (#3378) (@mistercrunch)
- [#3379](https://github.com/apache/incubator-superset/pull/3379) [dashboard] load list of slices at modal enter time (#3379) (@mistercrunch)
- [#3371](https://github.com/apache/incubator-superset/pull/3371) [explore] Improved time filters controls (#3371) (@mistercrunch)
- [#3363](https://github.com/apache/incubator-superset/pull/3363) [sql lab] using react-split-pane (#3363) (@mistercrunch)
### 0.19.1 (2017/08/26 22:07 +00:00)
- [#3376](https://github.com/apache/incubator-superset/pull/3376) v1.9.1 (#3376) (@mistercrunch)
- [#3373](https://github.com/apache/incubator-superset/pull/3373) Apply advanced analytics processing to comparison time series (#3373) (@mxmzdlv)
- [#3362](https://github.com/apache/incubator-superset/pull/3362) [webpack] add a 'npm run dev-fast' command that is much faster (#3362) (@mistercrunch)
- [#3366](https://github.com/apache/incubator-superset/pull/3366) bugfix for addTotalValues with negative values (#3366) (@hajdbo)
- [#3339](https://github.com/apache/incubator-superset/pull/3339) [explore] Fix and test slice id logging issue (#3339) (@timifasubaa)
- [#3364](https://github.com/apache/incubator-superset/pull/3364) Bump fab to 1.9.4 (#3364) (@mistercrunch)
- [#3242](https://github.com/apache/incubator-superset/pull/3242) Revert "[sql lab] Make sql editor resizable (#3242)" (#3360) (@mistercrunch)
- [#3357](https://github.com/apache/incubator-superset/pull/3357) [dist_bar] break down control groups (#3357) (@mistercrunch)
- [#3356](https://github.com/apache/incubator-superset/pull/3356) delete unused csv file (#3356) (@timifasubaa)
- [#3358](https://github.com/apache/incubator-superset/pull/3358) [hotfix] react-select dropdown autocomplete are invisible (#3358) (@mistercrunch)
- [#3354](https://github.com/apache/incubator-superset/pull/3354) Collapsible Control sections (#3354) (@mistercrunch)
- [#3353](https://github.com/apache/incubator-superset/pull/3353) [bugfix] `Y bounds` in line chart (#3353) (@mistercrunch)
- [#3351](https://github.com/apache/incubator-superset/pull/3351) [css] react-select only in theme (#3351) (@mistercrunch)
- [#3352](https://github.com/apache/incubator-superset/pull/3352) fix multi-value react select style (#3352) (@graceguo-supercat)
- [#3345](https://github.com/apache/incubator-superset/pull/3345) Better looking checkboxes (#3345) (@mistercrunch)
- [#3338](https://github.com/apache/incubator-superset/pull/3338) [hotfix] self-immune filter_box fix (#3338) (@mistercrunch)
- [#3242](https://github.com/apache/incubator-superset/pull/3242) [sql lab] Make sql editor resizable (#3242) (@dmigo)
- [#3308](https://github.com/apache/incubator-superset/pull/3308) [sql lab] improve error messages (#3308) (@mistercrunch)
- [#3329](https://github.com/apache/incubator-superset/pull/3329) Syncing the timeout param from backend (#3329) (@mistercrunch)
- [#3335](https://github.com/apache/incubator-superset/pull/3335) [dashboard] re-enabling cascading filters (#3335) (@mistercrunch)
- [#3332](https://github.com/apache/incubator-superset/pull/3332) [nvd3] fix bubble axis (#3332) (@mistercrunch)
- [#3333](https://github.com/apache/incubator-superset/pull/3333) [hotfix] hotfixing the hotfix (#3333) (@mistercrunch)
- [#3331](https://github.com/apache/incubator-superset/pull/3331) Unnecessary to specify order_columns for DatasourceModelView (#3331) (@RoganW)
- [#3328](https://github.com/apache/incubator-superset/pull/3328) disable immediately re-render for color scheme change (#3328) (@graceguo-supercat)
- [#3330](https://github.com/apache/incubator-superset/pull/3330) [hotfix] dashboard widget resize is broken (#3330) (@mistercrunch)
- [#3322](https://github.com/apache/incubator-superset/pull/3322) docs: add references to Flask-Appbuilder Security documentation (#3322) (@xrmx)
- [#3315](https://github.com/apache/incubator-superset/pull/3315) Use react-alert for backend message flashing (#3315) (@mistercrunch)
- [#3295](https://github.com/apache/incubator-superset/pull/3295) Allow for multiple color schemes (#3295) (@graceguo-supercat)
- [#3313](https://github.com/apache/incubator-superset/pull/3313) French translation (#3313) (@invenis-paris)
- [#3305](https://github.com/apache/incubator-superset/pull/3305) [hive] improve error messages (#3305) (@mistercrunch)
- [#3309](https://github.com/apache/incubator-superset/pull/3309) Fix styles in Separator widget (#3309) (@mistercrunch)
- [#3310](https://github.com/apache/incubator-superset/pull/3310) [sql lab] run button shortcut tooltip (#3310) (@mistercrunch)
- [#3291](https://github.com/apache/incubator-superset/pull/3291) [bugfix] Presto KeyError 'errorLocation' (#3291) (@mistercrunch)
- [#3292](https://github.com/apache/incubator-superset/pull/3292) [sql lab] add pending to the list of searchable statuses (#3292) (@mistercrunch)
- [#3293](https://github.com/apache/incubator-superset/pull/3293) [mapbox] fix viewport alterations (#3293) (@mistercrunch)
- [#3298](https://github.com/apache/incubator-superset/pull/3298) Fix raise error when query datasource (#3298) (@RoganW)
- [#3296](https://github.com/apache/incubator-superset/pull/3296) [docs] document how to compile/publish docs (#3296) (@mistercrunch)
- [#3280](https://github.com/apache/incubator-superset/pull/3280) [dashboard] add link to export CSV from dashboard (#3280) (@mistercrunch)
- [#3282](https://github.com/apache/incubator-superset/pull/3282) FAQ entry for backend support (#3282) (@mistercrunch)
- [#3286](https://github.com/apache/incubator-superset/pull/3286) [sql lab] fix sluggish backspace in editor (#3286) (@mistercrunch)
- [#3287](https://github.com/apache/incubator-superset/pull/3287) Fix Chart Error Message Display (#3287) (@graceguo-supercat)
- [#3284](https://github.com/apache/incubator-superset/pull/3284) [dashboard] fix standalone mode that hides the navbar (#3284) (@mistercrunch)
- [#3031](https://github.com/apache/incubator-superset/pull/3031) Improve superset list view content layout (#3031) (@graceguo-supercat)
- [#3281](https://github.com/apache/incubator-superset/pull/3281) [markup] fix CSS, remove scrollbar (#3281) (@mistercrunch)
- [#2033](https://github.com/apache/incubator-superset/pull/2033) Fix returned time parse_human_datetime (#2033) (@0x0ece)
- [#3032](https://github.com/apache/incubator-superset/pull/3032) Add translatable columns in label_columns of the view (#3032) (@RoganW)
- [#3211](https://github.com/apache/incubator-superset/pull/3211) [security] prevent XSS markup viz (#3211) (@mistercrunch)
- [#3034](https://github.com/apache/incubator-superset/pull/3034) add `_()` to Exception messages (#3034) (@RoganW)
- [#3275](https://github.com/apache/incubator-superset/pull/3275) display the verbose_name of columns in list view, just like in the metrics list (#3275) (@RoganW)
- [#3274](https://github.com/apache/incubator-superset/pull/3274) add placeholder to Select components (#3274) (@RoganW)
- [#3277](https://github.com/apache/incubator-superset/pull/3277) Added Konfio to 'Who uses Superset' list. (#3277) (@luis-rodriguez)
- [#3278](https://github.com/apache/incubator-superset/pull/3278) Fix celery worker (#3278) (@saguziel)
- [#3183](https://github.com/apache/incubator-superset/pull/3183) [add] Save filters to dashboard (#3183) (@RoganW)
- [#3110](https://github.com/apache/incubator-superset/pull/3110) Explore view save modal spec (#3110) (@graceguo-supercat)
- [#3279](https://github.com/apache/incubator-superset/pull/3279) [explore] fixed padding bug on filter section (#3279) (@timifasubaa)
- [#3088](https://github.com/apache/incubator-superset/pull/3088) [explore] Split large reducer logic in ExploreViewContainer (#3088) (@graceguo-supercat)
- [#3267](https://github.com/apache/incubator-superset/pull/3267) Use sane Celery defaults to prevent tasks from being delayed (#3267) (@saguziel)
- [#3268](https://github.com/apache/incubator-superset/pull/3268) [bugfix] preserve order in groupby (#3268) (@mistercrunch)
- [#3266](https://github.com/apache/incubator-superset/pull/3266) Set default ports Druid (#3266) (@Fokko)
- [#3262](https://github.com/apache/incubator-superset/pull/3262) [webpack] break CSS and JS files while webpackin' (#3262) (@mistercrunch)
- [#3241](https://github.com/apache/incubator-superset/pull/3241) Improve the chart type of Visualize in sqllab (#3241) (@eeve)
- [#3256](https://github.com/apache/incubator-superset/pull/3256) Modernize SQLA pessimistic handling (#3256) (@mistercrunch)
- [#3252](https://github.com/apache/incubator-superset/pull/3252) Explicitly add Flask as dependancy (#3252) (@Fokko)
- [#3261](https://github.com/apache/incubator-superset/pull/3261) Relying on FAB for font-awesome.min.css (#3261) (@mistercrunch)
- [#3264](https://github.com/apache/incubator-superset/pull/3264) import logging (#3264) (@cclauss)
- [#3244](https://github.com/apache/incubator-superset/pull/3244) [explore] make edit datasource a basic link (#3244) (@mistercrunch)
- [#3254](https://github.com/apache/incubator-superset/pull/3254) [bugfix] wrong 'Cant have overlap between Series and Breakdowns' (#3254) (@mistercrunch)
- [#3249](https://github.com/apache/incubator-superset/pull/3249) Fix Yahoo's website link (#3249) (@pedro-valentim)
- [#3246](https://github.com/apache/incubator-superset/pull/3246) Fix typo (#3246) (@zeeshanu)
- [#3235](https://github.com/apache/incubator-superset/pull/3235) docs: use yarn in making your own build (#3235) (@xrmx)
- [#3067](https://github.com/apache/incubator-superset/pull/3067) explore: redraw chart on width change too (#3067) (@xrmx)
- [#3225](https://github.com/apache/incubator-superset/pull/3225) Add basic Impala engine spec (#3225) (@mistercrunch)
- [#3237](https://github.com/apache/incubator-superset/pull/3237) Treemap vis verbose metric name (#3237) (@RichRadics)
- [#3240](https://github.com/apache/incubator-superset/pull/3240) [bug fix] Fix to #3137 and #3239 (#3240) (@FrederichCheng)
- [#3238](https://github.com/apache/incubator-superset/pull/3238) SUPERSET_HOME enviroment variable (#3238) (@RichRadics)
- [#3236](https://github.com/apache/incubator-superset/pull/3236) Handle Time at query_obj generation time (#3236) (@mistercrunch)
- [#3230](https://github.com/apache/incubator-superset/pull/3230) [pivot] add support for in Pivot on Druid (#3230) (@mistercrunch)
- [#3229](https://github.com/apache/incubator-superset/pull/3229) Allowing to integrate time as a groupby value (#3229) (@mistercrunch)
- [#3227](https://github.com/apache/incubator-superset/pull/3227) 0.19.0 (#3227) (@mistercrunch)
- [#2974](https://github.com/apache/incubator-superset/pull/2974) Allow 'refresh_immune_slices' (#2974) (@RichRadics)
- [#3111](https://github.com/apache/incubator-superset/pull/3111) sql_lab: re-raise exception in get_sql_results (#3111) (@xrmx)
### 0.19.0 (2017/08/02 05:16 +00:00)
- [#3210](https://github.com/apache/incubator-superset/pull/3210) [explore] DatasourceControl to pick datasource in modal (#3210) (@mistercrunch)
- [#3214](https://github.com/apache/incubator-superset/pull/3214) [sqllab] fix UI shows 'The query returned no results' momentarily (#3214) (@mistercrunch)
- [#3197](https://github.com/apache/incubator-superset/pull/3197) [explore] nvd3 sort values in rich tooltip (#3197) (@mistercrunch)
- [#3222](https://github.com/apache/incubator-superset/pull/3222) [sqllab/cosmetics] add margin-top for labels in query history (#3222) (@mistercrunch)
- [#3212](https://github.com/apache/incubator-superset/pull/3212) [docs] update url in CONTRIBUTING.md (#3212) (@diggzhang)
- [#3213](https://github.com/apache/incubator-superset/pull/3213) [bugfix] capture Hive job_id pre-url transformation (#3213) (@mistercrunch)
- [#3205](https://github.com/apache/incubator-superset/pull/3205) fix issue 3204 (#3205) (@diggzhang)
- [#3203](https://github.com/apache/incubator-superset/pull/3203) Speed up JS build time (#3203) (@mistercrunch)
- [#2929](https://github.com/apache/incubator-superset/pull/2929) Autofocus search input in VizTypeControl modal onEnter (#2929) (@pariser)
- [#3086](https://github.com/apache/incubator-superset/pull/3086) add combine config for metrics in pivot table (#3086) (@RoganW)
- [#3146](https://github.com/apache/incubator-superset/pull/3146) [druid] Allow custom druid postaggregators (#3146) (@brianwolfe)
- [#3194](https://github.com/apache/incubator-superset/pull/3194) Adding 'apache' to docs (#3194) (@mistercrunch)
- [#3196](https://github.com/apache/incubator-superset/pull/3196) [bugfix] fix merge conflict that broke Hive support (#3196) (@mistercrunch)
- [#3193](https://github.com/apache/incubator-superset/pull/3193) Add BigQuery engine specifications (#3193) (@mistercrunch)
- [#3187](https://github.com/apache/incubator-superset/pull/3187) [sqllab] improve Hive support (#3187) (@mistercrunch)
- [#3186](https://github.com/apache/incubator-superset/pull/3186) Escaping the user's SQL in the explore view (#3186) (@mistercrunch)
- [#3065](https://github.com/apache/incubator-superset/pull/3065) Bump cryptography to 1.9 (#3065) (@xrmx)
- [#3174](https://github.com/apache/incubator-superset/pull/3174) Fix the segment interval for pulling metadata (#3174) (@Fokko)
- [#3181](https://github.com/apache/incubator-superset/pull/3181) [bugfix] visualize flow error: 'Metric x is not valid' (#3181) (@mistercrunch)
- [#3180](https://github.com/apache/incubator-superset/pull/3180) [bugfix] fix bar order (#3180) (@mistercrunch)
- [#3169](https://github.com/apache/incubator-superset/pull/3169) docs: fixup installation examples code indentation (#3169) (@xrmx)
- [#3171](https://github.com/apache/incubator-superset/pull/3171) add Zalando to the list of organizations (#3171) (@dmigo)
- [#2968](https://github.com/apache/incubator-superset/pull/2968) fix hive.fetch_logs (#2968) (@timfeirg)
- [#3036](https://github.com/apache/incubator-superset/pull/3036) [bugfix] numeric value for date fields in table viz (#3036) (@mistercrunch)
- [#3101](https://github.com/apache/incubator-superset/pull/3101) Add 'show/hide totals' option to pivot table vis (#3101) (@RichRadics)
- [#3045](https://github.com/apache/incubator-superset/pull/3045) add title description to model view (#3045) (@RoganW)
- [#3035](https://github.com/apache/incubator-superset/pull/3035) Datasource cannot be empty (#3035) (@RoganW)
- [#3105](https://github.com/apache/incubator-superset/pull/3105) [bugfix] only filterable columns should show up in FilterBox list (#3105) (@mistercrunch)
- [#3179](https://github.com/apache/incubator-superset/pull/3179) Fixing the damn build (#3179) (@mistercrunch)
- [#3102](https://github.com/apache/incubator-superset/pull/3102) Add event-flow visualization (#3102) (@williaster)
- [#3163](https://github.com/apache/incubator-superset/pull/3163) Prevent people from deleting datasources that have associate slices (#3163) (@mistercrunch)
- [#3164](https://github.com/apache/incubator-superset/pull/3164) More logging to csv endpoint (#3164) (@mistercrunch)
- [#3159](https://github.com/apache/incubator-superset/pull/3159) [bugfix] SQLA instance has been deleted (#3159) (@mistercrunch)
- [#3157](https://github.com/apache/incubator-superset/pull/3157) add douban to the orgs. (#3157) (@luchuan)
- [#3150](https://github.com/apache/incubator-superset/pull/3150) [docs] use yarn in CONTRIBUTING.md (#3150) (@mistercrunch)
- [#3155](https://github.com/apache/incubator-superset/pull/3155) [bugfix] fails on None view_menu (#3155) (@mistercrunch)
- [#3112](https://github.com/apache/incubator-superset/pull/3112) allow user press Enter key to end editing title (#3112) (@graceguo-supercat)
- [#3116](https://github.com/apache/incubator-superset/pull/3116) [minor] change tooltip on 'Edit slice properties' (#3116) (@mistercrunch)
- [#3133](https://github.com/apache/incubator-superset/pull/3133) Prevent SQLA warning related to SQLALCHEMY_TRACK_MODIFICATION (#3133) (@mistercrunch)
- [#3138](https://github.com/apache/incubator-superset/pull/3138) [#3137] Use state.datasource.type instead of state.datasource_type when rendering ControlPanelsContainer (#3138) (@FrederichCheng)
- [#3119](https://github.com/apache/incubator-superset/pull/3119) [heatmap] basic non empty validation (#3119) (@mistercrunch)
- [#3135](https://github.com/apache/incubator-superset/pull/3135) Fixes #3134 by correct response content-type of /testconn (#3135) (@shawnzhu)
- [#3126](https://github.com/apache/incubator-superset/pull/3126) [Celery] fix the celery worker concurrency settings (#3126) (@dingguitao)
- [#3118](https://github.com/apache/incubator-superset/pull/3118) [CLI] Improve the missing perm creation logic (#3118) (@mistercrunch)
- [#3120](https://github.com/apache/incubator-superset/pull/3120) Using yarn instead of npm install (#3120) (@mistercrunch)
- [#3044](https://github.com/apache/incubator-superset/pull/3044) clarify Superset different timeout config (#3044) (@graceguo-supercat)
- [3d136aa](https://github.com/apache/incubator-superset/commit/3d136aa0a4d3c6ebb26821e1b308b6eff4c2fd8f) Update docs links on README (@mistercrunch)
- [#3042](https://github.com/apache/incubator-superset/pull/3042) fix default checkbox alignment (#3042) (@graceguo-supercat)
- [#3013](https://github.com/apache/incubator-superset/pull/3013) New chart type : Chord Diagrams (#3013) (@mistercrunch)
- [#3041](https://github.com/apache/incubator-superset/pull/3041) [bugfix] issue creating separators & markup slices (#3041) (@mistercrunch)
- [#3011](https://github.com/apache/incubator-superset/pull/3011) Bug fix: Datasource -> Slice relationship (#3011) (@fabianmenges)
### 0.18.5 (2017/06/22 22:46 +00:00)
- [fdbb569](https://github.com/apache/incubator-superset/commit/fdbb569c3e2842fdfc80e0418f5817593e5c64fb) 0.18.5 (@mistercrunch)
- [cc3e63f](https://github.com/apache/incubator-superset/commit/cc3e63f1de0a6e5c2fd68464297620ac878fe2a0) [docs] adding info on how to create new viz (@mistercrunch)
- [#3022](https://github.com/apache/incubator-superset/pull/3022) add test coverage for sql lab components (#3022) (@graceguo-supercat)
- [6eba6ca](https://github.com/apache/incubator-superset/commit/6eba6cac0b49a06172ba3dc817eb7aeef7cd310c) [hotfix] xAxis broken on time series viz (@mistercrunch)
- [bd706eb](https://github.com/apache/incubator-superset/commit/bd706ebbd17e6d147962df5f20dabdf3af3a6730) Fixing image sizes for horizon and country_map (@mistercrunch)
- [abbf138](https://github.com/apache/incubator-superset/commit/abbf138cfb6149277cbbfd1b38aa65a1e0170f3c) Bumping SQLLAB_ASYNC_TIME_LIMIT_SEC default config to 6 hours (@mistercrunch)
- [#3021](https://github.com/apache/incubator-superset/pull/3021) CONTRIBUTING: add python unittes setup (#3021) (@graceguo-supercat)
- [#3014](https://github.com/apache/incubator-superset/pull/3014) A set of minor fixes (#3014) (@mistercrunch)
- [5344a80](https://github.com/apache/incubator-superset/commit/5344a805359fe6b72bcc7a4298b22f0dfb0cccfa) Bumping flask-appbuilder to 1.9.1 (@mistercrunch)
- [0b09a74](https://github.com/apache/incubator-superset/commit/0b09a74d37874f9c6aa101c9566257873a6e41a0) Downgrading celery to 3.1.25 (@mistercrunch)
- [#3017](https://github.com/apache/incubator-superset/pull/3017) CONTRIBUTING: ask to quote python stacktraces (#3017) (@xrmx)
- [#3009](https://github.com/apache/incubator-superset/pull/3009) [bugfix] fix metrics/metric control default (#3009) (@mistercrunch)
- [53dead9](https://github.com/apache/incubator-superset/commit/53dead9c2983ca9e3f940354e1fecb3d85f62b2b) Revert "Bumping FAB to 1.9.1" (@mistercrunch)
- [f64e2ba](https://github.com/apache/incubator-superset/commit/f64e2ba7d52c442461b59ee1230476eae6b9ff22) Bumping FAB to 1.9.1 (@mistercrunch)
- [#3012](https://github.com/apache/incubator-superset/pull/3012) Revert change in npm run build command (#3012) (@yolken)
- [#3008](https://github.com/apache/incubator-superset/pull/3008) Adding missing dependency and linting webpack.js (#3008) (@mistercrunch)
- [#2981](https://github.com/apache/incubator-superset/pull/2981) Stabilizing Celery / SQL Lab (#2981) (@mistercrunch)
- [#2994](https://github.com/apache/incubator-superset/pull/2994) Misc. tweaks to improve webpack performance (#2994) (@yolken)
- [#2990](https://github.com/apache/incubator-superset/pull/2990) translations extracted by pybabel (#2990) (@RoganW)
- [#2983](https://github.com/apache/incubator-superset/pull/2983) Fix importing config from env var (#2983) (@andrewmchen)
- [#2988](https://github.com/apache/incubator-superset/pull/2988) Improving TextAreaControl to support code and modal (#2988) (@mistercrunch)
- [#2957](https://github.com/apache/incubator-superset/pull/2957) [pivot viz] fix formatting and verbose names (#2957) (@mistercrunch)
- [#2927](https://github.com/apache/incubator-superset/pull/2927) [explore] improve bubble viz (#2927) (@mistercrunch)
- [#2984](https://github.com/apache/incubator-superset/pull/2984) add test coverage for SqlEditorLeftBar (#2984) (@graceguo-supercat)
- [#2985](https://github.com/apache/incubator-superset/pull/2985) fix is_owner check (#2985) (@graceguo-supercat)
- [#2970](https://github.com/apache/incubator-superset/pull/2970) [FilterBox] use column verbose names (#2970) (@mistercrunch)
- [1ce3b81](https://github.com/apache/incubator-superset/commit/1ce3b81d01e1453fb34469fa6ba66f9b7d09bcb2) Imporving the README (@mistercrunch)
- [#2978](https://github.com/apache/incubator-superset/pull/2978) [bufix] superset views not getting from_dttm-to_dttm in template context (#2978) (@mistercrunch)
- [#2963](https://github.com/apache/incubator-superset/pull/2963) [CLI] adding 'superset flower' command (flower is a UI for Celery) (#2963) (@mistercrunch)
- [#2979](https://github.com/apache/incubator-superset/pull/2979) tests for saveQuery, fetchQueryResults, runQuery, postStopQuery (#2979) (@ascott)
- [#2896](https://github.com/apache/incubator-superset/pull/2896) fix local state 'columns' (#2896) (@graceguo-supercat)
- [#2977](https://github.com/apache/incubator-superset/pull/2977) test props on alert wrapper (#2977) (@ascott)
- [#2972](https://github.com/apache/incubator-superset/pull/2972) add test coverage for ResultSet component (#2972) (@graceguo-supercat)
- [#2976](https://github.com/apache/incubator-superset/pull/2976) [js-testing] add tests for explore actions (#2976) (@ascott)
- [#2940](https://github.com/apache/incubator-superset/pull/2940) Edit Dashboard title and Slice title in place (#2940) (@graceguo-supercat)
- [#2961](https://github.com/apache/incubator-superset/pull/2961) add test for ControlPanelSection (#2961) (@ascott)
- [#2952](https://github.com/apache/incubator-superset/pull/2952) [js] remove unused npm dependencies (#2952) (@mistercrunch)
- [#2939](https://github.com/apache/incubator-superset/pull/2939) add new slice test (#2939) (@ascott)
- [#2951](https://github.com/apache/incubator-superset/pull/2951) [js] version js file names using webpack chunkhash (#2951) (@ascott)
- [#2941](https://github.com/apache/incubator-superset/pull/2941) [dashboard] notify instead of modal onSave (#2941) (@mistercrunch)
- [987cb99](https://github.com/apache/incubator-superset/commit/987cb9978dcd053ebac550c790a9d87d8d25aee6) [hotfix] bumping pandas version to 0.20.2 (@mistercrunch)
- [#1742](https://github.com/apache/incubator-superset/pull/1742) Fix handling of Chunked requests (#1742) (@nishantmonu51)
- [#2943](https://github.com/apache/incubator-superset/pull/2943) [table viz] get metrics to right-align (#2943) (@mistercrunch)
- [#2945](https://github.com/apache/incubator-superset/pull/2945) Bumping some dependencies (#2945) (@mistercrunch)
- [#2946](https://github.com/apache/incubator-superset/pull/2946) remove reference for CSRF_ENABLED, and use WTF_CSRF_ENABLED instead (#2946) (@timfeirg)
- [#2921](https://github.com/apache/incubator-superset/pull/2921) [explore] improve metric(s) and groupby(s) controls (#2921) (@mistercrunch)
- [34f381b](https://github.com/apache/incubator-superset/commit/34f381bc250cf7c74669b52d5cc5f9061c7184c5) v 0.18.5-alpha.3 (@ascott)
- [#2928](https://github.com/apache/incubator-superset/pull/2928) add new slice form improvements (#2928) (@ascott)
- [#2912](https://github.com/apache/incubator-superset/pull/2912) [big number] various improvements (#2912) (@mistercrunch)
- [#2924](https://github.com/apache/incubator-superset/pull/2924) Fix #2814 - json serialization edge case (#2924) (@mistercrunch)
- [fb85f00](https://github.com/apache/incubator-superset/commit/fb85f008fac2694bea7f6705cf21dc666490bcd0) v 0.18.5-alpha.2 (@ascott)
- [85fb4a9](https://github.com/apache/incubator-superset/commit/85fb4a933d8ab7348082a6849ff96f199b8c02fa) [hotfix] only apply SQLAlchemy limit where needed (@mistercrunch)
- [#2893](https://github.com/apache/incubator-superset/pull/2893) [js-testing] type checking for dates.js (#2893) (@ascott)
- [#2889](https://github.com/apache/incubator-superset/pull/2889) add more tests for Timer (#2889) (@ascott)
- [#2800](https://github.com/apache/incubator-superset/pull/2800) [slices] add simple new slice form (#2800) (@ascott)
- [#2923](https://github.com/apache/incubator-superset/pull/2923) updating react-alert dependency to v2.0.1 (#2923) (@dennybiasiolli)
- [#2906](https://github.com/apache/incubator-superset/pull/2906) Ignore pyenv files in .gitignore. (#2906) (@xiaohanyu)
- [9aba77d](https://github.com/apache/incubator-superset/commit/9aba77db74f8c7e823fcba73fc4e0a1b7efbadd4) 0.18.5-alpha.1 (@mistercrunch)
- [#2910](https://github.com/apache/incubator-superset/pull/2910) [dashboard]Add timeout message on Dashboard view (#2910) (@graceguo-supercat)
- [#2908](https://github.com/apache/incubator-superset/pull/2908) [explore] fix IN filter on numeric field (#2908) (@mistercrunch)
- [#2911](https://github.com/apache/incubator-superset/pull/2911) Removed time column from druid metadata refresh, added long and double schema support (#2911) (@joshwalters)
- [#2897](https://github.com/apache/incubator-superset/pull/2897) fix visualize modal checkbox alignment (#2897) (@graceguo-supercat)
- [#2902](https://github.com/apache/incubator-superset/pull/2902) update for the italian translation (#2902) (@napo)
- [#2888](https://github.com/apache/incubator-superset/pull/2888) [docs faq] how do I add new columns to an existing table (#2888) (@mistercrunch)
- [#2903](https://github.com/apache/incubator-superset/pull/2903) update contributing a bit re contributing code (#2903) (@xrmx)
- [#2904](https://github.com/apache/incubator-superset/pull/2904) travis: no need to install python3.5 (#2904) (@xrmx)
### 0.18.4 (2017/06/05 00:54 +00:00)
- [72291d6](https://github.com/apache/incubator-superset/commit/72291d65c929306792bc62aeaff51e083bc8c09f) 0.18.4 (@mistercrunch)
- [#2895](https://github.com/apache/incubator-superset/pull/2895) fix a linting error (#2895) (@graceguo-supercat)
- [#2894](https://github.com/apache/incubator-superset/pull/2894) fix js error on explore view (#2894) (@ascott)
- [155fec0](https://github.com/apache/incubator-superset/commit/155fec0a6bcb9733c64301e9e8b86aa2c384673b) Updating CHANGELOG.md to 0.18.3 (@mistercrunch)
### 0.18.3 (2017/06/02 15:27 +00:00)
- [d90044c](https://github.com/airbnb/superset/commit/d90044cd523253aa01b5cdf6509b43abeef34079) 0.18.3 (@mistercrunch)
- [62bd4eb](https://github.com/airbnb/superset/commit/62bd4eb2118e4f1e771b58cd455b928be002a461) Converting filter argument to number if column is number (#2891) (@fabianmenges)
- [677c427](https://github.com/airbnb/superset/commit/677c427b1615a2a9b9054932b5e07868d7d63e42) delete DataPreviewModal, it doesn't get used anywhere (#2882) (@ascott)
- [52b0716](https://github.com/airbnb/superset/commit/52b0716571c5b68f65d08719e54343e0a6ec8c8e) [bugfix] allow database macro to work when CSRF is diabled (#2884) (@justinr1234)
- [04b662e](https://github.com/airbnb/superset/commit/04b662ea1154b75e2c362aed97e33946251d1bed) Fix a type error in rst' sub list. (#2881) (@xiaohanyu)
- [db052b1](https://github.com/airbnb/superset/commit/db052b17ea1782c472687095e1365d071e592dd0) Add visualize advise for long query (#2879) (@graceguo-supercat)
- [e300273](https://github.com/airbnb/superset/commit/e300273e71f0b6ca8b63ae974cc13534d94c56de) [explore] adding y_axis_bounds to force Y axis bounds (#2878) (@mistercrunch)
- [c5f2eaf](https://github.com/airbnb/superset/commit/c5f2eafc906bebf1d238e62ff5a8821cf549220c) [explore] 'Save as' -> 'Save' as it can be used to overwrite (#2875) (@mistercrunch)
- [90e4d64](https://github.com/airbnb/superset/commit/90e4d6469d3d420cf839a4c9f3a2408ab0ff0a42) [js-testing] more tests for SelectControl (#2877) (@ascott)
- [1e7773e](https://github.com/airbnb/superset/commit/1e7773eb169d29607991d0c4619ee930104e18de) Improve visualize modal test coverage (#2811) (@graceguo-supercat)
- [3c89c8c](https://github.com/airbnb/superset/commit/3c89c8cc4613d938e4e8726c30142fa32b1249f7) 0.18.3-alpha.3 (@mistercrunch)
- [74086da](https://github.com/airbnb/superset/commit/74086dae2ba66029917a7ed640cfcfc7555c0520) [bars] fix sort numeric bar on x axis (#2812) (@mistercrunch)
- [66403f1](https://github.com/airbnb/superset/commit/66403f1876bb7bcf31eb8187517c116a2d5b6b96) [explore] viz type selector as modal (#2787) (@mistercrunch)
- [3a4cd3a](https://github.com/airbnb/superset/commit/3a4cd3ae24c811e21fb76c5f9efecb2a6c4a6da2) Applying specified limit in bubble plot (#2815) (@mistercrunch)
- [4ffc1f6](https://github.com/airbnb/superset/commit/4ffc1f613e1d2bf012dc5eb66751fea8c698804e) Fix filter values populating for views (#2816) (@mistercrunch)
- [dfbba84](https://github.com/airbnb/superset/commit/dfbba84400986451f5068354a7626537e7b377a4) 0.18.3-alpha.2 (@mistercrunch)
- [77864e6](https://github.com/airbnb/superset/commit/77864e6cf4d5394a5080300097ae21cf9abfcc53) reduce clientside timeout limit (#2820) (@graceguo-supercat)
- [4d12251](https://github.com/airbnb/superset/commit/4d1225180618b4c4f05c67f6534bf273692a9243) [explore] include ControlHeader as part of Control interface (#2809) (@mistercrunch)
- [0c9f9b6](https://github.com/airbnb/superset/commit/0c9f9b695b921c7e17cec83e1d51e4aa3cae7cc9) [clarity/consistency] rename /explorev2/ -> /explore/ (#2802) (@ascott)
- [a4a2bf7](https://github.com/airbnb/superset/commit/a4a2bf7ae9cc1075a38cc980bb696d6512125f2b) filter_box: allow creatable entries (#2804) (@vavrusa)
- [d0a04cd](https://github.com/airbnb/superset/commit/d0a04cde49c86185b779b16f1da05450b1ccf571) apply redux for VisualizeModal (#2795) (@graceguo-supercat)
- [69685b9](https://github.com/airbnb/superset/commit/69685b9dcc0c26f819ff7edeedc10ee302e97f83) Fixing country maps (#2801) (@mistercrunch)
- [b308a3e](https://github.com/airbnb/superset/commit/b308a3eb4eb08de39edbff6490c06a6bef7b7ce1) Added Country Map : New Visualization tools (#2708) (@ymatagne)
- [bfa40bd](https://github.com/airbnb/superset/commit/bfa40bd360021874628477ee3eb2272033cd2d54) [hotfix] 'filter box from and to date filter #2649' (#2785) (@yamdraco)
- [b0e2904](https://github.com/airbnb/superset/commit/b0e2904c245e5569473f425af2806271e33a5176) Updating permission when refreshing druid datasource (#2655) (@ShengyaoQian)
- [ce506bd](https://github.com/airbnb/superset/commit/ce506bdf65b46f5bccee84ca8254417f63b124a5) Logging a few more actions (#2783) (@mistercrunch)
- [922cc03](https://github.com/airbnb/superset/commit/922cc037bf859c935cc5eacbcd96bf6fa004c5fe) 0.18.3-alpha.1 (@mistercrunch)
- [8252ada](https://github.com/airbnb/superset/commit/8252ada1f9ac94866b91eac55b77ed6d0ef7d02f) [docs] more details on how filters are applied (#2778) (@mistercrunch)
- [a2d2f8b](https://github.com/airbnb/superset/commit/a2d2f8bb8c006adcf80bb2ac18b82f3b486f366a) Enable filter value autocomplete in examples (#2781) (@mistercrunch)
- [7c5f61d](https://github.com/airbnb/superset/commit/7c5f61d6a61e1a3cb6d20d0918610abafa2cd326) Adding some STATSD logging (#2715) (@mistercrunch)
- [841e18a](https://github.com/airbnb/superset/commit/841e18a08c4b375fdff5b846f5d9f108903a3eb6) [sql lab] make database ordering alphabetical in left panel (#2769) (@mistercrunch)
- [dbc7fef](https://github.com/airbnb/superset/commit/dbc7fef7f501cd59ebd99524fa171d9e4dee0325) [sql lab] fix user timestamp is off (#2774) (@mistercrunch)
### 0.18.2 (2017/05/17 06:08 +00:00)
- [cbfe3cb](https://github.com/airbnb/superset/commit/cbfe3cb2dcadedeedfcf55f2bb4883b76a484b36) 0.18.2 (@mistercrunch)
- [5fcd25d](https://github.com/airbnb/superset/commit/5fcd25def15b5990c10b5045cb89b88f94ba8716) 0.18.1-alpha.2 (@mistercrunch)
- [fe3f5f6](https://github.com/airbnb/superset/commit/fe3f5f69ae83eaf96415926661b272ebb460a4e0) [hotfix] 'No numeric types to aggregate' (@mistercrunch)
- [2395fbb](https://github.com/airbnb/superset/commit/2395fbbdaaa5c81c3559f17cedf2e998b8341cb9) Adding `end_result_backend_time` to Query model (#2766) (@mistercrunch)
- [960b26c](https://github.com/airbnb/superset/commit/960b26c7a2cad58b39c359f44c385980434dacb8) Show clear and actionable query timeout error message (#2763) (@graceguo-supercat)
- [28ac350](https://github.com/airbnb/superset/commit/28ac3504d67f76c31aac23435dd15d76e0ca75bf) 0.18.1-alpha.1 (@mistercrunch)
- [ecc00bd](https://github.com/airbnb/superset/commit/ecc00bdd26517a832a35529f0fdd7d17972e6f8f) [explore] a bit less margin in left panel (#2758) (@mistercrunch)
- [e794645](https://github.com/airbnb/superset/commit/e7946451d6aa84229d0c70b7a683b29b784ca1a1) fixed 500 error when export dashboard (#2760) (@eeve)
- [9b34600](https://github.com/airbnb/superset/commit/9b34600c8e8df72ecbdfaaf94bdf023c08e26701) Remove duplicate text (#2761) (@awbush)
- [8846108](https://github.com/airbnb/superset/commit/884610861b8d39da91e4c1bce7934172d2486da9) 0.18.0 (@mistercrunch)
- [d9bd3d6](https://github.com/airbnb/superset/commit/d9bd3d646006d9e6ddf2ccded21d7984935c98c8) fix percentage change viz (#2757) (@yileic)
- [38375be](https://github.com/airbnb/superset/commit/38375be5c3062caf9f6cd4d6ac62109e1940bd10) Fix issues around % signs and Presto (#2755) (@mistercrunch)
- [91d951a](https://github.com/airbnb/superset/commit/91d951ac422a6411e59b2ec195011ea4dc44b0b1) Change hardcoded references to 'User' security model to allow custom class override (#2728) (@RichRadics)
### 0.18.0 (2017/05/12 03:36 +00:00)
- [d79a45f](https://github.com/airbnb/superset/commit/d79a45ff32ff8e2b5d601601507680dccf693bbc) add number format to pivot table (#2703) (@yileic)
- [818251f](https://github.com/airbnb/superset/commit/818251fc8519167be7e0730083c4a694972fb06b) make margin consistent (#2753) (@yileic)
- [75abd1f](https://github.com/airbnb/superset/commit/75abd1f44a12208fd54f28a1185d40ea8639396a) 0.18.0-alpha.4 (@mistercrunch)
- [f55df3b](https://github.com/airbnb/superset/commit/f55df3b18b67ff58d5ad3f6f12f7fe76e9697084) [sql lab] fix responsivity of grid (#2742) (@mistercrunch)
- [5dbfdef](https://github.com/airbnb/superset/commit/5dbfdefae82674d71ab1f1464622d199a6f72f30) [sql lab] fix partitionned table has no partitions (#2740) (@mistercrunch)
- [e558444](https://github.com/airbnb/superset/commit/e5584440cecdb0d9a79ba6c4ff1050e73e774035) Speed up all CRUD list views (#2747) (@mistercrunch)
- [d5e9d5d](https://github.com/airbnb/superset/commit/d5e9d5d045d342ef203c7d7cd480011626b6d7a1) fix auto select override pre-selected value bug (#2745) (@graceguo-supercat)
- [3208a01](https://github.com/airbnb/superset/commit/3208a014ffccfe44238fb5982f6e391a1764d4b3) fix dual line chart margin (#2737) (@yileic)
- [874c12a](https://github.com/airbnb/superset/commit/874c12ad2d99059b2f8f979bdd05e77d8768db03) 0.18.0-alpha.3 (@mistercrunch)
- [22d8075](https://github.com/airbnb/superset/commit/22d8075c536bdfc1790b23381e0017720cc921a5) Making the stop button instantaneous (#2738) (@mistercrunch)
- [baebba1](https://github.com/airbnb/superset/commit/baebba115930e95076e9252987fb4e107ddd23d5) 0.18.0-alpha.2 (@mistercrunch)
- [04748b4](https://github.com/airbnb/superset/commit/04748b4cdac7a4fd53f5d7716a36ceebea7bf7ca) [SQL Lab] fix gamma metadata access (#2702) (@mistercrunch)
- [a471afe](https://github.com/airbnb/superset/commit/a471afe206ca3357ea4c27c1accf94d44c8f5122) [sql lab] improvements to the left panel (#2709) (@mistercrunch)
- [5d0a01d](https://github.com/airbnb/superset/commit/5d0a01d0d099a9d73ba04fded7cad223a10e86f2) Decimal is a valid numeric type (#2720) (@hajdbo)
- [9e1272e](https://github.com/airbnb/superset/commit/9e1272e97c88a3ce2e8dfd15fa819de52e331342) 0.18.0-alpha.1 (@mistercrunch)
- [aeebd88](https://github.com/airbnb/superset/commit/aeebd8840d0551a7cd9a2d43039dcd07648d66ed) [table] fixing CSS glitches on table view (#2725) (@mistercrunch)
- [55d3b01](https://github.com/airbnb/superset/commit/55d3b012e504f788732488bf11a1ec7ef223a821) refactor: recentActions ajax call is redundant (#2722) (@S-YOU)
- [a6e1e18](https://github.com/airbnb/superset/commit/a6e1e18244951b5bf68ac76e897a16713c7d279b) [sql lab] fix CREATE TABLE AS (#2719) (@mistercrunch)
- [46d7a92](https://github.com/airbnb/superset/commit/46d7a925bb4be8891c89ac05d2f447e5ec750bf5) chore: remove unused methods with invalid models.Query usage (#2721) (@S-YOU)
- [5929ab7](https://github.com/airbnb/superset/commit/5929ab76890232068bef5412f23a54226dbed0ec) [dashboard] fix missing datasource issue (#2718) (@mistercrunch)
- [fffb7b5](https://github.com/airbnb/superset/commit/fffb7b500a313b9f9d76eecab18241bf0406c933) [sql lab]Add autoSelect (#2713) (@graceguo-supercat)
- [cb14640](https://github.com/airbnb/superset/commit/cb14640a823c3c6cc768169391779064c2469a68) Removing uneeded results_backends.py (#2717) (@mistercrunch)
- [d65054e](https://github.com/airbnb/superset/commit/d65054e01533f62e63e1c8788da4b97309f65cee) [sql lab] fix csv export where `%` in query (#2711) (@mistercrunch)
- [5d5060e](https://github.com/airbnb/superset/commit/5d5060eca61ad1a7f6baf7adced2985088c82d95) Remove unecessary handling of %% (#2714) (@mistercrunch)
- [9ff3515](https://github.com/airbnb/superset/commit/9ff351532ada993afc4da5060b9a942216e2a74b) Basic integration with ClickHouse (#1844) (@vavrusa)
- [59a6f44](https://github.com/airbnb/superset/commit/59a6f447ec1e92a0319a617ecdf4e22847bf5d95) Fix missing curUserId from SliderAdder.jsx (#2705) (@songyanho)
### 0.17.6 (2017/05/01 20:13 +00:00)
- [1887b5e](https://github.com/airbnb/superset/commit/1887b5e934b17864850a46d6e88a606b594e0634) 0.17.6 (@mistercrunch)
- [33758bf](https://github.com/airbnb/superset/commit/33758bfff59b9cdc86b58973244ef0613942dc80) 0.17.6-alpha.2 (@mistercrunch)
- [2d5beb1](https://github.com/airbnb/superset/commit/2d5beb1f91c304df948e943100cbfb66345a00e9) improve csrf expiration error handling (#2695) (@ascott)
- [5fd0e7d](https://github.com/airbnb/superset/commit/5fd0e7d02828df4bb02b6a3b34779517fe637123) [vis] bar values should match y axis format (#2701) (@justinpark)
- [ef0c4be](https://github.com/airbnb/superset/commit/ef0c4be06743083da5c33ed9ffbda7ff77b43e74) Fix for referring specific svg (#2612) (@songyanho)
- [ac3aba7](https://github.com/airbnb/superset/commit/ac3aba7c7da905f0f4bfeb0f80efb87136812b90) [sql lab] visualization flow: fixing the groupby parameter (#2681) (@mistercrunch)
- [0fdb57a](https://github.com/airbnb/superset/commit/0fdb57a18153912c2675b54a2c4e5e00691c7cc0) fix (#2696) (@yileic)
- [3e7b5df](https://github.com/airbnb/superset/commit/3e7b5df2876d1014a8411a57cdd7bb18ce64e5d9) [explore] fix empty chart when changing viz type (#2698) (@mistercrunch)
- [3cd16cf](https://github.com/airbnb/superset/commit/3cd16cf3680169dd17a542d83c84f94ca8220805) Fix test's warnings (#2697) (@dennybiasiolli)
- [a58adc8](https://github.com/airbnb/superset/commit/a58adc862ec28842a3ac7f9f1f205fa1c173015e) Fix orm query in HiveEngineSpec.handle_cursor (#2699) (@xrmx)
- [7d88f80](https://github.com/airbnb/superset/commit/7d88f80a9b2003f4529560160aea41c444283a9e) hack to dynamically adjust y axis left margin (#2689) (@yileic)
- [09be02f](https://github.com/airbnb/superset/commit/09be02f70a716819332629144160360e21c8920b) fix x axis label (#2691) (@yileic)
- [50fcdd3](https://github.com/airbnb/superset/commit/50fcdd3a34f3efe58435760ba0bf321d6767a3a5) Adding tails.com to inthewild (#2685) (@alanmcruickshank)
- [dee3649](https://github.com/airbnb/superset/commit/dee36491c5e9394c19dfbc00def353675079aa83) Fix js warnings (#2693) (@dennybiasiolli)
- [903612a](https://github.com/airbnb/superset/commit/903612ac6c802dd042417c1fa8a742812a2094bb) fix (#2692) (@yileic)
- [ce70505](https://github.com/airbnb/superset/commit/ce705054fa2e738612d746c8f07b577f6941a6e3) fix a bug in 'getMaxLabelSize' and x axis label not shown problem (#2694) (@yileic)
- [c589616](https://github.com/airbnb/superset/commit/c5896168830c0901a6488817d970a92ce3fa8f9a) [sql lab] Update event handler name (#2680) (@graceguo-supercat)
- [58309f2](https://github.com/airbnb/superset/commit/58309f275f3b9d123f75e795fe3e42b918a66aab) Mark a few more string for translation (#2651) (@xrmx)
- [edf4e4f](https://github.com/airbnb/superset/commit/edf4e4f24e9eeceb44e2b9a98d2cb02d8cefa6dd) Update README.md (#2676) (@aioue)
- [b3e0b5b](https://github.com/airbnb/superset/commit/b3e0b5b586d530cdd1def10ef38550f680f1922b) Specifying cryptography version in install docs (@mistercrunch)
- [6880298](https://github.com/airbnb/superset/commit/68802989bc8a13f76988eed004dc07fa06208733) Pinning cryptography lib to 1.7.2 (@mistercrunch)
- [70887d7](https://github.com/airbnb/superset/commit/70887d72e2a54fdae2ba58ad8f408528bd694878) 0.17.6-alpha.1 (@ascott)
- [1922225](https://github.com/airbnb/superset/commit/192222504292aed3ffa7368f85ca6cdc7f92aab5) Alternate fix for #2665 (#2671) (@mistercrunch)
- [0bdc301](https://github.com/airbnb/superset/commit/0bdc3010d8da0789df99d588105d6e62cc6b3280) [vis] fix pivot table scrolling when using more than 1 groupy col (#2674) (@ascott)
- [1df37e6](https://github.com/airbnb/superset/commit/1df37e6e4d609f7c0751faf2360a98a896e30f46) add option for pulling favourited dashboards by username (#2661) (@robert-digit)
- [e9ed416](https://github.com/airbnb/superset/commit/e9ed4166549cb515f5c15357b2395c3858736df1) fix csrf error on import_dashboards (#2672) (@ascott)
- [03c42b5](https://github.com/airbnb/superset/commit/03c42b5b87429f2a29ce1b5ef8c13e9a004b907e) Showing slices on datasource edit form (#2645) (@mistercrunch)
- [e055e6d](https://github.com/airbnb/superset/commit/e055e6d2c22e6087bf7c906174c08d543617a514) Fixing PropTypes warning messages (#2670) (@mistercrunch)
- [2978082](https://github.com/airbnb/superset/commit/29780821e8797fee3fbcbcfacbe3e0871750d19b) [druid] fixing the having clause in the explore view (#2648) (@mistercrunch)
- [f10ee13](https://github.com/airbnb/superset/commit/f10ee139011767fd72e20ff0fb6a6411f6b06d6b) [druid] fix FilterBox viz gets timestamps as values if granularity != all (#2647) (@mistercrunch)
- [cdfc4a3](https://github.com/airbnb/superset/commit/cdfc4a35b22e8b07bf2b0503214074761143e7d9) Optimizing the standalone view (#2663) (@mistercrunch)
- [eb762c8](https://github.com/airbnb/superset/commit/eb762c8bfec56a0da664c4aa71baf2197f58042f) add the missing right bracket (#2662) (@yileic)
- [83abfef](https://github.com/airbnb/superset/commit/83abfef8304a8fe83248d959136e7421ba0e04a8) superset: fix argument swap for SqliteEngineSpec.get_table_names (#2664) (@xrmx)
- [54137ad](https://github.com/airbnb/superset/commit/54137ad023f046780bd0e2089ccc57620787f118) Updating CHANGELOG (@mistercrunch)
### 0.17.5 (2017/04/21 20:56 +00:00)
- [4be6bfa](https://github.com/airbnb/superset/commit/4be6bfafaa07695cf47a9a27977855ab30ff87e4) 0.17.5 (@mistercrunch)
- [9ba6d48](https://github.com/airbnb/superset/commit/9ba6d489f31d2aba38594dac3cb7d75fbabcdc78) v0.17.5-alpha.10 (#2654) (@ascott)
- [af4bd40](https://github.com/airbnb/superset/commit/af4bd40853d477e5104d62c81931b65be0026b50) fix scrolling on markup vis (#2644) (@ascott)
- [84fa0d1](https://github.com/airbnb/superset/commit/84fa0d19407d7fe662ea1945bb0f9e2570945e50) don't default sort by to first column (#2653) (@ascott)
- [938e13a](https://github.com/airbnb/superset/commit/938e13a4297f13354ae7a989de1268cddbf042c4) [hotfix] Presto's latest_sub_partion rendering fail (@mistercrunch)
- [dc364da](https://github.com/airbnb/superset/commit/dc364daffddd740bd827aaaa71d07c13a928c7ef) [query-search] fix scrolling on query search and pagination styling (#2646) (@ascott)
- [1cadfec](https://github.com/airbnb/superset/commit/1cadfecd4bc0c69e0c66ddce12727fd5607b4364) update core.py label and zh po file (#2642) (@RoganW)
- [5b26667](https://github.com/airbnb/superset/commit/5b26667fd520ccf2b668f9d3f7b1a928a1bdaba7) 0.17.5-alpha.9 (@ascott)
- [899caf9](https://github.com/airbnb/superset/commit/899caf94497e22ab8d6a59f695d3805999ab2e4c) [sql-lab] fix scrolling in left hand panel for table meta data (#2641) (@ascott)
- [e6063f2](https://github.com/airbnb/superset/commit/e6063f2ddf14ae9ddb8c9fd8b5ebd548e272e7d5) 0.17.5-alpha.8 (@mistercrunch)
- [46486f8](https://github.com/airbnb/superset/commit/46486f82d9352cd7d340e4dfb6bd9ba2676b2c6c) Moving the warning message to the navbar (#2640) (@mistercrunch)
- [0089762](https://github.com/airbnb/superset/commit/00897629558a4d89c5a500b173b345d8136f52fa) 0.17.5-alpha.7 (@ascott)
- [2bd60c0](https://github.com/airbnb/superset/commit/2bd60c074716faf57a8a10e3a9c73b9fe500080f) [vis] fix line chart when slice is really narrow (#2620) (@ascott)
- [db6cd21](https://github.com/airbnb/superset/commit/db6cd215040220f3cf3636f1decb25139f395cad) [sqllab] table refactor (#2587) (@ascott)
- [f40499e](https://github.com/airbnb/superset/commit/f40499e550ae3ed7fea534b8c657c2c76d9f6070) [dashboard] improve error handling on dashboard (#2624) (@mistercrunch)
- [67a85b9](https://github.com/airbnb/superset/commit/67a85b9831f86a78fe987037000c8f2e6bd9c7d7) Fix dashboard edit button is disabled (#2634) (@mistercrunch)
- [cb3384b](https://github.com/airbnb/superset/commit/cb3384b3b225c1c392453616ce09c1c9e7136baa) Improving Presto error message in explore/dashboard (#2633) (@mistercrunch)
- [ac51a30](https://github.com/airbnb/superset/commit/ac51a30f98019d8cc593f03cd0f542aa35646889) Remove metrics control non-null validator in Table context (#2635) (@mistercrunch)
- [91fe02c](https://github.com/airbnb/superset/commit/91fe02cdc879097d517cddc06a8492536bc3b6ea) Setting adjust_database_uri for HiveEngineSpec (#2636) (@mistercrunch)
- [76042be](https://github.com/airbnb/superset/commit/76042be7c3b52c5019114b372dc841137205e14f) [hotfix/sqllab] setting up the connection in the try: block (@mistercrunch)
- [d3f55a0](https://github.com/airbnb/superset/commit/d3f55a0905e4aa7a2da22113ea8e25c174903c9f) 0.17.5-alpha.6 (@mistercrunch)
- [efaef8f](https://github.com/airbnb/superset/commit/efaef8fe0924ff39e77edbe8fe5e2ed337adccf3) [hotfix] fix endpoint (@mistercrunch)
- [8757a24](https://github.com/airbnb/superset/commit/8757a24d89e44c13b44b8ae84be9ae12a50b8d48) 0.17.5-alpha.5 (@mistercrunch)
- [63785f0](https://github.com/airbnb/superset/commit/63785f039c0f7763c410c9e7a40a0d477b9bf23a) [hotfix] using UTC for caching timestamps (@mistercrunch)
- [d6689ee](https://github.com/airbnb/superset/commit/d6689ee700102926ebd7efa352cb3c66d970445f) 0.17.5-alpha.4 (@mistercrunch)
- [787daf6](https://github.com/airbnb/superset/commit/787daf6005d325b68a52644804d802a1168cf314) A nice CacheLabel React component (#2628) (@mistercrunch)
- [23aeee5](https://github.com/airbnb/superset/commit/23aeee5a9c1c17ef486fa5106da964acc0b4bd43) Slice level cache_timeout isn't taken into consideration (#2631) (@mistercrunch)
- [70c6cad](https://github.com/airbnb/superset/commit/70c6cad0e3b5e276158c1d9057de40b6fd9498eb) Add UNIX socket option to runserver (#2627) (@scaba)
- [6b1bf3b](https://github.com/airbnb/superset/commit/6b1bf3b395a61a8549b9f3297c8411bb41db52fa) [hotfix] missing explore's main.css (@mistercrunch)
- [f5216f6](https://github.com/airbnb/superset/commit/f5216f60479a2580b5a5532ec8c1b0882905d7a0) Adding owner(s) to dashboard makes them own underlying slices (#2610) (@mistercrunch)
- [15654a3](https://github.com/airbnb/superset/commit/15654a3082f4d6030fafd38d671299670443374e) fix filters on dashboard (#2619) (@ascott)
- [baff0cb](https://github.com/airbnb/superset/commit/baff0cba38554ae28e1024f2114ee5765648c45b) Fix separator widget CSS (#2623) (@mistercrunch)
- [c4ee098](https://github.com/airbnb/superset/commit/c4ee098bb7ffc0db970eba608bfe464ee7b3e60b) 0.17.5-alpha.3 (@mistercrunch)
- [612b8ca](https://github.com/airbnb/superset/commit/612b8ca3d7de9988f22b8f7f81c583ff0b8b19bc) [hotfix] legacy url not handled properly (@mistercrunch)
- [c43a9fd](https://github.com/airbnb/superset/commit/c43a9fd5541d5de0987607d913eddd899ee84e75) [hotfix] fixing the build (@mistercrunch)
- [6c68a21](https://github.com/airbnb/superset/commit/6c68a21e4f77757df57042eedbb91a96b21fa040) [sql lab] fix alt-enter runs out-of-date SQL (#2603) (@mistercrunch)
- [db02b33](https://github.com/airbnb/superset/commit/db02b33e09dd6391fb1d8f777b19d5c16a511abe) [explore] fix query text modal while loading (#2596) (@mistercrunch)
- [2df6baa](https://github.com/airbnb/superset/commit/2df6baa7a741a4bfff786b0f675f1165b122aaac) [sql lab] sorting database names in dropdowns (#2611) (@mistercrunch)
- [fc7bd63](https://github.com/airbnb/superset/commit/fc7bd630399c9f4f936b59be347d5d4d0e516744) [sql lab] fixes issues specific to Sqlite (#2606) (@mistercrunch)
- [959a09c](https://github.com/airbnb/superset/commit/959a09cc92682854e0051fae302bd866d9d5b8b5) [dashboard] fix css padding for markup viz (#2602) (@mistercrunch)
- [366ecef](https://github.com/airbnb/superset/commit/366ecefbaaf4cc31234cc981ebab7eb420efe019) Bumping the JS libs to fix the build (#2616) (@mistercrunch)
- [a2b30f3](https://github.com/airbnb/superset/commit/a2b30f35fcc3c081448d55df31ad445d4d9cec6c) 0.17.5-alpha.2 (@mistercrunch)
- [8bceda8](https://github.com/airbnb/superset/commit/8bceda8134c6e53f62b5b30910ec0eeb02f051e7) [hotfix] fix iframe viz (@mistercrunch)
- [bae1067](https://github.com/airbnb/superset/commit/bae1067015a4b8041d39b806062a45c1950e3f7c) 0.17.5-alpha.1 (@mistercrunch)
- [116dca3](https://github.com/airbnb/superset/commit/116dca3e6fc78ef109f0385b6c4dbf2650dda080) validationErrors is undedfined (@mistercrunch)
- [b448394](https://github.com/airbnb/superset/commit/b448394077eef18b9ed01c9703c58cf05f14d34c) 0.17.5-alpha.0 (@mistercrunch)
- [09f407f](https://github.com/airbnb/superset/commit/09f407f553eb8bca90f6da79cf60c742296488c7) add tooltips to big number vis (#2599) (@ascott)
- [0479118](https://github.com/airbnb/superset/commit/0479118efc0069da2b62c20dc631ebbd00493758) 0.17.5.dev0 (@mistercrunch)
- [c93411b](https://github.com/airbnb/superset/commit/c93411b1e75bc59b174d1256f3108d783eea3264) Fix for merge string as array (#2597) (@songyanho)
- [31283f1](https://github.com/airbnb/superset/commit/31283f14246ccd9f7cac4df238bd65cdd68c840b) Fix metric formating in Dashboard view + some refactoring (#2598) (@mistercrunch)
- [93c6597](https://github.com/airbnb/superset/commit/93c6597cf4f2c47869f9cf4f62cfdbe80cd37760) Adding docs/ to .eslintignore (@mistercrunch)
- [4446c74](https://github.com/airbnb/superset/commit/4446c745a88d4b31de8a30ccb45b4cd6dcc49dae) Fix backend-sync 2 (@mistercrunch)
- [38e90fe](https://github.com/airbnb/superset/commit/38e90fe3098018655a8e2206a053c60c8d7e64aa) Fix backend-sync (@mistercrunch)
- [f548946](https://github.com/airbnb/superset/commit/f5489467e534f3625079843cad82ae12de6cbf3a) Use correct dialect for escaping functions. (#2593) (@steveniemitz)
- [ab0bc5a](https://github.com/airbnb/superset/commit/ab0bc5a3fa81f3951b50828400de6bfc54235860) handle percentage case for tooltips (#2570) (@ascott)
- [412634c](https://github.com/airbnb/superset/commit/412634cb57f6094bbba168d252b8b5dbd56da954) Add missing flask-wtf dependency (#2586) (@xrmx)
- [a0ddbb9](https://github.com/airbnb/superset/commit/a0ddbb9ec954a65a77350bc054b83e35bc4dffeb) Make form_data dict a macro (#2585) (@mistercrunch)
- [a803705](https://github.com/airbnb/superset/commit/a803705ddca1c869ccd50977d033faa5c8a0464b) [bugfix] clarifying how to create a slice (#2565) (@mistercrunch)
- [75a358c](https://github.com/airbnb/superset/commit/75a358c616bf30e15dc752da59de1c3cd333a89c) [explore] force control validation before runQuery (#2544) (@mistercrunch)
- [493ba18](https://github.com/airbnb/superset/commit/493ba1836241146502d5dfa4d5c9ea57f4d8ad6c) Adding macros current_user_id & current_username (#2582) (@mistercrunch)
- [5e4fca4](https://github.com/airbnb/superset/commit/5e4fca4ea4b896a9c427032f30a30b59efbcec63) Bumping a set of Python libraries to the latest release (#2575) (@mistercrunch)
- [d289783](https://github.com/airbnb/superset/commit/d289783b67ef6503f58a330bcd729e3301c20393) Adding Vertica to installation docs (#2581) (@mistercrunch)
- [ac84fc2](https://github.com/airbnb/superset/commit/ac84fc2b65976c1473488e2ed47979d880df34f5) Fixing confusion when selecting schema across engines (#2572) (@mistercrunch)
- [40b3d3b](https://github.com/airbnb/superset/commit/40b3d3b3ef61124ec38d49130b57d751b98a1a67) [hotfix] add csrf_token api endpoint (@mistercrunch)
- [50a9e13](https://github.com/airbnb/superset/commit/50a9e13f9bb9bf0c10ca3b748e1989a15c97ee8a) [hotfix] add csrf_token api endpoint (@mistercrunch)
- [66bff01](https://github.com/airbnb/superset/commit/66bff01b45658547d9853e0d0c22e788550d8267) Changelog for 0.17.4 (@mistercrunch)
- [9691234](https://github.com/airbnb/superset/commit/9691234b7e33d8162253a6971f6eb298c037b748) [hotfix] casting db_id to int (@mistercrunch)
### 0.17.4 (2017/04/07 17:57 +00:00)
- [ddeabdd](https://github.com/airbnb/superset/commit/ddeabdd048296732c24bb7ca2317e5d3683fa17d) Fixing CSRF issues (#2569) (@mistercrunch)
- [3ed45ab](https://github.com/airbnb/superset/commit/3ed45ab98c2e351ced9520bcfce222dd34d45a94) [bugfix] saved query restore wouldn't pick the db (#2568) (@mistercrunch)
+84
View File
@@ -0,0 +1,84 @@
# Code of Conduct
## 1. Purpose
A primary goal of Apache Superset is to be inclusive to the largest number of contributors, with the most varied and diverse backgrounds possible. As such, we are committed to providing a friendly, safe and welcoming environment for all, regardless of gender, sexual orientation, ability, ethnicity, socioeconomic status, and religion (or lack thereof).
This code of conduct outlines our expectations for all those who participate in our community, as well as the consequences for unacceptable behavior.
We invite all those who participate in Apache Superset to help us create safe and positive experiences for everyone.
## 2. Open Source Citizenship
A supplemental goal of this Code of Conduct is to increase open source citizenship by encouraging participants to recognize and strengthen the relationships between our actions and their effects on our community.
Communities mirror the societies in which they exist and positive action is essential to counteract the many forms of inequality and abuses of power that exist in society.
If you see someone who is making an extra effort to ensure our community is welcoming, friendly, and encourages all participants to contribute to the fullest extent, we want to know.
## 3. Expected Behavior
The following behaviors are expected and requested of all community members:
* Participate in an authentic and active way. In doing so, you contribute to the health and longevity of this community.
* Exercise consideration and respect in your speech and actions.
* Attempt collaboration before conflict.
* Refrain from demeaning, discriminatory, or harassing behavior and speech.
* Be mindful of your surroundings and of your fellow participants. Alert community leaders if you notice a dangerous situation, someone in distress, or violations of this Code of Conduct, even if they seem inconsequential.
* Remember that community event venues may be shared with members of the public; please be respectful to all patrons of these locations.
## 4. Unacceptable Behavior
The following behaviors are considered harassment and are unacceptable within our community:
* Violence, threats of violence or violent language directed against another person.
* Sexist, racist, homophobic, transphobic, ableist or otherwise discriminatory jokes and language.
* Posting or displaying sexually explicit or violent material.
* Posting or threatening to post other peoples personally identifying information ("doxing").
* Personal insults, particularly those related to gender, sexual orientation, race, religion, or disability.
* Inappropriate photography or recording.
* Inappropriate physical contact. You should have someones consent before touching them.
* Unwelcome sexual attention. This includes, sexualized comments or jokes; inappropriate touching, groping, and unwelcomed sexual advances.
* Deliberate intimidation, stalking or following (online or in person).
* Advocating for, or encouraging, any of the above behavior.
* Sustained disruption of community events, including talks and presentations.
## 5. Consequences of Unacceptable Behavior
Unacceptable behavior from any community member, including sponsors and those with decision-making authority, will not be tolerated.
Anyone asked to stop unacceptable behavior is expected to comply immediately.
If a community member engages in unacceptable behavior, the community organizers may take any action they deem appropriate, up to and including a temporary ban or permanent expulsion from the community without warning (and without refund in the case of a paid event).
## 6. Reporting Guidelines
If you are subject to or witness unacceptable behavior, or have any other concerns, please notify a community organizer as soon as possible. dev@superset.incubator.apache.org .
Additionally, community organizers are available to help community members engage with local law enforcement or to otherwise help those experiencing unacceptable behavior feel safe. In the context of in-person events, organizers will also provide escorts as desired by the person experiencing distress.
## 7. Addressing Grievances
If you feel you have been falsely or unfairly accused of violating this Code of Conduct, you should notify Apache with a concise description of your grievance. Your grievance will be handled in accordance with our existing governing policies.
## 8. Scope
We expect all community participants (contributors, paid or otherwise; sponsors; and other guests) to abide by this Code of Conduct in all community venuesonline and in-personas well as in all one-on-one communications pertaining to community business.
This code of conduct and its related procedures also applies to unacceptable behavior occurring outside the scope of community activities when such behavior has the potential to adversely affect the safety and well-being of community members.
## 9. Contact info
dev@superset.incubator.apache.org
## 10. License and attribution
This Code of Conduct is distributed under a [Creative Commons Attribution-ShareAlike license](http://creativecommons.org/licenses/by-sa/3.0/).
Portions of text derived from the [Django Code of Conduct](https://www.djangoproject.com/conduct/) and the [Geek Feminism Anti-Harassment Policy](http://geekfeminism.wikia.com/wiki/Conference_anti-harassment/Policy).
Retrieved on November 22, 2016 from [http://citizencodeofconduct.org/](http://citizencodeofconduct.org/)
+110 -35
View File
@@ -18,6 +18,9 @@ If you are reporting a bug, please include:
troubleshooting.
- Detailed steps to reproduce the bug.
When you post python stack traces please quote them using
[markdown blocks](https://help.github.com/articles/creating-and-highlighting-code-blocks/).
### Fix Bugs
Look through the GitHub issues for bugs. Anything tagged with "bug" is
@@ -26,7 +29,7 @@ open to whoever wants to implement it.
### Implement Features
Look through the GitHub issues for features. Anything tagged with
"feature" is open to whoever wants to implement it.
"feature" or "starter_task" is open to whoever wants to implement it.
### Documentation
@@ -46,10 +49,32 @@ If you are proposing a feature:
implement.
- Remember that this is a volunteer-driven project, and that
contributions are welcome :)
### Questions
There is a dedicated [tag](https://stackoverflow.com/questions/tagged/apache-superset) on [stackoverflow](https://stackoverflow.com/). Please use it when asking questions.
## Pull Request Guidelines
Before you submit a pull request from your forked repo, check that it
meets these guidelines:
1. The pull request should include tests, either as doctests,
unit tests, or both.
2. If the pull request adds functionality, the docs should be updated
as part of the same PR. Doc string are often sufficient, make
sure to follow the sphinx compatible standards.
3. The pull request should work for Python 2.7, and ideally python 3.4+.
``from __future__ import`` will be required in every `.py` file soon.
4. Code will be reviewed by re running the unittests, flake8 and syntax
should be as rigorous as the core Python project.
5. Please rebase and resolve all conflicts before submitting.
6. If you are asked to update your pull request with some changes there's
no need to create a new one. Push your changes to the same branch.
## Documentation
The latest documentation and tutorial are available [here](http://airbnb.io/superset).
The latest documentation and tutorial are available [here](https://superset.incubator.apache.org/).
Contributing to the official documentation is relatively easy, once you've setup
your environment and done an edit end-to-end. The docs can be found in the
@@ -64,7 +89,7 @@ Before you start changing the docs, you'll want to
[fork the Superset project on Github](https://help.github.com/articles/fork-a-repo/).
Once that new repository has been created, clone it on your local machine:
git clone git@github.com:your_username/superset.git
git clone git@github.com:your_username/incubator-superset.git
At this point, you may also want to create a
[Python virtual environment](http://docs.python-guide.org/en/latest/dev/virtualenvs/)
@@ -76,7 +101,7 @@ to manage the Python packages you're about to install:
Finally, to make changes to the rst files and build the docs using Sphinx,
you'll need to install a handful of dependencies from the repo you cloned:
cd superset
cd incubator-superset
pip install -r dev-reqs-for-docs.txt
To get the feel for how to edit and build the docs, let's edit a file, build
@@ -123,7 +148,7 @@ referenced in the rst, e.g.
aren't actually included in that directory. _Instead_, you'll want to add and commit
images (and any other static assets) to the _superset/assets/images_ directory.
When the docs are being pushed to [airbnb.io](http://airbnb.io/superset/), images
When the docs are being pushed to [Apache Superset (incubating)](https://superset.incubator.apache.org/), images
will be moved from there to the _\_static/img_ directory, just like they're referenced
in the docs.
@@ -140,19 +165,19 @@ instead.
## Setting up a Python development environment
Check the [OS dependencies](http://airbnb.io/superset/installation.html#os-dependencies) before follows these steps.
Check the [OS dependencies](https://superset.incubator.apache.org/installation.html#os-dependencies) before follows these steps.
# fork the repo on GitHub and then clone it
# alternatively you may want to clone the main repo but that won't work
# so well if you are planning on sending PRs
# git clone git@github.com:airbnb/superset.git
# git clone git@github.com:apache/incubator-superset.git
# [optional] setup a virtual env and activate it
virtualenv env
source env/bin/activate
# install for development
python setup.py develop
pip install -e .
# Create an admin user
fabmanager create-admin --app superset
@@ -202,8 +227,13 @@ To install third party libraries defined in `package.json`, run the
following within the `superset/assets/` directory which will install them in a
new `node_modules/` folder within `assets/`.
```
npm install
```bash
# from the root of the repository, move to where our JS package.json lives
cd superset/assets/
# install yarn, a replacement for `npm install` that is faster and more deterministic
npm install -g yarn
# run yarn to fetch all the dependencies
yarn
```
To parse and generate bundled files for superset, run either of the
@@ -231,9 +261,20 @@ npm run dev
## Testing
Python tests can be run with:
Before running python unit tests, please setup local testing environment:
```
pip install -r dev-reqs.txt
```
All python tests can be run with:
./run_tests.sh
Alternatively, you can run a specific test with:
./run_specific_test.sh tests.core_tests:CoreTests.test_function_name
Note that before running specific tests, you have to both setup the local testing environment and run all tests.
We use [Mocha](https://mochajs.org/), [Chai](http://chaijs.com/) and [Enzyme](http://airbnb.io/enzyme/) to test Javascript. Tests can be run with:
@@ -245,9 +286,8 @@ We use [Mocha](https://mochajs.org/), [Chai](http://chaijs.com/) and [Enzyme](ht
Lint the project with:
# for python changes
flake8 changes tests
flake8 changes superset
# for python
flake8
# for javascript
npm run lint
@@ -292,23 +332,6 @@ The `variables.less` and `bootswatch.less` files that ship with Superset are der
[Bootswatch](https://bootswatch.com) and thus extend Bootstrap. Modify variables in these files directly, or
swap them out entirely with the equivalent files from other Bootswatch (themes)[https://github.com/thomaspark/bootswatch.git]
## Pull Request Guidelines
Before you submit a pull request from your forked repo, check that it
meets these guidelines:
1. The pull request should include tests, either as doctests,
unit tests, or both.
2. If the pull request adds functionality, the docs should be updated
as part of the same PR. Doc string are often sufficient, make
sure to follow the sphinx compatible standards.
3. The pull request should work for Python 2.6, 2.7, and ideally python 3.3.
``from __future__ import`` will be required in every `.py` file soon.
4. Code will be reviewed by re running the unittests, flake8 and syntax
should be as rigorous as the core Python project.
5. Please rebase and resolve all conflicts before submitting.
## Translations
We use [Babel](http://babel.pocoo.org/en/latest/) to translate Superset. The
@@ -317,6 +340,8 @@ key is to instrument the strings that need translation using
a module, all you have to do is to `_("Wrap your strings")` using the
underscore `_` "function".
We use `import {t, tn, TCT} from locales;` in js, JSX file, locales is in `./superset/assets/javascripts/` directory.
To enable changing language in your environment, you can simply add the
`LANGUAGES` parameter to your `superset_config.py`. Having more than one
options here will add a language selection dropdown on the right side of the
@@ -329,14 +354,15 @@ navigation bar.
}
As per the [Flask AppBuilder documentation] about translation, to create a
new language dictionary, run the following command:
new language dictionary, run the following command (where `es` is replaced with
the language code for your target language):
pybabel init -i ./babel/messages.pot -d superset/translations -l es
pybabel init -i superset/translations/messages.pot -d superset/translations -l es
Then it's a matter of running the statement below to gather all stings that
Then it's a matter of running the statement below to gather all strings that
need translation
fabmanager babel-extract --target superset/translations/
fabmanager babel-extract --target superset/translations/ --output superset/translations/messages.pot --config superset/translations/babel.cfg -k _ -k __ -k t -k tn -k tct
You can then translate the strings gathered in files located under
`superset/translation`, where there's one per language. For the translations
@@ -344,6 +370,19 @@ to take effect, they need to be compiled using this command:
fabmanager babel-compile --target superset/translations/
In the case of JS translation, we need to convert the PO file into a JSON file, and we need the global download of the npm package po2json.
We need to be compiled using this command:
npm install po2json -g
Execute this command to convert the en PO file into a json file:
po2json -d superset -f jed1.x superset/translations/en/LC_MESSAGES/messages.po superset/translations/en/LC_MESSAGES/messages.json
If you get errors running `po2json`, you might be running the ubuntu package with the same
name rather than the nodejs package (they have a different format for the arguments). You
need to be running the nodejs version, and so if there is a conflict you may need to point
directly at `/usr/local/bin/po2json` rather than just `po2json`.
## Adding new datasources
@@ -360,3 +399,39 @@ to take effect, they need to be compiled using this command:
`ADDITIONAL_MODULE_DS_MAP = {'superset.my_models': ['MyDatasource', 'MyOtherDatasource']}`
This means it'll register MyDatasource and MyOtherDatasource in superset.my_models module in the source registry.
## Creating a new visualization type
Here's an example as a Github PR with comments that describe what the
different sections of the code do:
https://github.com/apache/incubator-superset/pull/3013
## Refresh documentation website
Every once in a while we want to compile the documentation and publish it.
Here's how to do it.
.. code::
# install doc dependencies
pip install -r dev-reqs-for-docs.txt
# build the docs
python setup.py build_sphinx
# copy html files to temp folder
cp -r docs/_build/html/ /tmp/tmp_superset_docs/
# clone the docs repo
cd ~/
git clone https://git-wip-us.apache.org/repos/asf/incubator-superset-site.git
# copy
cp -r /tmp/tmp_superset_docs/ ~/incubator-superset-site.git/
# commit and push to `asf-site` branch
cd ~/incubator-superset-site.git/
git checkout asf-site
git add .
git commit -a -m "New doc version"
git push origin master
-24
View File
@@ -1,24 +0,0 @@
Please use [pull requests](https://github.com/airbnb/superset/pull/new/master)
to add your organization and/or project to this document!
Organizations
----------
- [Airbnb](https://github.com/airbnb)
- [GfK Data Lab](http://datalab.gfk.com)
- [Maieutical Labs](https://cloudschooling.it)
- [Shopkick](https://www.shopkick.com)
- [Amino](https://amino.com)
- [Faasos](http://faasos.com/)
- [Clark.de](http://clark.de/)
- [Yahoo!](www.yahoo.com)
- [Digit Game Studios](https://www.digitgaming.com/)
- [Brilliant.org](https://brilliant.org/)
- [Qunar](https://www.qunar.com/)
- [Udemy](https://www.udemy.com/)
- [Tooploox](https://www.tooploox.com/)
- [Tobii](http://www.tobii.com/)
- [Endress+Hauser](http://www.endress.com/)
Projects
----------
- None we know of yet
+7 -7
View File
@@ -1,9 +1,9 @@
recursive-include superset/templates *
recursive-include superset/static *
recursive-exclude superset/static/assets/node_modules *
recursive-include superset/static/assets/node_modules/font-awesome *
recursive-exclude superset/static/docs *
recursive-exclude superset/static/spec *
recursive-exclude tests *
recursive-include superset/data *
recursive-include superset/migrations *
recursive-include superset/static *
recursive-exclude superset/static/docs *
recursive-exclude superset/static/spec *
recursive-exclude superset/static/assets/node_modules *
recursive-include superset/templates *
recursive-include superset/translations *
recursive-exclude tests *
+110 -58
View File
@@ -1,17 +1,14 @@
Superset
=========
[![Build Status](https://travis-ci.org/airbnb/superset.svg?branch=master)](https://travis-ci.org/airbnb/superset)
[![Build Status](https://travis-ci.org/apache/incubator-superset.svg?branch=master)](https://travis-ci.org/apache/incubator-superset)
[![PyPI version](https://badge.fury.io/py/superset.svg)](https://badge.fury.io/py/superset)
[![Coverage Status](https://coveralls.io/repos/airbnb/superset/badge.svg?branch=master&service=github)](https://coveralls.io/github/airbnb/superset?branch=master)
[![JS Test Coverage](https://codeclimate.com/github/airbnb/superset/badges/coverage.svg)](https://codeclimate.com/github/airbnb/superset/coverage)
[![Code Health](https://landscape.io/github/airbnb/superset/master/landscape.svg?style=flat)](https://landscape.io/github/airbnb/superset/master)
[![Code Climate](https://codeclimate.com/github/airbnb/superset/badges/gpa.svg)](https://codeclimate.com/github/airbnb/superset)
[![Coverage Status](https://coveralls.io/repos/apache/incubator-superset/badge.svg?branch=master&service=github)](https://coveralls.io/github/apache/incubator-superset?branch=master)
[![PyPI](https://img.shields.io/pypi/pyversions/superset.svg?maxAge=2592000)](https://pypi.python.org/pypi/superset)
[![Requirements Status](https://requires.io/github/airbnb/superset/requirements.svg?branch=master)](https://requires.io/github/airbnb/superset/requirements/?branch=master)
[![Join the chat at https://gitter.im/airbnb/superset](https://badges.gitter.im/airbnb/superset.svg)](https://gitter.im/airbnb/superset?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
[![Documentation](https://img.shields.io/badge/docs-airbnb.io-blue.svg)](http://airbnb.io/superset/)
[![dependencies Status](https://david-dm.org/airbnb/superset/status.svg?path=superset/assets)](https://david-dm.org/airbnb/superset?path=superset/assets)
[![Requirements Status](https://requires.io/github/apache/incubator-superset/requirements.svg?branch=master)](https://requires.io/github/apache/incubator-superset/requirements/?branch=master)
[![Join the chat at https://gitter.im/airbnb/superset](https://badges.gitter.im/apache/incubator-superset.svg)](https://gitter.im/airbnb/superset?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
[![Documentation](https://img.shields.io/badge/docs-apache.org-blue.svg)](https://superset.incubator.apache.org)
[![dependencies Status](https://david-dm.org/apache/incubator-superset/status.svg?path=superset/assets)](https://david-dm.org/apache/incubator-superset?path=superset/assets)
<img
src="https://cloud.githubusercontent.com/assets/130878/20946612/49a8a25c-bbc0-11e6-8314-10bef902af51.png"
@@ -19,8 +16,8 @@ Superset
width="500"
/>
**Superset** is a data exploration platform designed to be visual, intuitive
and interactive.
**Apache Superset** (incubating) is a modern, enterprise-ready
business intelligence web application
[this project used to be named **Caravel**, and **Panoramix** in the past]
@@ -52,24 +49,26 @@ Screenshots & Gifs
![superset-query-search](https://cloud.githubusercontent.com/assets/130878/20234706/0f430a10-a835-11e6-8a0d-8b26cc2e6bbd.png)
Superset
---------
Superset's main goal is to make it easy to slice, dice and visualize data.
It empowers users to perform **analytics at the speed of thought**.
Apache Superset
---------------
Apache Superset is a data exploration and visualization web application.
Superset provides:
* A quick way to intuitively visualize datasets by allowing users to create
and share interactive dashboards
* A rich set of visualizations to analyze your data, as well as a flexible
way to extend the capabilities
* An intuitive interface to explore and visualize datasets, and
create interactive dashboards.
* A wide array of beautiful visualizations to showcase your data.
* Easy, code-free, user flows to drill down and slice and dice the data
underlying exposed dashboards. The dashboards and charts acts as a starting
point for deeper analysis.
* A state of the art SQL editor/IDE exposing a rich metadata browser, and
an easy workflow to create visualizations out of any result set.
* An extensible, high granularity security model allowing intricate rules
on who can access which features, and integration with major
authentication providers (database, OpenID, LDAP, OAuth & REMOTE_USER
through Flask AppBuiler)
* A simple semantic layer, allowing to control how data sources are
displayed in the UI, by defining which fields should show up in
which dropdown and which aggregation and function (metrics) are
made available to the user
on who can access which product features and datasets.
Integration with major
authentication backends (database, OpenID, LDAP, OAuth, REMOTE_USER, ...)
* A lightweight semantic layer, allowing to control how data sources are
exposed to the user by defining dimensions and metrics
* Out of the box support for most SQL-speaking databases
* Deep integration with Druid allows for Superset to stay blazing fast while
slicing and dicing large, realtime datasets
* Fast loading dashboards with configurable caching
@@ -78,15 +77,41 @@ Superset provides:
Database Support
----------------
Superset was originally designed on top of Druid.io, but quickly broadened
its scope to support other databases through the use of SQLAlchemy, a Python
Superset speaks many SQL dialects through SQLAlchemy, a Python
ORM that is compatible with
[most common databases](http://docs.sqlalchemy.org/en/rel_1_0/core/engines.html).
Superset can be used to visualize data out of most databases:
* MySQL
* Postgres
* Vertica
* Oracle
* Microsoft SQL Server
* SQLite
* Greenplum
* Firebird
* MariaDB
* Sybase
* IBM DB2
* Exasol
* MonetDB
* Snowflake
* Redshift
* **more!** look for the availability of a SQLAlchemy dialect for your database
to find out whether it will work with Superset
What is Druid?
-------------
From their website at http://druid.io
Druid!
------
On top of having the ability to query your relational databases,
Superset has ships with deep integration with Druid (a real time distributed
column-store). When querying Druid,
Superset can query humongous amounts of data on top of real time dataset.
Note that Superset does not require Druid in any way to function, it's simply
another database backend that it can query.
Here's a description of Druid from the http://druid.io website:
*Druid is an open-source analytics data store designed for
business intelligence (OLAP) queries on event data. Druid provides low
@@ -99,7 +124,60 @@ power analytic dashboards and applications.*
Installation & Configuration
----------------------------
[See in the documentation](http://airbnb.io/superset/installation.html)
[See in the documentation](https://superset.incubator.apache.org/installation.html)
Resources
-------------
* [Mailing list](https://lists.apache.org/list.html?dev@superset.apache.org/)
* [Gitter (live chat) Channel](https://gitter.im/airbnb/superset)
* [Docker image](https://hub.docker.com/r/amancevice/superset/) (community contributed)
* [Slides from Strata (March 2016)](https://drive.google.com/open?id=0B5PVE0gzO81oOVJkdF9aNkJMSmM)
* [Stackoverflow tag](https://stackoverflow.com/questions/tagged/apache-superset)
* [DEPRECATED Google Group](https://groups.google.com/forum/#!forum/airbnb_superset)
Contributing
------------
Interested in contributing? Casual hacking? Check out
[Contributing.MD](https://github.com/airbnb/superset/blob/master/CONTRIBUTING.md)
Who uses Apache Superset (incubating)?
--------------------------------------
Here's a list of organizations who have taken the time to send a PR to let
the world know they are using Superset. Join our growing community!
- [AiHello](https://www.aihello.com)
- [Airbnb](https://github.com/airbnb)
- [Amino](https://amino.com)
- [Brilliant.org](https://brilliant.org/)
- [Capital Service S.A.](http://capitalservice.pl)
- [Clark.de](http://clark.de/)
- [Digit Game Studios](https://www.digitgaming.com/)
- [Douban](https://www.douban.com/)
- [Endress+Hauser](http://www.endress.com/)
- [FBK - ICT center](http://ict.fbk.eu)
- [Faasos](http://faasos.com/)
- [GfK Data Lab](http://datalab.gfk.com)
- [Konfío](http://konfio.mx)
- [Lyft](https://www.lyft.com/)
- [Maieutical Labs](https://cloudschooling.it)
- [Ona](https://ona.io)
- [Pronto Tools](http://www.prontotools.io)
- [Qunar](https://www.qunar.com/)
- [Shopee](https://shopee.sg)
- [Shopkick](https://www.shopkick.com)
- [Tails.com](https://tails.com)
- [Tobii](http://www.tobii.com/)
- [Tooploox](https://www.tooploox.com/)
- [Twitter](https://twitter.com/)
- [Udemy](https://www.udemy.com/)
- [VIPKID](https://www.vipkid.com.cn/)
- [Yahoo!](https://yahoo.com/)
- [Zalando](https://www.zalando.com)
More screenshots
@@ -120,29 +198,3 @@ More screenshots
![superset-sql-lab-2](https://cloud.githubusercontent.com/assets/130878/20234713/0f67b856-a835-11e6-9d50-7a52168f66fd.png)
![superset-sql-lab](https://cloud.githubusercontent.com/assets/130878/20234714/0f68f45a-a835-11e6-9467-f47ad0af7e79.png)
Resources
-------------
* [Superset Google Group](https://groups.google.com/forum/#!forum/airbnb_superset)
* [Gitter (live chat) Channel](https://gitter.im/airbnb/superset)
* [Docker image](https://hub.docker.com/r/amancevice/superset/) (community contributed)
* [Slides from Strata (March 2016)](https://drive.google.com/open?id=0B5PVE0gzO81oOVJkdF9aNkJMSmM)
Tip of the Hat
--------------
Superset would not be possible without these great frameworks / libs
* Flask App Builder - Allowing us to focus on building the app quickly while
getting the foundation for free
* The Flask ecosystem - Simply amazing. So much Plug, easy play.
* NVD3 - One of the best charting libraries out there
* Much more, check out the `install_requires` section in the [setup.py](https://github.com/airbnb/superset/blob/master/setup.py) file!
Contributing
------------
Interested in contributing? Casual hacking? Check out [Contributing.MD](https://github.com/airbnb/superset/blob/master/CONTRIBUTING.md)
-4
View File
@@ -1,4 +0,0 @@
[ignore: superset/assets/node_modules/**]
[python: superset/**.py]
[jinja2: superset/**/templates/**.html]
encoding = utf-8
-1809
View File
File diff suppressed because it is too large Load Diff
+2 -1
View File
@@ -7,7 +7,8 @@ mysqlclient
nose
psycopg2
pylint
pythrifthiveapi
pyyaml
redis
statsd
# Also install everything we need to build Sphinx docs
-r dev-reqs-for-docs.txt
+1
View File
@@ -0,0 +1 @@
Folder containing the sphinx-generated documentation
+1 -1
View File
@@ -51,7 +51,7 @@ source_suffix = '.rst'
master_doc = 'index'
# General information about the project.
project = "Superset's documentation"
project = "Apache Superset"
copyright = None
author = u'Maxime Beauchemin'
+135 -10
View File
@@ -45,15 +45,31 @@ visualizations.
https://github.com/airbnb/superset/issues?q=label%3Aexample+is%3Aclosed
Can I upload and visualize csv data?
------------------------------------
Yes, using the ``Upload a CSV`` button under the ``Sources``
menu item. This brings up a form that allows you specify required information. After creating the table from CSV, it can then be loaded like any other on the ``Sources -> Tables``page.
Why are my queries timing out?
------------------------------
If you are seeing timeouts (504 Gateway Time-out) when running queries,
it's because the web server is timing out web requests. If you want to
increase the default (50), you can specify the timeout when starting the
web server with the ``-t`` flag, which is expressed in seconds.
There are many reasons may cause long query timing out.
``superset runserver -t 300``
- For running long query from Sql Lab, by default Superset allows it run as long as 6 hours before it being killed by celery. If you want to increase the time for running query, you can specify the timeout in configuration. For example:
``SQLLAB_ASYNC_TIME_LIMIT_SEC = 60 * 60 * 6``
- Superset is running on gunicorn web server, which may time out web requests. If you want to increase the default (50), you can specify the timeout when starting the web server with the ``-t`` flag, which is expressed in seconds.
``superset runserver -t 300``
- If you are seeing timeouts (504 Gateway Time-out) when loading dashboard or explore slice, you are probably behind gateway or proxy server (such as Nginx). If it did not receive a timely response from Superset server (which is processing long queries), these web servers will send 504 status code to clients directly. Superset has a client-side timeout limit to address this issue. If query didn't come back within clint-side timeout (60 seconds by default), Superset will display warning message to avoid gateway timeout message. If you have a longer gateway timeout limit, you can change the timeout settings in ``superset_config.py``:
``SUPERSET_WEBSERVER_TIMEOUT = 60``
Why is the map not visible in the mapbox visualization?
@@ -78,6 +94,11 @@ The widget also has a checkbox ``Date Filter``, which enables time filtering
capabilities to your dashboard. After checking the box and refreshing, you'll
see a ``from`` and a ``to`` dropdown show up.
By default, the filtering will be applied to all the slices that are built
on top of a datasource that shares the column name that the filter is based
on. It's also a requirement for that column to be checked as "filterable"
in the column tab of the table editor.
But what about if you don't want certain widgets to get filtered on your
dashboard? You can do that by editing your dashboard, and in the form,
edit the ``JSON Metadata`` field, more specifically the
@@ -85,7 +106,7 @@ edit the ``JSON Metadata`` field, more specifically the
never be affected by any dashboard level filtering.
..code::
..code:: json
{
"filter_immune_slices": [324, 65, 92],
@@ -93,7 +114,8 @@ never be affected by any dashboard level filtering.
"filter_immune_slice_fields": {
"177": ["country_name", "__from", "__to"],
"32": ["__from", "__to"]
}
},
"timed_refresh_immune_slices": [324]
}
In the json blob above, slices 324, 65 and 92 won't be affected by any
@@ -110,12 +132,115 @@ But what happens with filtering when dealing with slices coming from
different tables or databases? If the column name is shared, the filter will
be applied, it's as simple as that.
How to limit the timed refresh on a dashboard?
----------------------------------------------
By default, the dashboard timed refresh feature allows you to automatically re-query every slice
on a dashboard according to a set schedule. Sometimes, however, you won't want all of the slices
to be refreshed - especially if some data is slow moving, or run heavy queries. To exclude specific
slices from the timed refresh process, add the ``timed_refresh_immune_slices`` key to the dashboard
``JSON Metadata`` field:
..code:: json
{
"filter_immune_slices": [],
"expanded_slices": {},
"filter_immune_slice_fields": {},
"timed_refresh_immune_slices": [324]
}
In the example above, if a timed refresh is set for the dashboard, then every slice except 324 will
be automatically re-queried on schedule.
Slice refresh will also be staggered over the specified period. You can turn off this staggering
by setting the ``stagger_refresh`` to ``false`` and modify the stagger period by setting
``stagger_time`` to a value in milliseconds in the ``JSON Metadata`` field:
..code:: json
{
"stagger_refresh": false,
"stagger_time": 2500
}
Here, the entire dashboard will refresh at once if periodic refresh is on. The stagger time of
2.5 seconds is ignored.
Why does fabmanager or superset freezed/hung/not responding when started (my home directory is NFS mounted)?
-----------------------------------------------------------------------------------------
superset creates and uses an sqlite database at ``~/.superset/superset.db``. Sqlite is known to `don't work well if used on NFS`__ due to broken file locking implementation on NFS.
By default, superset creates and uses an sqlite database at ``~/.superset/superset.db``. Sqlite is known to `don't work well if used on NFS`__ due to broken file locking implementation on NFS.
__ https://www.sqlite.org/lockingv3.html
One work around is to create a symlink from ~/.superset to a directory located on a non-NFS partition.
You can override this path using the ``SUPERSET_HOME`` environment variable.
Another work around is to change where superset stores the sqlite database by adding ``SQLALCHEMY_DATABASE_URI = 'sqlite:////new/localtion/superset.db'`` in superset_config.py (create the file if needed), then adding the directory where superset_config.py lives to PYTHONPATH environment variable (e.g. ``export PYTHONPATH=/opt/logs/sandbox/airbnb/``).
Another work around is to change where superset stores the sqlite database by adding ``SQLALCHEMY_DATABASE_URI = 'sqlite:////new/location/superset.db'`` in superset_config.py (create the file if needed), then adding the directory where superset_config.py lives to PYTHONPATH environment variable (e.g. ``export PYTHONPATH=/opt/logs/sandbox/airbnb/``).
What if the table schema changed?
---------------------------------
Table schemas evolve, and Superset needs to reflect that. It's pretty common
in the life cycle of a dashboard to want to add a new dimension or metric.
To get Superset to discover your new columns, all you have to do is to
go to ``Menu -> Sources -> Tables``, click the ``edit`` icon next to the
table who's schema has changed, and hit ``Save`` from the ``Detail`` tab.
Behind the scene, the new columns will get merged it. Following this,
you may want to
re-edit the table afterwards to configure the ``Column`` tab, check the
appropriate boxes and save again.
How do I go about developing a new visualization type?
------------------------------------------------------
Here's an example as a Github PR with comments that describe what the
different sections of the code do:
https://github.com/airbnb/superset/pull/3013
What database engine can I use as a backend for Superset?
---------------------------------------------------------
To clarify, the *database backend* is an OLTP database used by Superset to store its internal
information like your list of users, slices and dashboard definitions.
Superset is tested using Mysql, Postgresql and Sqlite for its backend. It's recommended you
install Superset on one of these database server for production.
Using a column-store, non-OLTP databases like Vertica, Redshift or Presto as a database backend simply won't work as these databases are not designed for this type of workload. Installation on Oracle, Microsoft SQL Server, or other OLTP databases may work but isn't tested.
Please note that pretty much any databases that have a SqlAlchemy integration should work perfectly fine as a datasource for Superset, just not as the OLTP backend.
How can i configure OAuth authentication and authorization?
-----------------------------------------------------------
You can take a look at this Flask-AppBuilder `configuration example
<https://github.com/dpgaspar/Flask-AppBuilder/blob/master/examples/oauth/config.py>`_.
How can I set a default filter on my dashboard?
-----------------------------------------------
Easy. Simply apply the filter and save the dashboard while the filter
is active.
How do I get Superset to refresh the schema of my table?
--------------------------------------------------------
When adding columns to a table, you can have Superset detect and merge the
new columns in by using the "Refresh Metadata" action in the
``Source -> Tables`` page. Simply check the box next to the tables
you want the schema refreshed, and click ``Actions -> Refresh Metadata``.
Is there a way to force the use specific colors?
------------------------------------------------
It is possible on a per-dashboard basis by providing a mapping of
labels to colors in the ``JSON Metadata`` attribute using the
``label_colors`` key.
..code:: json
{
"label_colors": {
"Girls": "#FF69B4",
"Boys": "#ADD8E6"
}
}
+103
View File
@@ -0,0 +1,103 @@
Importing and Exporting Datasources
===================================
The superset cli allows you to import and export datasources from and to YAML.
Datasources include both databases and druid clusters. The data is expected to be organized in the following hierarchy: ::
.
├──databases
| ├──database_1
| | ├──table_1
| | | ├──columns
| | | | ├──column_1
| | | | ├──column_2
| | | | └──... (more columns)
| | | └──metrics
| | | ├──metric_1
| | | ├──metric_2
| | | └──... (more metrics)
| | └── ... (more tables)
| └── ... (more databases)
└──druid_clusters
├──cluster_1
| ├──datasource_1
| | ├──columns
| | | ├──column_1
| | | ├──column_2
| | | └──... (more columns)
| | └──metrics
| | ├──metric_1
| | ├──metric_2
| | └──... (more metrics)
| └── ... (more datasources)
└── ... (more clusters)
Exporting Datasources to YAML
-----------------------------
You can print your current datasources to stdout by running: ::
superset export_datasources
To save your datasources to a file run: ::
superset export_datasources -f <filename>
By default, default (null) values will be omitted. Use the ``-d`` flag to include them.
If you want back references to be included (e.g. a column to include the table id
it belongs to) use the ``-b`` flag.
Alternatively you can export datasources using the UI: ::
1. Open **Sources** -> **Databases** to export all tables associated to a single or multiple databases. (**Tables** for one or more tables, **Druid Clusters** for clusters, **Druid Datasources** for datasources)
2. Select the items you would like to export
3. Click **Actions** -> **Export to YAML**
4. If you want to import an item that you exported through the UI, you will need to nest it inside its parent element, e.g. a `database` needs to be nested under `databases` a `table` needs to be nested inside a `database` element.
Exporting the complete supported YAML schema
--------------------------------------------
In order to obtain an exhaustive list of all fields you can import using the YAML import run: ::
superset export_datasource_schema
Again, you can use the ``-b`` flag to include back references.
Importing Datasources from YAML
-------------------------------
In order to import datasources from a YAML file(s), run: ::
superset import_datasources -p <path or filename>
If you supply a path all files ending with ``*.yaml`` or ``*.yml`` will be parsed.
You can apply additional flags e.g.: ::
superset import_datasources -p <path> -r
Will search the supplied path recursively.
The sync flag ``-s`` takes parameters in order to sync the supplied elements with
your file. Be careful this can delete the contents of your meta database. Example:
superset import_datasources -p <path / filename> -s columns,metrics
This will sync all ``metrics`` and ``columns`` for all datasources found in the
``<path / filename>`` in the Superset meta database. This means columns and metrics
not specified in YAML will be deleted. If you would add ``tables`` to ``columns,metrics``
those would be synchronised as well.
If you don't supply the sync flag (``-s``) importing will only add and update (override) fields.
E.g. you can add a ``verbose_name`` to the the column ``ds`` in the table ``random_time_series`` from the example datasets
by saving the following YAML to file and then running the ``import_datasources`` command. ::
databases:
- database_name: main
tables:
- table_name: random_time_series
columns:
- column_name: ds
verbose_name: datetime
+26 -13
View File
@@ -1,10 +1,10 @@
.. image:: _static/img/s.png
Superset's documentation
''''''''''''''''''''''''
Apache Superset (incubating)
''''''''''''''''''''''''''''
Superset is a data exploration platform designed to be visual, intuitive
and interactive.
Apache Superset (incubating) is a modern, enterprise-ready business
intelligence web application
----------------
@@ -12,25 +12,37 @@ and interactive.
.. warning:: This project was originally named Panoramix, was renamed to
Caravel in March 2016, and is currently named Superset as of November 2016
.. important::
**Disclaimer**: Apache Superset is an effort undergoing incubation at The
Apache Software Foundation (ASF), sponsored by the Apache Incubator.
Incubation is required of all newly accepted projects until a further
review indicates that the infrastructure, communications, and
decision making process have stabilized in a manner consistent with
other successful ASF projects. While incubation status is not
necessarily a reflection of the completeness or stability of
the code, it does indicate that the project has yet to be fully
endorsed by the ASF.
Overview
=======================================
========
Features
---------
--------
- A rich set of data visualizations, integrated from some of the best
visualization libraries
- Create and share simple dashboards
- An extensible, high-granularity security/permission model allowing
intricate rules on who can access individual features and the dataset
- A rich set of data visualizations
- An easy-to-use interface for exploring and visualizing data
- Create and share dashboards
- Enterprise-ready authentication with integration with major authentication
providers (database, OpenID, LDAP, OAuth & REMOTE_USER through
Flask AppBuilder)
- An extensible, high-granularity security/permission model allowing
intricate rules on who can access individual features and the dataset
- A simple semantic layer, allowing users to control how data sources are
displayed in the UI by defining which fields should show up in which
drop-down and which aggregation and function metrics are made available
to the user
- Integration with most RDBMS through SqlAlchemy
- Integration with most SQL-speaking RDBMS through SQLAlchemy
- Deep integration with Druid.io
------
@@ -49,7 +61,7 @@ Features
Contents
---------
--------
.. toctree::
:maxdepth: 2
@@ -58,6 +70,7 @@ Contents
tutorial
security
sqllab
visualization
videos
gallery
druid
+202 -26
View File
@@ -8,6 +8,32 @@ Superset is tested against Python ``2.7`` and Python ``3.4``.
Airbnb currently uses 2.7.* in production. We do not plan on supporting
Python ``2.6``.
Cloud-native!
-------------
Superset is designed to be highly available. It is
"cloud-native" as it has been designed scale out in large,
distributed environments, and works well inside containers.
While you can easily
test drive Superset on a modest setup or simply on your laptop,
there's virtually no limit around scaling out the platform.
Superset is also cloud-native in the sense that it is
flexible and lets you choose your web server (Gunicorn, Nginx, Apache),
your metadata database engine (MySQL, Postgres, MariaDB, ...),
your message queue (Redis, RabbitMQ, SQS, ...),
your results backend (S3, Redis, Memcached, ...), your caching layer
(memcached, Redis, ...), works well with services like NewRelic, StatsD and
DataDog, and has the ability to run analytic workloads against
most popular database technologies.
Superset is battle tested in large environments with hundreds
of concurrent users. Airbnb's production environment runs inside
Kubernetes and serves 600+ daily active users viewing over 100K charts a
day.
The Superset web server and the Superset Celery workers (optional)
are stateless, so you can scale out by running on as many servers
as needed.
OS dependencies
---------------
@@ -36,7 +62,7 @@ that the required dependencies are installed: ::
**OSX**, system python is not recommended. brew's python also ships with pip ::
brew install pkg-config libffi openssl python
env LDFLAGS="-L$(brew --prefix openssl)/lib" CFLAGS="-I$(brew --prefix openssl)/include" pip install cryptography
env LDFLAGS="-L$(brew --prefix openssl)/lib" CFLAGS="-I$(brew --prefix openssl)/include" pip install cryptography==1.9
**Windows** isn't officially supported at this point, but if you want to
attempt it, download `get-pip.py <https://bootstrap.pypa.io/get-pip.py>`_, and run ``python get-pip.py`` which may need admin access. Then run the following: ::
@@ -107,10 +133,61 @@ the credential you entered while creating the admin account, and navigate to
your datasources for Superset to be aware of, and they should show up in
`Menu -> Datasources`, from where you can start playing with your data!
Please note that *gunicorn*, Superset default application server, does not
work on Windows so you need to use the development web server.
The development web server though is not intended to be used on production systems
so better use a supported platform that can run *gunicorn*.
A proper WSGI HTTP Server
-------------------------
While you can setup Superset to run on Nginx or Apache, many use
Gunicorn, preferably in **async mode**, which allows for impressive
concurrency even and is fairly easy to install and configure. Please
refer to the
documentation of your preferred technology to set up this Flask WSGI
application in a way that works well in your environment.
While the `superset runserver` command act as an quick wrapper
around `gunicorn`, it doesn't expose all the options you may need,
so you'll want to craft your own `gunicorn` command in your production
environment. Here's an **async** setup known to work well: ::
 gunicorn \
-w 10 \
-k gevent \
--timeout 120 \
-b 0.0.0.0:6666 \
--limit-request-line 0 \
--limit-request-field_size 0 \
--statsd-host localhost:8125 \
superset:app
Refer to the
[Gunicorn documentation](http://docs.gunicorn.org/en/stable/design.html)
for more information.
Note that *gunicorn* does not
work on Windows so the `superset runserver` command is not expected to work
in that context. Also note that the development web
server (`superset runserver -d`) is not intended for production use.
Flask-AppBuilder Permissions
----------------------------
By default every time the Flask-AppBuilder (FAB) app is initialized the
permissions and views are added automatically to the backend and associated with
the Admin role. The issue however is when you are running multiple concurrent
workers this creates a lot of contention and race conditions when defining
permissions and views.
To alleviate this issue, the automatic updating of permissions can be disabled
by setting the :envvar:`SUPERSET_UPDATE_PERMS` environment variable to `0`.
The value `1` enables it, `0` disables it. Note if undefined the functionality
is enabled to maintain backwards compatibility.
In a production environment initialization could take on the following form:
export SUPERSET_UPDATE_PERMS=1
superset init
export SUPERSET_UPDATE_PERMS=0
gunicorn -w 10 ... superset:app
Configuration behind a load balancer
------------------------------------
@@ -125,6 +202,11 @@ If the load balancer is inserting X-Forwarded-For/X-Forwarded-Proto headers, you
should set `ENABLE_PROXY_FIX = True` in the superset config file to extract and use
the headers.
In case that the reverse proxy is used for providing ssl encryption,
an explicit definition of the `X-Forwarded-Proto` may be required.
For the Apache webserver this can be set as follows: ::
 RequestHeader set X-Forwarded-Proto "https"
Configuration
-------------
@@ -156,7 +238,9 @@ of the parameters you can copy / paste in that configuration module: ::
SQLALCHEMY_DATABASE_URI = 'sqlite:////path/to/superset.db'
# Flask-WTF flag for CSRF
CSRF_ENABLED = True
WTF_CSRF_ENABLED = True
# Add endpoints that need to be exempt from CSRF protection
WTF_CSRF_EXEMPT_LIST = []
# Set this API key to enable Mapbox visualizations
MAPBOX_API_KEY = ''
@@ -172,6 +256,11 @@ Please make sure to change:
* *SQLALCHEMY_DATABASE_URI*, by default it is stored at *~/.superset/superset.db*
* *SECRET_KEY*, to a long random string
In case you need to exempt endpoints from CSRF, e.g. you are running a custom
auth postback endpoint, you can add them to *WTF_CSRF_EXEMPT_LIST*
WTF_CSRF_EXEMPT_LIST = ['']
Database dependencies
---------------------
@@ -211,6 +300,11 @@ Here's a list of some of the recommended packages.
| Vertica | ``pip install | ``vertica+vertica_python://`` |
| | sqlalchemy-vertica-python`` | |
+---------------+-------------------------------------+-------------------------------------------------+
| ClickHouse | ``pip install | ``clickhouse://`` |
| | sqlalchemy-clickhouse`` | |
+---------------+-------------------------------------+-------------------------------------------------+
| Kylin | ``pip install kylinpy`` | ``kylin://`` |
+---------------+-------------------------------------+-------------------------------------------------+
Note that many other database are supported, the main criteria being the
existence of a functional SqlAlchemy dialect and Python driver. Googling
@@ -220,10 +314,6 @@ database you want to connect to should get you to the right place.
(AWS) Athena
------------
This currently relies on an unreleased future version of `PyAthenaJDBC <https://github.com/laughingman7743/PyAthenaJDBC>`_. If you're adventurous or simply impatient, you can install directly from git: ::
pip install git+https://github.com/laughingman7743/PyAthenaJDBC@support_sqlalchemy
The connection string for Athena looks like this ::
awsathena+jdbc://{aws_access_key_id}:{aws_secret_access_key}@athena.{region_name}.amazonaws.com/{schema_name}?s3_staging_dir={s3_staging_dir}&...
@@ -281,6 +371,24 @@ on top of the **database**. For Superset to connect to a specific schema,
there's a **schema** parameter you can set in the table form.
External Password store for SQLAlchemy connections
--------------------------------------------------
It is possible to use an external store for you database passwords. This is
useful if you a running a custom secret distribution framework and do not wish
to store secrets in Superset's meta database.
Example:
Write a function that takes a single argument of type ``sqla.engine.url`` and returns
the password for the given connection string. Then set ``SQLALCHEMY_CUSTOM_PASSWORD_STORE``
in your config file to point to that function. ::
def example_lookup_password(url):
secret = <<get password from external framework>>
return 'secret'
SQLALCHEMY_CUSTOM_PASSWORD_STORE = example_lookup_password
SSL Access to databases
-----------------------
This example worked with a MySQL database that requires SSL. The configuration
@@ -302,10 +410,10 @@ Druid
-----
* From the UI, enter the information about your clusters in the
``Admin->Clusters`` menu by hitting the + sign.
`Sources -> Druid Clusters` menu by hitting the + sign.
* Once the Druid cluster connection information is entered, hit the
``Admin->Refresh Metadata`` menu item to populate
`Sources -> Refresh Druid Metadata` menu item to populate
* Navigate to your datasources
@@ -314,7 +422,7 @@ metadata from your Druid cluster(s)
CORS
-----
----
The extra CORS Dependency must be installed:
@@ -363,28 +471,79 @@ Upgrading should be as straightforward as running::
SQL Lab
-------
SQL Lab is a powerful SQL IDE that works with all SQLAlchemy compatible
databases out there. By default, queries are run in a web request, and
databases. By default, queries are executed in the scope of a web
request so they
may eventually timeout as queries exceed the maximum duration of a web
request in your environment, whether it'd be a reverse proxy or the Superset
server itself.
In the modern analytics world, it's not uncommon to run large queries that
run for minutes or hours.
On large analytic databases, it's common to run queries that
execute for minutes or hours.
To enable support for long running queries that
execute beyond the typical web request's timeout (30-60 seconds), it is
necessary to deploy an asynchronous backend, which consist of one or many
Superset worker, which is implemented as a Celery worker, and a Celery
broker for which we recommend using Redis or RabbitMQ.
necessary to configure an asynchronous backend for Superset which consist of:
It's also preferable to setup an async result backend as a key value store
that can hold the long-running query results for a period of time. More
details to come as to how to set this up here soon.
* one or many Superset worker (which is implemented as a Celery worker), and
can be started with the ``superset worker`` command, run
``superset worker --help`` to view the related options
* a celery broker (message queue) for which we recommend using Redis
or RabbitMQ
* a results backend that defines where the worker will persist the query
results
SQL Lab supports templating in queries, and it's possible to override
Configuring Celery requires defining a ``CELERY_CONFIG`` in your
``superset_config.py``. Both the worker and web server processes should
have the same configuration.
.. code-block:: python
class CeleryConfig(object):
BROKER_URL = 'redis://localhost:6379/0'
CELERY_IMPORTS = ('superset.sql_lab', )
CELERY_RESULT_BACKEND = 'redis://localhost:6379/0'
CELERY_ANNOTATIONS = {'tasks.add': {'rate_limit': '10/s'}}
CELERY_CONFIG = CeleryConfig
To setup a result backend, you need to pass an instance of a derivative
of ``werkzeug.contrib.cache.BaseCache`` to the ``RESULTS_BACKEND``
configuration key in your ``superset_config.py``. It's possible to use
Memcached, Redis, S3 (https://pypi.python.org/pypi/s3werkzeugcache),
memory or the file system (in a single server-type setup or for testing),
or to write your own caching interface. Your ``superset_config.py`` may
look something like:
.. code-block:: python
# On S3
from s3cache.s3cache import S3Cache
S3_CACHE_BUCKET = 'foobar-superset'
S3_CACHE_KEY_PREFIX = 'sql_lab_result'
RESULTS_BACKEND = S3Cache(S3_CACHE_BUCKET, S3_CACHE_KEY_PREFIX)
# On Redis
from werkzeug.contrib.cache import RedisCache
RESULTS_BACKEND = RedisCache(
host='localhost', port=6379, key_prefix='superset_results')
Note that it's important that all the worker nodes and web servers in
the Superset cluster share a common metadata database.
This means that SQLite will not work in this context since it has
limited support for concurrency and
typically lives on the local file system.
Also note that SQL Lab supports Jinja templating in queries, and that it's
possible to overload
the default Jinja context in your environment by defining the
``JINJA_CONTEXT_ADDONS`` in your superset configuration. Objects referenced
in this dictionary are made available for users to use in their SQL.
.. code-block:: python
JINJA_CONTEXT_ADDONS = {
'my_crazy_macro': lambda x: x*2,
}
Making your own build
---------------------
@@ -395,8 +554,8 @@ your environment.::
# assuming $SUPERSET_HOME as the root of the repo
cd $SUPERSET_HOME/superset/assets
npm install
npm run build
yarn
yarn run build
cd $SUPERSET_HOME
python setup.py install
@@ -406,7 +565,7 @@ Blueprints
`Blueprints are Flask's reusable apps <http://flask.pocoo.org/docs/0.12/blueprints/>`_.
Superset allows you to specify an array of Blueprints
an array of Blueprints in your ``superset_config`` module. Here's
in your ``superset_config`` module. Here's
an example on how this can work with a simple Blueprint. By doing
so, you can expect Superset to serve a page that says "OK"
at the ``/simple_page`` url. This can allow you to run other things such
@@ -424,3 +583,20 @@ same server.
return "Ok"
BLUEPRINTS = [simple_page]
StatsD logging
--------------
Superset is instrumented to log events to StatsD if desired. Most endpoints hit
are logged as well as key events like query start and end in SQL Lab.
To setup StatsD logging, it's a matter of configuring the logger in your
``superset_config.py``.
..code ::
from superset.stats_logger import StatsdStatsLogger
STATS_LOGGER = StatsdStatsLogger(host='localhost', port=8125, prefix='superset')
Note that it's also possible to implement you own logger by deriving
``superset.stats_logger.BaseStatsLogger``.
+4 -3
View File
@@ -3,13 +3,14 @@ Security
Security in Superset is handled by Flask AppBuilder (FAB). FAB is a
"Simple and rapid application development framework, built on top of Flask.".
FAB provides authentication, user management, permissions and roles.
Please read its `Security documentation
<http://flask-appbuilder.readthedocs.io/en/latest/security.html>`_.
Provided Roles
--------------
Superset ships with a set of roles that are handled by Superset itself.
You can assume that these roles will stay up-to-date as Superset evolves.
Even though it's possible for ``Admin`` usrs to do so, it is not recommended
Even though it's possible for ``Admin`` users to do so, it is not recommended
that you alter these roles in any way by removing
or adding permissions to them as these roles will be re-synchronized to
their original values as you run your next ``superset init`` command.
@@ -35,7 +36,7 @@ own. Alpha users can add and alter data sources.
Gamma
"""""
Gamma have limited access. They can only consume data coming from data sources
they have been giving access to through another complementary role.
they have been given access to through another complementary role.
They only have access to view the slices and
dashboards made from data sources that they have access to. Currently Gamma
users are not able to alter or add data sources. We assume that they are
+12 -2
View File
@@ -13,9 +13,11 @@ Feature Overview
visualization capabilities
- Browse database metadata: tables, columns, indexes, partitions
- Support for long-running queries
- uses the `Celery distributed queue <http://www.python.org/>`_
to dispatch query handling to workers
- supports defining a "results backend" to persist query results
- A search engine to find queries executed in the past
- Supports templating using the
`Jinja templating language <http://jinja.pocoo.org/docs/dev/>`_
@@ -46,17 +48,25 @@ Available macros
We expose certain modules from Python's standard library in
Superset's Jinja context:
- ``time``: ``time``
- ``datetime``: ``datetime.datetime``
- ``uuid``: ``uuid``
- ``random``: ``random``
- ``relativedelta``: ``dateutil.relativedelta.relativedelta``
- more to come!
`Jinja's builtin filters <http://jinja.pocoo.org/docs/dev/templates/>`_ can be also be applied where needed.
.. autoclass:: superset.jinja_context.PrestoTemplateProcessor
:members:
.. autofunction:: superset.jinja_context.url_param
Extending macros
''''''''''''''''
As mentioned in the `Installation & Configuration <https://superset.incubator.apache.org/installation.html#installation-configuration>`_ documentation,
it's possible for administrators to expose more more macros in their
environment using the configuration variable ``JINJA_CONTEXT_ADDONS``.
All objects referenced in this dictionary will become available for users
to integrate in their queries in **SQL Lab**.
+1 -1
View File
@@ -23,7 +23,7 @@ Under the **Sources** menu, select the *Databases* option:
.. image:: _static/img/tutorial/tutorial_01_sources_database.png
:scale: 70%
On the resulting page, click on the green plus sign, near the top left:
On the resulting page, click on the green plus sign, near the top right:
.. image:: _static/img/tutorial/tutorial_02_add_database.png
:scale: 70%
File diff suppressed because it is too large Load Diff
BIN
View File
Binary file not shown.
+7
View File
@@ -0,0 +1,7 @@
# requires github-changes, run
# `npm install -g github-changes`
# requires $GITHUB_TOKEN to be set
# usage: ./github-changes 0.20.0 0.20.1
# will overwrites the local CHANGELOG.md, somehow you need to merge it in
github-changes -o apache -r incubator-superset --token $GITHUB_TOKEN --between-tags $1...$2
+3 -1
View File
@@ -9,4 +9,6 @@ set -e
superset/bin/superset db upgrade
superset/bin/superset version -v
python setup.py nosetests
coveralls
if [ "$CI" = "true" ] ; then
coveralls
fi
+2 -1
View File
@@ -1,6 +1,7 @@
from superset import sm
from collections import defaultdict
from superset import sm
def cleanup_permissions():
# 1. Clean up duplicates.
-3
View File
@@ -23,6 +23,3 @@ detailed-errors=1
with-coverage=1
nocapture=1
cover-package=superset
[pycodestyle]
max-line-length=90
+33 -21
View File
@@ -1,7 +1,8 @@
import json
import os
import subprocess
import json
from setuptools import setup, find_packages
from setuptools import find_packages, setup
BASE_DIR = os.path.abspath(os.path.dirname(__file__))
PACKAGE_DIR = os.path.join(BASE_DIR, 'superset', 'static', 'assets')
@@ -14,18 +15,19 @@ def get_git_sha():
try:
s = str(subprocess.check_output(['git', 'rev-parse', 'HEAD']))
return s.strip()
except:
return ""
except Exception:
return ''
GIT_SHA = get_git_sha()
version_info = {
'GIT_SHA': GIT_SHA,
'version': version_string,
}
print("-==-" * 15)
print("VERSION: " + version_string)
print("GIT SHA: " + GIT_SHA)
print("-==-" * 15)
print('-==-' * 15)
print('VERSION: ' + version_string)
print('GIT SHA: ' + GIT_SHA)
print('-==-' * 15)
with open(os.path.join(PACKAGE_DIR, 'version_info.json'), 'w') as version_file:
json.dump(version_info, version_file)
@@ -34,41 +36,50 @@ with open(os.path.join(PACKAGE_DIR, 'version_info.json'), 'w') as version_file:
setup(
name='superset',
description=(
"A interactive data visualization platform build on SqlAlchemy "
"and druid.io"),
'A interactive data visualization platform build on SqlAlchemy '
'and druid.io'),
version=version_string,
packages=find_packages(),
include_package_data=True,
zip_safe=False,
scripts=['superset/bin/superset'],
install_requires=[
'boto3==1.4.4',
'celery==3.1.23',
'cryptography==1.8.1',
'flask-appbuilder==1.8.1',
'boto3>=1.4.6',
'celery==4.1.0',
'colorama==0.3.9',
'cryptography==1.9',
'flask==0.12.2',
'flask-appbuilder==1.9.5',
'flask-cache==0.13.1',
'flask-migrate==2.0.3',
'flask-script==2.0.5',
'flask-sqlalchemy==2.0',
'flask-sqlalchemy==2.1',
'flask-testing==0.6.2',
'flask-wtf==0.14.2',
'flower==0.9.2',
'future>=0.16.0, <0.17',
'python-geohash==0.8.5',
'humanize==0.5.1',
'gunicorn==19.7.1',
'idna==2.5',
'markdown==2.6.8',
'pandas==0.19.2',
'pandas==0.20.3',
'parsedatetime==2.0.0',
'pathlib2==2.3.0',
'polyline==1.3.2',
'pydruid==0.3.1',
'PyHive>=0.2.1',
'PyHive>=0.4.0',
'python-dateutil==2.6.0',
'requests==2.13.0',
'pyyaml>=3.11',
'requests==2.17.3',
'simplejson==3.10.0',
'six==1.10.0',
'sqlalchemy==1.1.9',
'sqlalchemy-utils==0.32.14',
'six==1.11.0',
'sqlalchemy==1.2.2',
'sqlalchemy-utils==0.32.21',
'sqlparse==0.2.3',
'thrift>=0.9.3',
'thrift-sasl>=0.2.1',
'unidecode>=0.04.21',
],
extras_require={
'cors': ['Flask-Cors>=2.0.0'],
@@ -78,6 +89,7 @@ setup(
'coverage',
'mock',
'nose',
'redis',
],
author='Maxime Beauchemin',
author_email='maximebeauchemin@gmail.com',
+78 -18
View File
@@ -4,14 +4,13 @@ from __future__ import division
from __future__ import print_function
from __future__ import unicode_literals
import json
import logging
from logging.handlers import TimedRotatingFileHandler
import json
import os
from flask import Flask, redirect
from flask_appbuilder import SQLA, AppBuilder, IndexView
from flask_appbuilder import AppBuilder, IndexView, SQLA
from flask_appbuilder.baseviews import expose
from flask_migrate import Migrate
from flask_wtf.csrf import CSRFProtect
@@ -20,24 +19,57 @@ from werkzeug.contrib.fixers import ProxyFix
from superset.connectors.connector_registry import ConnectorRegistry
from superset import utils, config # noqa
APP_DIR = os.path.dirname(__file__)
CONFIG_MODULE = os.environ.get('SUPERSET_CONFIG', 'superset.config')
if not os.path.exists(config.DATA_DIR):
os.makedirs(config.DATA_DIR)
with open(APP_DIR + '/static/assets/backendSync.json', 'r') as f:
frontend_config = json.load(f)
app = Flask(__name__)
app.config.from_object(CONFIG_MODULE)
conf = app.config
#################################################################
# Handling manifest file logic at app start
#################################################################
MANIFEST_FILE = APP_DIR + '/static/assets/dist/manifest.json'
manifest = {}
def parse_manifest_json():
global manifest
try:
with open(MANIFEST_FILE, 'r') as f:
manifest = json.load(f)
except Exception:
pass
def get_manifest_file(filename):
if app.debug:
parse_manifest_json()
return '/static/assets/dist/' + manifest.get(filename, '')
parse_manifest_json()
@app.context_processor
def get_js_manifest():
return dict(js_manifest=get_manifest_file)
#################################################################
for bp in conf.get('BLUEPRINTS'):
try:
print("Registering blueprint: '{}'".format(bp.name))
app.register_blueprint(bp)
except Exception as e:
print("blueprint registration failed")
print('blueprint registration failed')
logging.exception(e)
if conf.get('SILENCE_FAB'):
@@ -53,13 +85,16 @@ db = SQLA(app)
if conf.get('WTF_CSRF_ENABLED'):
csrf = CSRFProtect(app)
csrf_exempt_list = conf.get('WTF_CSRF_EXEMPT_LIST', [])
for ex in csrf_exempt_list:
csrf.exempt(ex)
utils.pessimistic_connection_handling(db.engine.pool)
utils.pessimistic_connection_handling(db.engine)
cache = utils.setup_cache(app, conf.get('CACHE_CONFIG'))
tables_cache = utils.setup_cache(app, conf.get('TABLE_NAMES_CACHE_CONFIG'))
migrate = Migrate(app, db, directory=APP_DIR + "/migrations")
migrate = Migrate(app, db, directory=APP_DIR + '/migrations')
# Logging configuration
logging.basicConfig(format=app.config.get('LOG_FORMAT'))
@@ -67,10 +102,11 @@ logging.getLogger().setLevel(app.config.get('LOG_LEVEL'))
if app.config.get('ENABLE_TIME_ROTATE'):
logging.getLogger().setLevel(app.config.get('TIME_ROTATE_LOG_LEVEL'))
handler = TimedRotatingFileHandler(app.config.get('FILENAME'),
when=app.config.get('ROLLOVER'),
interval=app.config.get('INTERVAL'),
backupCount=app.config.get('BACKUP_COUNT'))
handler = TimedRotatingFileHandler(
app.config.get('FILENAME'),
when=app.config.get('ROLLOVER'),
interval=app.config.get('INTERVAL'),
backupCount=app.config.get('BACKUP_COUNT'))
logging.getLogger().addHandler(handler)
if app.config.get('ENABLE_CORS'):
@@ -80,6 +116,21 @@ if app.config.get('ENABLE_CORS'):
if app.config.get('ENABLE_PROXY_FIX'):
app.wsgi_app = ProxyFix(app.wsgi_app)
if app.config.get('ENABLE_CHUNK_ENCODING'):
class ChunkedEncodingFix(object):
def __init__(self, app):
self.app = app
def __call__(self, environ, start_response):
# Setting wsgi.input_terminated tells werkzeug.wsgi to ignore
# content-length and read the stream till the end.
if environ.get('HTTP_TRANSFER_ENCODING', '').lower() == u'chunked':
environ['wsgi.input_terminated'] = True
return self.app(environ, start_response)
app.wsgi_app = ChunkedEncodingFix(app.wsgi_app)
if app.config.get('UPLOAD_FOLDER'):
try:
os.makedirs(app.config.get('UPLOAD_FOLDER'))
@@ -95,20 +146,29 @@ class MyIndexView(IndexView):
def index(self):
return redirect('/superset/welcome')
appbuilder = AppBuilder(
app, db.session,
app,
db.session,
base_template='superset/base.html',
indexview=MyIndexView,
security_manager_class=app.config.get("CUSTOM_SECURITY_MANAGER"))
security_manager_class=app.config.get('CUSTOM_SECURITY_MANAGER'),
update_perms=utils.get_update_perms_flag(),
)
sm = appbuilder.sm
get_session = appbuilder.get_session
results_backend = app.config.get("RESULTS_BACKEND")
results_backend = app.config.get('RESULTS_BACKEND')
# Registering sources
module_datasource_map = app.config.get("DEFAULT_MODULE_DS_MAP")
module_datasource_map.update(app.config.get("ADDITIONAL_MODULE_DS_MAP"))
module_datasource_map = app.config.get('DEFAULT_MODULE_DS_MAP')
module_datasource_map.update(app.config.get('ADDITIONAL_MODULE_DS_MAP'))
ConnectorRegistry.register_sources(module_datasource_map)
# Hook that provides administrators a handle on the Flask APP
# after initialization
flask_app_mutator = app.config.get('FLASK_APP_MUTATOR')
if flask_app_mutator:
flask_app_mutator(app)
from superset import views # noqa
+1 -1
View File
@@ -1,3 +1,3 @@
{
"presets" : ["airbnb", "es2015", "react"],
"presets" : ["airbnb"],
}
File diff suppressed because it is too large Load Diff

Before

Width:  |  Height:  |  Size: 6.6 KiB

After

Width:  |  Height:  |  Size: 6.6 KiB

Before

Width:  |  Height:  |  Size: 29 KiB

After

Width:  |  Height:  |  Size: 29 KiB

Before

Width:  |  Height:  |  Size: 6.1 KiB

After

Width:  |  Height:  |  Size: 6.1 KiB

Before

Width:  |  Height:  |  Size: 22 KiB

After

Width:  |  Height:  |  Size: 22 KiB

Before

Width:  |  Height:  |  Size: 12 KiB

After

Width:  |  Height:  |  Size: 12 KiB

Before

Width:  |  Height:  |  Size: 3.2 KiB

After

Width:  |  Height:  |  Size: 3.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 5.5 KiB

After

Width:  |  Height:  |  Size: 6.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 154 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 19 KiB

After

Width:  |  Height:  |  Size: 24 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 398 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 296 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 225 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 177 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.0 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 968 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 511 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 433 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 777 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 578 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 106 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 100 KiB

After

Width:  |  Height:  |  Size: 161 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 743 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 230 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 194 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 82 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 64 KiB

+102 -34
View File
@@ -1,6 +1,7 @@
/* global notify */
import shortid from 'shortid';
import { now } from '../modules/dates';
import { t } from '../locales';
const $ = require('jquery');
@@ -19,7 +20,10 @@ export const QUERY_EDITOR_SET_SCHEMA = 'QUERY_EDITOR_SET_SCHEMA';
export const QUERY_EDITOR_SET_TITLE = 'QUERY_EDITOR_SET_TITLE';
export const QUERY_EDITOR_SET_AUTORUN = 'QUERY_EDITOR_SET_AUTORUN';
export const QUERY_EDITOR_SET_SQL = 'QUERY_EDITOR_SET_SQL';
export const QUERY_EDITOR_SET_TEMPLATE_PARAMS = 'QUERY_EDITOR_SET_TEMPLATE_PARAMS';
export const QUERY_EDITOR_SET_SELECTED_TEXT = 'QUERY_EDITOR_SET_SELECTED_TEXT';
export const QUERY_EDITOR_PERSIST_HEIGHT = 'QUERY_EDITOR_PERSIST_HEIGHT';
export const SET_DATABASES = 'SET_DATABASES';
export const SET_ACTIVE_QUERY_EDITOR = 'SET_ACTIVE_QUERY_EDITOR';
export const SET_ACTIVE_SOUTHPANE_TAB = 'SET_ACTIVE_SOUTHPANE_TAB';
@@ -37,6 +41,10 @@ export const REMOVE_DATA_PREVIEW = 'REMOVE_DATA_PREVIEW';
export const CHANGE_DATA_PREVIEW_ID = 'CHANGE_DATA_PREVIEW_ID';
export const SAVE_QUERY = 'SAVE_QUERY';
export const CREATE_DATASOURCE_STARTED = 'CREATE_DATASOURCE_STARTED';
export const CREATE_DATASOURCE_SUCCESS = 'CREATE_DATASOURCE_SUCCESS';
export const CREATE_DATASOURCE_FAILED = 'CREATE_DATASOURCE_FAILED';
export function resetState() {
return { type: RESET_STATE };
}
@@ -47,8 +55,8 @@ export function saveQuery(query) {
type: 'POST',
url,
data: query,
success: () => notify.success('Your query was saved'),
error: () => notify.error('Your query could not be saved'),
success: () => notify.success(t('Your query was saved')),
error: () => notify.error(t('Your query could not be saved')),
dataType: 'json',
});
return { type: SAVE_QUERY };
@@ -101,7 +109,7 @@ export function fetchQueryResults(query) {
dispatch(querySuccess(query, results));
},
error(err) {
let msg = 'Failed at retrieving results from the results backend';
let msg = t('Failed at retrieving results from the results backend');
if (err.responseJSON && err.responseJSON.error) {
msg = err.responseJSON.error;
}
@@ -125,6 +133,7 @@ export function runQuery(query) {
tab: query.tab,
tmp_table_name: query.tempTableName,
select_as_cta: query.ctas,
templateParams: query.templateParams,
};
const sqlJsonUrl = '/superset/sql_json/' + location.search;
$.ajax({
@@ -146,10 +155,15 @@ export function runQuery(query) {
msg = err.responseText;
}
}
if (textStatus === 'error' && errorThrown === '') {
msg = 'Could not connect to server';
} else if (msg === null) {
msg = `[${textStatus}] ${errorThrown}`;
if (msg === null) {
if (errorThrown) {
msg = `[${textStatus}] ${errorThrown}`;
} else {
msg = t('Unknown error');
}
}
if (msg.indexOf('CSRF token') > 0) {
msg = t('Your session timed out, please refresh your page and try again.');
}
dispatch(queryFailed(query, msg));
},
@@ -161,15 +175,17 @@ export function postStopQuery(query) {
return function (dispatch) {
const stopQueryUrl = '/superset/stop_query/';
const stopQueryRequestData = { client_id: query.id };
dispatch(stopQuery(query));
$.ajax({
type: 'POST',
dataType: 'json',
url: stopQueryUrl,
data: stopQueryRequestData,
success() {
if (!query.runAsync) {
dispatch(stopQuery(query));
}
notify.success(t('Query was stopped.'));
},
error() {
notify.error(t('Failed at stopping query.'));
},
});
};
@@ -234,6 +250,10 @@ export function queryEditorSetSql(queryEditor, sql) {
return { type: QUERY_EDITOR_SET_SQL, queryEditor, sql };
}
export function queryEditorSetTemplateParams(queryEditor, templateParams) {
return { type: QUERY_EDITOR_SET_TEMPLATE_PARAMS, queryEditor, templateParams };
}
export function queryEditorSetSelectedText(queryEditor, sql) {
return { type: QUERY_EDITOR_SET_SELECTED_TEXT, queryEditor, sql };
}
@@ -244,6 +264,18 @@ export function mergeTable(table, query) {
export function addTable(query, tableName, schemaName) {
return function (dispatch) {
let table = {
dbId: query.dbId,
queryEditorId: query.id,
schema: schemaName,
name: tableName,
};
dispatch(mergeTable(Object.assign({}, table, {
isMetadataLoading: true,
isExtraMetadataLoading: true,
expanded: false,
})));
let url = `/superset/table/${query.dbId}/${tableName}/${schemaName}/`;
$.get(url, (data) => {
const dataPreviewQuery = {
@@ -257,36 +289,33 @@ export function addTable(query, tableName, schemaName) {
ctas: false,
};
// Merge table to tables in state
dispatch(mergeTable(
Object.assign(data, {
dbId: query.dbId,
queryEditorId: query.id,
schema: schemaName,
expanded: true,
}), dataPreviewQuery),
);
const newTable = Object.assign({}, table, data, {
expanded: true,
isMetadataLoading: false,
});
dispatch(mergeTable(newTable, dataPreviewQuery));
// Run query to get preview data for table
dispatch(runQuery(dataPreviewQuery));
})
.fail(() => {
dispatch(
addAlert({
msg: 'Error occurred while fetching metadata',
bsStyle: 'danger',
}),
);
const newTable = Object.assign({}, table, {
isMetadataLoading: false,
});
dispatch(mergeTable(newTable));
notify.error(t('Error occurred while fetching table metadata'));
});
url = `/superset/extra_table_metadata/${query.dbId}/${tableName}/${schemaName}/`;
$.get(url, (data) => {
const table = {
dbId: query.dbId,
queryEditorId: query.id,
schema: schemaName,
name: tableName,
};
Object.assign(table, data);
table = Object.assign({}, table, data, { isExtraMetadataLoading: false });
dispatch(mergeTable(table));
})
.fail(() => {
const newTable = Object.assign({}, table, {
isExtraMetadataLoading: false,
});
dispatch(mergeTable(newTable));
notify.error(t('Error occurred while fetching table metadata'));
});
};
}
@@ -328,6 +357,10 @@ export function refreshQueries(alteredQueries) {
return { type: REFRESH_QUERIES, alteredQueries };
}
export function persistEditorHeight(queryEditor, currentHeight) {
return { type: QUERY_EDITOR_PERSIST_HEIGHT, queryEditor, currentHeight };
}
export function popStoredQuery(urlId) {
return function (dispatch) {
$.ajax({
@@ -336,7 +369,7 @@ export function popStoredQuery(urlId) {
success: (data) => {
const newQuery = JSON.parse(data);
const queryEditorProps = {
title: newQuery.title ? newQuery.title : 'shared query',
title: newQuery.title ? newQuery.title : t('shared query'),
dbId: newQuery.dbId ? parseInt(newQuery.dbId, 10) : null,
schema: newQuery.schema ? newQuery.schema : null,
autorun: newQuery.autorun ? newQuery.autorun : false,
@@ -344,7 +377,7 @@ export function popStoredQuery(urlId) {
};
dispatch(addQueryEditor(queryEditorProps));
},
error: () => notify.error("The query couldn't be loaded"),
error: () => notify.error(t('The query couldn\'t be loaded')),
});
};
}
@@ -364,7 +397,42 @@ export function popSavedQuery(saveQueryId) {
};
dispatch(addQueryEditor(queryEditorProps));
},
error: () => notify.error("The query couldn't be loaded"),
error: () => notify.error(t('The query couldn\'t be loaded')),
});
};
}
export function createDatasourceStarted() {
return { type: CREATE_DATASOURCE_STARTED };
}
export function createDatasourceSuccess(response) {
const data = JSON.parse(response);
const datasource = `${data.table_id}__table`;
return { type: CREATE_DATASOURCE_SUCCESS, datasource };
}
export function createDatasourceFailed(err) {
return { type: CREATE_DATASOURCE_FAILED, err };
}
export function createDatasource(vizOptions, context) {
return (dispatch) => {
dispatch(createDatasourceStarted());
return $.ajax({
type: 'POST',
url: '/superset/sqllab_viz/',
async: false,
data: {
data: JSON.stringify(vizOptions),
},
context,
dataType: 'json',
success: (resp) => {
dispatch(createDatasourceSuccess(resp));
},
error: () => {
dispatch(createDatasourceFailed(t('An error occurred while creating the data source')));
},
});
};
}
@@ -1,4 +1,5 @@
import React from 'react';
import PropTypes from 'prop-types';
import AceEditor from 'react-ace';
import 'brace/mode/sql';
import 'brace/theme/github';
@@ -25,12 +26,13 @@ const sqlWords = sqlKeywords.map(s => ({
}));
const propTypes = {
actions: React.PropTypes.object.isRequired,
onBlur: React.PropTypes.func,
onAltEnter: React.PropTypes.func,
sql: React.PropTypes.string.isRequired,
tables: React.PropTypes.array,
queryEditor: React.PropTypes.object.isRequired,
actions: PropTypes.object.isRequired,
onBlur: PropTypes.func,
onAltEnter: PropTypes.func,
sql: PropTypes.string.isRequired,
tables: PropTypes.array,
queryEditor: PropTypes.object.isRequired,
height: PropTypes.string,
};
const defaultProps = {
@@ -44,6 +46,7 @@ class AceEditorWrapper extends React.PureComponent {
super(props);
this.state = {
sql: props.sql,
selectedText: '',
};
}
componentDidMount() {
@@ -76,8 +79,13 @@ class AceEditorWrapper extends React.PureComponent {
});
editor.$blockScrolling = Infinity; // eslint-disable-line no-param-reassign
editor.selection.on('changeSelection', () => {
this.props.actions.queryEditorSetSelectedText(
this.props.queryEditor, editor.getSelectedText());
const selectedText = editor.getSelectedText();
// Backspace trigger 1 character selection, ignoring
if (selectedText !== this.state.selectedText && selectedText.length !== 1) {
this.setState({ selectedText });
this.props.actions.queryEditorSetSelectedText(
this.props.queryEditor, selectedText);
}
});
}
getCompletions(aceEditor, session, pos, prefix, callback) {
@@ -118,8 +126,7 @@ class AceEditorWrapper extends React.PureComponent {
theme="github"
onLoad={this.onEditorLoad.bind(this)}
onBlur={this.onBlur.bind(this)}
minLines={12}
maxLines={12}
height={this.props.height}
onChange={this.textChange.bind(this)}
width="100%"
editorProps={{ $blockScrolling: true }}
@@ -1,4 +1,5 @@
import React from 'react';
import PropTypes from 'prop-types';
import { bindActionCreators } from 'redux';
import { connect } from 'react-redux';
@@ -69,7 +70,7 @@ class App extends React.PureComponent {
}
return (
<div className="App SqlLab">
<AlertsWrapper />
<AlertsWrapper initMessages={this.props.initMessages} />
<div className="container-fluid">
{content}
</div>
@@ -79,13 +80,15 @@ class App extends React.PureComponent {
}
App.propTypes = {
alerts: React.PropTypes.array,
actions: React.PropTypes.object,
alerts: PropTypes.array,
actions: PropTypes.object,
initMessages: PropTypes.array,
};
function mapStateToProps(state) {
return {
alerts: state.alerts,
initMessages: state.flash_messages,
};
}
function mapDispatchToProps(dispatch) {
@@ -1,9 +1,10 @@
import React from 'react';
import PropTypes from 'prop-types';
import { OverlayTrigger, Tooltip } from 'react-bootstrap';
const propTypes = {
column: React.PropTypes.object.isRequired,
column: PropTypes.object.isRequired,
};
const iconMap = {
@@ -1,9 +1,11 @@
import React from 'react';
import PropTypes from 'prop-types';
import CopyToClipboard from '../../components/CopyToClipboard';
import { storeQuery } from '../../../utils/common';
import { t } from '../../locales';
const propTypes = {
queryEditor: React.PropTypes.object.isRequired,
queryEditor: PropTypes.object.isRequired,
};
export default class CopyQueryTabUrl extends React.PureComponent {
@@ -25,10 +27,10 @@ export default class CopyQueryTabUrl extends React.PureComponent {
inMenu
copyNode={(
<div>
<i className="fa fa-clipboard" /> <span>share query</span>
<i className="fa fa-clipboard" /> <span>{t('share query')}</span>
</div>
)}
tooltipText="copy URL to clipboard"
tooltipText={t('copy URL to clipboard')}
shouldShowText={false}
getText={this.getUrl.bind(this)}
/>
@@ -1,64 +0,0 @@
import React from 'react';
import { bindActionCreators } from 'redux';
import { connect } from 'react-redux';
import { Modal } from 'react-bootstrap';
import * as Actions from '../actions';
import ResultSet from './ResultSet';
const propTypes = {
queries: React.PropTypes.object,
actions: React.PropTypes.object,
showDataPreviewModal: React.PropTypes.bool,
dataPreviewQueryId: React.PropTypes.string,
};
class DataPreviewModal extends React.PureComponent {
hide() {
this.props.actions.hideDataPreview();
}
render() {
if (this.props.showDataPreviewModal && this.props.dataPreviewQueryId) {
const query = this.props.queries[this.props.dataPreviewQueryId];
return (
<Modal
show={this.props.showDataPreviewModal}
onHide={this.hide.bind(this)}
bsStyle="lg"
>
<Modal.Header closeButton>
<Modal.Title>
Data preview for <strong>{query.tableName}</strong>
</Modal.Title>
</Modal.Header>
<Modal.Body>
<ResultSet
query={query}
visualize={false}
csv={false}
actions={this.props.actions}
height={400}
/>
</Modal.Body>
</Modal>
);
}
return null;
}
}
DataPreviewModal.propTypes = propTypes;
function mapStateToProps(state) {
return {
queries: state.queries,
showDataPreviewModal: state.showDataPreviewModal,
dataPreviewQueryId: state.dataPreviewQueryId,
};
}
function mapDispatchToProps(dispatch) {
return {
actions: bindActionCreators(Actions, dispatch),
};
}
export default connect(mapStateToProps, mapDispatchToProps)(DataPreviewModal);
@@ -1,7 +1,14 @@
import React from 'react';
import SyntaxHighlighter from 'react-syntax-highlighter';
import { github } from 'react-syntax-highlighter/dist/styles';
import PropTypes from 'prop-types';
import SyntaxHighlighter, { registerLanguage } from 'react-syntax-highlighter/dist/light';
import sql from 'react-syntax-highlighter/dist/languages/sql';
import github from 'react-syntax-highlighter/dist/styles/github';
import ModalTrigger from '../../components/ModalTrigger';
import { t } from '../../locales';
registerLanguage('sql', sql);
const defaultProps = {
maxWidth: 50,
@@ -10,11 +17,11 @@ const defaultProps = {
};
const propTypes = {
sql: React.PropTypes.string.isRequired,
rawSql: React.PropTypes.string,
maxWidth: React.PropTypes.number,
maxLines: React.PropTypes.number,
shrink: React.PropTypes.bool,
sql: PropTypes.string.isRequired,
rawSql: PropTypes.string,
maxWidth: PropTypes.number,
maxLines: PropTypes.number,
shrink: PropTypes.bool,
};
class HighlightedSql extends React.Component {
@@ -25,8 +32,8 @@ class HighlightedSql extends React.Component {
};
}
shrinkSql() {
const sql = this.props.sql || '';
let lines = sql.split('\n');
const ssql = this.props.sql || '';
let lines = ssql.split('\n');
if (lines.length >= this.props.maxLines) {
lines = lines.slice(0, this.props.maxLines);
lines.push('{...}');
@@ -51,7 +58,7 @@ class HighlightedSql extends React.Component {
if (this.props.rawSql && this.props.rawSql !== this.props.sql) {
rawSql = (
<div>
<h4>Raw SQL</h4>
<h4>{t('Raw SQL')}</h4>
<SyntaxHighlighter language="sql" style={github}>
{this.props.rawSql}
</SyntaxHighlighter>
@@ -61,7 +68,7 @@ class HighlightedSql extends React.Component {
this.setState({
modalBody: (
<div>
<h4>Source SQL</h4>
<h4>{t('Source SQL')}</h4>
<SyntaxHighlighter language="sql" style={github}>
{this.props.sql}
</SyntaxHighlighter>
@@ -73,7 +80,7 @@ class HighlightedSql extends React.Component {
render() {
return (
<ModalTrigger
modalTitle="SQL"
modalTitle={t('SQL')}
triggerNode={this.triggerNode()}
modalBody={this.state.modalBody}
beforeOpen={this.generateModal.bind(this)}
@@ -1,14 +1,15 @@
import React from 'react';
import PropTypes from 'prop-types';
import { OverlayTrigger, Tooltip } from 'react-bootstrap';
const propTypes = {
children: React.PropTypes.node,
className: React.PropTypes.string,
href: React.PropTypes.string,
onClick: React.PropTypes.func,
placement: React.PropTypes.string,
style: React.PropTypes.object,
tooltip: React.PropTypes.string,
children: PropTypes.node,
className: PropTypes.string,
href: PropTypes.string,
onClick: PropTypes.func,
placement: PropTypes.string,
style: PropTypes.object,
tooltip: PropTypes.string,
};
const defaultProps = {
className: '',
@@ -1,4 +1,5 @@
import React from 'react';
import PropTypes from 'prop-types';
import { bindActionCreators } from 'redux';
import { connect } from 'react-redux';
import * as Actions from '../actions';
@@ -35,7 +36,7 @@ class QueryAutoRefresh extends React.PureComponent {
stopwatch() {
// only poll /superset/queries/ if there are started or running queries
if (this.shouldCheckForQueries()) {
const url = '/superset/queries/' + (this.props.queriesLastUpdate - QUERY_UPDATE_BUFFER_MS);
const url = `/superset/queries/${this.props.queriesLastUpdate - QUERY_UPDATE_BUFFER_MS}`;
$.getJSON(url, (data) => {
if (Object.keys(data).length > 0) {
this.props.actions.refreshQueries(data);
@@ -48,9 +49,9 @@ class QueryAutoRefresh extends React.PureComponent {
}
}
QueryAutoRefresh.propTypes = {
queries: React.PropTypes.object.isRequired,
actions: React.PropTypes.object.isRequired,
queriesLastUpdate: React.PropTypes.number.isRequired,
queries: PropTypes.object.isRequired,
actions: PropTypes.object.isRequired,
queriesLastUpdate: PropTypes.number.isRequired,
};
function mapStateToProps(state) {
@@ -1,11 +1,13 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Alert } from 'react-bootstrap';
import QueryTable from './QueryTable';
import { t } from '../../locales';
const propTypes = {
queries: React.PropTypes.array.isRequired,
actions: React.PropTypes.object.isRequired,
queries: PropTypes.array.isRequired,
actions: PropTypes.object.isRequired,
};
const QueryHistory = (props) => {
@@ -23,7 +25,7 @@ const QueryHistory = (props) => {
}
return (
<Alert bsStyle="info">
No query history yet...
{t('No query history yet...')}
</Alert>
);
};
@@ -1,4 +1,5 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Button } from 'react-bootstrap';
import Select from 'react-select';
import QueryTable from './QueryTable';
@@ -6,12 +7,13 @@ import { now, epochTimeXHoursAgo,
epochTimeXDaysAgo, epochTimeXYearsAgo } from '../../modules/dates';
import { STATUS_OPTIONS, TIME_OPTIONS } from '../constants';
import AsyncSelect from '../../components/AsyncSelect';
import { t } from '../../locales';
const $ = window.$ = require('jquery');
const propTypes = {
actions: React.PropTypes.object.isRequired,
height: React.PropTypes.number.isRequired,
actions: PropTypes.object.isRequired,
height: PropTypes.number.isRequired,
};
class QuerySearch extends React.PureComponent {
@@ -101,7 +103,7 @@ class QuerySearch extends React.PureComponent {
if (data.result.length === 0) {
this.props.actions.addAlert({
bsStyle: 'danger',
msg: "It seems you don't have access to any database",
msg: t('It seems you don\'t have access to any database'),
});
}
return options;
@@ -149,44 +151,43 @@ class QuerySearch extends React.PureComponent {
type="text"
onChange={this.changeSearch.bind(this)}
className="form-control input-sm"
placeholder="Search Results"
placeholder={t('Search Results')}
/>
</div>
<div className="col-sm-1">
<div className="col-sm-4 search-date-filter-container">
<Select
name="select-from"
placeholder="[From]-"
placeholder={t('[From]-')}
options={TIME_OPTIONS
.slice(1, TIME_OPTIONS.length).map(t => ({ value: t, label: t }))}
.slice(1, TIME_OPTIONS.length).map(xt => ({ value: xt, label: xt }))}
value={this.state.from}
autosize={false}
onChange={this.changeFrom.bind(this)}
/>
</div>
<div className="col-sm-1">
<Select
name="select-to"
placeholder="[To]-"
options={TIME_OPTIONS.map(t => ({ value: t, label: t }))}
placeholder={t('[To]-')}
options={TIME_OPTIONS.map(xt => ({ value: xt, label: xt }))}
value={this.state.to}
autosize={false}
onChange={this.changeTo.bind(this)}
/>
</div>
<div className="col-sm-1">
<Select
name="select-status"
placeholder="[Query Status]"
placeholder={t('[Query Status]')}
options={STATUS_OPTIONS.map(s => ({ value: s, label: s }))}
value={this.state.status}
isLoading={false}
autosize={false}
onChange={this.changeStatus.bind(this)}
/>
<Button bsSize="small" bsStyle="success" onClick={this.refreshQueries.bind(this)}>
{t('Search')}
</Button>
</div>
<Button bsSize="small" bsStyle="success" onClick={this.refreshQueries.bind(this)}>
Search
</Button>
</div>
{this.state.queriesLoading ?
(<img className="loading" alt="Loading..." src="/static/assets/images/loading.gif" />)
@@ -0,0 +1,19 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Label } from 'react-bootstrap';
import { STATE_BSSTYLE_MAP } from '../constants';
const propTypes = {
query: PropTypes.object.isRequired,
};
export default function QueryStateLabel({ query }) {
const bsStyle = STATE_BSSTYLE_MAP[query.state];
return (
<Label className="m-r-3" bsStyle={bsStyle}>
{query.state}
</Label>
);
}
QueryStateLabel.propTypes = propTypes;
@@ -1,4 +1,5 @@
import React from 'react';
import PropTypes from 'prop-types';
import moment from 'moment';
import { Table } from 'reactable';
@@ -8,16 +9,17 @@ import VisualizeModal from './VisualizeModal';
import ResultSet from './ResultSet';
import ModalTrigger from '../../components/ModalTrigger';
import HighlightedSql from './HighlightedSql';
import { STATE_BSSTYLE_MAP } from '../constants';
import { fDuration } from '../../modules/dates';
import { storeQuery } from '../../../utils/common';
import QueryStateLabel from './QueryStateLabel';
import { t } from '../../locales';
const propTypes = {
columns: React.PropTypes.array,
actions: React.PropTypes.object,
queries: React.PropTypes.array,
onUserClicked: React.PropTypes.func,
onDbClicked: React.PropTypes.func,
columns: PropTypes.array,
actions: PropTypes.object,
queries: PropTypes.array,
onUserClicked: PropTypes.func,
onDbClicked: PropTypes.func,
};
const defaultProps = {
columns: ['started', 'duration', 'rows'],
@@ -44,7 +46,7 @@ class QueryTable extends React.PureComponent {
openQuery(dbId, schema, sql) {
const newQuery = {
dbId,
title: 'Untitled Query',
title: t('Untitled Query'),
schema,
sql,
};
@@ -109,7 +111,7 @@ class QueryTable extends React.PureComponent {
className="btn btn-link btn-xs"
onClick={this.openQuery.bind(this, q.dbId, q.schema, q.sql)}
>
<i className="fa fa-external-link" />Open in SQL Editor
<i className="fa fa-external-link" />{t('Open in SQL Editor')}
</button>
</div>
);
@@ -128,10 +130,10 @@ class QueryTable extends React.PureComponent {
bsStyle="info"
style={{ cursor: 'pointer' }}
>
view results
{t('view results')}
</Label>
)}
modalTitle={'Data preview'}
modalTitle={t('Data preview')}
beforeOpen={this.openAsyncResults.bind(this, query)}
onExit={this.clearQueryResults.bind(this, query)}
modalBody={
@@ -163,9 +165,7 @@ class QueryTable extends React.PureComponent {
}
q.state = (
<div>
<span className={'m-r-3 label label-' + STATE_BSSTYLE_MAP[q.state]}>
{q.state}
</span>
<QueryStateLabel query={query} />
{errorTooltip}
</div>
);
@@ -173,24 +173,24 @@ class QueryTable extends React.PureComponent {
<div style={{ width: '75px' }}>
<Link
className="fa fa-line-chart m-r-3"
tooltip="Visualize the data out of this query"
tooltip={t('Visualize the data out of this query')}
onClick={this.showVisualizeModal.bind(this, query)}
/>
<Link
className="fa fa-pencil m-r-3"
onClick={this.restoreSql.bind(this, query)}
tooltip="Overwrite text in editor with a query on this table"
tooltip={t('Overwrite text in editor with a query on this table')}
placement="top"
/>
<Link
className="fa fa-plus-circle m-r-3"
onClick={this.openQueryInNewTab.bind(this, query)}
tooltip="Run query in a new tab"
tooltip={t('Run query in a new tab')}
placement="top"
/>
<Link
className="fa fa-trash m-r-3"
tooltip="Remove query from log"
tooltip={t('Remove query from log')}
onClick={this.removeQuery.bind(this, query)}
/>
</div>
@@ -1,20 +1,23 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Alert, Button, ButtonGroup, ProgressBar } from 'react-bootstrap';
import shortid from 'shortid';
import VisualizeModal from './VisualizeModal';
import HighlightedSql from './HighlightedSql';
import FilterableTable from '../../components/FilterableTable/FilterableTable';
import QueryStateLabel from './QueryStateLabel';
import { t } from '../../locales';
const propTypes = {
actions: React.PropTypes.object,
csv: React.PropTypes.bool,
query: React.PropTypes.object,
search: React.PropTypes.bool,
showSql: React.PropTypes.bool,
visualize: React.PropTypes.bool,
cache: React.PropTypes.bool,
height: React.PropTypes.number.isRequired,
actions: PropTypes.object,
csv: PropTypes.bool,
query: PropTypes.object,
search: PropTypes.bool,
showSql: PropTypes.bool,
visualize: PropTypes.bool,
cache: PropTypes.bool,
height: PropTypes.number.isRequired,
};
const defaultProps = {
search: true,
@@ -25,7 +28,7 @@ const defaultProps = {
cache: false,
};
const RESULT_SET_CONTROLS_HEIGHT = 46;
const SEARCH_HEIGHT = 46;
export default class ResultSet extends React.PureComponent {
constructor(props) {
@@ -33,10 +36,13 @@ export default class ResultSet extends React.PureComponent {
this.state = {
searchText: '',
showModal: false,
data: [],
height: props.search ? props.height - RESULT_SET_CONTROLS_HEIGHT : props.height,
data: null,
};
}
componentDidMount() {
// only do this the first time the component is rendered/mounted
this.reRunQueryIfSessionTimeoutErrorOnMount();
}
componentWillReceiveProps(nextProps) {
// when new results comes in, save them locally and clear in store
if (this.props.cache && (!nextProps.query.cached)
@@ -52,14 +58,13 @@ export default class ResultSet extends React.PureComponent {
this.fetchResults(nextProps.query);
}
}
getControls() {
if (this.props.search || this.props.visualize || this.props.csv) {
let csvButton;
if (this.props.csv) {
csvButton = (
<Button bsSize="small" href={'/superset/csv/' + this.props.query.id}>
<i className="fa fa-file-text-o" /> .CSV
<i className="fa fa-file-text-o" /> {t('.CSV')}
</Button>
);
}
@@ -70,7 +75,7 @@ export default class ResultSet extends React.PureComponent {
bsSize="small"
onClick={this.showModal.bind(this)}
>
<i className="fa fa-line-chart m-l-1" /> Visualize
<i className="fa fa-line-chart m-l-1" /> {t('Visualize')}
</Button>
);
}
@@ -81,7 +86,7 @@ export default class ResultSet extends React.PureComponent {
type="text"
onChange={this.changeSearch.bind(this)}
className="form-control input-sm"
placeholder="Search Results"
placeholder={t('Search Results')}
/>
);
}
@@ -131,61 +136,50 @@ export default class ResultSet extends React.PureComponent {
reFetchQueryResults(query) {
this.props.actions.reFetchQueryResults(query);
}
reRunQueryIfSessionTimeoutErrorOnMount() {
const { query } = this.props;
if (query.errorMessage && query.errorMessage.indexOf('session timed out') > 0) {
this.props.actions.runQuery(query, true);
}
}
render() {
const query = this.props.query;
const results = query.results;
let data;
if (this.props.cache && query.cached) {
data = this.state.data;
} else {
data = results ? results.data : [];
}
const height = Math.max(0,
(this.props.search ? this.props.height - SEARCH_HEIGHT : this.props.height));
let sql;
if (query.state === 'stopped') {
return <Alert bsStyle="warning">Query was stopped</Alert>;
}
if (this.props.showSql) {
sql = <HighlightedSql sql={query.sql} />;
}
if (['running', 'pending', 'fetching'].indexOf(query.state) > -1) {
let progressBar;
if (query.progress > 0 && query.state === 'running') {
progressBar = (
<ProgressBar
striped
now={query.progress}
label={`${query.progress}%`}
/>);
}
return (
<div>
<img className="loading" alt="Loading..." src="/static/assets/images/loading.gif" />
{progressBar}
</div>
);
if (query.state === 'stopped') {
return <Alert bsStyle="warning">Query was stopped</Alert>;
} else if (query.state === 'failed') {
return <Alert bsStyle="danger">{query.errorMessage}</Alert>;
} else if (query.state === 'success' && query.ctas) {
return (
<div>
<Alert bsStyle="info">
Table [<strong>{query.tempTable}</strong>] was
created &nbsp;
{t('Table')} [<strong>{query.tempTable}</strong>] {t('was ' +
'created')} &nbsp;
<Button
bsSize="small"
className="m-r-5"
onClick={this.popSelectStar.bind(this)}
>
Query in a new tab
{t('Query in a new tab')}
</Button>
</Alert>
</div>);
} else if (query.state === 'success') {
if (results && data && data.length > 0) {
const results = query.results;
let data;
if (this.props.cache && query.cached) {
data = this.state.data;
} else if (results && results.data) {
data = results.data;
}
if (data && data.length > 0) {
return (
<div>
<VisualizeModal
@@ -198,11 +192,13 @@ export default class ResultSet extends React.PureComponent {
<FilterableTable
data={data}
orderedColumnKeys={results.columns.map(col => col.name)}
height={this.state.height}
height={height}
filterText={this.state.searchText}
/>
</div>
);
} else if (data && data.length === 0) {
return <Alert bsStyle="warning">The query returned no data</Alert>;
}
}
if (query.cached) {
@@ -212,11 +208,40 @@ export default class ResultSet extends React.PureComponent {
bsStyle="primary"
onClick={this.reFetchQueryResults.bind(this, query)}
>
Fetch data preview
{t('Fetch data preview')}
</Button>
);
}
return <Alert bsStyle="warning">The query returned no data</Alert>;
let progressBar;
let trackingUrl;
if (query.progress > 0 && query.state === 'running') {
progressBar = (
<ProgressBar
striped
now={query.progress}
label={`${query.progress}%`}
/>);
}
if (query.trackingUrl) {
trackingUrl = (
<Button
bsSize="small"
onClick={() => { window.open(query.trackingUrl); }}
>
{t('Track Job')}
</Button>
);
}
return (
<div>
<img className="loading" alt={t('Loading...')} src="/static/assets/images/loading.gif" />
<QueryStateLabel query={query} />
{progressBar}
<div>
{trackingUrl}
</div>
</div>
);
}
}
ResultSet.propTypes = propTypes;
@@ -1,10 +1,12 @@
import React, { PropTypes } from 'react';
import React from 'react';
import PropTypes from 'prop-types';
import Button from '../../components/Button';
import { t } from '../../locales';
const propTypes = {
allowAsync: PropTypes.bool.isRequired,
dbId: PropTypes.number,
queryState: PropTypes.string.isRequired,
queryState: PropTypes.string,
runQuery: PropTypes.func.isRequired,
selectedText: PropTypes.string,
stopQuery: PropTypes.func.isRequired,
@@ -14,10 +16,9 @@ const defaultProps = {
};
export default function RunQueryActionButton(props) {
const runBtnText = props.selectedText ? 'Run Selected Query' : 'Run Query';
const runBtnText = props.selectedText ? t('Run Selected Query') : t('Run Query');
const btnStyle = props.selectedText ? 'warning' : 'primary';
const shouldShowStopBtn = ['running', 'pending'].indexOf(props.queryState) > -1;
const asyncToolTip = 'Run query asynchronously';
const commonBtnProps = {
bsSize: 'small',
@@ -30,6 +31,7 @@ export default function RunQueryActionButton(props) {
{...commonBtnProps}
onClick={() => props.runQuery(false)}
key="run-btn"
tooltip={t('Run query synchronously')}
>
<i className="fa fa-refresh" /> {runBtnText}
</Button>
@@ -40,7 +42,7 @@ export default function RunQueryActionButton(props) {
{...commonBtnProps}
onClick={() => props.runQuery(true)}
key="run-async-btn"
tooltip={asyncToolTip}
tooltip={t('Run query asynchronously')}
>
<i className="fa fa-table" /> {runBtnText}
</Button>
@@ -51,7 +53,7 @@ export default function RunQueryActionButton(props) {
{...commonBtnProps}
onClick={props.stopQuery}
>
<i className="fa fa-stop" /> Stop
<i className="fa fa-stop" /> {t('Stop')}
</Button>
);
@@ -63,12 +65,7 @@ export default function RunQueryActionButton(props) {
} else {
button = syncBtn;
}
return (
<div className="inline m-r-5 pull-left">
{button}
</div>
);
return button;
}
RunQueryActionButton.propTypes = propTypes;
@@ -1,18 +1,21 @@
/* global notify */
import React from 'react';
import { FormControl, FormGroup, Overlay, Popover, Row, Col } from 'react-bootstrap';
import PropTypes from 'prop-types';
import { FormControl, FormGroup, Row, Col } from 'react-bootstrap';
import Button from '../../components/Button';
import ModalTrigger from '../../components/ModalTrigger';
import { t } from '../../locales';
const propTypes = {
defaultLabel: React.PropTypes.string,
sql: React.PropTypes.string,
schema: React.PropTypes.string,
dbId: React.PropTypes.number,
animation: React.PropTypes.bool,
onSave: React.PropTypes.func,
defaultLabel: PropTypes.string,
sql: PropTypes.string,
schema: PropTypes.string,
dbId: PropTypes.number,
animation: PropTypes.bool,
onSave: PropTypes.func,
};
const defaultProps = {
defaultLabel: 'Undefined',
defaultLabel: t('Undefined'),
animation: true,
onSave: () => {},
};
@@ -40,10 +43,10 @@ class SaveQuery extends React.PureComponent {
sql: this.props.sql,
};
this.props.onSave(query);
this.setState({ showSave: false });
this.saveModal.close();
}
onCancel() {
this.setState({ showSave: false });
this.saveModal.close();
}
onLabelChange(e) {
this.setState({ label: e.target.value });
@@ -54,73 +57,70 @@ class SaveQuery extends React.PureComponent {
toggleSave(e) {
this.setState({ target: e.target, showSave: !this.state.showSave });
}
renderPopover() {
renderModalBody() {
return (
<Popover id="embed-code-popover">
<FormGroup bsSize="small" style={{ width: '350px' }}>
<Row>
<Col md={12}>
<small>
<label className="control-label" htmlFor="embed-height">
Label
</label>
</small>
<FormControl
type="text"
placeholder="Label for your query"
value={this.state.label}
onChange={this.onLabelChange}
/>
</Col>
</Row>
<br />
<Row>
<Col md={12}>
<small>
<label className="control-label" htmlFor="embed-height">Description</label>
</small>
<FormControl
componentClass="textarea"
placeholder="Write a description for your query"
value={this.state.description}
onChange={this.onDescriptionChange}
/>
</Col>
</Row>
<br />
<Row>
<Col md={12}>
<Button
bsStyle="primary"
onClick={this.onSave}
className="m-r-3"
>
Save
</Button>
<Button onClick={this.onCancel} className="cancelQuery">
Cancel
</Button>
</Col>
</Row>
</FormGroup>
</Popover>
<FormGroup bsSize="small">
<Row>
<Col md={12}>
<small>
<label className="control-label" htmlFor="embed-height">
{t('Label')}
</label>
</small>
<FormControl
type="text"
placeholder={t('Label for your query')}
value={this.state.label}
onChange={this.onLabelChange}
/>
</Col>
</Row>
<br />
<Row>
<Col md={12}>
<small>
<label className="control-label" htmlFor="embed-height">{t('Description')}</label>
</small>
<FormControl
componentClass="textarea"
placeholder={t('Write a description for your query')}
value={this.state.description}
onChange={this.onDescriptionChange}
/>
</Col>
</Row>
<br />
<Row>
<Col md={12}>
<Button
bsStyle="primary"
onClick={this.onSave}
className="m-r-3"
>
{t('Save')}
</Button>
<Button onClick={this.onCancel} className="cancelQuery">
{t('Cancel')}
</Button>
</Col>
</Row>
</FormGroup>
);
}
render() {
return (
<span className="SaveQuery">
<Overlay
trigger="click"
target={this.state.target}
show={this.state.showSave}
placement="bottom"
animation={this.props.animation}
>
{this.renderPopover()}
</Overlay>
<Button bsSize="small" className="toggleSave" onClick={this.toggleSave}>
<i className="fa fa-save" /> Save Query
</Button>
<ModalTrigger
ref={(ref) => { this.saveModal = ref; }}
modalTitle={t('Save Query')}
modalBody={this.renderModalBody()}
triggerNode={
<Button bsSize="small" className="toggleSave" onClick={this.toggleSave}>
<i className="fa fa-save" /> {t('Save Query')}
</Button>
}
bsSize="small"
/>
</span>
);
}
@@ -1,4 +1,5 @@
import React from 'react';
import PropTypes from 'prop-types';
import shortid from 'shortid';
import { Alert, Tab, Tabs } from 'react-bootstrap';
import { connect } from 'react-redux';
@@ -7,16 +8,18 @@ import { bindActionCreators } from 'redux';
import * as Actions from '../actions';
import QueryHistory from './QueryHistory';
import ResultSet from './ResultSet';
import { t } from '../../locales';
/*
editorQueries are queries executed by users passed from SqlEditor component
dataPrebiewQueries are all queries executed for preview of table data (from SqlEditorLeft)
*/
const propTypes = {
editorQueries: React.PropTypes.array.isRequired,
dataPreviewQueries: React.PropTypes.array.isRequired,
actions: React.PropTypes.object.isRequired,
activeSouthPaneTab: React.PropTypes.string,
editorQueries: PropTypes.array.isRequired,
dataPreviewQueries: PropTypes.array.isRequired,
actions: PropTypes.object.isRequired,
activeSouthPaneTab: PropTypes.string,
height: PropTypes.number,
};
const defaultProps = {
@@ -24,40 +27,11 @@ const defaultProps = {
};
class SouthPane extends React.PureComponent {
constructor(props) {
super(props);
this.state = {
innerTabHeight: this.getInnerTabHeight(),
};
}
getInnerTabHeight() {
// hack to get height the tab container so it can be fixed and scroll in place
// calculate inner tab height
// document.getElementById('brace-editor').getBoundingClientRect().height;
const sqlEditorHeight = 192;
// document.getElementById('js-sql-toolbar').getBoundingClientRect().height;
const sqlToolbar = 30;
// document.getElementsByClassName('nav-tabs')[0].getBoundingClientRect().height * 2;
const tabsHeight = 88;
// document.getElementsByTagName('header')[0].getBoundingClientRect().height;
const headerHeight = 59;
const sum =
sqlEditorHeight +
sqlToolbar +
tabsHeight +
headerHeight;
return window.innerHeight - sum - 95;
}
switchTab(id) {
this.props.actions.setActiveSouthPaneTab(id);
}
render() {
const innerTabHeight = this.props.height - 55;
let latestQuery;
const props = this.props;
if (props.editorQueries.length > 0) {
@@ -71,16 +45,16 @@ class SouthPane extends React.PureComponent {
search
query={latestQuery}
actions={props.actions}
height={this.state.innerTabHeight}
height={innerTabHeight}
/>
);
} else {
results = <Alert bsStyle="info">Run a query to display results here</Alert>;
results = <Alert bsStyle="info">{t('Run a query to display results here')}</Alert>;
}
const dataPreviewTabs = props.dataPreviewQueries.map(query => (
<Tab
title={`Preview for ${query.tableName}`}
title={t('Preview for %s', query.tableName)}
eventKey={query.id}
key={query.id}
>
@@ -90,7 +64,7 @@ class SouthPane extends React.PureComponent {
csv={false}
actions={props.actions}
cache
height={this.state.innerTabHeight}
height={innerTabHeight}
/>
</Tab>
));
@@ -104,16 +78,16 @@ class SouthPane extends React.PureComponent {
onSelect={this.switchTab.bind(this)}
>
<Tab
title="Results"
title={t('Results')}
eventKey="Results"
>
{results}
</Tab>
<Tab
title="Query History"
title={t('Query History')}
eventKey="History"
>
<div style={{ height: `${this.state.innerTabHeight}px`, overflow: 'scroll' }}>
<div style={{ height: `${innerTabHeight}px`, overflow: 'scroll' }}>
<QueryHistory queries={props.editorQueries} actions={props.actions} />
</div>
</Tab>
@@ -1,4 +1,6 @@
import React from 'react';
import PropTypes from 'prop-types';
import throttle from 'lodash.throttle';
import {
Col,
FormGroup,
@@ -11,9 +13,10 @@ import {
Tooltip,
Collapse,
} from 'react-bootstrap';
import SplitPane from 'react-split-pane';
import Button from '../../components/Button';
import TemplateParamsEditor from './TemplateParamsEditor';
import SouthPane from './SouthPane';
import SaveQuery from './SaveQuery';
import Timer from '../../components/Timer';
@@ -21,17 +24,19 @@ import SqlEditorLeftBar from './SqlEditorLeftBar';
import AceEditorWrapper from './AceEditorWrapper';
import { STATE_BSSTYLE_MAP } from '../constants';
import RunQueryActionButton from './RunQueryActionButton';
import { t } from '../../locales';
const propTypes = {
actions: React.PropTypes.object.isRequired,
height: React.PropTypes.string.isRequired,
database: React.PropTypes.object,
latestQuery: React.PropTypes.object,
tables: React.PropTypes.array.isRequired,
editorQueries: React.PropTypes.array.isRequired,
dataPreviewQueries: React.PropTypes.array.isRequired,
queryEditor: React.PropTypes.object.isRequired,
hideLeftBar: React.PropTypes.bool,
actions: PropTypes.object.isRequired,
height: PropTypes.string.isRequired,
database: PropTypes.object,
latestQuery: PropTypes.object,
tables: PropTypes.array.isRequired,
editorQueries: PropTypes.array.isRequired,
dataPreviewQueries: PropTypes.array.isRequired,
queryEditor: PropTypes.object.isRequired,
hideLeftBar: PropTypes.bool,
};
const defaultProps = {
@@ -48,21 +53,43 @@ class SqlEditor extends React.PureComponent {
autorun: props.queryEditor.autorun,
ctas: '',
};
this.onResize = this.onResize.bind(this);
this.throttledResize = throttle(this.onResize, 250);
}
componentDidMount() {
this.onMount();
}
onMount() {
componentWillMount() {
if (this.state.autorun) {
this.setState({ autorun: false });
this.props.actions.queryEditorSetAutorun(this.props.queryEditor, false);
this.startQuery();
}
}
componentDidMount() {
this.onResize();
window.addEventListener('resize', this.throttledResize);
}
componentWillUnmount() {
window.removeEventListener('resize', this.throttledResize);
}
onResize() {
const height = this.sqlEditorHeight();
this.setState({
editorPaneHeight: this.props.queryEditor.height,
southPaneHeight: height - this.props.queryEditor.height,
height,
});
if (this.refs.ace.clientHeight) {
this.props.actions.persistEditorHeight(this.props.queryEditor, this.refs.ace.clientHeight);
}
}
setQueryEditorSql(sql) {
this.props.actions.queryEditorSetSql(this.props.queryEditor, sql);
}
runQuery(runAsync = false) {
if (!this.props.queryEditor.sql) {
return;
}
let effectiveRunAsync = runAsync;
if (!this.props.database.allow_run_sync) {
effectiveRunAsync = true;
@@ -78,6 +105,7 @@ class SqlEditor extends React.PureComponent {
tab: qe.title,
schema: qe.schema,
tempTableName: ctas ? this.state.ctas : '',
templateParams: qe.templateParams,
runAsync,
ctas,
};
@@ -100,27 +128,10 @@ class SqlEditor extends React.PureComponent {
const mysteryVerticalHeight = 50;
return window.innerHeight - tabNavHeight - navBarHeight - mysteryVerticalHeight;
}
render() {
const qe = this.props.queryEditor;
let limitWarning = null;
if (this.props.latestQuery && this.props.latestQuery.limit_reached) {
const tooltip = (
<Tooltip id="tooltip">
It appears that the number of rows in the query results displayed
was limited on the server side to
the {this.props.latestQuery.rows} limit.
</Tooltip>
);
limitWarning = (
<OverlayTrigger placement="left" overlay={tooltip}>
<Label bsStyle="warning" className="m-r-5">LIMIT</Label>
</OverlayTrigger>
);
}
renderEditorBottomBar() {
let ctasControls;
if (this.props.database && this.props.database.allow_ctas) {
const ctasToolTip = 'Create table as with query results';
const ctasToolTip = t('Create table as with query results');
ctasControls = (
<FormGroup>
<InputGroup>
@@ -128,7 +139,7 @@ class SqlEditor extends React.PureComponent {
type="text"
bsSize="small"
className="input-sm"
placeholder="new table name"
placeholder={t('new table name')}
onChange={this.ctasChanged.bind(this)}
/>
<InputGroup.Button>
@@ -145,29 +156,57 @@ class SqlEditor extends React.PureComponent {
</FormGroup>
);
}
const editorBottomBar = (
const qe = this.props.queryEditor;
let limitWarning = null;
if (this.props.latestQuery && this.props.latestQuery.limit_reached) {
const tooltip = (
<Tooltip id="tooltip">
It appears that the number of rows in the query results displayed
was limited on the server side to
the {this.props.latestQuery.rows} limit.
</Tooltip>
);
limitWarning = (
<OverlayTrigger placement="left" overlay={tooltip}>
<Label bsStyle="warning" className="m-r-5">LIMIT</Label>
</OverlayTrigger>
);
}
return (
<div className="sql-toolbar clearfix" id="js-sql-toolbar">
<div className="pull-left">
<Form inline>
<RunQueryActionButton
allowAsync={this.props.database ? this.props.database.allow_run_async : false}
dbId={qe.dbId}
queryState={this.props.latestQuery && this.props.latestQuery.state}
runQuery={this.runQuery.bind(this)}
selectedText={qe.selectedText}
stopQuery={this.stopQuery.bind(this)}
/>
<SaveQuery
defaultLabel={qe.title}
sql={qe.sql}
onSave={this.props.actions.saveQuery}
schema={qe.schema}
dbId={qe.dbId}
/>
<span className="m-r-5">
<RunQueryActionButton
allowAsync={this.props.database ? this.props.database.allow_run_async : false}
dbId={qe.dbId}
queryState={this.props.latestQuery && this.props.latestQuery.state}
runQuery={this.runQuery.bind(this)}
selectedText={qe.selectedText}
stopQuery={this.stopQuery.bind(this)}
/>
</span>
<span className="m-r-5">
<SaveQuery
defaultLabel={qe.title}
sql={qe.sql}
className="m-r-5"
onSave={this.props.actions.saveQuery}
schema={qe.schema}
dbId={qe.dbId}
/>
</span>
{ctasControls}
</Form>
</div>
<div className="pull-right">
<TemplateParamsEditor
language="json"
onChange={(params) => {
this.props.actions.queryEditorSetTemplateParams(qe, params);
}}
code={qe.templateParams}
/>
{limitWarning}
{this.props.latestQuery &&
<Timer
@@ -180,11 +219,15 @@ class SqlEditor extends React.PureComponent {
</div>
</div>
);
}
render() {
const height = this.sqlEditorHeight();
const defaultNorthHeight = this.props.queryEditor.height || 200;
return (
<div
className="SqlEditor"
style={{
minHeight: this.sqlEditorHeight(),
minHeight: height,
height: this.props.height,
}}
>
@@ -192,31 +235,56 @@ class SqlEditor extends React.PureComponent {
<Collapse
in={!this.props.hideLeftBar}
>
<Col md={3}>
<Col
xs={6}
sm={5}
md={4}
lg={3}
>
<SqlEditorLeftBar
height={this.sqlEditorHeight()}
height={height}
queryEditor={this.props.queryEditor}
tables={this.props.tables}
actions={this.props.actions}
/>
</Col>
</Collapse>
<Col md={this.props.hideLeftBar ? 12 : 9}>
<AceEditorWrapper
actions={this.props.actions}
onBlur={this.setQueryEditorSql.bind(this)}
queryEditor={this.props.queryEditor}
onAltEnter={this.runQuery.bind(this)}
sql={this.props.queryEditor.sql}
tables={this.props.tables}
/>
{editorBottomBar}
<br />
<SouthPane
editorQueries={this.props.editorQueries}
dataPreviewQueries={this.props.dataPreviewQueries}
actions={this.props.actions}
/>
<Col
xs={this.props.hideLeftBar ? 12 : 6}
sm={this.props.hideLeftBar ? 12 : 7}
md={this.props.hideLeftBar ? 12 : 8}
lg={this.props.hideLeftBar ? 12 : 9}
style={{ height: this.state.height }}
>
<SplitPane
split="horizontal"
defaultSize={defaultNorthHeight}
minSize={100}
onChange={this.onResize}
>
<div ref="ace" style={{ width: '100%' }}>
<div>
<AceEditorWrapper
actions={this.props.actions}
onBlur={this.setQueryEditorSql.bind(this)}
queryEditor={this.props.queryEditor}
onAltEnter={this.runQuery.bind(this)}
sql={this.props.queryEditor.sql}
tables={this.props.tables}
height={((this.state.editorPaneHeight || defaultNorthHeight) - 50).toString()}
/>
{this.renderEditorBottomBar()}
</div>
</div>
<div ref="south">
<SouthPane
editorQueries={this.props.editorQueries}
dataPreviewQueries={this.props.dataPreviewQueries}
actions={this.props.actions}
height={this.state.southPaneHeight || 0}
/>
</div>
</SplitPane>
</Col>
</Row>
</div>
@@ -1,18 +1,21 @@
/* global notify */
import React from 'react';
import PropTypes from 'prop-types';
import { Button } from 'react-bootstrap';
import Select from 'react-virtualized-select';
import createFilterOptions from 'react-select-fast-filter-options';
import TableElement from './TableElement';
import AsyncSelect from '../../components/AsyncSelect';
import { t } from '../../locales';
const $ = window.$ = require('jquery');
const propTypes = {
queryEditor: React.PropTypes.object.isRequired,
height: React.PropTypes.number.isRequired,
tables: React.PropTypes.array,
actions: React.PropTypes.object,
queryEditor: PropTypes.object.isRequired,
height: PropTypes.number.isRequired,
tables: PropTypes.array,
actions: PropTypes.object,
};
const defaultProps = {
@@ -34,7 +37,7 @@ class SqlEditorLeftBar extends React.PureComponent {
this.fetchSchemas(this.props.queryEditor.dbId);
this.fetchTables(this.props.queryEditor.dbId, this.props.queryEditor.schema);
}
onChange(db) {
onDatabaseChange(db) {
const val = db ? db.value : null;
this.setState({ schemaOptions: [] });
this.props.actions.queryEditorSetSchema(this.props.queryEditor, null);
@@ -60,7 +63,7 @@ class SqlEditorLeftBar extends React.PureComponent {
if (data.result.length === 0) {
this.props.actions.addAlert({
bsStyle: 'danger',
msg: "It seems you don't have access to any database",
msg: t('It seems you don\'t have access to any database'),
});
}
return options;
@@ -73,7 +76,7 @@ class SqlEditorLeftBar extends React.PureComponent {
if (dbId && schema) {
this.setState({ tableLoading: true, tableOptions: [] });
const url = `/superset/tables/${dbId}/${schema}/${substr}/`;
$.get(url, (data) => {
$.get(url).done((data) => {
const filterOptions = createFilterOptions({ options: data.options });
this.setState({
filterOptions,
@@ -81,6 +84,10 @@ class SqlEditorLeftBar extends React.PureComponent {
tableOptions: data.options,
tableLength: data.tableLength,
});
})
.fail(() => {
this.setState({ tableLoading: false, tableOptions: [], tableLength: 0 });
notify.error(t('Error while fetching table list'));
});
} else {
this.setState({ tableLoading: false, tableOptions: [], filterOptions: null });
@@ -103,11 +110,7 @@ class SqlEditorLeftBar extends React.PureComponent {
this.props.actions.queryEditorSetSchema(this.props.queryEditor, schemaName);
this.fetchTables(this.props.queryEditor.dbId, schemaName);
}
this.setState({ tableLoading: true });
// TODO: handle setting the tableLoading state depending on success or
// failure of the addTable async call in the action.
this.props.actions.addTable(this.props.queryEditor, tableName, schemaName);
this.setState({ tableLoading: false });
}
changeSchema(schemaOpt) {
const schema = (schemaOpt) ? schemaOpt.value : null;
@@ -119,10 +122,13 @@ class SqlEditorLeftBar extends React.PureComponent {
if (actualDbId) {
this.setState({ schemaLoading: true });
const url = `/superset/schemas/${actualDbId}/`;
$.get(url, (data) => {
$.get(url).done((data) => {
const schemaOptions = data.schemas.map(s => ({ value: s, label: s }));
this.setState({ schemaOptions });
this.setState({ schemaLoading: false });
this.setState({ schemaOptions, schemaLoading: false });
})
.fail(() => {
this.setState({ schemaLoading: false, schemaOptions: [] });
notify.error(t('Error while fetching schema list'));
});
}
}
@@ -140,31 +146,33 @@ class SqlEditorLeftBar extends React.PureComponent {
dataEndpoint={
'/databaseasync/api/' +
'read?_flt_0_expose_in_sqllab=1&' +
'_oc_DatabaseView=database_name&' +
'_od_DatabaseView=asc'
'_oc_DatabaseAsync=database_name&' +
'_od_DatabaseAsync=asc'
}
onChange={this.onChange.bind(this)}
onChange={this.onDatabaseChange.bind(this)}
onAsyncError={() => notify.error(t('Error while fetching database list'))}
value={this.props.queryEditor.dbId}
databaseId={this.props.queryEditor.dbId}
actions={this.props.actions}
valueRenderer={o => (
<div>
<span className="text-muted">Database:</span> {o.label}
<span className="text-muted">{t('Database:')}</span> {o.label}
</div>
)}
mutator={this.dbMutator.bind(this)}
placeholder="Select a database"
placeholder={t('Select a database')}
autoSelect
/>
</div>
<div className="m-t-5">
<Select
name="select-schema"
placeholder={`Select a schema (${this.state.schemaOptions.length})`}
placeholder={t('Select a schema (%s)', this.state.schemaOptions.length)}
options={this.state.schemaOptions}
value={this.props.queryEditor.schema}
valueRenderer={o => (
<div>
<span className="text-muted">Schema:</span> {o.label}
<span className="text-muted">{t('Schema:')}</span> {o.label}
</div>
)}
isLoading={this.state.schemaLoading}
@@ -179,7 +187,7 @@ class SqlEditorLeftBar extends React.PureComponent {
ref="selectTable"
isLoading={this.state.tableLoading}
value={this.state.tableName}
placeholder={`Add a table (${this.state.tableOptions.length})`}
placeholder={t('Add a table (%s)', this.state.tableOptions.length)}
autosize={false}
onChange={this.changeTable.bind(this)}
filterOptions={this.state.filterOptions}
@@ -192,7 +200,7 @@ class SqlEditorLeftBar extends React.PureComponent {
name="async-select-table"
ref="selectTable"
value={this.state.tableName}
placeholder={'Type to search ...'}
placeholder={t('Type to search ...')}
autosize={false}
onChange={this.changeTable.bind(this)}
loadOptions={this.getTableNamesBySubStr.bind(this)}
@@ -215,7 +223,7 @@ class SqlEditorLeftBar extends React.PureComponent {
</div>
{shouldShowReset &&
<Button bsSize="small" bsStyle="danger" onClick={this.resetState.bind(this)}>
<i className="fa fa-bomb" /> Reset State
<i className="fa fa-bomb" /> {t('Reset State')}
</Button>
}
</div>
@@ -1,4 +1,5 @@
import React from 'react';
import PropTypes from 'prop-types';
import { DropdownButton, MenuItem, Tab, Tabs } from 'react-bootstrap';
import { connect } from 'react-redux';
import { bindActionCreators } from 'redux';
@@ -8,16 +9,17 @@ import * as Actions from '../actions';
import SqlEditor from './SqlEditor';
import CopyQueryTabUrl from './CopyQueryTabUrl';
import { areArraysShallowEqual } from '../../reduxUtils';
import { t } from '../../locales';
const propTypes = {
actions: React.PropTypes.object.isRequired,
defaultDbId: React.PropTypes.number,
databases: React.PropTypes.object.isRequired,
queries: React.PropTypes.object.isRequired,
queryEditors: React.PropTypes.array,
tabHistory: React.PropTypes.array.isRequired,
tables: React.PropTypes.array.isRequired,
editorHeight: React.PropTypes.string.isRequired,
actions: PropTypes.object.isRequired,
defaultDbId: PropTypes.number,
databases: PropTypes.object.isRequired,
queries: PropTypes.object.isRequired,
queryEditors: PropTypes.array,
tabHistory: PropTypes.array.isRequired,
tables: PropTypes.array.isRequired,
editorHeight: PropTypes.string.isRequired,
};
const defaultProps = {
queryEditors: [],
@@ -100,7 +102,7 @@ class TabbedSqlEditors extends React.PureComponent {
}
renameTab(qe) {
/* eslint no-alert: 0 */
const newTitle = prompt('Enter a new title for the tab');
const newTitle = prompt(t('Enter a new title for the tab'));
if (newTitle) {
this.props.actions.queryEditorSetTitle(qe, newTitle);
}
@@ -119,7 +121,7 @@ class TabbedSqlEditors extends React.PureComponent {
queryCount++;
const activeQueryEditor = this.activeQueryEditor();
const qe = {
title: `Untitled Query ${queryCount}`,
title: t('Untitled Query %s', queryCount),
dbId: (activeQueryEditor && activeQueryEditor.dbId) ?
activeQueryEditor.dbId :
this.props.defaultDbId,
@@ -165,10 +167,10 @@ class TabbedSqlEditors extends React.PureComponent {
title=""
>
<MenuItem eventKey="1" onClick={this.removeQueryEditor.bind(this, qe)}>
<i className="fa fa-close" /> close tab
<i className="fa fa-close" /> {t('close tab')}
</MenuItem>
<MenuItem eventKey="2" onClick={this.renameTab.bind(this, qe)}>
<i className="fa fa-i-cursor" /> rename tab
<i className="fa fa-i-cursor" /> {t('rename tab')}
</MenuItem>
{qe &&
<CopyQueryTabUrl queryEditor={qe} />
@@ -176,7 +178,7 @@ class TabbedSqlEditors extends React.PureComponent {
<MenuItem eventKey="4" onClick={this.toggleLeftBar.bind(this)}>
<i className="fa fa-cogs" />
&nbsp;
{this.state.hideLeftBar ? 'expand tool bar' : 'hide tool bar'}
{this.state.hideLeftBar ? t('expand tool bar') : t('hide tool bar')}
</MenuItem>
</DropdownButton>
</div>
@@ -192,7 +194,7 @@ class TabbedSqlEditors extends React.PureComponent {
{isSelected &&
<SqlEditor
height={this.props.editorHeight}
tables={this.props.tables.filter(t => (t.queryEditorId === qe.id))}
tables={this.props.tables.filter(xt => (xt.queryEditorId === qe.id))}
queryEditor={qe}
editorQueries={this.state.queriesArray}
dataPreviewQueries={this.state.dataPreviewQueries}
@@ -1,4 +1,5 @@
import React from 'react';
import PropTypes from 'prop-types';
import { ButtonGroup, Collapse, Well } from 'react-bootstrap';
import shortid from 'shortid';
@@ -7,11 +8,13 @@ import CopyToClipboard from '../../components/CopyToClipboard';
import Link from './Link';
import ColumnElement from './ColumnElement';
import ModalTrigger from '../../components/ModalTrigger';
import Loading from '../../components/Loading';
import { t } from '../../locales';
const propTypes = {
table: React.PropTypes.object,
actions: React.PropTypes.object,
timeout: React.PropTypes.number, // used for tests
table: PropTypes.object,
actions: PropTypes.object,
timeout: PropTypes.number, // used for tests
};
const defaultProps = {
@@ -61,7 +64,7 @@ class TableElement extends React.PureComponent {
this.props.actions.removeTable(this.props.table);
}
renderHeader() {
renderWell() {
const table = this.props.table;
let header;
if (table.partitions) {
@@ -69,7 +72,7 @@ class TableElement extends React.PureComponent {
let partitionClipBoard;
if (table.partitions.partitionQuery) {
partitionQuery = table.partitions.partitionQuery;
const tt = 'Copy partition query to clipboard';
const tt = t('Copy partition query to clipboard');
partitionClipBoard = (
<CopyToClipboard
text={partitionQuery}
@@ -88,7 +91,7 @@ class TableElement extends React.PureComponent {
<Well bsSize="small">
<div>
<small>
latest partition: {latest}
{t('latest partition:')} {latest}
</small> {partitionClipBoard}
</div>
</Well>
@@ -96,7 +99,89 @@ class TableElement extends React.PureComponent {
}
return header;
}
renderMetadata() {
renderControls() {
let keyLink;
const table = this.props.table;
if (table.indexes && table.indexes.length > 0) {
keyLink = (
<ModalTrigger
modalTitle={
<div>
{t('Keys for table')} <strong>{table.name}</strong>
</div>
}
modalBody={table.indexes.map((ix, i) => (
<pre key={i}>{JSON.stringify(ix, null, ' ')}</pre>
))}
triggerNode={
<Link
className="fa fa-key pull-left m-l-2"
tooltip={t('View keys & indexes (%s)', table.indexes.length)}
/>
}
/>
);
}
return (
<ButtonGroup className="ws-el-controls pull-right">
{keyLink}
<Link
className={
`fa fa-sort-${!this.state.sortColumns ? 'alpha' : 'numeric'}-asc ` +
'pull-left sort-cols m-l-2'}
onClick={this.toggleSortColumns.bind(this)}
tooltip={
!this.state.sortColumns ?
t('Sort columns alphabetically') :
t('Original table column order')}
href="#"
/>
{table.selectStar &&
<CopyToClipboard
copyNode={
<a className="fa fa-clipboard pull-left m-l-2" />
}
text={table.selectStar}
shouldShowText={false}
tooltipText={t('Copy SELECT statement to clipboard')}
/>
}
<Link
className="fa fa-times table-remove pull-left m-l-2"
onClick={this.removeTable.bind(this)}
tooltip={t('Remove table preview')}
href="#"
/>
</ButtonGroup>
);
}
renderHeader() {
const table = this.props.table;
return (
<div className="clearfix">
<div className="pull-left">
<a
href="#"
className="table-name"
onClick={(e) => { this.toggleTable(e); }}
>
<strong>{table.name}</strong>
<small className="m-l-5">
<i className={`fa fa-${table.expanded ? 'minus' : 'plus'}-square-o`} />
</small>
</a>
</div>
<div className="pull-right">
{table.isMetadataLoading || table.isExtraMetadataLoading ?
<Loading size={20} />
:
this.renderControls()
}
</div>
</div>
);
}
renderBody() {
const table = this.props.table;
let cols;
if (table.columns) {
@@ -111,7 +196,7 @@ class TableElement extends React.PureComponent {
timeout={this.props.timeout}
>
<div>
{this.renderHeader()}
{this.renderWell()}
<div className="table-columns">
{cols && cols.map(col => (
<ColumnElement column={col} key={col.name} />
@@ -125,28 +210,6 @@ class TableElement extends React.PureComponent {
}
render() {
const table = this.props.table;
let keyLink;
if (table.indexes && table.indexes.length > 0) {
keyLink = (
<ModalTrigger
modalTitle={
<div>
Keys for table <strong>{table.name}</strong>
</div>
}
modalBody={table.indexes.map((ix, i) => (
<pre key={i}>{JSON.stringify(ix, null, ' ')}</pre>
))}
triggerNode={
<Link
className="fa fa-key pull-left m-l-2"
tooltip={`View keys & indexes (${table.indexes.length})`}
/>
}
/>
);
}
return (
<Collapse
in={this.state.expanded}
@@ -155,54 +218,9 @@ class TableElement extends React.PureComponent {
onExited={this.removeFromStore.bind(this)}
>
<div className="TableElement">
<div className="clearfix">
<div className="pull-left">
<a
href="#"
className="table-name"
onClick={(e) => { this.toggleTable(e); }}
>
<strong>{table.name}</strong>
<small className="m-l-5">
<i className={`fa fa-${table.expanded ? 'minus' : 'plus'}-square-o`} />
</small>
</a>
</div>
<div className="pull-right">
<ButtonGroup className="ws-el-controls pull-right">
{keyLink}
<Link
className={
`fa fa-sort-${!this.state.sortColumns ? 'alpha' : 'numeric'}-asc ` +
'pull-left sort-cols m-l-2'}
onClick={this.toggleSortColumns.bind(this)}
tooltip={
!this.state.sortColumns ?
'Sort columns alphabetically' :
'Original table column order'}
href="#"
/>
{table.selectStar &&
<CopyToClipboard
copyNode={
<a className="fa fa-clipboard pull-left m-l-2" />
}
text={table.selectStar}
shouldShowText={false}
tooltipText="Copy SELECT statement to clipboard"
/>
}
<Link
className="fa fa-trash table-remove pull-left m-l-2"
onClick={this.removeTable.bind(this)}
tooltip="Remove table preview"
href="#"
/>
</ButtonGroup>
</div>
</div>
{this.renderHeader()}
<div>
{this.renderMetadata()}
{this.renderBody()}
</div>
</div>
</Collapse>
@@ -0,0 +1,129 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Badge } from 'react-bootstrap';
import AceEditor from 'react-ace';
import 'brace/mode/sql';
import 'brace/mode/json';
import 'brace/mode/html';
import 'brace/mode/markdown';
import 'brace/theme/textmate';
import ModalTrigger from '../../components/ModalTrigger';
import InfoTooltipWithTrigger from '../../components/InfoTooltipWithTrigger';
import Button from '../../components/Button';
import { t } from '../../locales';
const propTypes = {
onChange: PropTypes.func,
code: PropTypes.string,
language: PropTypes.oneOf(['yaml', 'json']),
};
const defaultProps = {
label: null,
description: null,
onChange: () => {},
code: '{}',
};
export default class TemplateParamsEditor extends React.Component {
constructor(props) {
super(props);
const codeText = props.code || '{}';
this.state = {
codeText,
parsedJSON: null,
isValid: true,
};
this.onChange = this.onChange.bind(this);
}
componentDidMount() {
this.onChange(this.state.codeText);
}
onChange(value) {
const codeText = value;
let isValid;
let parsedJSON = {};
try {
parsedJSON = JSON.parse(value);
isValid = true;
} catch (e) {
isValid = false;
}
this.setState({ parsedJSON, isValid, codeText });
if (isValid) {
this.props.onChange(codeText);
} else {
this.props.onChange('{}');
}
}
renderDoc() {
return (
<p>
Assign a set of parameters as <code>JSON</code> below
(example: <code>{'{"my_table": "foo"}'}</code>),
and they become available
in your SQL (example: <code>SELECT * FROM {'{{ my_table }}'} </code>)
by using
<a
href="http://superset.apache.org/sqllab.html#templating-with-jinja"
target="_blank"
rel="noopener noreferrer"
>
Jinja templating
</a> syntax.
</p>
);
}
renderModalBody() {
return (
<div>
{this.renderDoc()}
<AceEditor
mode={this.props.language}
theme="textmate"
style={{ border: '1px solid #CCC' }}
minLines={25}
maxLines={50}
onChange={this.onChange}
width="100%"
editorProps={{ $blockScrolling: true }}
enableLiveAutocompletion
value={this.state.codeText}
/>
</div>
);
}
render() {
const paramCount = this.state.parsedJSON ? Object.keys(this.state.parsedJSON).length : 0;
return (
<ModalTrigger
modalTitle={t('Template Parameters')}
triggerNode={
<Button
className="m-r-5"
tooltip={t('Edit template parameters')}
>
{`${t('parameters')} `}
{paramCount > 0 &&
<Badge>{paramCount}</Badge>
}
{!this.state.isValid &&
<InfoTooltipWithTrigger
icon="exclamation-triangle"
bsStyle="danger"
tooltip={t('Invalid JSON')}
label="invalid-json"
/>
}
</Button>
}
modalBody={this.renderModalBody(true)}
/>
);
}
}
TemplateParamsEditor.propTypes = propTypes;
TemplateParamsEditor.defaultProps = defaultProps;
@@ -1,24 +1,39 @@
/* global notify */
import moment from 'moment';
import React from 'react';
import PropTypes from 'prop-types';
import { bindActionCreators } from 'redux';
import { connect } from 'react-redux';
import { Alert, Button, Col, Modal } from 'react-bootstrap';
import Select from 'react-select';
import { Table } from 'reactable';
import shortid from 'shortid';
import $ from 'jquery';
import { getExploreUrl } from '../../explorev2/exploreUtils';
import { getExploreUrl } from '../../explore/exploreUtils';
import * as actions from '../actions';
import { VISUALIZE_VALIDATION_ERRORS } from '../constants';
import visTypes from '../../explore/stores/visTypes';
import { t } from '../../locales';
const CHART_TYPES = [
{ value: 'dist_bar', label: 'Distribution - Bar Chart', requiresTime: false },
{ value: 'pie', label: 'Pie Chart', requiresTime: false },
{ value: 'line', label: 'Time Series - Line Chart', requiresTime: true },
{ value: 'bar', label: 'Time Series - Bar Chart', requiresTime: true },
];
const CHART_TYPES = Object.keys(visTypes)
.filter(typeName => !!visTypes[typeName].showOnExplore)
.map((typeName) => {
const vis = visTypes[typeName];
return {
value: typeName,
label: vis.label,
requiresTime: !!vis.requiresTime,
};
});
const propTypes = {
onHide: React.PropTypes.func,
query: React.PropTypes.object,
show: React.PropTypes.bool,
actions: PropTypes.object.isRequired,
onHide: PropTypes.func,
query: PropTypes.object,
show: PropTypes.bool,
datasource: PropTypes.string,
errorMessage: PropTypes.string,
timeout: PropTypes.number,
};
const defaultProps = {
show: false,
@@ -32,28 +47,26 @@ class VisualizeModal extends React.PureComponent {
this.state = {
chartType: CHART_TYPES[0],
datasourceName: this.datasourceName(),
columns: {},
columns: this.getColumnFromProps(),
hints: [],
};
}
componentDidMount() {
this.validate();
}
componentWillReceiveProps(nextProps) {
this.setStateFromProps(nextProps);
}
setStateFromProps(props) {
if (
getColumnFromProps() {
const props = this.props;
if (!props ||
!props.query ||
!props.query.results ||
!props.query.results.columns) {
return;
return {};
}
const columns = {};
props.query.results.columns.forEach((col) => {
columns[col.name] = col;
});
this.setState({ columns });
return columns;
}
datasourceName() {
const { query } = this.props;
@@ -74,14 +87,14 @@ class VisualizeModal extends React.PureComponent {
if (!re.test(colName)) {
hints.push(
<div>
"{colName}" is not right as a column name, please alias it
(as in SELECT count(*) <strong>AS my_alias</strong>) using only
alphanumeric characters and underscores
{t('%s is not right as a column name, please alias it ' +
'(as in SELECT count(*) ', colName)} <strong>{t('AS my_alias')}</strong>) {t('using only ' +
'alphanumeric characters and underscores')}
</div>);
}
});
if (this.state.chartType === null) {
hints.push('Pick a chart type!');
hints.push(VISUALIZE_VALIDATION_ERRORS.REQUIRE_CHART_TYPE);
} else if (this.state.chartType.requiresTime) {
let hasTime = false;
for (const colName in cols) {
@@ -91,9 +104,7 @@ class VisualizeModal extends React.PureComponent {
}
}
if (!hasTime) {
hints.push(
'To use this chart type you need at least one column ' +
'flagged as a date');
hints.push(VISUALIZE_VALIDATION_ERRORS.REQUIRE_TIME);
}
}
this.setState({ hints });
@@ -112,27 +123,37 @@ class VisualizeModal extends React.PureComponent {
}
return columns;
}
visualize() {
const vizOptions = {
buildVizOptions() {
return {
chartType: this.state.chartType.value,
datasourceName: this.state.datasourceName,
columns: this.state.columns,
sql: this.props.query.sql,
dbId: this.props.query.dbId,
};
notify.info('Creating a data source and popping a new tab');
$.ajax({
type: 'POST',
url: '/superset/sqllab_viz/',
async: false,
data: {
data: JSON.stringify(vizOptions),
},
dataType: 'json',
success: (resp) => {
}
buildVisualizeAdvise() {
let advise;
const timeout = this.props.timeout;
const queryDuration = moment.duration(this.props.query.endDttm - this.props.query.startDttm);
if (Math.round(queryDuration.asMilliseconds()) > timeout * 1000) {
advise = (
<Alert bsStyle="warning">
This query took {Math.round(queryDuration.asSeconds())} seconds to run,
and the explore view times out at {timeout} seconds,
following this flow will most likely lead to your query timing out.
We recommend your summarize your data further before following that flow.
If activated you can use the <strong>CREATE TABLE AS</strong> feature
to store a summarized data set that you can then explore.
</Alert>);
}
return advise;
}
visualize() {
this.props.actions.createDatasource(this.buildVizOptions(), this)
.done((resp) => {
const columns = Object.keys(this.state.columns).map(k => this.state.columns[k]);
const data = JSON.parse(resp);
const mainMetric = columns.filter(d => d.agg)[0];
const mainGroupBy = columns.filter(d => d.is_dim)[0];
const formData = {
datasource: `${data.table_id}__table`,
@@ -140,21 +161,19 @@ class VisualizeModal extends React.PureComponent {
since: '100 years ago',
limit: '0',
};
if (mainMetric) {
formData.metrics = [mainMetric.name];
formData.metric = mainMetric.name;
}
if (mainGroupBy) {
formData.groupby = mainGroupBy.name;
formData.groupby = [mainGroupBy.name];
}
notify.info(t('Creating a data source and popping a new tab'));
window.open(getExploreUrl(formData));
},
error: () => notify('An error occurred while creating the data source'),
});
})
.fail(() => {
notify.error(this.props.errorMessage);
});
}
changeDatasourceName(event) {
this.setState({ datasourceName: event.target.value });
this.validate();
this.setState({ datasourceName: event.target.value }, this.validate);
}
changeCheckbox(attr, columnName, event) {
let columns = this.mergedColumns();
@@ -175,7 +194,7 @@ class VisualizeModal extends React.PureComponent {
<div className="VisualizeModal">
<Modal show={this.props.show} onHide={this.props.onHide}>
<Modal.Body>
No results available for this query
{t('No results available for this query')}
</Modal.Body>
</Modal>
</div>
@@ -220,16 +239,17 @@ class VisualizeModal extends React.PureComponent {
<div className="VisualizeModal">
<Modal show={this.props.show} onHide={this.props.onHide}>
<Modal.Header closeButton>
<Modal.Title>Visualize</Modal.Title>
<Modal.Title>{t('Visualize')}</Modal.Title>
</Modal.Header>
<Modal.Body>
{alerts}
{this.buildVisualizeAdvise()}
<div className="row">
<Col md={6}>
Chart Type
{t('Chart Type')}
<Select
name="select-chart-type"
placeholder="[Chart Type]"
placeholder={t('[Chart Type]')}
options={CHART_TYPES}
value={(this.state.chartType) ? this.state.chartType.value : null}
autosize={false}
@@ -237,11 +257,11 @@ class VisualizeModal extends React.PureComponent {
/>
</Col>
<Col md={6}>
Datasource Name
{t('Datasource Name')}
<input
type="text"
className="form-control input-sm"
placeholder="datasource name"
placeholder={t('datasource name')}
onChange={this.changeDatasourceName.bind(this)}
value={this.state.datasourceName}
/>
@@ -258,7 +278,7 @@ class VisualizeModal extends React.PureComponent {
bsStyle="primary"
disabled={(this.state.hints.length > 0)}
>
Visualize
{t('Visualize')}
</Button>
</Modal.Body>
</Modal>
@@ -270,4 +290,19 @@ class VisualizeModal extends React.PureComponent {
VisualizeModal.propTypes = propTypes;
VisualizeModal.defaultProps = defaultProps;
export default VisualizeModal;
function mapStateToProps(state) {
return {
datasource: state.datasource,
errorMessage: state.errorMessage,
timeout: state.common ? state.common.conf.SUPERSET_WEBSERVER_TIMEOUT : null,
};
}
function mapDispatchToProps(dispatch) {
return {
actions: bindActionCreators(actions, dispatch),
};
}
export { VisualizeModal };
export default connect(mapStateToProps, mapDispatchToProps)(VisualizeModal);
@@ -1,3 +1,5 @@
import { t } from '../locales';
export const STATE_BSSTYLE_MAP = {
failed: 'danger',
pending: 'info',
@@ -11,6 +13,7 @@ export const STATUS_OPTIONS = [
'success',
'failed',
'running',
'pending',
];
export const TIME_OPTIONS = [
@@ -22,3 +25,10 @@ export const TIME_OPTIONS = [
'90 days ago',
'1 year ago',
];
export const VISUALIZE_VALIDATION_ERRORS = {
REQUIRE_CHART_TYPE: t('Pick a chart type!'),
REQUIRE_TIME: t('To use this chart type you need at least one column flagged as a date'),
REQUIRE_DIMENSION: t('To use this chart type you need at least one dimension'),
REQUIRE_AGGREGATION_FUNCTION: t('To use this chart type you need at least one aggregation function'),
};
+4 -4
View File
@@ -6,16 +6,16 @@ import thunkMiddleware from 'redux-thunk';
import { getInitialState, sqlLabReducer } from './reducers';
import { initEnhancer } from '../reduxUtils';
import { initJQueryAjaxCSRF } from '../modules/utils';
import { initJQueryAjax } from '../modules/utils';
import App from './components/App';
import { appSetup } from '../common';
import './main.css';
import './reactable-pagination.css';
import './main.less';
import '../../stylesheets/reactable-pagination.css';
import '../components/FilterableTable/FilterableTableStyles.css';
appSetup();
initJQueryAjaxCSRF();
initJQueryAjax();
const appContainer = document.getElementById('app');
const bootstrapData = JSON.parse(appContainer.getAttribute('data-bootstrap'));
@@ -130,9 +130,6 @@ div.Workspace {
display: inline-block;
background-color: #ccc;
}
.Pane2 {
width: 0;
}
.running {
background-color: lime;
color: black;
@@ -161,7 +158,6 @@ div.Workspace {
margin: 0px;
border: none;
font-size: 12px;
line-height: @line-height-base;
background-color: transparent !important;
}
@@ -265,7 +261,7 @@ div.tablePopover:hover {
}
.QueryTable .label {
margin-top: 5px;
display: inline-block;
}
.ResultsModal .modal-body {
@@ -293,3 +289,19 @@ a.Link {
.tooltip-inner {
max-width: 500px;
}
.SplitPane.horizontal {
padding-right: 4px;
}
.SouthPane {
margin-top: 10px;
position: absolute;
width: 100%;
overflow: scroll;
}
.search-date-filter-container {
display: flex;
.Select {
margin-right: 3px;
}
}
+43 -15
View File
@@ -3,11 +3,12 @@ import * as actions from './actions';
import { now } from '../modules/dates';
import { addToObject, alterInObject, alterInArr, removeFromArr, getFromArr, addToArr }
from '../reduxUtils';
import { t } from '../locales';
export function getInitialState(defaultDbId) {
const defaultQueryEditor = {
id: shortid.generate(),
title: 'Untitled Query',
title: t('Untitled Query'),
sql: 'SELECT *\nFROM\nWHERE',
selectedText: null,
latestQueryId: null,
@@ -40,7 +41,7 @@ export const sqlLabReducer = function (state, action) {
qe.id === state.tabHistory[state.tabHistory.length - 1]);
const qe = {
id: shortid.generate(),
title: `Copy of ${progenitor.title}`,
title: t('Copy of %s', progenitor.title),
dbId: (action.query.dbId) ? action.query.dbId : null,
schema: (action.query.schema) ? action.query.schema : null,
autorun: true,
@@ -76,13 +77,13 @@ export const sqlLabReducer = function (state, action) {
[actions.MERGE_TABLE]() {
const at = Object.assign({}, action.table);
let existingTable;
state.tables.forEach((t) => {
state.tables.forEach((xt) => {
if (
t.dbId === at.dbId &&
t.queryEditorId === at.queryEditorId &&
t.schema === at.schema &&
t.name === at.name) {
existingTable = t;
xt.dbId === at.dbId &&
xt.queryEditorId === at.queryEditorId &&
xt.schema === at.schema &&
xt.name === at.name) {
existingTable = xt;
}
});
if (existingTable) {
@@ -115,11 +116,11 @@ export const sqlLabReducer = function (state, action) {
delete queries[action.oldQueryId];
const newTables = [];
state.tables.forEach((t) => {
if (t.dataPreviewQueryId === action.oldQueryId) {
newTables.push(Object.assign({}, t, { dataPreviewQueryId: action.newQuery.id }));
state.tables.forEach((xt) => {
if (xt.dataPreviewQueryId === action.oldQueryId) {
newTables.push(Object.assign({}, xt, { dataPreviewQueryId: action.newQuery.id }));
} else {
newTables.push(t);
newTables.push(xt);
}
});
return Object.assign(
@@ -210,12 +211,18 @@ export const sqlLabReducer = function (state, action) {
[actions.QUERY_EDITOR_SET_SQL]() {
return alterInArr(state, 'queryEditors', action.queryEditor, { sql: action.sql });
},
[actions.QUERY_EDITOR_SET_TEMPLATE_PARAMS]() {
return alterInArr(state, 'queryEditors', action.queryEditor, { templateParams: action.templateParams });
},
[actions.QUERY_EDITOR_SET_SELECTED_TEXT]() {
return alterInArr(state, 'queryEditors', action.queryEditor, { selectedText: action.sql });
},
[actions.QUERY_EDITOR_SET_AUTORUN]() {
return alterInArr(state, 'queryEditors', action.queryEditor, { autorun: action.autorun });
},
[actions.QUERY_EDITOR_PERSIST_HEIGHT]() {
return alterInArr(state, 'queryEditors', action.queryEditor, { height: action.currentHeight });
},
[actions.ADD_ALERT]() {
return addToArr(state, 'alerts', action.alert);
},
@@ -233,11 +240,14 @@ export const sqlLabReducer = function (state, action) {
let newQueries = Object.assign({}, state.queries);
// Fetch the updates to the queries present in the store.
let change = false;
let queriesLastUpdate = state.queriesLastUpdate;
for (const id in action.alteredQueries) {
const changedQuery = action.alteredQueries[id];
if (!state.queries.hasOwnProperty(id) ||
(state.queries[id].changedOn !== changedQuery.changedOn &&
state.queries[id].state !== 'stopped')) {
state.queries[id].state !== 'stopped') {
if (changedQuery.changedOn > queriesLastUpdate) {
queriesLastUpdate = changedQuery.changedOn;
}
newQueries[id] = Object.assign({}, state.queries[id], changedQuery);
change = true;
}
@@ -245,9 +255,27 @@ export const sqlLabReducer = function (state, action) {
if (!change) {
newQueries = state.queries;
}
const queriesLastUpdate = now();
return Object.assign({}, state, { queries: newQueries, queriesLastUpdate });
},
[actions.CREATE_DATASOURCE_STARTED]() {
return Object.assign({}, state, {
isDatasourceLoading: true,
errorMessage: null,
});
},
[actions.CREATE_DATASOURCE_SUCCESS]() {
return Object.assign({}, state, {
isDatasourceLoading: false,
errorMessage: null,
datasource: action.datasource,
});
},
[actions.CREATE_DATASOURCE_FAILED]() {
return Object.assign({}, state, {
isDatasourceLoading: false,
errorMessage: action.err,
});
},
};
if (action.type in actionHandlers) {
return actionHandlers[action.type]();
@@ -0,0 +1,99 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Button, Panel, Grid, Row, Col } from 'react-bootstrap';
import Select from 'react-virtualized-select';
import visTypes from '../explore/stores/visTypes';
import { t } from '../locales';
const propTypes = {
datasources: PropTypes.arrayOf(PropTypes.shape({
label: PropTypes.string.isRequired,
value: PropTypes.string.isRequired,
})).isRequired,
};
export default class AddSliceContainer extends React.PureComponent {
constructor(props) {
super(props);
const visTypeKeys = Object.keys(visTypes);
this.vizTypeOptions = visTypeKeys.map(vt => ({ label: visTypes[vt].label, value: vt }));
this.state = {
visType: 'table',
};
}
exploreUrl() {
const baseUrl = `/superset/explore/${this.state.datasourceType}/${this.state.datasourceId}`;
const formData = encodeURIComponent(JSON.stringify({ viz_type: this.state.visType }));
return `${baseUrl}?form_data=${formData}`;
}
gotoSlice() {
window.location.href = this.exploreUrl();
}
changeDatasource(e) {
this.setState({
datasourceValue: e.value,
datasourceId: e.value.split('__')[0],
datasourceType: e.value.split('__')[1],
});
}
changeVisType(e) {
this.setState({ visType: e.value });
}
isBtnDisabled() {
return !(this.state.datasourceId && this.state.visType);
}
render() {
return (
<div className="container">
<Panel header={<h3>{t('Create a new slice')}</h3>}>
<Grid>
<Row>
<Col xs={12} sm={6}>
<div>
<p>{t('Choose a datasource')}</p>
<Select
clearable={false}
name="select-datasource"
onChange={this.changeDatasource.bind(this)}
options={this.props.datasources}
placeholder={t('Choose a datasource')}
value={this.state.datasourceValue}
/>
</div>
<br />
<div>
<p>{t('Choose a visualization type')}</p>
<Select
clearable={false}
name="select-vis-type"
onChange={this.changeVisType.bind(this)}
options={this.vizTypeOptions}
placeholder={t('Choose a visualization type')}
value={this.state.visType}
/>
</div>
<br />
<Button
bsStyle="primary"
disabled={this.isBtnDisabled()}
onClick={this.gotoSlice.bind(this)}
>
{t('Create new slice')}
</Button>
<br /><br />
</Col>
</Row>
</Grid>
</Panel>
</div>
);
}
}
AddSliceContainer.propTypes = propTypes;
@@ -0,0 +1,14 @@
import React from 'react';
import ReactDOM from 'react-dom';
import { appSetup } from '../common';
import AddSliceContainer from './AddSliceContainer';
appSetup();
const addSliceContainer = document.getElementById('js-add-slice-container');
const bootstrapData = JSON.parse(addSliceContainer.getAttribute('data-bootstrap'));
ReactDOM.render(
<AddSliceContainer datasources={bootstrapData.datasources} />,
addSliceContainer,
);
+220
View File
@@ -0,0 +1,220 @@
/* eslint camelcase: 0 */
import React from 'react';
import PropTypes from 'prop-types';
import Mustache from 'mustache';
import { Tooltip } from 'react-bootstrap';
import { d3format } from '../modules/utils';
import ChartBody from './ChartBody';
import Loading from '../components/Loading';
import StackTraceMessage from '../components/StackTraceMessage';
import visMap from '../../visualizations/main';
import sandboxedEval from '../modules/sandbox';
import './chart.css';
const propTypes = {
annotationData: PropTypes.object,
actions: PropTypes.object,
chartKey: PropTypes.string.isRequired,
containerId: PropTypes.string.isRequired,
datasource: PropTypes.object.isRequired,
formData: PropTypes.object.isRequired,
height: PropTypes.number,
width: PropTypes.number,
setControlValue: PropTypes.func,
timeout: PropTypes.number,
vizType: PropTypes.string.isRequired,
// state
chartAlert: PropTypes.string,
chartStatus: PropTypes.string,
chartUpdateEndTime: PropTypes.number,
chartUpdateStartTime: PropTypes.number,
latestQueryFormData: PropTypes.object,
queryRequest: PropTypes.object,
queryResponse: PropTypes.object,
lastRendered: PropTypes.number,
triggerQuery: PropTypes.bool,
// dashboard callbacks
addFilter: PropTypes.func,
getFilters: PropTypes.func,
clearFilter: PropTypes.func,
removeFilter: PropTypes.func,
};
const defaultProps = {
addFilter: () => ({}),
getFilters: () => ({}),
clearFilter: () => ({}),
removeFilter: () => ({}),
};
class Chart extends React.PureComponent {
constructor(props) {
super(props);
this.state = {};
// these properties are used by visualizations
this.annotationData = props.annotationData;
this.containerId = props.containerId;
this.selector = `#${this.containerId}`;
this.formData = props.formData;
this.datasource = props.datasource;
this.addFilter = this.addFilter.bind(this);
this.getFilters = this.getFilters.bind(this);
this.clearFilter = this.clearFilter.bind(this);
this.removeFilter = this.removeFilter.bind(this);
this.height = this.height.bind(this);
this.width = this.width.bind(this);
}
componentDidMount() {
if (this.props.triggerQuery) {
this.props.actions.runQuery(this.props.formData, false,
this.props.timeout,
this.props.chartKey,
);
}
}
componentWillReceiveProps(nextProps) {
this.annotationData = nextProps.annotationData;
this.containerId = nextProps.containerId;
this.selector = `#${this.containerId}`;
this.formData = nextProps.formData;
this.datasource = nextProps.datasource;
}
componentDidUpdate(prevProps) {
if (
this.props.queryResponse &&
this.props.chartStatus === 'success' &&
!this.props.queryResponse.error && (
prevProps.annotationData !== this.props.annotationData ||
prevProps.queryResponse !== this.props.queryResponse ||
prevProps.height !== this.props.height ||
prevProps.width !== this.props.width ||
prevProps.lastRendered !== this.props.lastRendered)
) {
this.renderViz();
}
}
getFilters() {
return this.props.getFilters();
}
setTooltip(tooltip) {
this.setState({ tooltip });
}
addFilter(col, vals, merge = true, refresh = true) {
this.props.addFilter(col, vals, merge, refresh);
}
clearFilter() {
this.props.clearFilter();
}
removeFilter(col, vals, refresh = true) {
this.props.removeFilter(col, vals, refresh);
}
clearError() {
this.setState({
errorMsg: null,
});
}
width() {
return this.props.width || this.container.el.offsetWidth;
}
height() {
return this.props.height || this.container.el.offsetHeight;
}
d3format(col, number) {
const { datasource } = this.props;
const format = (datasource.column_formats && datasource.column_formats[col]) || '0.3s';
return d3format(format, number);
}
render_template(s) {
const context = {
width: this.width(),
height: this.height(),
};
return Mustache.render(s, context);
}
renderTooltip() {
if (this.state.tooltip) {
/* eslint-disable react/no-danger */
return (
<Tooltip
className="chart-tooltip"
id="chart-tooltip"
placement="right"
positionTop={this.state.tooltip.y - 10}
positionLeft={this.state.tooltip.x + 30}
arrowOffsetTop={10}
>
<div dangerouslySetInnerHTML={{ __html: this.state.tooltip.content }} />
</Tooltip>
);
/* eslint-enable react/no-danger */
}
return null;
}
renderViz() {
const viz = visMap[this.props.vizType];
const fd = this.props.formData;
const qr = this.props.queryResponse;
try {
// Executing user-defined data mutator function
if (fd.js_data) {
qr.data = sandboxedEval(fd.js_data)(qr.data);
}
// [re]rendering the visualization
viz(this, qr, this.props.setControlValue);
} catch (e) {
this.props.actions.chartRenderingFailed(e, this.props.chartKey);
}
}
render() {
const isLoading = this.props.chartStatus === 'loading';
return (
<div className={`token col-md-12 ${isLoading ? 'is-loading' : ''}`}>
{this.renderTooltip()}
{isLoading &&
<Loading size={25} />
}
{this.props.chartAlert &&
<StackTraceMessage
message={this.props.chartAlert}
queryResponse={this.props.queryResponse}
/>
}
{!this.props.chartAlert &&
<ChartBody
containerId={this.containerId}
vizType={this.props.formData.viz_type}
height={this.height}
width={this.width}
ref={(inner) => {
this.container = inner;
}}
/>
}
</div>
);
}
}
Chart.propTypes = propTypes;
Chart.defaultProps = defaultProps;
export default Chart;
@@ -0,0 +1,54 @@
import React from 'react';
import PropTypes from 'prop-types';
import $ from 'jquery';
const propTypes = {
containerId: PropTypes.string.isRequired,
vizType: PropTypes.string.isRequired,
height: PropTypes.func.isRequired,
width: PropTypes.func.isRequired,
};
class ChartBody extends React.PureComponent {
html(data) {
this.el.innerHTML = data;
}
css(property, value) {
this.el.style[property] = value;
}
get(n) {
return $(this.el).get(n);
}
find(classname) {
return $(this.el).find(classname);
}
show() {
return $(this.el).show();
}
height() {
return this.props.height();
}
width() {
return this.props.width();
}
render() {
return (
<div
id={this.props.containerId}
className={`slice_container ${this.props.vizType}`}
ref={(el) => { this.el = el; }}
/>
);
}
}
ChartBody.propTypes = propTypes;
export default ChartBody;
@@ -0,0 +1,29 @@
import { connect } from 'react-redux';
import { bindActionCreators } from 'redux';
import * as Actions from './chartAction';
import Chart from './Chart';
function mapStateToProps({ charts }, ownProps) {
const chart = charts[ownProps.chartKey];
return {
annotationData: chart.annotationData,
chartAlert: chart.chartAlert,
chartStatus: chart.chartStatus,
chartUpdateEndTime: chart.chartUpdateEndTime,
chartUpdateStartTime: chart.chartUpdateStartTime,
latestQueryFormData: chart.latestQueryFormData,
lastRendered: chart.lastRendered,
queryResponse: chart.queryResponse,
queryRequest: chart.queryRequest,
triggerQuery: chart.triggerQuery,
};
}
function mapDispatchToProps(dispatch) {
return {
actions: bindActionCreators(Actions, dispatch),
};
}
export default connect(mapStateToProps, mapDispatchToProps)(Chart);
@@ -0,0 +1,4 @@
.chart-tooltip {
opacity: 0.75;
font-size: 12px;
}
@@ -0,0 +1,146 @@
import { getExploreUrl, getAnnotationJsonUrl } from '../explore/exploreUtils';
import { requiresQuery, ANNOTATION_SOURCE_TYPES } from '../modules/AnnotationTypes';
const $ = window.$ = require('jquery');
export const CHART_UPDATE_STARTED = 'CHART_UPDATE_STARTED';
export function chartUpdateStarted(queryRequest, key) {
return { type: CHART_UPDATE_STARTED, queryRequest, key };
}
export const CHART_UPDATE_SUCCEEDED = 'CHART_UPDATE_SUCCEEDED';
export function chartUpdateSucceeded(queryResponse, key) {
return { type: CHART_UPDATE_SUCCEEDED, queryResponse, key };
}
export const CHART_UPDATE_STOPPED = 'CHART_UPDATE_STOPPED';
export function chartUpdateStopped(queryRequest, key) {
if (queryRequest) {
queryRequest.abort();
}
return { type: CHART_UPDATE_STOPPED, key };
}
export const CHART_UPDATE_TIMEOUT = 'CHART_UPDATE_TIMEOUT';
export function chartUpdateTimeout(statusText, timeout, key) {
return { type: CHART_UPDATE_TIMEOUT, statusText, timeout, key };
}
export const CHART_UPDATE_FAILED = 'CHART_UPDATE_FAILED';
export function chartUpdateFailed(queryResponse, key) {
return { type: CHART_UPDATE_FAILED, queryResponse, key };
}
export const CHART_RENDERING_FAILED = 'CHART_RENDERING_FAILED';
export function chartRenderingFailed(error, key) {
return { type: CHART_RENDERING_FAILED, error, key };
}
export const REMOVE_CHART = 'REMOVE_CHART';
export function removeChart(key) {
return { type: REMOVE_CHART, key };
}
export const ANNOTATION_QUERY_SUCCESS = 'ANNOTATION_QUERY_SUCCESS';
export function annotationQuerySuccess(annotation, queryResponse, key) {
return { type: ANNOTATION_QUERY_SUCCESS, annotation, queryResponse, key };
}
export const ANNOTATION_QUERY_STARTED = 'ANNOTATION_QUERY_STARTED';
export function annotationQueryStarted(annotation, queryRequest, key) {
return { type: ANNOTATION_QUERY_STARTED, annotation, queryRequest, key };
}
export const ANNOTATION_QUERY_FAILED = 'ANNOTATION_QUERY_FAILED';
export function annotationQueryFailed(annotation, queryResponse, key) {
return { type: ANNOTATION_QUERY_FAILED, annotation, queryResponse, key };
}
export function runAnnotationQuery(annotation, timeout = 60, formData = null, key) {
return function (dispatch, getState) {
const sliceKey = key || Object.keys(getState().charts)[0];
const fd = formData || getState().charts[sliceKey].latestQueryFormData;
if (!requiresQuery(annotation.sourceType)) {
return Promise.resolve();
}
const sliceFormData = Object.keys(annotation.overrides)
.reduce((d, k) => ({
...d,
[k]: annotation.overrides[k] || fd[k],
}), {});
const isNative = annotation.sourceType === ANNOTATION_SOURCE_TYPES.NATIVE;
const url = getAnnotationJsonUrl(annotation.value, sliceFormData, isNative);
const queryRequest = $.ajax({
url,
dataType: 'json',
timeout: timeout * 1000,
});
dispatch(annotationQueryStarted(annotation, queryRequest, sliceKey));
return queryRequest
.then(queryResponse => dispatch(annotationQuerySuccess(annotation, queryResponse, sliceKey)))
.catch((err) => {
if (err.statusText === 'timeout') {
dispatch(annotationQueryFailed(annotation, { error: 'Query Timeout' }, sliceKey));
} else if ((err.responseJSON.error || '').toLowerCase().startsWith('no data')) {
dispatch(annotationQuerySuccess(annotation, err, sliceKey));
} else if (err.statusText !== 'abort') {
dispatch(annotationQueryFailed(annotation, err.responseJSON, sliceKey));
}
});
};
}
export const TRIGGER_QUERY = 'TRIGGER_QUERY';
export function triggerQuery(value = true, key) {
return { type: TRIGGER_QUERY, value, key };
}
// this action is used for forced re-render without fetch data
export const RENDER_TRIGGERED = 'RENDER_TRIGGERED';
export function renderTriggered(value, key) {
return { type: RENDER_TRIGGERED, value, key };
}
export const RUN_QUERY = 'RUN_QUERY';
export function runQuery(formData, force = false, timeout = 60, key) {
return (dispatch) => {
const url = getExploreUrl(formData, 'json', force);
const queryRequest = $.ajax({
url,
dataType: 'json',
timeout: timeout * 1000,
});
const queryPromise = Promise.resolve(dispatch(chartUpdateStarted(queryRequest, key)))
.then(() => queryRequest)
.then(queryResponse => dispatch(chartUpdateSucceeded(queryResponse, key)))
.catch((err) => {
if (err.statusText === 'timeout') {
dispatch(chartUpdateTimeout(err.statusText, timeout, key));
} else if (err.statusText !== 'abort') {
let errObject;
if (err.responseJSON) {
errObject = err.responseJSON;
} else if (err.stack) {
errObject = {
error: 'Unexpected error: ' + err.description,
stacktrace: err.stack,
};
} else {
errObject = {
error: 'Unexpected error.',
};
}
dispatch(chartUpdateFailed(errObject, key));
}
});
const annotationLayers = formData.annotation_layers || [];
return Promise.all([
queryPromise,
dispatch(triggerQuery(false, key)),
...annotationLayers.map(x => dispatch(runAnnotationQuery(x, timeout, formData, key))),
]);
};
}
@@ -0,0 +1,150 @@
/* eslint camelcase: 0 */
import PropTypes from 'prop-types';
import { now } from '../modules/dates';
import * as actions from './chartAction';
import { t } from '../locales';
export const chartPropType = {
chartKey: PropTypes.string.isRequired,
chartAlert: PropTypes.string,
chartStatus: PropTypes.string,
chartUpdateEndTime: PropTypes.number,
chartUpdateStartTime: PropTypes.number,
latestQueryFormData: PropTypes.object,
queryRequest: PropTypes.object,
queryResponse: PropTypes.object,
triggerQuery: PropTypes.bool,
lastRendered: PropTypes.number,
};
export const chart = {
chartKey: '',
chartAlert: null,
chartStatus: 'loading',
chartUpdateEndTime: null,
chartUpdateStartTime: now(),
latestQueryFormData: null,
queryRequest: null,
queryResponse: null,
triggerQuery: true,
lastRendered: 0,
};
export default function chartReducer(charts = {}, action) {
const actionHandlers = {
[actions.CHART_UPDATE_SUCCEEDED](state) {
return { ...state,
chartStatus: 'success',
queryResponse: action.queryResponse,
chartUpdateEndTime: now(),
};
},
[actions.CHART_UPDATE_STARTED](state) {
return { ...state,
chartStatus: 'loading',
chartAlert: null,
chartUpdateEndTime: null,
chartUpdateStartTime: now(),
queryRequest: action.queryRequest,
};
},
[actions.CHART_UPDATE_STOPPED](state) {
return { ...state,
chartStatus: 'stopped',
chartAlert: t('Updating chart was stopped'),
};
},
[actions.CHART_RENDERING_FAILED](state) {
return { ...state,
chartStatus: 'failed',
chartAlert: t('An error occurred while rendering the visualization: %s', action.error),
};
},
[actions.CHART_UPDATE_TIMEOUT](state) {
return { ...state,
chartStatus: 'failed',
chartAlert: (
`<strong>${t('Query timeout')}</strong> - ` +
t(`visualization queries are set to timeout at ${action.timeout} seconds. `) +
t('Perhaps your data has grown, your database is under unusual load, ' +
'or you are simply querying a data source that is too large ' +
'to be processed within the timeout range. ' +
'If that is the case, we recommend that you summarize your data further.')),
};
},
[actions.CHART_UPDATE_FAILED](state) {
return { ...state,
chartStatus: 'failed',
chartAlert: action.queryResponse ? action.queryResponse.error : t('Network error.'),
chartUpdateEndTime: now(),
queryResponse: action.queryResponse,
};
},
[actions.TRIGGER_QUERY](state) {
return { ...state, triggerQuery: action.value };
},
[actions.RENDER_TRIGGERED](state) {
return { ...state, lastRendered: action.value };
},
[actions.ANNOTATION_QUERY_STARTED](state) {
if (state.annotationQuery &&
state.annotationQuery[action.annotation.name]) {
state.annotationQuery[action.annotation.name].abort();
}
const annotationQuery = {
...state.annotationQuery,
[action.annotation.name]: action.queryRequest,
};
return {
...state,
annotationQuery,
};
},
[actions.ANNOTATION_QUERY_SUCCESS](state) {
const annotationData = {
...state.annotationData,
[action.annotation.name]: action.queryResponse.data,
};
const annotationError = { ...state.annotationError };
delete annotationError[action.annotation.name];
const annotationQuery = { ...state.annotationQuery };
delete annotationQuery[action.annotation.name];
return {
...state,
annotationData,
annotationError,
annotationQuery,
};
},
[actions.ANNOTATION_QUERY_FAILED](state) {
const annotationData = { ...state.annotationData };
delete annotationData[action.annotation.name];
const annotationError = {
...state.annotationError,
[action.annotation.name]: action.queryResponse ?
action.queryResponse.error : t('Network error.'),
};
const annotationQuery = { ...state.annotationQuery };
delete annotationQuery[action.annotation.name];
return {
...state,
annotationData,
annotationError,
annotationQuery,
};
},
};
/* eslint-disable no-param-reassign */
if (action.type === actions.REMOVE_CHART) {
delete charts[action.key];
return charts;
}
if (action.type in actionHandlers) {
return { ...charts, [action.key]: actionHandlers[action.type](charts[action.key], action) };
}
return charts;
}
+11
View File
@@ -10,6 +10,17 @@ $(document).ready(function () {
const id = $this.attr('id');
utils.toggleCheckbox(prefix, '#' + id);
});
// for language picker dropdown
$('#language-picker a').click(function (ev) {
ev.preventDefault();
const targetUrl = ev.currentTarget.href;
$.ajax(targetUrl)
.then(() => {
location.reload();
});
});
});
export function appSetup() {
@@ -1,7 +1,25 @@
/* global notify */
import React from 'react';
import AlertContainer from 'react-alert';
import PropTypes from 'prop-types';
const propTypes = {
initMessages: PropTypes.array,
};
const defaultProps = {
initMessages: [],
};
export default class AlertsWrapper extends React.PureComponent {
componentDidMount() {
this.props.initMessages.forEach((msg) => {
if (['info', 'error', 'success'].indexOf(msg[0]) >= 0) {
notify[msg[0]](msg[1]);
} else {
notify.show(msg[1]);
}
});
}
render() {
return (
<AlertContainer
@@ -16,3 +34,5 @@ export default class AlertsWrapper extends React.PureComponent {
/>);
}
}
AlertsWrapper.propTypes = propTypes;
AlertsWrapper.defaultProps = defaultProps;
@@ -0,0 +1,145 @@
import React from 'react';
import PropTypes from 'prop-types';
import { Table, Tr, Td, Thead, Th } from 'reactable';
import { isEqual, isEmpty } from 'underscore';
import TooltipWrapper from './TooltipWrapper';
import { controls } from '../explore/stores/controls';
import ModalTrigger from './ModalTrigger';
import { t } from '../locales';
const propTypes = {
origFormData: PropTypes.object.isRequired,
currentFormData: PropTypes.object.isRequired,
};
export default class AlteredSliceTag extends React.Component {
constructor(props) {
super(props);
const diffs = this.getDiffs(props);
this.state = { diffs, hasDiffs: !isEmpty(diffs) };
}
componentWillReceiveProps(newProps) {
// Update differences if need be
if (isEqual(this.props, newProps)) {
return;
}
const diffs = this.getDiffs(newProps);
this.setState({ diffs, hasDiffs: !isEmpty(diffs) });
}
getDiffs(props) {
// Returns all properties that differ in the
// current form data and the saved form data
const ofd = props.origFormData;
const cfd = props.currentFormData;
const fdKeys = Object.keys(cfd);
const diffs = {};
for (const fdKey of fdKeys) {
// Ignore values that are undefined/nonexisting in either
if (!ofd[fdKey] && !cfd[fdKey]) {
continue;
}
if (!isEqual(ofd[fdKey], cfd[fdKey])) {
diffs[fdKey] = { before: ofd[fdKey], after: cfd[fdKey] };
}
}
return diffs;
}
formatValue(value, key) {
// Format display value based on the control type
// or the value type
if (value === undefined) {
return 'N/A';
} else if (value === null) {
return 'null';
} else if (controls[key] && controls[key].type === 'FilterControl') {
if (!value.length) {
return '[]';
}
return value.map((v) => {
const filterVal = v.val.constructor === Array ? `[${v.val.join(', ')}]` : v.val;
return `${v.col} ${v.op} ${filterVal}`;
}).join(', ');
} else if (controls[key] && controls[key].type === 'BoundsControl') {
return `Min: ${value[0]}, Max: ${value[1]}`;
} else if (controls[key] && controls[key].type === 'CollectionControl') {
return value.map(v => JSON.stringify(v)).join(', ');
} else if (typeof value === 'boolean') {
return value ? 'true' : 'false';
} else if (value.constructor === Array) {
return value.length ? value.join(', ') : '[]';
} else if (typeof value === 'string' || typeof value === 'number') {
return value;
}
return JSON.stringify(value);
}
renderRows() {
const diffs = this.state.diffs;
const rows = [];
for (const key in diffs) {
rows.push(
<Tr key={key}>
<Td column="control" data={(controls[key] && controls[key].label) || key} />
<Td column="before">{this.formatValue(diffs[key].before, key)}</Td>
<Td column="after">{this.formatValue(diffs[key].after, key)}</Td>
</Tr>,
);
}
return rows;
}
renderModalBody() {
return (
<Table className="table" sortable>
<Thead>
<Th column="control">Control</Th>
<Th column="before">Before</Th>
<Th column="after">After</Th>
</Thead>
{this.renderRows()}
</Table>
);
}
renderTriggerNode() {
return (
<TooltipWrapper
label="difference"
tooltip={t('Click to see difference')}
>
<span
className="label label-warning m-l-5"
style={{ fontSize: '12px' }}
>
{t('Altered')}
</span>
</TooltipWrapper>
);
}
render() {
// Return nothing if there are no differences
if (!this.state.hasDiffs) {
return null;
}
// Render the label-warning 'Altered' tag which the user may
// click to open a modal containing a table summarizing the
// differences in the slice
return (
<ModalTrigger
animation
triggerNode={this.renderTriggerNode()}
modalTitle={t('Slice changes')}
bsSize="large"
modalBody={this.renderModalBody()}
/>
);
}
}
AlteredSliceTag.propTypes = propTypes;
@@ -1,20 +1,28 @@
import React from 'react';
import PropTypes from 'prop-types';
import Select from 'react-select';
import { t } from '../locales';
const $ = window.$ = require('jquery');
const propTypes = {
dataEndpoint: React.PropTypes.string.isRequired,
onChange: React.PropTypes.func.isRequired,
mutator: React.PropTypes.func.isRequired,
value: React.PropTypes.number,
valueRenderer: React.PropTypes.func,
placeholder: React.PropTypes.string,
dataEndpoint: PropTypes.string.isRequired,
onChange: PropTypes.func.isRequired,
mutator: PropTypes.func.isRequired,
onAsyncError: PropTypes.func,
value: PropTypes.oneOfType([
PropTypes.number,
PropTypes.arrayOf(PropTypes.number),
]),
valueRenderer: PropTypes.func,
placeholder: PropTypes.string,
autoSelect: PropTypes.bool,
};
const defaultProps = {
placeholder: 'Select ...',
placeholder: t('Select ...'),
valueRenderer: o => (<div>{o.label}</div>),
onAsyncError: () => {},
};
class AsyncSelect extends React.PureComponent {
@@ -34,9 +42,20 @@ class AsyncSelect extends React.PureComponent {
fetchOptions() {
this.setState({ isLoading: true });
const mutator = this.props.mutator;
$.get(this.props.dataEndpoint, (data) => {
this.setState({ options: mutator ? mutator(data) : data, isLoading: false });
});
$.get(this.props.dataEndpoint)
.done((data) => {
this.setState({ options: mutator ? mutator(data) : data, isLoading: false });
if (!this.props.value && this.props.autoSelect && this.state.options.length) {
this.onChange(this.state.options[0]);
}
})
.fail((xhr) => {
this.props.onAsyncError(xhr.responseText);
})
.always(() => {
this.setState({ isLoading: false });
});
}
render() {
return (
@@ -48,6 +67,7 @@ class AsyncSelect extends React.PureComponent {
isLoading={this.state.isLoading}
onChange={this.onChange.bind(this)}
valueRenderer={this.props.valueRenderer}
{...this.props}
/>
</div>
);

Some files were not shown because too many files have changed in this diff Show More