Completed
Push — master ( a10da3...25c806 )
by Chris
01:12
created

graphdata()   B

Complexity

Conditions 3

Size

Total Lines 24

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 3
dl 0
loc 24
rs 8.9713
c 0
b 0
f 0
1
"""A separate Flask app that serves fake endpoints for demo purposes."""
2
3
# -*- coding: utf-8 -*-
4
5
import json
6
import locale
7
import os
8
from datetime import timedelta as td
9
from datetime import datetime as dt
10
from random import randrange as rr
11
from random import choice, random
12
import time
13
14
from flask import (
15
    Flask,
16
    abort,
17
    request,
18
    render_template,
19
)
20
from flask.ext.cors import CORS
21
from flask.ext.cors import cross_origin
22
23
app = Flask('endpoints_test')
24
CORS(app)
25
app.config['SECRET_KEY'] = 'NOTSECURELOL'
26
app.debug = True
27
28
STRESS_MAX_POINTS = 300
29
30
locale.setlocale(locale.LC_ALL, '')
31
32
cwd = os.getcwd()
33
34
35
def recursive_d3_data(current=0, max_iters=12, data=None):
36
    """Generate d3js data for stress testing.
37
    Format is suitable in treemap, circlepack and dendrogram testing.
38
    """
39
    if current >= max_iters:
40
        return data
41
    if data is None:
42
        data = dict(name='foo', size=rr(10, 10000), children=[])
43
    data = dict(name='foo', size=rr(10, 10000),
44
                children=[data, data])
45
    return recursive_d3_data(
46
        current=current + 1,
47
        max_iters=max_iters,
48
        data=data)
49
50
51
def dates_list(max_dates=10):
52
    """Generate a timeseries dates list."""
53
    now = dt.now()
54
    return [str(now + td(days=i * 10))[0:10] for i in range(max_dates)]
55
56
57
def rr_list(max_range=10):
58
    """Generate a list of random integers."""
59
    return [rr(0, 100) for i in range(max_range)]
60
61
62
@cross_origin()
63
@app.route('/combination')
64
def combination():
65
    """Fake endpoint."""
66
    data = {
67
        'columns': [
68
            ['data1', 30, 20, 50, 40, 60, 50],
69
            ['data2', 200, 130, 90, 240, 130, 220],
70
            ['data3', 300, 200, 160, 400, 250, 250],
71
            ['data4', 200, 130, 90, 240, 130, 220],
72
            ['data5', 130, 120, 150, 140, 160, 150],
73
            ['data6', 90, 70, 20, 50, 60, 120],
74
        ],
75
        'type': 'bar',
76
        'types': {
77
            'data3': 'spline',
78
            'data4': 'line',
79
            'data6': 'area',
80
        },
81
        'groups': [
82
            ['data1', 'data2'],
83
        ]
84
    }
85
    return json.dumps(dict(data=data))
86
87
88
@cross_origin()
89
@app.route('/stacked-bar')
90
def stackedbar():
91
    """Fake endpoint."""
92
    return json.dumps({
93
        'data': {
94
            'columns': [
95
                ['data1', -30, 200, 200, 400, -150, 250],
96
                ['data2', 130, 100, -100, 200, -150, 50],
97
                ['data3', -230, 200, 200, -300, 250, 250]
98
            ],
99
            'type': 'bar',
100
            'groups': [
101
                ['data1', 'data2']
102
            ]
103
        },
104
        'grid': {
105
            'y': {
106
                'lines': [{'value': 0}]
107
            }
108
        }
109
    })
110
111
112
@cross_origin()
113
@app.route('/plotly')
114
def plotly():
115
    """Fake endpoint."""
116
    chart_type = request.args.get('chart', 'line')
117
    filename = '{}/examples/plotly/{}.json'.format(cwd, chart_type)
118
    with open(filename, 'r') as chartjson:
119
        return chartjson.read()
120
    return json.dumps({})
121
122
123
@cross_origin
124
@app.route('/plotly-dynamic')
125
def plotly_dynamic():
126
    """Fake endpoint."""
127
    filename = '{}/examples/plotly/bar_line_dynamic.json'.format(cwd)
128
    with open(filename, 'r') as chartjson:
129
        return chartjson.read()
130
    return json.dumps({})
131
132
133
@cross_origin()
134
@app.route('/timeline')
135
def timeline():
136
    """Fake endpoint."""
137
    with open('{}/examples/timeline3.json'.format(cwd), 'r') as timelinejson:
138
        return timelinejson.read()
139
    return json.dumps({})
140
141
142
@app.route('/dtable', methods=['GET'])
143
def dtable():
144
    """Fake endpoint."""
145
    if 'stress' in request.args:
146
        return json.dumps([
147
            dict(
148
                foo=rr(1, 1000),
149
                bar=rr(1, 1000),
150
                baz=rr(1, 1000),
151
                quux=rr(1, 1000)) for _ in range(STRESS_MAX_POINTS)
152
        ])
153
    fname = 'dtable-override' if 'override' in request.args else 'dtable'
154
    with open('{}/examples/{}.json'.format(os.getcwd(), fname), 'r') as djson:
155
        return djson.read()
156
    return json.dumps({})
157
158
159
@cross_origin()
160
@app.route('/timeseries')
161
def timeseries():
162
    """Fake endpoint."""
163
    return json.dumps({
164
        "dates": dates_list(),
165
        "line1": rr_list(max_range=10),
166
        "line2": rr_list(max_range=10),
167
        "line3": rr_list(max_range=10),
168
    })
169
170
171
@cross_origin()
172
@app.route('/custom')
173
def custompage():
174
    """Fake endpoint."""
175
    kwargs = dict(number=rr(1, 1000))
176
    return render_template('examples/custom.html', **kwargs)
177
178
179
@cross_origin()
180
@app.route('/gauge')
181
def gauge():
182
    """Fake endpoint."""
183
    return json.dumps({'data': rr(1, 100)})
184
185
186
@cross_origin()
187
@app.route('/area-custom')
188
def area_custom():
189
    """Fake endpoint."""
190
    return json.dumps({
191
        "data": {
192
            "columns": [
193
                ["data1", 300, 350, 300, 0, 0, 0],
194
                ["data2", 130, 100, 140, 200, 150, 50]
195
            ],
196
            "types": {
197
                "data1": "area",
198
                "data2": "area-spline"
199
            }
200
        }
201
    })
202
203
204
@cross_origin()
205
@app.route('/scatter')
206
def scatter():
207
    """Fake endpoint."""
208
    if 'override' in request.args:
209
        with open('{}/examples/overrides.json'.format(cwd), 'r') as jsonfile:
210
            return jsonfile.read()
211
    return json.dumps({
212
        "bar1": [1, 2, 30, 12, 100],
213
        "bar2": rr_list(max_range=40),
214
        "bar3": rr_list(max_range=40),
215
        "bar4": [-10, 1, 5, 4, 10, 20],
216
    })
217
218
219
@cross_origin()
220
@app.route('/pie')
221
def pie():
222
    """Fake endpoint."""
223
    letters = list('abcde')
224
    if 'stress' in request.args:
225
        letters = range(STRESS_MAX_POINTS)
226
    return json.dumps({'data {}'.format(name): rr(1, 100) for name in letters})
227
228
229
@cross_origin()
230
@app.route('/custom-inputs')
231
def custom_inputs():
232
    """Fake endpoint."""
233
    _range = int(request.args.get('range', 5))
234
    entries = int(request.args.get('entries', 3))
235
    starting = int(request.args.get('starting_num', 0))
236
    prefix = request.args.get('prefix', 'item')
237
    if 'override' in request.args:
238
        show_axes = request.args.get('show_axes', False)
239
        show_axes = show_axes == 'on'
240
        data = dict(
241
            data=dict(
242
                columns=[
243
                    ['{} {}'.format(prefix, i)] + rr_list(max_range=entries)
244
                    for i in range(starting, _range)
245
                ],
246
            )
247
        )
248
        if show_axes:
249
            data.update(axis=dict(
250
                x=dict(label='This is the X axis'),
251
                y=dict(label='This is the Y axis')))
252
        return json.dumps(data)
253
    return json.dumps({
254
        i: rr_list(max_range=_range) for i in range(starting, entries)
255
    })
256
257
258
@cross_origin()
259
@app.route('/bar')
260
def barchart():
261
    """Fake endpoint."""
262
    if 'stress' in request.args:
263
        return json.dumps({
264
            'bar-{}'.format(k): rr_list(max_range=STRESS_MAX_POINTS)
265
            for k in range(STRESS_MAX_POINTS)
266
        })
267
    return json.dumps({
268
        "bar1": [1, 2, 30, 12, 100],
269
        "bar2": rr_list(max_range=5),
270
        "bar3": rr_list(max_range=5),
271
    })
272
273
274
@cross_origin()
275
@app.route('/line')
276
def linechart():
277
    """Fake endpoint."""
278
    if 'stress' in request.args:
279
        return json.dumps({
280
            'bar-{}'.format(k): rr_list(max_range=STRESS_MAX_POINTS)
281
            for k in range(STRESS_MAX_POINTS)
282
        })
283
    return json.dumps({
284
        "line1": [1, 4, 3, 10, 12, 14, 18, 10],
285
        "line2": [1, 2, 10, 20, 30, 6, 10, 12, 18, 2],
286
        "line3": rr_list(),
287
    })
288
289
290
@cross_origin()
291
@app.route('/singlenum')
292
def singlenum():
293
    """Fake endpoint."""
294
    _min, _max = 10, 10000
295
    if 'sales' in request.args:
296
        val = locale.currency(float(rr(_min, _max)), grouping=True)
297
    else:
298
        val = rr(_min, _max)
299
    if 'negative' in request.args:
300
        val = '-{}'.format(val)
301
    return json.dumps(val)
302
303
304
@cross_origin()
305
@app.route('/deadend')
306
def test_die():
307
    """Fake endpoint that ends in a random 50x error."""
308
    # Simulate slow connection
309
    time.sleep(random())
310
    abort(choice([500, 501, 502, 503, 504]))
311
312
313
@cross_origin()
314
@app.route('/venn')
315
def test_venn():
316
    """Fake endpoint."""
317
    data = [
318
        {'sets': ['A'], 'size': rr(10, 100)},
319
        {'sets': ['B'], 'size': rr(10, 100)},
320
        {'sets': ['C'], 'size': rr(10, 100)},
321
        {'sets': ['A', 'B'], 'size': rr(10, 100)},
322
        {'sets': ['A', 'B', 'C'], 'size': rr(10, 100)},
323
    ]
324
    return json.dumps(data)
325
326
327
@cross_origin()
328
@app.route('/sparklines', methods=['GET'])
329
def sparklines():
330
    """Fake endpoint."""
331
    if any([
332
        'pie' in request.args,
333
        'discrete' in request.args,
334
    ]):
335
        return json.dumps([rr(1, 100) for _ in range(10)])
336
    return json.dumps([[i, rr(i, 100)] for i in range(10)])
337
338
339
@cross_origin()
340
@app.route('/circlepack', methods=['GET'])
341
def circlepack():
342
    """Fake endpoint."""
343
    if 'stress' in request.args:
344
        # Build a very large dataset
345
        return json.dumps(recursive_d3_data())
346
    with open('{}/examples/flare.json'.format(cwd), 'r') as djson:
347
        return djson.read()
348
    return json.dumps({})
349
350
351
@cross_origin()
352
@app.route('/treemap', methods=['GET'])
353
def treemap():
354
    """Fake endpoint."""
355
    if 'stress' in request.args:
356
        # Build a very large dataset
357
        return json.dumps(recursive_d3_data())
358
    with open('{}/examples/flare.json'.format(cwd), 'r') as djson:
359
        return djson.read()
360
    return json.dumps({})
361
362
363
@cross_origin()
364
@app.route('/map', methods=['GET'])
365
def datamap():
366
    """Fake endpoint."""
367
    return render_template('examples/map.html')
368
369
370
@cross_origin()
371
@app.route('/dendrogram', methods=['GET'])
372
def dendro():
373
    """Fake endpoint."""
374
    if 'stress' in request.args:
375
        # Build a very large dataset
376
        return json.dumps(recursive_d3_data())
377
    filename = 'flare-simple' if 'simple' in request.args else 'flare'
378
    with open('{}/examples/{}.json'.format(cwd, filename), 'r') as djson:
379
        return djson.read()
380
    return json.dumps({})
381
382
383
@cross_origin()
384
@app.route('/voronoi', methods=['GET'])
385
def voronoi():
386
    """Fake endpoint."""
387
    w, h = request.args.get('width', 800), request.args.get('height', 800)
388
    max_points = int(request.args.get('points', 100))
389
    if 'stress' in request.args:
390
        max_points = 500
391
    return json.dumps([[rr(1, h), rr(1, w)] for _ in range(max_points)])
392
393
394
@cross_origin()
395
@app.route('/digraph', methods=['GET'])
396
def graphdata():
397
    """Fake endpoint."""
398
    if 'simple' in request.args:
399
        graphdata = """
400
        digraph {
401
            a -> b;
402
            a -> c;
403
            b -> c;
404
            b -> a;
405
            b -> b;
406
        }
407
        """
408
        return json.dumps(dict(graph=graphdata))
409
    nodes = list('abcdefghijkl')
410
    node_data = '\n'.join([
411
        '{0} -> {1};'.format(choice(nodes), choice(nodes))
412
        for _ in range(10)
413
    ])
414
    graphdata = """digraph {lb} {nodes} {rb}""".format(
415
        lb='{', rb='}', nodes=node_data)
416
    return json.dumps(dict(
417
        graph=graphdata,
418
    ))
419
420
421
if __name__ == '__main__':
422
    app.run(debug=True, port=5004)
423