__init__.py 69 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517
  1. """Loads datasets, dashboards and slices in a new superset instance"""
  2. # pylint: disable=C,R,W
  3. import datetime
  4. import gzip
  5. import json
  6. import os
  7. import random
  8. import textwrap
  9. import pandas as pd
  10. from sqlalchemy import BigInteger, Date, DateTime, Float, String, Text
  11. import geohash
  12. import polyline
  13. from superset import app, db, utils
  14. from superset.connectors.connector_registry import ConnectorRegistry
  15. from superset.connectors.sqla.models import TableColumn
  16. from superset.models import core as models
  17. # Shortcuts
  18. DB = models.Database
  19. Slice = models.Slice
  20. Dash = models.Dashboard
  21. TBL = ConnectorRegistry.sources['table']
  22. config = app.config
  23. DATA_FOLDER = os.path.join(config.get("BASE_DIR"), 'data')
  24. misc_dash_slices = set() # slices assembled in a "Misc Chart" dashboard
  25. def update_slice_ids(layout_dict, slices):
  26. charts = [
  27. component for component in layout_dict.values()
  28. if isinstance(component, dict) and component['type'] == 'CHART'
  29. ]
  30. sorted_charts = sorted(charts, key=lambda k: k['meta']['chartId'])
  31. for i, chart_component in enumerate(sorted_charts):
  32. chart_component['meta']['chartId'] = int(slices[i].id)
  33. def merge_slice(slc):
  34. o = db.session.query(Slice).filter_by(slice_name=slc.slice_name).first()
  35. if o:
  36. db.session.delete(o)
  37. db.session.add(slc)
  38. db.session.commit()
  39. def get_slice_json(defaults, **kwargs):
  40. d = defaults.copy()
  41. d.update(kwargs)
  42. return json.dumps(d, indent=4, sort_keys=True)
  43. def load_energy():
  44. """Loads an energy related dataset to use with sankey and graphs"""
  45. tbl_name = 'energy_usage'
  46. with gzip.open(os.path.join(DATA_FOLDER, 'energy.json.gz')) as f:
  47. pdf = pd.read_json(f)
  48. pdf.to_sql(
  49. tbl_name,
  50. db.engine,
  51. if_exists='replace',
  52. chunksize=500,
  53. dtype={
  54. 'source': String(255),
  55. 'target': String(255),
  56. 'value': Float(),
  57. },
  58. index=False)
  59. print("Creating table [wb_health_population] reference")
  60. tbl = db.session.query(TBL).filter_by(table_name=tbl_name).first()
  61. if not tbl:
  62. tbl = TBL(table_name=tbl_name)
  63. tbl.description = "Energy consumption"
  64. tbl.database = utils.get_or_create_main_db()
  65. db.session.merge(tbl)
  66. db.session.commit()
  67. tbl.fetch_metadata()
  68. slc = Slice(
  69. slice_name="Energy Sankey",
  70. viz_type='sankey',
  71. datasource_type='table',
  72. datasource_id=tbl.id,
  73. params=textwrap.dedent("""\
  74. {
  75. "collapsed_fieldsets": "",
  76. "groupby": [
  77. "source",
  78. "target"
  79. ],
  80. "having": "",
  81. "metric": "sum__value",
  82. "row_limit": "5000",
  83. "slice_name": "Energy Sankey",
  84. "viz_type": "sankey",
  85. "where": ""
  86. }
  87. """),
  88. )
  89. misc_dash_slices.add(slc.slice_name)
  90. merge_slice(slc)
  91. slc = Slice(
  92. slice_name="Energy Force Layout",
  93. viz_type='directed_force',
  94. datasource_type='table',
  95. datasource_id=tbl.id,
  96. params=textwrap.dedent("""\
  97. {
  98. "charge": "-500",
  99. "collapsed_fieldsets": "",
  100. "groupby": [
  101. "source",
  102. "target"
  103. ],
  104. "having": "",
  105. "link_length": "200",
  106. "metric": "sum__value",
  107. "row_limit": "5000",
  108. "slice_name": "Force",
  109. "viz_type": "directed_force",
  110. "where": ""
  111. }
  112. """),
  113. )
  114. misc_dash_slices.add(slc.slice_name)
  115. merge_slice(slc)
  116. slc = Slice(
  117. slice_name="Heatmap",
  118. viz_type='heatmap',
  119. datasource_type='table',
  120. datasource_id=tbl.id,
  121. params=textwrap.dedent("""\
  122. {
  123. "all_columns_x": "source",
  124. "all_columns_y": "target",
  125. "canvas_image_rendering": "pixelated",
  126. "collapsed_fieldsets": "",
  127. "having": "",
  128. "linear_color_scheme": "blue_white_yellow",
  129. "metric": "sum__value",
  130. "normalize_across": "heatmap",
  131. "slice_name": "Heatmap",
  132. "viz_type": "heatmap",
  133. "where": "",
  134. "xscale_interval": "1",
  135. "yscale_interval": "1"
  136. }
  137. """),
  138. )
  139. misc_dash_slices.add(slc.slice_name)
  140. merge_slice(slc)
  141. def load_world_bank_health_n_pop():
  142. """Loads the world bank health dataset, slices and a dashboard"""
  143. tbl_name = 'wb_health_population'
  144. with gzip.open(os.path.join(DATA_FOLDER, 'countries.json.gz')) as f:
  145. pdf = pd.read_json(f)
  146. pdf.columns = [col.replace('.', '_') for col in pdf.columns]
  147. pdf.year = pd.to_datetime(pdf.year)
  148. pdf.to_sql(
  149. tbl_name,
  150. db.engine,
  151. if_exists='replace',
  152. chunksize=50,
  153. dtype={
  154. 'year': DateTime(),
  155. 'country_code': String(3),
  156. 'country_name': String(255),
  157. 'region': String(255),
  158. },
  159. index=False)
  160. print("Creating table [wb_health_population] reference")
  161. tbl = db.session.query(TBL).filter_by(table_name=tbl_name).first()
  162. if not tbl:
  163. tbl = TBL(table_name=tbl_name)
  164. tbl.description = utils.readfile(os.path.join(DATA_FOLDER, 'countries.md'))
  165. tbl.main_dttm_col = 'year'
  166. tbl.database = utils.get_or_create_main_db()
  167. tbl.filter_select_enabled = True
  168. db.session.merge(tbl)
  169. db.session.commit()
  170. tbl.fetch_metadata()
  171. defaults = {
  172. "compare_lag": "10",
  173. "compare_suffix": "o10Y",
  174. "limit": "25",
  175. "granularity_sqla": "year",
  176. "groupby": [],
  177. "metric": 'sum__SP_POP_TOTL',
  178. "metrics": ["sum__SP_POP_TOTL"],
  179. "row_limit": config.get("ROW_LIMIT"),
  180. "since": "2014-01-01",
  181. "until": "2014-01-02",
  182. "time_range": "2014-01-01 : 2014-01-02",
  183. "where": "",
  184. "markup_type": "markdown",
  185. "country_fieldtype": "cca3",
  186. "secondary_metric": "sum__SP_POP_TOTL",
  187. "entity": "country_code",
  188. "show_bubbles": True,
  189. }
  190. print("Creating slices")
  191. slices = [
  192. Slice(
  193. slice_name="Region Filter",
  194. viz_type='filter_box',
  195. datasource_type='table',
  196. datasource_id=tbl.id,
  197. params=get_slice_json(
  198. defaults,
  199. viz_type='filter_box',
  200. date_filter=False,
  201. groupby=['region', 'country_name'])),
  202. Slice(
  203. slice_name="World's Population",
  204. viz_type='big_number',
  205. datasource_type='table',
  206. datasource_id=tbl.id,
  207. params=get_slice_json(
  208. defaults,
  209. since='2000',
  210. viz_type='big_number',
  211. compare_lag="10",
  212. metric='sum__SP_POP_TOTL',
  213. compare_suffix="over 10Y")),
  214. Slice(
  215. slice_name="Most Populated Countries",
  216. viz_type='table',
  217. datasource_type='table',
  218. datasource_id=tbl.id,
  219. params=get_slice_json(
  220. defaults,
  221. viz_type='table',
  222. metrics=["sum__SP_POP_TOTL"],
  223. groupby=['country_name'])),
  224. Slice(
  225. slice_name="Growth Rate",
  226. viz_type='line',
  227. datasource_type='table',
  228. datasource_id=tbl.id,
  229. params=get_slice_json(
  230. defaults,
  231. viz_type='line',
  232. since="1960-01-01",
  233. metrics=["sum__SP_POP_TOTL"],
  234. num_period_compare="10",
  235. groupby=['country_name'])),
  236. Slice(
  237. slice_name="% Rural",
  238. viz_type='world_map',
  239. datasource_type='table',
  240. datasource_id=tbl.id,
  241. params=get_slice_json(
  242. defaults,
  243. viz_type='world_map',
  244. metric="sum__SP_RUR_TOTL_ZS",
  245. num_period_compare="10")),
  246. Slice(
  247. slice_name="Life Expectancy VS Rural %",
  248. viz_type='bubble',
  249. datasource_type='table',
  250. datasource_id=tbl.id,
  251. params=get_slice_json(
  252. defaults,
  253. viz_type='bubble',
  254. since="2011-01-01",
  255. until="2011-01-02",
  256. series="region",
  257. limit=0,
  258. entity="country_name",
  259. x="sum__SP_RUR_TOTL_ZS",
  260. y="sum__SP_DYN_LE00_IN",
  261. size="sum__SP_POP_TOTL",
  262. max_bubble_size="50",
  263. filters=[{
  264. "col": "country_code",
  265. "val": [
  266. "TCA", "MNP", "DMA", "MHL", "MCO", "SXM", "CYM",
  267. "TUV", "IMY", "KNA", "ASM", "ADO", "AMA", "PLW",
  268. ],
  269. "op": "not in"}],
  270. )),
  271. Slice(
  272. slice_name="Rural Breakdown",
  273. viz_type='sunburst',
  274. datasource_type='table',
  275. datasource_id=tbl.id,
  276. params=get_slice_json(
  277. defaults,
  278. viz_type='sunburst',
  279. groupby=["region", "country_name"],
  280. secondary_metric="sum__SP_RUR_TOTL",
  281. since="2011-01-01",
  282. until="2011-01-01",)),
  283. Slice(
  284. slice_name="World's Pop Growth",
  285. viz_type='area',
  286. datasource_type='table',
  287. datasource_id=tbl.id,
  288. params=get_slice_json(
  289. defaults,
  290. since="1960-01-01",
  291. until="now",
  292. viz_type='area',
  293. groupby=["region"],)),
  294. Slice(
  295. slice_name="Box plot",
  296. viz_type='box_plot',
  297. datasource_type='table',
  298. datasource_id=tbl.id,
  299. params=get_slice_json(
  300. defaults,
  301. since="1960-01-01",
  302. until="now",
  303. whisker_options="Min/max (no outliers)",
  304. viz_type='box_plot',
  305. groupby=["region"],)),
  306. Slice(
  307. slice_name="Treemap",
  308. viz_type='treemap',
  309. datasource_type='table',
  310. datasource_id=tbl.id,
  311. params=get_slice_json(
  312. defaults,
  313. since="1960-01-01",
  314. until="now",
  315. viz_type='treemap',
  316. metrics=["sum__SP_POP_TOTL"],
  317. groupby=["region", "country_code"],)),
  318. Slice(
  319. slice_name="Parallel Coordinates",
  320. viz_type='para',
  321. datasource_type='table',
  322. datasource_id=tbl.id,
  323. params=get_slice_json(
  324. defaults,
  325. since="2011-01-01",
  326. until="2011-01-01",
  327. viz_type='para',
  328. limit=100,
  329. metrics=[
  330. "sum__SP_POP_TOTL",
  331. 'sum__SP_RUR_TOTL_ZS',
  332. 'sum__SH_DYN_AIDS'],
  333. secondary_metric='sum__SP_POP_TOTL',
  334. series="country_name",)),
  335. ]
  336. misc_dash_slices.add(slices[-1].slice_name)
  337. for slc in slices:
  338. merge_slice(slc)
  339. print("Creating a World's Health Bank dashboard")
  340. dash_name = "World's Bank Data"
  341. slug = "world_health"
  342. dash = db.session.query(Dash).filter_by(slug=slug).first()
  343. if not dash:
  344. dash = Dash()
  345. js = textwrap.dedent("""\
  346. {
  347. "CHART-36bfc934": {
  348. "children": [],
  349. "id": "CHART-36bfc934",
  350. "meta": {
  351. "chartId": 40,
  352. "height": 25,
  353. "sliceName": "Region Filter",
  354. "width": 2
  355. },
  356. "type": "CHART"
  357. },
  358. "CHART-37982887": {
  359. "children": [],
  360. "id": "CHART-37982887",
  361. "meta": {
  362. "chartId": 41,
  363. "height": 25,
  364. "sliceName": "World's Population",
  365. "width": 2
  366. },
  367. "type": "CHART"
  368. },
  369. "CHART-17e0f8d8": {
  370. "children": [],
  371. "id": "CHART-17e0f8d8",
  372. "meta": {
  373. "chartId": 42,
  374. "height": 92,
  375. "sliceName": "Most Populated Countries",
  376. "width": 3
  377. },
  378. "type": "CHART"
  379. },
  380. "CHART-2ee52f30": {
  381. "children": [],
  382. "id": "CHART-2ee52f30",
  383. "meta": {
  384. "chartId": 43,
  385. "height": 38,
  386. "sliceName": "Growth Rate",
  387. "width": 6
  388. },
  389. "type": "CHART"
  390. },
  391. "CHART-2d5b6871": {
  392. "children": [],
  393. "id": "CHART-2d5b6871",
  394. "meta": {
  395. "chartId": 44,
  396. "height": 52,
  397. "sliceName": "% Rural",
  398. "width": 7
  399. },
  400. "type": "CHART"
  401. },
  402. "CHART-0fd0d252": {
  403. "children": [],
  404. "id": "CHART-0fd0d252",
  405. "meta": {
  406. "chartId": 45,
  407. "height": 50,
  408. "sliceName": "Life Expectancy VS Rural %",
  409. "width": 8
  410. },
  411. "type": "CHART"
  412. },
  413. "CHART-97f4cb48": {
  414. "children": [],
  415. "id": "CHART-97f4cb48",
  416. "meta": {
  417. "chartId": 46,
  418. "height": 38,
  419. "sliceName": "Rural Breakdown",
  420. "width": 3
  421. },
  422. "type": "CHART"
  423. },
  424. "CHART-b5e05d6f": {
  425. "children": [],
  426. "id": "CHART-b5e05d6f",
  427. "meta": {
  428. "chartId": 47,
  429. "height": 50,
  430. "sliceName": "World's Pop Growth",
  431. "width": 4
  432. },
  433. "type": "CHART"
  434. },
  435. "CHART-e76e9f5f": {
  436. "children": [],
  437. "id": "CHART-e76e9f5f",
  438. "meta": {
  439. "chartId": 48,
  440. "height": 50,
  441. "sliceName": "Box plot",
  442. "width": 4
  443. },
  444. "type": "CHART"
  445. },
  446. "CHART-a4808bba": {
  447. "children": [],
  448. "id": "CHART-a4808bba",
  449. "meta": {
  450. "chartId": 49,
  451. "height": 50,
  452. "sliceName": "Treemap",
  453. "width": 8
  454. },
  455. "type": "CHART"
  456. },
  457. "COLUMN-071bbbad": {
  458. "children": [
  459. "ROW-1e064e3c",
  460. "ROW-afdefba9"
  461. ],
  462. "id": "COLUMN-071bbbad",
  463. "meta": {
  464. "background": "BACKGROUND_TRANSPARENT",
  465. "width": 9
  466. },
  467. "type": "COLUMN"
  468. },
  469. "COLUMN-fe3914b8": {
  470. "children": [
  471. "CHART-36bfc934",
  472. "CHART-37982887"
  473. ],
  474. "id": "COLUMN-fe3914b8",
  475. "meta": {
  476. "background": "BACKGROUND_TRANSPARENT",
  477. "width": 2
  478. },
  479. "type": "COLUMN"
  480. },
  481. "GRID_ID": {
  482. "children": [
  483. "ROW-46632bc2",
  484. "ROW-3fa26c5d",
  485. "ROW-812b3f13"
  486. ],
  487. "id": "GRID_ID",
  488. "type": "GRID"
  489. },
  490. "HEADER_ID": {
  491. "id": "HEADER_ID",
  492. "meta": {
  493. "text": "World's Bank Data"
  494. },
  495. "type": "HEADER"
  496. },
  497. "ROOT_ID": {
  498. "children": [
  499. "GRID_ID"
  500. ],
  501. "id": "ROOT_ID",
  502. "type": "ROOT"
  503. },
  504. "ROW-1e064e3c": {
  505. "children": [
  506. "COLUMN-fe3914b8",
  507. "CHART-2d5b6871"
  508. ],
  509. "id": "ROW-1e064e3c",
  510. "meta": {
  511. "background": "BACKGROUND_TRANSPARENT"
  512. },
  513. "type": "ROW"
  514. },
  515. "ROW-3fa26c5d": {
  516. "children": [
  517. "CHART-b5e05d6f",
  518. "CHART-0fd0d252"
  519. ],
  520. "id": "ROW-3fa26c5d",
  521. "meta": {
  522. "background": "BACKGROUND_TRANSPARENT"
  523. },
  524. "type": "ROW"
  525. },
  526. "ROW-46632bc2": {
  527. "children": [
  528. "COLUMN-071bbbad",
  529. "CHART-17e0f8d8"
  530. ],
  531. "id": "ROW-46632bc2",
  532. "meta": {
  533. "background": "BACKGROUND_TRANSPARENT"
  534. },
  535. "type": "ROW"
  536. },
  537. "ROW-812b3f13": {
  538. "children": [
  539. "CHART-a4808bba",
  540. "CHART-e76e9f5f"
  541. ],
  542. "id": "ROW-812b3f13",
  543. "meta": {
  544. "background": "BACKGROUND_TRANSPARENT"
  545. },
  546. "type": "ROW"
  547. },
  548. "ROW-afdefba9": {
  549. "children": [
  550. "CHART-2ee52f30",
  551. "CHART-97f4cb48"
  552. ],
  553. "id": "ROW-afdefba9",
  554. "meta": {
  555. "background": "BACKGROUND_TRANSPARENT"
  556. },
  557. "type": "ROW"
  558. },
  559. "DASHBOARD_VERSION_KEY": "v2"
  560. }
  561. """)
  562. l = json.loads(js)
  563. update_slice_ids(l, slices)
  564. dash.dashboard_title = dash_name
  565. dash.position_json = json.dumps(l, indent=4)
  566. dash.slug = slug
  567. dash.slices = slices[:-1]
  568. db.session.merge(dash)
  569. db.session.commit()
  570. def load_css_templates():
  571. """Loads 2 css templates to demonstrate the feature"""
  572. print('Creating default CSS templates')
  573. CSS = models.CssTemplate # noqa
  574. obj = db.session.query(CSS).filter_by(template_name='Flat').first()
  575. if not obj:
  576. obj = CSS(template_name="Flat")
  577. css = textwrap.dedent("""\
  578. .gridster div.widget {
  579. transition: background-color 0.5s ease;
  580. background-color: #FAFAFA;
  581. border: 1px solid #CCC;
  582. box-shadow: none;
  583. border-radius: 0px;
  584. }
  585. .gridster div.widget:hover {
  586. border: 1px solid #000;
  587. background-color: #EAEAEA;
  588. }
  589. .navbar {
  590. transition: opacity 0.5s ease;
  591. opacity: 0.05;
  592. }
  593. .navbar:hover {
  594. opacity: 1;
  595. }
  596. .chart-header .header{
  597. font-weight: normal;
  598. font-size: 12px;
  599. }
  600. /*
  601. var bnbColors = [
  602. //rausch hackb kazan babu lima beach tirol
  603. '#ff5a5f', '#7b0051', '#007A87', '#00d1c1', '#8ce071', '#ffb400', '#b4a76c',
  604. '#ff8083', '#cc0086', '#00a1b3', '#00ffeb', '#bbedab', '#ffd266', '#cbc29a',
  605. '#ff3339', '#ff1ab1', '#005c66', '#00b3a5', '#55d12e', '#b37e00', '#988b4e',
  606. ];
  607. */
  608. """)
  609. obj.css = css
  610. db.session.merge(obj)
  611. db.session.commit()
  612. obj = (
  613. db.session.query(CSS).filter_by(template_name='Courier Black').first())
  614. if not obj:
  615. obj = CSS(template_name="Courier Black")
  616. css = textwrap.dedent("""\
  617. .gridster div.widget {
  618. transition: background-color 0.5s ease;
  619. background-color: #EEE;
  620. border: 2px solid #444;
  621. border-radius: 15px;
  622. box-shadow: none;
  623. }
  624. h2 {
  625. color: white;
  626. font-size: 52px;
  627. }
  628. .navbar {
  629. box-shadow: none;
  630. }
  631. .gridster div.widget:hover {
  632. border: 2px solid #000;
  633. background-color: #EAEAEA;
  634. }
  635. .navbar {
  636. transition: opacity 0.5s ease;
  637. opacity: 0.05;
  638. }
  639. .navbar:hover {
  640. opacity: 1;
  641. }
  642. .chart-header .header{
  643. font-weight: normal;
  644. font-size: 12px;
  645. }
  646. .nvd3 text {
  647. font-size: 12px;
  648. font-family: inherit;
  649. }
  650. body{
  651. background: #000;
  652. font-family: Courier, Monaco, monospace;;
  653. }
  654. /*
  655. var bnbColors = [
  656. //rausch hackb kazan babu lima beach tirol
  657. '#ff5a5f', '#7b0051', '#007A87', '#00d1c1', '#8ce071', '#ffb400', '#b4a76c',
  658. '#ff8083', '#cc0086', '#00a1b3', '#00ffeb', '#bbedab', '#ffd266', '#cbc29a',
  659. '#ff3339', '#ff1ab1', '#005c66', '#00b3a5', '#55d12e', '#b37e00', '#988b4e',
  660. ];
  661. */
  662. """)
  663. obj.css = css
  664. db.session.merge(obj)
  665. db.session.commit()
  666. def load_birth_names():
  667. """Loading birth name dataset from a zip file in the repo"""
  668. with gzip.open(os.path.join(DATA_FOLDER, 'birth_names.json.gz')) as f:
  669. pdf = pd.read_json(f)
  670. pdf.ds = pd.to_datetime(pdf.ds, unit='ms')
  671. pdf.to_sql(
  672. 'birth_names',
  673. db.engine,
  674. if_exists='replace',
  675. chunksize=500,
  676. dtype={
  677. 'ds': DateTime,
  678. 'gender': String(16),
  679. 'state': String(10),
  680. 'name': String(255),
  681. },
  682. index=False)
  683. l = []
  684. print("Done loading table!")
  685. print("-" * 80)
  686. print("Creating table [birth_names] reference")
  687. obj = db.session.query(TBL).filter_by(table_name='birth_names').first()
  688. if not obj:
  689. obj = TBL(table_name='birth_names')
  690. obj.main_dttm_col = 'ds'
  691. obj.database = utils.get_or_create_main_db()
  692. obj.filter_select_enabled = True
  693. if not any(col.column_name == 'num_california' for col in obj.columns):
  694. obj.columns.append(TableColumn(
  695. column_name='num_california',
  696. expression="CASE WHEN state = 'CA' THEN num ELSE 0 END"
  697. ))
  698. db.session.merge(obj)
  699. db.session.commit()
  700. obj.fetch_metadata()
  701. tbl = obj
  702. defaults = {
  703. "compare_lag": "10",
  704. "compare_suffix": "o10Y",
  705. "limit": "25",
  706. "granularity_sqla": "ds",
  707. "groupby": [],
  708. "metric": 'sum__num',
  709. "metrics": ["sum__num"],
  710. "row_limit": config.get("ROW_LIMIT"),
  711. "since": "100 years ago",
  712. "until": "now",
  713. "viz_type": "table",
  714. "where": "",
  715. "markup_type": "markdown",
  716. }
  717. print("Creating some slices")
  718. slices = [
  719. Slice(
  720. slice_name="Girls",
  721. viz_type='table',
  722. datasource_type='table',
  723. datasource_id=tbl.id,
  724. params=get_slice_json(
  725. defaults,
  726. groupby=['name'],
  727. filters=[{
  728. 'col': 'gender',
  729. 'op': 'in',
  730. 'val': ['girl'],
  731. }],
  732. row_limit=50,
  733. timeseries_limit_metric='sum__num')),
  734. Slice(
  735. slice_name="Boys",
  736. viz_type='table',
  737. datasource_type='table',
  738. datasource_id=tbl.id,
  739. params=get_slice_json(
  740. defaults,
  741. groupby=['name'],
  742. filters=[{
  743. 'col': 'gender',
  744. 'op': 'in',
  745. 'val': ['boy'],
  746. }],
  747. row_limit=50)),
  748. Slice(
  749. slice_name="Participants",
  750. viz_type='big_number',
  751. datasource_type='table',
  752. datasource_id=tbl.id,
  753. params=get_slice_json(
  754. defaults,
  755. viz_type="big_number", granularity_sqla="ds",
  756. compare_lag="5", compare_suffix="over 5Y")),
  757. Slice(
  758. slice_name="Genders",
  759. viz_type='pie',
  760. datasource_type='table',
  761. datasource_id=tbl.id,
  762. params=get_slice_json(
  763. defaults,
  764. viz_type="pie", groupby=['gender'])),
  765. Slice(
  766. slice_name="Genders by State",
  767. viz_type='dist_bar',
  768. datasource_type='table',
  769. datasource_id=tbl.id,
  770. params=get_slice_json(
  771. defaults,
  772. filters=[{
  773. 'col': 'state',
  774. 'op': 'not in',
  775. 'val': ['other'],
  776. }],
  777. viz_type="dist_bar",
  778. metrics=['sum__sum_girls', 'sum__sum_boys'],
  779. groupby=['state'])),
  780. Slice(
  781. slice_name="Trends",
  782. viz_type='line',
  783. datasource_type='table',
  784. datasource_id=tbl.id,
  785. params=get_slice_json(
  786. defaults,
  787. viz_type="line", groupby=['name'],
  788. granularity_sqla='ds', rich_tooltip=True, show_legend=True)),
  789. Slice(
  790. slice_name="Average and Sum Trends",
  791. viz_type='dual_line',
  792. datasource_type='table',
  793. datasource_id=tbl.id,
  794. params=get_slice_json(
  795. defaults,
  796. viz_type="dual_line", metric='avg__num', metric_2='sum__num',
  797. granularity_sqla='ds')),
  798. Slice(
  799. slice_name="Title",
  800. viz_type='markup',
  801. datasource_type='table',
  802. datasource_id=tbl.id,
  803. params=get_slice_json(
  804. defaults,
  805. viz_type="markup", markup_type="html",
  806. code="""\
  807. <div style="text-align:center">
  808. <h1>Birth Names Dashboard</h1>
  809. <p>
  810. The source dataset came from
  811. <a href="https://github.com/hadley/babynames" target="_blank">[here]</a>
  812. </p>
  813. <img src="/static/assets/images/babytux.jpg">
  814. </div>
  815. """)),
  816. Slice(
  817. slice_name="Name Cloud",
  818. viz_type='word_cloud',
  819. datasource_type='table',
  820. datasource_id=tbl.id,
  821. params=get_slice_json(
  822. defaults,
  823. viz_type="word_cloud", size_from="10",
  824. series='name', size_to="70", rotation="square",
  825. limit='100')),
  826. Slice(
  827. slice_name="Pivot Table",
  828. viz_type='pivot_table',
  829. datasource_type='table',
  830. datasource_id=tbl.id,
  831. params=get_slice_json(
  832. defaults,
  833. viz_type="pivot_table", metrics=['sum__num'],
  834. groupby=['name'], columns=['state'])),
  835. Slice(
  836. slice_name="Number of Girls",
  837. viz_type='big_number_total',
  838. datasource_type='table',
  839. datasource_id=tbl.id,
  840. params=get_slice_json(
  841. defaults,
  842. viz_type="big_number_total", granularity_sqla="ds",
  843. filters=[{
  844. 'col': 'gender',
  845. 'op': 'in',
  846. 'val': ['girl'],
  847. }],
  848. subheader='total female participants')),
  849. Slice(
  850. slice_name="Number of California Births",
  851. viz_type='big_number_total',
  852. datasource_type='table',
  853. datasource_id=tbl.id,
  854. params=get_slice_json(
  855. defaults,
  856. metric={
  857. "expressionType": "SIMPLE",
  858. "column": {
  859. "column_name": "num_california",
  860. "expression": "CASE WHEN state = 'CA' THEN num ELSE 0 END",
  861. },
  862. "aggregate": "SUM",
  863. "label": "SUM(num_california)",
  864. },
  865. viz_type="big_number_total",
  866. granularity_sqla="ds")),
  867. Slice(
  868. slice_name='Top 10 California Names Timeseries',
  869. viz_type='line',
  870. datasource_type='table',
  871. datasource_id=tbl.id,
  872. params=get_slice_json(
  873. defaults,
  874. metrics=[{
  875. 'expressionType': 'SIMPLE',
  876. 'column': {
  877. 'column_name': 'num_california',
  878. 'expression': "CASE WHEN state = 'CA' THEN num ELSE 0 END",
  879. },
  880. 'aggregate': 'SUM',
  881. 'label': 'SUM(num_california)',
  882. }],
  883. viz_type='line',
  884. granularity_sqla='ds',
  885. groupby=['name'],
  886. timeseries_limit_metric={
  887. 'expressionType': 'SIMPLE',
  888. 'column': {
  889. 'column_name': 'num_california',
  890. 'expression': "CASE WHEN state = 'CA' THEN num ELSE 0 END",
  891. },
  892. 'aggregate': 'SUM',
  893. 'label': 'SUM(num_california)',
  894. },
  895. limit='10')),
  896. Slice(
  897. slice_name="Names Sorted by Num in California",
  898. viz_type='table',
  899. datasource_type='table',
  900. datasource_id=tbl.id,
  901. params=get_slice_json(
  902. defaults,
  903. groupby=['name'],
  904. row_limit=50,
  905. timeseries_limit_metric={
  906. 'expressionType': 'SIMPLE',
  907. 'column': {
  908. 'column_name': 'num_california',
  909. 'expression': "CASE WHEN state = 'CA' THEN num ELSE 0 END",
  910. },
  911. 'aggregate': 'SUM',
  912. 'label': 'SUM(num_california)',
  913. })),
  914. Slice(
  915. slice_name="Num Births Trend",
  916. viz_type='line',
  917. datasource_type='table',
  918. datasource_id=tbl.id,
  919. params=get_slice_json(
  920. defaults,
  921. viz_type="line")),
  922. ]
  923. for slc in slices:
  924. merge_slice(slc)
  925. print("Creating a dashboard")
  926. dash = db.session.query(Dash).filter_by(dashboard_title="Births").first()
  927. if not dash:
  928. dash = Dash()
  929. js = textwrap.dedent("""\
  930. {
  931. "CHART-0dd270f0": {
  932. "meta": {
  933. "chartId": 51,
  934. "width": 2,
  935. "height": 50
  936. },
  937. "type": "CHART",
  938. "id": "CHART-0dd270f0",
  939. "children": []
  940. },
  941. "CHART-a3c21bcc": {
  942. "meta": {
  943. "chartId": 52,
  944. "width": 2,
  945. "height": 50
  946. },
  947. "type": "CHART",
  948. "id": "CHART-a3c21bcc",
  949. "children": []
  950. },
  951. "CHART-976960a5": {
  952. "meta": {
  953. "chartId": 53,
  954. "width": 2,
  955. "height": 25
  956. },
  957. "type": "CHART",
  958. "id": "CHART-976960a5",
  959. "children": []
  960. },
  961. "CHART-58575537": {
  962. "meta": {
  963. "chartId": 54,
  964. "width": 2,
  965. "height": 25
  966. },
  967. "type": "CHART",
  968. "id": "CHART-58575537",
  969. "children": []
  970. },
  971. "CHART-e9cd8f0b": {
  972. "meta": {
  973. "chartId": 55,
  974. "width": 8,
  975. "height": 38
  976. },
  977. "type": "CHART",
  978. "id": "CHART-e9cd8f0b",
  979. "children": []
  980. },
  981. "CHART-e440d205": {
  982. "meta": {
  983. "chartId": 56,
  984. "width": 8,
  985. "height": 50
  986. },
  987. "type": "CHART",
  988. "id": "CHART-e440d205",
  989. "children": []
  990. },
  991. "CHART-59444e0b": {
  992. "meta": {
  993. "chartId": 57,
  994. "width": 3,
  995. "height": 38
  996. },
  997. "type": "CHART",
  998. "id": "CHART-59444e0b",
  999. "children": []
  1000. },
  1001. "CHART-e2cb4997": {
  1002. "meta": {
  1003. "chartId": 59,
  1004. "width": 4,
  1005. "height": 50
  1006. },
  1007. "type": "CHART",
  1008. "id": "CHART-e2cb4997",
  1009. "children": []
  1010. },
  1011. "CHART-e8774b49": {
  1012. "meta": {
  1013. "chartId": 60,
  1014. "width": 12,
  1015. "height": 50
  1016. },
  1017. "type": "CHART",
  1018. "id": "CHART-e8774b49",
  1019. "children": []
  1020. },
  1021. "CHART-985bfd1e": {
  1022. "meta": {
  1023. "chartId": 61,
  1024. "width": 4,
  1025. "height": 50
  1026. },
  1027. "type": "CHART",
  1028. "id": "CHART-985bfd1e",
  1029. "children": []
  1030. },
  1031. "CHART-17f13246": {
  1032. "meta": {
  1033. "chartId": 62,
  1034. "width": 4,
  1035. "height": 50
  1036. },
  1037. "type": "CHART",
  1038. "id": "CHART-17f13246",
  1039. "children": []
  1040. },
  1041. "CHART-729324f6": {
  1042. "meta": {
  1043. "chartId": 63,
  1044. "width": 4,
  1045. "height": 50
  1046. },
  1047. "type": "CHART",
  1048. "id": "CHART-729324f6",
  1049. "children": []
  1050. },
  1051. "COLUMN-25a865d6": {
  1052. "meta": {
  1053. "width": 4,
  1054. "background": "BACKGROUND_TRANSPARENT"
  1055. },
  1056. "type": "COLUMN",
  1057. "id": "COLUMN-25a865d6",
  1058. "children": [
  1059. "ROW-cc97c6ac",
  1060. "CHART-e2cb4997"
  1061. ]
  1062. },
  1063. "COLUMN-4557b6ba": {
  1064. "meta": {
  1065. "width": 8,
  1066. "background": "BACKGROUND_TRANSPARENT"
  1067. },
  1068. "type": "COLUMN",
  1069. "id": "COLUMN-4557b6ba",
  1070. "children": [
  1071. "ROW-d2e78e59",
  1072. "CHART-e9cd8f0b"
  1073. ]
  1074. },
  1075. "GRID_ID": {
  1076. "type": "GRID",
  1077. "id": "GRID_ID",
  1078. "children": [
  1079. "ROW-8515ace3",
  1080. "ROW-1890385f",
  1081. "ROW-f0b64094",
  1082. "ROW-be9526b8"
  1083. ]
  1084. },
  1085. "HEADER_ID": {
  1086. "meta": {
  1087. "text": "Births"
  1088. },
  1089. "type": "HEADER",
  1090. "id": "HEADER_ID"
  1091. },
  1092. "MARKDOWN-00178c27": {
  1093. "meta": {
  1094. "width": 5,
  1095. "code": "<div style=\\"text-align:center\\">\\n <h1>Birth Names Dashboard</h1>\\n <p>\\n The source dataset came from\\n <a href=\\"https://github.com/hadley/babynames\\" target=\\"_blank\\">[here]</a>\\n </p>\\n <img src=\\"/static/assets/images/babytux.jpg\\">\\n</div>\\n",
  1096. "height": 38
  1097. },
  1098. "type": "MARKDOWN",
  1099. "id": "MARKDOWN-00178c27",
  1100. "children": []
  1101. },
  1102. "ROOT_ID": {
  1103. "type": "ROOT",
  1104. "id": "ROOT_ID",
  1105. "children": [
  1106. "GRID_ID"
  1107. ]
  1108. },
  1109. "ROW-1890385f": {
  1110. "meta": {
  1111. "background": "BACKGROUND_TRANSPARENT"
  1112. },
  1113. "type": "ROW",
  1114. "id": "ROW-1890385f",
  1115. "children": [
  1116. "CHART-e440d205",
  1117. "CHART-0dd270f0",
  1118. "CHART-a3c21bcc"
  1119. ]
  1120. },
  1121. "ROW-8515ace3": {
  1122. "meta": {
  1123. "background": "BACKGROUND_TRANSPARENT"
  1124. },
  1125. "type": "ROW",
  1126. "id": "ROW-8515ace3",
  1127. "children": [
  1128. "COLUMN-25a865d6",
  1129. "COLUMN-4557b6ba"
  1130. ]
  1131. },
  1132. "ROW-be9526b8": {
  1133. "meta": {
  1134. "background": "BACKGROUND_TRANSPARENT"
  1135. },
  1136. "type": "ROW",
  1137. "id": "ROW-be9526b8",
  1138. "children": [
  1139. "CHART-985bfd1e",
  1140. "CHART-17f13246",
  1141. "CHART-729324f6"
  1142. ]
  1143. },
  1144. "ROW-cc97c6ac": {
  1145. "meta": {
  1146. "background": "BACKGROUND_TRANSPARENT"
  1147. },
  1148. "type": "ROW",
  1149. "id": "ROW-cc97c6ac",
  1150. "children": [
  1151. "CHART-976960a5",
  1152. "CHART-58575537"
  1153. ]
  1154. },
  1155. "ROW-d2e78e59": {
  1156. "meta": {
  1157. "background": "BACKGROUND_TRANSPARENT"
  1158. },
  1159. "type": "ROW",
  1160. "id": "ROW-d2e78e59",
  1161. "children": [
  1162. "MARKDOWN-00178c27",
  1163. "CHART-59444e0b"
  1164. ]
  1165. },
  1166. "ROW-f0b64094": {
  1167. "meta": {
  1168. "background": "BACKGROUND_TRANSPARENT"
  1169. },
  1170. "type": "ROW",
  1171. "id": "ROW-f0b64094",
  1172. "children": [
  1173. "CHART-e8774b49"
  1174. ]
  1175. },
  1176. "DASHBOARD_VERSION_KEY": "v2"
  1177. }
  1178. """)
  1179. l = json.loads(js)
  1180. # dashboard v2 doesn't allow add markup slice
  1181. dash.slices = [slc for slc in slices if slc.viz_type != 'markup']
  1182. update_slice_ids(l, dash.slices)
  1183. dash.dashboard_title = "Births"
  1184. dash.position_json = json.dumps(l, indent=4)
  1185. dash.slug = "births"
  1186. db.session.merge(dash)
  1187. db.session.commit()
  1188. def load_unicode_test_data():
  1189. """Loading unicode test dataset from a csv file in the repo"""
  1190. df = pd.read_csv(os.path.join(DATA_FOLDER, 'unicode_utf8_unixnl_test.csv'),
  1191. encoding="utf-8")
  1192. # generate date/numeric data
  1193. df['dttm'] = datetime.datetime.now().date()
  1194. df['value'] = [random.randint(1, 100) for _ in range(len(df))]
  1195. df.to_sql( # pylint: disable=no-member
  1196. 'unicode_test',
  1197. db.engine,
  1198. if_exists='replace',
  1199. chunksize=500,
  1200. dtype={
  1201. 'phrase': String(500),
  1202. 'short_phrase': String(10),
  1203. 'with_missing': String(100),
  1204. 'dttm': Date(),
  1205. 'value': Float(),
  1206. },
  1207. index=False)
  1208. print("Done loading table!")
  1209. print("-" * 80)
  1210. print("Creating table [unicode_test] reference")
  1211. obj = db.session.query(TBL).filter_by(table_name='unicode_test').first()
  1212. if not obj:
  1213. obj = TBL(table_name='unicode_test')
  1214. obj.main_dttm_col = 'dttm'
  1215. obj.database = utils.get_or_create_main_db()
  1216. db.session.merge(obj)
  1217. db.session.commit()
  1218. obj.fetch_metadata()
  1219. tbl = obj
  1220. slice_data = {
  1221. "granularity_sqla": "dttm",
  1222. "groupby": [],
  1223. "metric": 'sum__value',
  1224. "row_limit": config.get("ROW_LIMIT"),
  1225. "since": "100 years ago",
  1226. "until": "now",
  1227. "where": "",
  1228. "viz_type": "word_cloud",
  1229. "size_from": "10",
  1230. "series": "short_phrase",
  1231. "size_to": "70",
  1232. "rotation": "square",
  1233. "limit": "100",
  1234. }
  1235. print("Creating a slice")
  1236. slc = Slice(
  1237. slice_name="Unicode Cloud",
  1238. viz_type='word_cloud',
  1239. datasource_type='table',
  1240. datasource_id=tbl.id,
  1241. params=get_slice_json(slice_data),
  1242. )
  1243. merge_slice(slc)
  1244. print("Creating a dashboard")
  1245. dash = (
  1246. db.session.query(Dash)
  1247. .filter_by(dashboard_title="Unicode Test")
  1248. .first()
  1249. )
  1250. if not dash:
  1251. dash = Dash()
  1252. js = """\
  1253. {
  1254. "CHART-Hkx6154FEm": {
  1255. "children": [],
  1256. "id": "CHART-Hkx6154FEm",
  1257. "meta": {
  1258. "chartId": 2225,
  1259. "height": 30,
  1260. "sliceName": "slice 1",
  1261. "width": 4
  1262. },
  1263. "type": "CHART"
  1264. },
  1265. "GRID_ID": {
  1266. "children": [
  1267. "ROW-SyT19EFEQ"
  1268. ],
  1269. "id": "GRID_ID",
  1270. "type": "GRID"
  1271. },
  1272. "ROOT_ID": {
  1273. "children": [
  1274. "GRID_ID"
  1275. ],
  1276. "id": "ROOT_ID",
  1277. "type": "ROOT"
  1278. },
  1279. "ROW-SyT19EFEQ": {
  1280. "children": [
  1281. "CHART-Hkx6154FEm"
  1282. ],
  1283. "id": "ROW-SyT19EFEQ",
  1284. "meta": {
  1285. "background": "BACKGROUND_TRANSPARENT"
  1286. },
  1287. "type": "ROW"
  1288. },
  1289. "DASHBOARD_VERSION_KEY": "v2"
  1290. }
  1291. """
  1292. dash.dashboard_title = "Unicode Test"
  1293. l = json.loads(js)
  1294. update_slice_ids(l, [slc])
  1295. dash.position_json = json.dumps(l, indent=4)
  1296. dash.slug = "unicode-test"
  1297. dash.slices = [slc]
  1298. db.session.merge(dash)
  1299. db.session.commit()
  1300. def load_random_time_series_data():
  1301. """Loading random time series data from a zip file in the repo"""
  1302. with gzip.open(os.path.join(DATA_FOLDER, 'random_time_series.json.gz')) as f:
  1303. pdf = pd.read_json(f)
  1304. pdf.ds = pd.to_datetime(pdf.ds, unit='s')
  1305. pdf.to_sql(
  1306. 'random_time_series',
  1307. db.engine,
  1308. if_exists='replace',
  1309. chunksize=500,
  1310. dtype={
  1311. 'ds': DateTime,
  1312. },
  1313. index=False)
  1314. print("Done loading table!")
  1315. print("-" * 80)
  1316. print("Creating table [random_time_series] reference")
  1317. obj = db.session.query(TBL).filter_by(table_name='random_time_series').first()
  1318. if not obj:
  1319. obj = TBL(table_name='random_time_series')
  1320. obj.main_dttm_col = 'ds'
  1321. obj.database = utils.get_or_create_main_db()
  1322. db.session.merge(obj)
  1323. db.session.commit()
  1324. obj.fetch_metadata()
  1325. tbl = obj
  1326. slice_data = {
  1327. "granularity_sqla": "day",
  1328. "row_limit": config.get("ROW_LIMIT"),
  1329. "since": "1 year ago",
  1330. "until": "now",
  1331. "metric": "count",
  1332. "where": "",
  1333. "viz_type": "cal_heatmap",
  1334. "domain_granularity": "month",
  1335. "subdomain_granularity": "day",
  1336. }
  1337. print("Creating a slice")
  1338. slc = Slice(
  1339. slice_name="Calendar Heatmap",
  1340. viz_type='cal_heatmap',
  1341. datasource_type='table',
  1342. datasource_id=tbl.id,
  1343. params=get_slice_json(slice_data),
  1344. )
  1345. merge_slice(slc)
  1346. def load_country_map_data():
  1347. """Loading data for map with country map"""
  1348. csv_path = os.path.join(DATA_FOLDER, 'birth_france_data_for_country_map.csv')
  1349. data = pd.read_csv(csv_path, encoding="utf-8")
  1350. data['dttm'] = datetime.datetime.now().date()
  1351. data.to_sql( # pylint: disable=no-member
  1352. 'birth_france_by_region',
  1353. db.engine,
  1354. if_exists='replace',
  1355. chunksize=500,
  1356. dtype={
  1357. 'DEPT_ID': String(10),
  1358. '2003': BigInteger,
  1359. '2004': BigInteger,
  1360. '2005': BigInteger,
  1361. '2006': BigInteger,
  1362. '2007': BigInteger,
  1363. '2008': BigInteger,
  1364. '2009': BigInteger,
  1365. '2010': BigInteger,
  1366. '2011': BigInteger,
  1367. '2012': BigInteger,
  1368. '2013': BigInteger,
  1369. '2014': BigInteger,
  1370. 'dttm': Date(),
  1371. },
  1372. index=False)
  1373. print("Done loading table!")
  1374. print("-" * 80)
  1375. print("Creating table reference")
  1376. obj = db.session.query(TBL).filter_by(table_name='birth_france_by_region').first()
  1377. if not obj:
  1378. obj = TBL(table_name='birth_france_by_region')
  1379. obj.main_dttm_col = 'dttm'
  1380. obj.database = utils.get_or_create_main_db()
  1381. db.session.merge(obj)
  1382. db.session.commit()
  1383. obj.fetch_metadata()
  1384. tbl = obj
  1385. slice_data = {
  1386. "granularity_sqla": "",
  1387. "since": "",
  1388. "until": "",
  1389. "where": "",
  1390. "viz_type": "country_map",
  1391. "entity": "DEPT_ID",
  1392. "metric": "avg__2004",
  1393. "row_limit": 500000,
  1394. }
  1395. print("Creating a slice")
  1396. slc = Slice(
  1397. slice_name="Birth in France by department in 2016",
  1398. viz_type='country_map',
  1399. datasource_type='table',
  1400. datasource_id=tbl.id,
  1401. params=get_slice_json(slice_data),
  1402. )
  1403. misc_dash_slices.add(slc.slice_name)
  1404. merge_slice(slc)
  1405. def load_long_lat_data():
  1406. """Loading lat/long data from a csv file in the repo"""
  1407. with gzip.open(os.path.join(DATA_FOLDER, 'san_francisco.csv.gz')) as f:
  1408. pdf = pd.read_csv(f, encoding="utf-8")
  1409. start = datetime.datetime.now().replace(
  1410. hour=0, minute=0, second=0, microsecond=0)
  1411. pdf['datetime'] = [
  1412. start + datetime.timedelta(hours=i * 24 / (len(pdf) - 1))
  1413. for i in range(len(pdf))
  1414. ]
  1415. pdf['occupancy'] = [random.randint(1, 6) for _ in range(len(pdf))]
  1416. pdf['radius_miles'] = [random.uniform(1, 3) for _ in range(len(pdf))]
  1417. pdf['geohash'] = pdf[['LAT', 'LON']].apply(
  1418. lambda x: geohash.encode(*x), axis=1)
  1419. pdf['delimited'] = pdf['LAT'].map(str).str.cat(pdf['LON'].map(str), sep=',')
  1420. pdf.to_sql( # pylint: disable=no-member
  1421. 'long_lat',
  1422. db.engine,
  1423. if_exists='replace',
  1424. chunksize=500,
  1425. dtype={
  1426. 'longitude': Float(),
  1427. 'latitude': Float(),
  1428. 'number': Float(),
  1429. 'street': String(100),
  1430. 'unit': String(10),
  1431. 'city': String(50),
  1432. 'district': String(50),
  1433. 'region': String(50),
  1434. 'postcode': Float(),
  1435. 'id': String(100),
  1436. 'datetime': DateTime(),
  1437. 'occupancy': Float(),
  1438. 'radius_miles': Float(),
  1439. 'geohash': String(12),
  1440. 'delimited': String(60),
  1441. },
  1442. index=False)
  1443. print("Done loading table!")
  1444. print("-" * 80)
  1445. print("Creating table reference")
  1446. obj = db.session.query(TBL).filter_by(table_name='long_lat').first()
  1447. if not obj:
  1448. obj = TBL(table_name='long_lat')
  1449. obj.main_dttm_col = 'datetime'
  1450. obj.database = utils.get_or_create_main_db()
  1451. db.session.merge(obj)
  1452. db.session.commit()
  1453. obj.fetch_metadata()
  1454. tbl = obj
  1455. slice_data = {
  1456. "granularity_sqla": "day",
  1457. "since": "2014-01-01",
  1458. "until": "now",
  1459. "where": "",
  1460. "viz_type": "mapbox",
  1461. "all_columns_x": "LON",
  1462. "all_columns_y": "LAT",
  1463. "mapbox_style": "mapbox://styles/mapbox/light-v9",
  1464. "all_columns": ["occupancy"],
  1465. "row_limit": 500000,
  1466. }
  1467. print("Creating a slice")
  1468. slc = Slice(
  1469. slice_name="Mapbox Long/Lat",
  1470. viz_type='mapbox',
  1471. datasource_type='table',
  1472. datasource_id=tbl.id,
  1473. params=get_slice_json(slice_data),
  1474. )
  1475. misc_dash_slices.add(slc.slice_name)
  1476. merge_slice(slc)
  1477. def load_multiformat_time_series_data():
  1478. """Loading time series data from a zip file in the repo"""
  1479. with gzip.open(os.path.join(DATA_FOLDER, 'multiformat_time_series.json.gz')) as f:
  1480. pdf = pd.read_json(f)
  1481. pdf.ds = pd.to_datetime(pdf.ds, unit='s')
  1482. pdf.ds2 = pd.to_datetime(pdf.ds2, unit='s')
  1483. pdf.to_sql(
  1484. 'multiformat_time_series',
  1485. db.engine,
  1486. if_exists='replace',
  1487. chunksize=500,
  1488. dtype={
  1489. "ds": Date,
  1490. 'ds2': DateTime,
  1491. "epoch_s": BigInteger,
  1492. "epoch_ms": BigInteger,
  1493. "string0": String(100),
  1494. "string1": String(100),
  1495. "string2": String(100),
  1496. "string3": String(100),
  1497. },
  1498. index=False)
  1499. print("Done loading table!")
  1500. print("-" * 80)
  1501. print("Creating table [multiformat_time_series] reference")
  1502. obj = db.session.query(TBL).filter_by(table_name='multiformat_time_series').first()
  1503. if not obj:
  1504. obj = TBL(table_name='multiformat_time_series')
  1505. obj.main_dttm_col = 'ds'
  1506. obj.database = utils.get_or_create_main_db()
  1507. dttm_and_expr_dict = {
  1508. 'ds': [None, None],
  1509. 'ds2': [None, None],
  1510. 'epoch_s': ['epoch_s', None],
  1511. 'epoch_ms': ['epoch_ms', None],
  1512. 'string2': ['%Y%m%d-%H%M%S', None],
  1513. 'string1': ['%Y-%m-%d^%H:%M:%S', None],
  1514. 'string0': ['%Y-%m-%d %H:%M:%S.%f', None],
  1515. 'string3': ['%Y/%m/%d%H:%M:%S.%f', None],
  1516. }
  1517. for col in obj.columns:
  1518. dttm_and_expr = dttm_and_expr_dict[col.column_name]
  1519. col.python_date_format = dttm_and_expr[0]
  1520. col.dbatabase_expr = dttm_and_expr[1]
  1521. col.is_dttm = True
  1522. db.session.merge(obj)
  1523. db.session.commit()
  1524. obj.fetch_metadata()
  1525. tbl = obj
  1526. print("Creating Heatmap charts")
  1527. for i, col in enumerate(tbl.columns):
  1528. slice_data = {
  1529. "metrics": ['count'],
  1530. "granularity_sqla": col.column_name,
  1531. "granularity_sqla": "day",
  1532. "row_limit": config.get("ROW_LIMIT"),
  1533. "since": "1 year ago",
  1534. "until": "now",
  1535. "where": "",
  1536. "viz_type": "cal_heatmap",
  1537. "domain_granularity": "month",
  1538. "subdomain_granularity": "day",
  1539. }
  1540. slc = Slice(
  1541. slice_name="Calendar Heatmap multiformat " + str(i),
  1542. viz_type='cal_heatmap',
  1543. datasource_type='table',
  1544. datasource_id=tbl.id,
  1545. params=get_slice_json(slice_data),
  1546. )
  1547. merge_slice(slc)
  1548. misc_dash_slices.add(slc.slice_name)
  1549. def load_misc_dashboard():
  1550. """Loading a dashboard featuring misc charts"""
  1551. print("Creating the dashboard")
  1552. db.session.expunge_all()
  1553. DASH_SLUG = "misc_charts"
  1554. dash = db.session.query(Dash).filter_by(slug=DASH_SLUG).first()
  1555. if not dash:
  1556. dash = Dash()
  1557. js = textwrap.dedent("""\
  1558. {
  1559. "CHART-BkeVbh8ANQ": {
  1560. "children": [],
  1561. "id": "CHART-BkeVbh8ANQ",
  1562. "meta": {
  1563. "chartId": 4004,
  1564. "height": 34,
  1565. "sliceName": "Multi Line",
  1566. "width": 8
  1567. },
  1568. "type": "CHART"
  1569. },
  1570. "CHART-H1HYNzEANX": {
  1571. "children": [],
  1572. "id": "CHART-H1HYNzEANX",
  1573. "meta": {
  1574. "chartId": 3940,
  1575. "height": 50,
  1576. "sliceName": "Energy Sankey",
  1577. "width": 6
  1578. },
  1579. "type": "CHART"
  1580. },
  1581. "CHART-HJOYVMV0E7": {
  1582. "children": [],
  1583. "id": "CHART-HJOYVMV0E7",
  1584. "meta": {
  1585. "chartId": 3969,
  1586. "height": 63,
  1587. "sliceName": "Mapbox Long/Lat",
  1588. "width": 6
  1589. },
  1590. "type": "CHART"
  1591. },
  1592. "CHART-S1WYNz4AVX": {
  1593. "children": [],
  1594. "id": "CHART-S1WYNz4AVX",
  1595. "meta": {
  1596. "chartId": 3989,
  1597. "height": 25,
  1598. "sliceName": "Parallel Coordinates",
  1599. "width": 4
  1600. },
  1601. "type": "CHART"
  1602. },
  1603. "CHART-r19KVMNCE7": {
  1604. "children": [],
  1605. "id": "CHART-r19KVMNCE7",
  1606. "meta": {
  1607. "chartId": 3978,
  1608. "height": 34,
  1609. "sliceName": "Calendar Heatmap multiformat 7",
  1610. "width": 4
  1611. },
  1612. "type": "CHART"
  1613. },
  1614. "CHART-rJ4K4GV04Q": {
  1615. "children": [],
  1616. "id": "CHART-rJ4K4GV04Q",
  1617. "meta": {
  1618. "chartId": 3941,
  1619. "height": 63,
  1620. "sliceName": "Energy Force Layout",
  1621. "width": 6
  1622. },
  1623. "type": "CHART"
  1624. },
  1625. "CHART-rkgF4G4A4X": {
  1626. "children": [],
  1627. "id": "CHART-rkgF4G4A4X",
  1628. "meta": {
  1629. "chartId": 3970,
  1630. "height": 25,
  1631. "sliceName": "Birth in France by department in 2016",
  1632. "width": 8
  1633. },
  1634. "type": "CHART"
  1635. },
  1636. "CHART-rywK4GVR4X": {
  1637. "children": [],
  1638. "id": "CHART-rywK4GVR4X",
  1639. "meta": {
  1640. "chartId": 3942,
  1641. "height": 50,
  1642. "sliceName": "Heatmap",
  1643. "width": 6
  1644. },
  1645. "type": "CHART"
  1646. },
  1647. "COLUMN-ByUFVf40EQ": {
  1648. "children": [
  1649. "CHART-rywK4GVR4X",
  1650. "CHART-HJOYVMV0E7"
  1651. ],
  1652. "id": "COLUMN-ByUFVf40EQ",
  1653. "meta": {
  1654. "background": "BACKGROUND_TRANSPARENT",
  1655. "width": 6
  1656. },
  1657. "type": "COLUMN"
  1658. },
  1659. "COLUMN-rkmYVGN04Q": {
  1660. "children": [
  1661. "CHART-rJ4K4GV04Q",
  1662. "CHART-H1HYNzEANX"
  1663. ],
  1664. "id": "COLUMN-rkmYVGN04Q",
  1665. "meta": {
  1666. "background": "BACKGROUND_TRANSPARENT",
  1667. "width": 6
  1668. },
  1669. "type": "COLUMN"
  1670. },
  1671. "GRID_ID": {
  1672. "children": [
  1673. "ROW-SytNzNA4X",
  1674. "ROW-S1MK4M4A4X",
  1675. "ROW-HkFFEzVRVm"
  1676. ],
  1677. "id": "GRID_ID",
  1678. "type": "GRID"
  1679. },
  1680. "HEADER_ID": {
  1681. "id": "HEADER_ID",
  1682. "meta": {
  1683. "text": "Misc Charts"
  1684. },
  1685. "type": "HEADER"
  1686. },
  1687. "ROOT_ID": {
  1688. "children": [
  1689. "GRID_ID"
  1690. ],
  1691. "id": "ROOT_ID",
  1692. "type": "ROOT"
  1693. },
  1694. "ROW-HkFFEzVRVm": {
  1695. "children": [
  1696. "CHART-r19KVMNCE7",
  1697. "CHART-BkeVbh8ANQ"
  1698. ],
  1699. "id": "ROW-HkFFEzVRVm",
  1700. "meta": {
  1701. "background": "BACKGROUND_TRANSPARENT"
  1702. },
  1703. "type": "ROW"
  1704. },
  1705. "ROW-S1MK4M4A4X": {
  1706. "children": [
  1707. "COLUMN-rkmYVGN04Q",
  1708. "COLUMN-ByUFVf40EQ"
  1709. ],
  1710. "id": "ROW-S1MK4M4A4X",
  1711. "meta": {
  1712. "background": "BACKGROUND_TRANSPARENT"
  1713. },
  1714. "type": "ROW"
  1715. },
  1716. "ROW-SytNzNA4X": {
  1717. "children": [
  1718. "CHART-rkgF4G4A4X",
  1719. "CHART-S1WYNz4AVX"
  1720. ],
  1721. "id": "ROW-SytNzNA4X",
  1722. "meta": {
  1723. "background": "BACKGROUND_TRANSPARENT"
  1724. },
  1725. "type": "ROW"
  1726. },
  1727. "DASHBOARD_VERSION_KEY": "v2"
  1728. }
  1729. """)
  1730. l = json.loads(js)
  1731. slices = (
  1732. db.session
  1733. .query(Slice)
  1734. .filter(Slice.slice_name.in_(misc_dash_slices))
  1735. .all()
  1736. )
  1737. slices = sorted(slices, key=lambda x: x.id)
  1738. update_slice_ids(l, slices)
  1739. dash.dashboard_title = "Misc Charts"
  1740. dash.position_json = json.dumps(l, indent=4)
  1741. dash.slug = DASH_SLUG
  1742. dash.slices = slices
  1743. db.session.merge(dash)
  1744. db.session.commit()
  1745. def load_deck_dash():
  1746. print("Loading deck.gl dashboard")
  1747. slices = []
  1748. tbl = db.session.query(TBL).filter_by(table_name='long_lat').first()
  1749. slice_data = {
  1750. "spatial": {
  1751. "type": "latlong",
  1752. "lonCol": "LON",
  1753. "latCol": "LAT",
  1754. },
  1755. "color_picker": {
  1756. "r": 205,
  1757. "g": 0,
  1758. "b": 3,
  1759. "a": 0.82,
  1760. },
  1761. "datasource": "5__table",
  1762. "filters": [],
  1763. "granularity_sqla": "dttm",
  1764. "groupby": [],
  1765. "having": "",
  1766. "mapbox_style": "mapbox://styles/mapbox/light-v9",
  1767. "multiplier": 10,
  1768. "point_radius_fixed": {"type": "metric", "value": "count"},
  1769. "point_unit": "square_m",
  1770. "min_radius": 1,
  1771. "row_limit": 5000,
  1772. "since": None,
  1773. "size": "count",
  1774. "time_grain_sqla": None,
  1775. "until": None,
  1776. "viewport": {
  1777. "bearing": -4.952916738791771,
  1778. "latitude": 37.78926922909199,
  1779. "longitude": -122.42613341901688,
  1780. "pitch": 4.750411100577438,
  1781. "zoom": 12.729132798697304,
  1782. },
  1783. "viz_type": "deck_scatter",
  1784. "where": "",
  1785. }
  1786. print("Creating Scatterplot slice")
  1787. slc = Slice(
  1788. slice_name="Scatterplot",
  1789. viz_type='deck_scatter',
  1790. datasource_type='table',
  1791. datasource_id=tbl.id,
  1792. params=get_slice_json(slice_data),
  1793. )
  1794. merge_slice(slc)
  1795. slices.append(slc)
  1796. slice_data = {
  1797. "point_unit": "square_m",
  1798. "filters": [],
  1799. "row_limit": 5000,
  1800. "spatial": {
  1801. "type": "latlong",
  1802. "lonCol": "LON",
  1803. "latCol": "LAT",
  1804. },
  1805. "mapbox_style": "mapbox://styles/mapbox/dark-v9",
  1806. "granularity_sqla": "dttm",
  1807. "size": "count",
  1808. "viz_type": "deck_screengrid",
  1809. "since": None,
  1810. "point_radius": "Auto",
  1811. "until": None,
  1812. "color_picker": {
  1813. "a": 1,
  1814. "r": 14,
  1815. "b": 0,
  1816. "g": 255,
  1817. },
  1818. "grid_size": 20,
  1819. "where": "",
  1820. "having": "",
  1821. "viewport": {
  1822. "zoom": 14.161641703941438,
  1823. "longitude": -122.41827069521386,
  1824. "bearing": -4.952916738791771,
  1825. "latitude": 37.76024135844065,
  1826. "pitch": 4.750411100577438,
  1827. },
  1828. "point_radius_fixed": {"type": "fix", "value": 2000},
  1829. "datasource": "5__table",
  1830. "time_grain_sqla": None,
  1831. "groupby": [],
  1832. }
  1833. print("Creating Screen Grid slice")
  1834. slc = Slice(
  1835. slice_name="Screen grid",
  1836. viz_type='deck_screengrid',
  1837. datasource_type='table',
  1838. datasource_id=tbl.id,
  1839. params=get_slice_json(slice_data),
  1840. )
  1841. merge_slice(slc)
  1842. slices.append(slc)
  1843. slice_data = {
  1844. "spatial": {
  1845. "type": "latlong",
  1846. "lonCol": "LON",
  1847. "latCol": "LAT",
  1848. },
  1849. "filters": [],
  1850. "row_limit": 5000,
  1851. "mapbox_style": "mapbox://styles/mapbox/streets-v9",
  1852. "granularity_sqla": "dttm",
  1853. "size": "count",
  1854. "viz_type": "deck_hex",
  1855. "since": None,
  1856. "point_radius_unit": "Pixels",
  1857. "point_radius": "Auto",
  1858. "until": None,
  1859. "color_picker": {
  1860. "a": 1,
  1861. "r": 14,
  1862. "b": 0,
  1863. "g": 255,
  1864. },
  1865. "grid_size": 40,
  1866. "extruded": True,
  1867. "having": "",
  1868. "viewport": {
  1869. "latitude": 37.789795085160335,
  1870. "pitch": 54.08961642447763,
  1871. "zoom": 13.835465702403654,
  1872. "longitude": -122.40632230075536,
  1873. "bearing": -2.3984797349335167,
  1874. },
  1875. "where": "",
  1876. "point_radius_fixed": {"type": "fix", "value": 2000},
  1877. "datasource": "5__table",
  1878. "time_grain_sqla": None,
  1879. "groupby": [],
  1880. }
  1881. print("Creating Hex slice")
  1882. slc = Slice(
  1883. slice_name="Hexagons",
  1884. viz_type='deck_hex',
  1885. datasource_type='table',
  1886. datasource_id=tbl.id,
  1887. params=get_slice_json(slice_data),
  1888. )
  1889. merge_slice(slc)
  1890. slices.append(slc)
  1891. slice_data = {
  1892. "spatial": {
  1893. "type": "latlong",
  1894. "lonCol": "LON",
  1895. "latCol": "LAT",
  1896. },
  1897. "filters": [],
  1898. "row_limit": 5000,
  1899. "mapbox_style": "mapbox://styles/mapbox/satellite-streets-v9",
  1900. "granularity_sqla": "dttm",
  1901. "size": "count",
  1902. "viz_type": "deck_grid",
  1903. "point_radius_unit": "Pixels",
  1904. "point_radius": "Auto",
  1905. "time_range": "No filter",
  1906. "color_picker": {
  1907. "a": 1,
  1908. "r": 14,
  1909. "b": 0,
  1910. "g": 255,
  1911. },
  1912. "grid_size": 120,
  1913. "extruded": True,
  1914. "having": "",
  1915. "viewport": {
  1916. "longitude": -122.42066918995666,
  1917. "bearing": 155.80099696026355,
  1918. "zoom": 12.699690845482069,
  1919. "latitude": 37.7942314882596,
  1920. "pitch": 53.470800300695146,
  1921. },
  1922. "where": "",
  1923. "point_radius_fixed": {"type": "fix", "value": 2000},
  1924. "datasource": "5__table",
  1925. "time_grain_sqla": None,
  1926. "groupby": [],
  1927. }
  1928. print("Creating Grid slice")
  1929. slc = Slice(
  1930. slice_name="Grid",
  1931. viz_type='deck_grid',
  1932. datasource_type='table',
  1933. datasource_id=tbl.id,
  1934. params=get_slice_json(slice_data),
  1935. )
  1936. merge_slice(slc)
  1937. slices.append(slc)
  1938. polygon_tbl = db.session.query(TBL) \
  1939. .filter_by(table_name='sf_population_polygons').first()
  1940. slice_data = {
  1941. "datasource": "11__table",
  1942. "viz_type": "deck_polygon",
  1943. "slice_id": 41,
  1944. "granularity_sqla": None,
  1945. "time_grain_sqla": None,
  1946. "since": None,
  1947. "until": None,
  1948. "line_column": "contour",
  1949. "line_type": "json",
  1950. "mapbox_style": "mapbox://styles/mapbox/light-v9",
  1951. "viewport": {
  1952. "longitude": -122.43388541747726,
  1953. "latitude": 37.752020331384834,
  1954. "zoom": 11.133995608594631,
  1955. "bearing": 37.89506450385642,
  1956. "pitch": 60,
  1957. "width": 667,
  1958. "height": 906,
  1959. "altitude": 1.5,
  1960. "maxZoom": 20,
  1961. "minZoom": 0,
  1962. "maxPitch": 60,
  1963. "minPitch": 0,
  1964. "maxLatitude": 85.05113,
  1965. "minLatitude": -85.05113
  1966. },
  1967. "reverse_long_lat": False,
  1968. "fill_color_picker": {
  1969. "r": 3,
  1970. "g": 65,
  1971. "b": 73,
  1972. "a": 1
  1973. },
  1974. "stroke_color_picker": {
  1975. "r": 0,
  1976. "g": 122,
  1977. "b": 135,
  1978. "a": 1
  1979. },
  1980. "filled": True,
  1981. "stroked": False,
  1982. "extruded": True,
  1983. "point_radius_scale": 100,
  1984. "js_columns": [
  1985. "population",
  1986. "area"
  1987. ],
  1988. "js_datapoint_mutator": "(d) => {\n d.elevation = d.extraProps.population/d.extraProps.area/10\n \
  1989. d.fillColor = [d.extraProps.population/d.extraProps.area/60,140,0]\n \
  1990. return d;\n}",
  1991. "js_tooltip": "",
  1992. "js_onclick_href": "",
  1993. "where": "",
  1994. "having": "",
  1995. "filters": []
  1996. }
  1997. print("Creating Polygon slice")
  1998. slc = Slice(
  1999. slice_name="Polygons",
  2000. viz_type='deck_polygon',
  2001. datasource_type='table',
  2002. datasource_id=polygon_tbl.id,
  2003. params=get_slice_json(slice_data),
  2004. )
  2005. merge_slice(slc)
  2006. slices.append(slc)
  2007. slice_data = {
  2008. "datasource": "10__table",
  2009. "viz_type": "deck_arc",
  2010. "slice_id": 42,
  2011. "granularity_sqla": "dttm",
  2012. "time_grain_sqla": "Time Column",
  2013. "since": None,
  2014. "until": None,
  2015. "start_spatial": {
  2016. "type": "latlong",
  2017. "latCol": "LATITUDE",
  2018. "lonCol": "LONGITUDE"
  2019. },
  2020. "end_spatial": {
  2021. "type": "latlong",
  2022. "latCol": "LATITUDE_DEST",
  2023. "lonCol": "LONGITUDE_DEST"
  2024. },
  2025. "row_limit": 5000,
  2026. "mapbox_style": "mapbox://styles/mapbox/light-v9",
  2027. "viewport": {
  2028. "altitude": 1.5,
  2029. "bearing": 8.546256357301871,
  2030. "height": 642,
  2031. "latitude": 44.596651438714254,
  2032. "longitude": -91.84340711201104,
  2033. "maxLatitude": 85.05113,
  2034. "maxPitch": 60,
  2035. "maxZoom": 20,
  2036. "minLatitude": -85.05113,
  2037. "minPitch": 0,
  2038. "minZoom": 0,
  2039. "pitch": 60,
  2040. "width": 997,
  2041. "zoom": 2.929837070560775
  2042. },
  2043. "color_picker": {
  2044. "r": 0,
  2045. "g": 122,
  2046. "b": 135,
  2047. "a": 1
  2048. },
  2049. "stroke_width": 1,
  2050. "where": "",
  2051. "having": "",
  2052. "filters": []
  2053. }
  2054. print("Creating Arc slice")
  2055. slc = Slice(
  2056. slice_name="Arcs",
  2057. viz_type='deck_arc',
  2058. datasource_type='table',
  2059. datasource_id=db.session.query(TBL).filter_by(table_name='flights').first().id,
  2060. params=get_slice_json(slice_data),
  2061. )
  2062. merge_slice(slc)
  2063. slices.append(slc)
  2064. slice_data = {
  2065. "datasource": "12__table",
  2066. "slice_id": 43,
  2067. "viz_type": "deck_path",
  2068. "time_grain_sqla": "Time Column",
  2069. "since": None,
  2070. "until": None,
  2071. "line_column": "path_json",
  2072. "line_type": "json",
  2073. "row_limit": 5000,
  2074. "mapbox_style": "mapbox://styles/mapbox/light-v9",
  2075. "viewport": {
  2076. "longitude": -122.18885402582598,
  2077. "latitude": 37.73671752604488,
  2078. "zoom": 9.51847667620428,
  2079. "bearing": 0,
  2080. "pitch": 0,
  2081. "width": 669,
  2082. "height": 1094,
  2083. "altitude": 1.5,
  2084. "maxZoom": 20,
  2085. "minZoom": 0,
  2086. "maxPitch": 60,
  2087. "minPitch": 0,
  2088. "maxLatitude": 85.05113,
  2089. "minLatitude": -85.05113
  2090. },
  2091. "color_picker": {
  2092. "r": 0,
  2093. "g": 122,
  2094. "b": 135,
  2095. "a": 1
  2096. },
  2097. "line_width": 150,
  2098. "reverse_long_lat": False,
  2099. "js_columns": [
  2100. "color"
  2101. ],
  2102. "js_datapoint_mutator": "d => {\n return {\n ...d,\n color: \
  2103. colors.hexToRGB(d.extraProps.color),\n }\n}",
  2104. "js_tooltip": "",
  2105. "js_onclick_href": "",
  2106. "where": "",
  2107. "having": "",
  2108. "filters": []
  2109. }
  2110. print("Creating Path slice")
  2111. slc = Slice(
  2112. slice_name="Path",
  2113. viz_type='deck_path',
  2114. datasource_type='table',
  2115. datasource_id=db.session.query(TBL).filter_by(table_name='bart_lines').first().id,
  2116. params=get_slice_json(slice_data),
  2117. )
  2118. merge_slice(slc)
  2119. slices.append(slc)
  2120. print("Creating a dashboard")
  2121. title = "deck.gl Demo"
  2122. dash = db.session.query(Dash).filter_by(dashboard_title=title).first()
  2123. if not dash:
  2124. dash = Dash()
  2125. js = textwrap.dedent("""\
  2126. {
  2127. "CHART-3afd9d70": {
  2128. "meta": {
  2129. "chartId": 66,
  2130. "width": 6,
  2131. "height": 50
  2132. },
  2133. "type": "CHART",
  2134. "id": "CHART-3afd9d70",
  2135. "children": []
  2136. },
  2137. "CHART-2ee7fa5e": {
  2138. "meta": {
  2139. "chartId": 67,
  2140. "width": 6,
  2141. "height": 50
  2142. },
  2143. "type": "CHART",
  2144. "id": "CHART-2ee7fa5e",
  2145. "children": []
  2146. },
  2147. "CHART-201f7715": {
  2148. "meta": {
  2149. "chartId": 68,
  2150. "width": 6,
  2151. "height": 50
  2152. },
  2153. "type": "CHART",
  2154. "id": "CHART-201f7715",
  2155. "children": []
  2156. },
  2157. "CHART-d02f6c40": {
  2158. "meta": {
  2159. "chartId": 69,
  2160. "width": 6,
  2161. "height": 50
  2162. },
  2163. "type": "CHART",
  2164. "id": "CHART-d02f6c40",
  2165. "children": []
  2166. },
  2167. "CHART-2673431d": {
  2168. "meta": {
  2169. "chartId": 70,
  2170. "width": 6,
  2171. "height": 50
  2172. },
  2173. "type": "CHART",
  2174. "id": "CHART-2673431d",
  2175. "children": []
  2176. },
  2177. "CHART-85265a60": {
  2178. "meta": {
  2179. "chartId": 71,
  2180. "width": 6,
  2181. "height": 50
  2182. },
  2183. "type": "CHART",
  2184. "id": "CHART-85265a60",
  2185. "children": []
  2186. },
  2187. "CHART-2b87513c": {
  2188. "meta": {
  2189. "chartId": 72,
  2190. "width": 6,
  2191. "height": 50
  2192. },
  2193. "type": "CHART",
  2194. "id": "CHART-2b87513c",
  2195. "children": []
  2196. },
  2197. "GRID_ID": {
  2198. "type": "GRID",
  2199. "id": "GRID_ID",
  2200. "children": [
  2201. "ROW-a7b16cb5",
  2202. "ROW-72c218a5",
  2203. "ROW-957ba55b",
  2204. "ROW-af041bdd"
  2205. ]
  2206. },
  2207. "HEADER_ID": {
  2208. "meta": {
  2209. "text": "deck.gl Demo"
  2210. },
  2211. "type": "HEADER",
  2212. "id": "HEADER_ID"
  2213. },
  2214. "ROOT_ID": {
  2215. "type": "ROOT",
  2216. "id": "ROOT_ID",
  2217. "children": [
  2218. "GRID_ID"
  2219. ]
  2220. },
  2221. "ROW-72c218a5": {
  2222. "meta": {
  2223. "background": "BACKGROUND_TRANSPARENT"
  2224. },
  2225. "type": "ROW",
  2226. "id": "ROW-72c218a5",
  2227. "children": [
  2228. "CHART-d02f6c40",
  2229. "CHART-201f7715"
  2230. ]
  2231. },
  2232. "ROW-957ba55b": {
  2233. "meta": {
  2234. "background": "BACKGROUND_TRANSPARENT"
  2235. },
  2236. "type": "ROW",
  2237. "id": "ROW-957ba55b",
  2238. "children": [
  2239. "CHART-2673431d",
  2240. "CHART-85265a60"
  2241. ]
  2242. },
  2243. "ROW-a7b16cb5": {
  2244. "meta": {
  2245. "background": "BACKGROUND_TRANSPARENT"
  2246. },
  2247. "type": "ROW",
  2248. "id": "ROW-a7b16cb5",
  2249. "children": [
  2250. "CHART-3afd9d70",
  2251. "CHART-2ee7fa5e"
  2252. ]
  2253. },
  2254. "ROW-af041bdd": {
  2255. "meta": {
  2256. "background": "BACKGROUND_TRANSPARENT"
  2257. },
  2258. "type": "ROW",
  2259. "id": "ROW-af041bdd",
  2260. "children": [
  2261. "CHART-2b87513c"
  2262. ]
  2263. },
  2264. "DASHBOARD_VERSION_KEY": "v2"
  2265. }
  2266. """)
  2267. l = json.loads(js)
  2268. update_slice_ids(l, slices)
  2269. dash.dashboard_title = title
  2270. dash.position_json = json.dumps(l, indent=4)
  2271. dash.slug = "deck"
  2272. dash.slices = slices
  2273. db.session.merge(dash)
  2274. db.session.commit()
  2275. def load_flights():
  2276. """Loading random time series data from a zip file in the repo"""
  2277. tbl_name = 'flights'
  2278. with gzip.open(os.path.join(DATA_FOLDER, 'fligth_data.csv.gz')) as f:
  2279. pdf = pd.read_csv(f, encoding='latin-1')
  2280. # Loading airports info to join and get lat/long
  2281. with gzip.open(os.path.join(DATA_FOLDER, 'airports.csv.gz')) as f:
  2282. airports = pd.read_csv(f, encoding='latin-1')
  2283. airports = airports.set_index('IATA_CODE')
  2284. pdf['ds'] = pdf.YEAR.map(str) + '-0' + pdf.MONTH.map(str) + '-0' + pdf.DAY.map(str)
  2285. pdf.ds = pd.to_datetime(pdf.ds)
  2286. del pdf['YEAR']
  2287. del pdf['MONTH']
  2288. del pdf['DAY']
  2289. pdf = pdf.join(airports, on='ORIGIN_AIRPORT', rsuffix='_ORIG')
  2290. pdf = pdf.join(airports, on='DESTINATION_AIRPORT', rsuffix='_DEST')
  2291. pdf.to_sql(
  2292. tbl_name,
  2293. db.engine,
  2294. if_exists='replace',
  2295. chunksize=500,
  2296. dtype={
  2297. 'ds': DateTime,
  2298. },
  2299. index=False)
  2300. tbl = db.session.query(TBL).filter_by(table_name=tbl_name).first()
  2301. if not tbl:
  2302. tbl = TBL(table_name=tbl_name)
  2303. tbl.description = "Random set of flights in the US"
  2304. tbl.database = utils.get_or_create_main_db()
  2305. db.session.merge(tbl)
  2306. db.session.commit()
  2307. tbl.fetch_metadata()
  2308. print("Done loading table!")
  2309. def load_paris_iris_geojson():
  2310. tbl_name = 'paris_iris_mapping'
  2311. with gzip.open(os.path.join(DATA_FOLDER, 'paris_iris.json.gz')) as f:
  2312. df = pd.read_json(f)
  2313. df['features'] = df.features.map(json.dumps)
  2314. df.to_sql(
  2315. tbl_name,
  2316. db.engine,
  2317. if_exists='replace',
  2318. chunksize=500,
  2319. dtype={
  2320. 'color': String(255),
  2321. 'name': String(255),
  2322. 'features': Text,
  2323. 'type': Text,
  2324. },
  2325. index=False)
  2326. print("Creating table {} reference".format(tbl_name))
  2327. tbl = db.session.query(TBL).filter_by(table_name=tbl_name).first()
  2328. if not tbl:
  2329. tbl = TBL(table_name=tbl_name)
  2330. tbl.description = "Map of Paris"
  2331. tbl.database = utils.get_or_create_main_db()
  2332. db.session.merge(tbl)
  2333. db.session.commit()
  2334. tbl.fetch_metadata()
  2335. def load_sf_population_polygons():
  2336. tbl_name = 'sf_population_polygons'
  2337. with gzip.open(os.path.join(DATA_FOLDER, 'sf_population.json.gz')) as f:
  2338. df = pd.read_json(f)
  2339. df['contour'] = df.contour.map(json.dumps)
  2340. df.to_sql(
  2341. tbl_name,
  2342. db.engine,
  2343. if_exists='replace',
  2344. chunksize=500,
  2345. dtype={
  2346. 'zipcode': BigInteger,
  2347. 'population': BigInteger,
  2348. 'contour': Text,
  2349. 'area': BigInteger,
  2350. },
  2351. index=False)
  2352. print("Creating table {} reference".format(tbl_name))
  2353. tbl = db.session.query(TBL).filter_by(table_name=tbl_name).first()
  2354. if not tbl:
  2355. tbl = TBL(table_name=tbl_name)
  2356. tbl.description = "Population density of San Francisco"
  2357. tbl.database = utils.get_or_create_main_db()
  2358. db.session.merge(tbl)
  2359. db.session.commit()
  2360. tbl.fetch_metadata()
  2361. def load_bart_lines():
  2362. tbl_name = 'bart_lines'
  2363. with gzip.open(os.path.join(DATA_FOLDER, 'bart-lines.json.gz')) as f:
  2364. df = pd.read_json(f, encoding='latin-1')
  2365. df['path_json'] = df.path.map(json.dumps)
  2366. df['polyline'] = df.path.map(polyline.encode)
  2367. del df['path']
  2368. df.to_sql(
  2369. tbl_name,
  2370. db.engine,
  2371. if_exists='replace',
  2372. chunksize=500,
  2373. dtype={
  2374. 'color': String(255),
  2375. 'name': String(255),
  2376. 'polyline': Text,
  2377. 'path_json': Text,
  2378. },
  2379. index=False)
  2380. print("Creating table {} reference".format(tbl_name))
  2381. tbl = db.session.query(TBL).filter_by(table_name=tbl_name).first()
  2382. if not tbl:
  2383. tbl = TBL(table_name=tbl_name)
  2384. tbl.description = "BART lines"
  2385. tbl.database = utils.get_or_create_main_db()
  2386. db.session.merge(tbl)
  2387. db.session.commit()
  2388. tbl.fetch_metadata()
  2389. def load_multi_line():
  2390. load_world_bank_health_n_pop()
  2391. load_birth_names()
  2392. ids = [
  2393. row.id for row in
  2394. db.session.query(Slice).filter(
  2395. Slice.slice_name.in_(['Growth Rate', 'Trends']))
  2396. ]
  2397. slc = Slice(
  2398. datasource_type='table', # not true, but needed
  2399. datasource_id=1, # cannot be empty
  2400. slice_name="Multi Line",
  2401. viz_type='line_multi',
  2402. params=json.dumps({
  2403. "slice_name": "Multi Line",
  2404. "viz_type": "line_multi",
  2405. "line_charts": [ids[0]],
  2406. "line_charts_2": [ids[1]],
  2407. "since": "1960-01-01",
  2408. "prefix_metric_with_slice_name": True,
  2409. }),
  2410. )
  2411. misc_dash_slices.add(slc.slice_name)
  2412. merge_slice(slc)