async def test_session(start_visit, browser, backend): app = Dazzler(__name__) app.config.session.enable = False app.config.session.duration = 3 app.middlewares.append(SessionMiddleware(app, backend=backend(app))) page = Page(__name__, url='/', layout=core.Container([ core.Button('Click', identity='session-click'), core.Container(identity='session-output'), core.Button('Remove session', identity='remove-session'), ])) @page.bind(Trigger('session-click', 'clicks')) async def on_session(ctx: BindingContext): session = ctx.request['session'] clicks = await session.get('clicks') or 0 clicks += 1 await session.set('clicks', clicks) await ctx.set_aspect('session-output', children=f'Clicked {clicks}') @page.bind(Trigger('remove-session', 'clicks')) async def on_remove(ctx: BindingContext): session = ctx.request['session'] await session.delete('clicks') app.add_page(page) await start_visit(app) for i in range(1, 4): await browser.get('http://localhost:8150/') await browser.click('#session-click') await browser.wait_for_text_to_equal('#session-output', f'Clicked {i}') # Delete session item await browser.click('#remove-session') await browser.click('#session-click') await browser.wait_for_text_to_equal('#session-output', 'Clicked 1')
def session_app(): app = Dazzler(__name__) app.config.session.duration = 3 app.config.secret_key = uuid.uuid4().hex page = Page(__name__, core.Container( [core.Container(identity='session-output', clicks=1)]), url='/') @page.bind(Trigger('session-output', 'clicks')) async def on_session(ctx: BindingContext): await ctx.set_aspect('session-output', children=ctx.session.session_id) app.add_page(page) return app
async def test_middleware(start_visit, browser): page = Page(__name__, layout=layout, url='/') @page.bind(Trigger('cookie-setter', 'clicks')) async def on_cookie(ctx: BindingContext): cookie = ctx.request.cookies.get('dummy') await ctx.set_aspect('cookie-output', children=cookie) app = Dazzler(__name__) app.middlewares.append(DummyMiddleware()) app.add_page(page) await start_visit(app) await browser.wait_for_text_to_equal('#request-output', 'dummy') await browser.click('#cookie-setter') await browser.wait_for_text_to_equal('#cookie-output', 'dummy-cookie')
def auth_app(): app = Dazzler(__name__) page = Page('test-auth', core.Container([ core.Html('h2', 'logged-in', identity='header'), core.Container(identity='username-output'), _auth.Logout('/auth/logout', identity='logout') ]), url='/', require_login=True) @page.bind(Trigger('header', 'children')) async def on_username(ctx): user = ctx.request['user'] await ctx.set_aspect('username-output', children=user.username) app.add_page(page) app.config.session.backend = 'Redis' DazzlerAuth(app, DummyAuthenticator()) return app
page = Page( __name__, core.Container([ core.Select([{ 'value': x, 'label': str(x) } for x in range(1, 11)], identity='select'), core.Select([{ 'value': x, 'label': str(x) } for x in range(1, 11)], multi=True, identity='multi'), core.Container(identity='output'), core.Container(identity='multi-output'), ]), ) @page.bind(Trigger('select', 'value')) async def on_value(ctx: BindingContext): await ctx.set_aspect('output', children=ctx.trigger.value) @page.bind(Trigger('multi', 'value')) async def on_multi(ctx: BindingContext): await ctx.set_aspect('multi-output', children=json.dumps(ctx.trigger.value))
""" Page radio of dazzler Created 2019-06-20 """ from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext radio = core.RadioList(identity='radio', options=[{ 'label': f'option {x}', 'value': x } for x in range(1, 12)]) page = Page(__name__, core.Container([ radio, core.Container(identity='output'), ])) @page.bind(Trigger('radio', 'value')) async def on_radio(ctx: BindingContext): await ctx.set_aspect('output', children=f'Selected: {ctx.trigger.value}')
import json from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page( __name__, core.Container([ core.Button('Set local', identity='local-btn'), core.Container(identity='local-output'), core.Button('Set session', identity='session-btn'), core.Container(identity='session-output') ])) @page.bind(Trigger('local-btn', 'clicks')) async def on_click_local(ctx: BindingContext): data = await ctx.get_local_storage('data') if not data: data = {'clicks': 0} data['clicks'] += 1 await ctx.set_local_storage('data', data) await ctx.set_aspect('local-output', children=json.dumps(data)) @page.bind(Trigger('session-btn', 'clicks')) async def on_clicks_session(ctx: BindingContext): data = await ctx.get_session_storage('data') if not data: data = {'clicks': 0} data['clicks'] += 1
""" Page progress of dazzler Created 2019-06-26 """ from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext, State page = Page( __name__, core.Container([ core.ProgressBar(identity='progress', minimum=0, high=80, low=20, maximum=100, rounded=True, optimum=21, striped=True, progress_text='percent'), core.Button('add progress', identity='progress-btn'), core.Container(identity='counter') ])) @page.bind(Trigger('progress-btn', 'clicks'), State('progress', 'value')) async def on_meter(ctx: BindingContext): new_value = (ctx.states['progress']['value'] or 0) + 1 await ctx.set_aspect('progress', value=new_value) await ctx.set_aspect('counter', children=new_value)
core.Container([ core.Container([ core.Input(identity=f'output-{i}', type='number') for i in range(1, 3) ]), core.Container([ core.Input(identity=f'value-{i}', type='number') for i in range(1, 11) ]), core.Container('[]', identity='output'), core.Container(identity='done') ]) ])) @page.bind(Trigger('trigger', 'clicks')) async def trigger_click(context: BindingContext): await context.set_aspect('output-1', value=1) # Got to alternate the inputs for the first set to complete and let # frontend to register the state and all, # so as long as this start after and the other delay # is a little higher it should be ok. # otherwise the test is flaky because the state won't have updated before # the trigger and there be missing numbers. await asyncio.sleep(0.1) await context.set_aspect('output-2', value=2) async def trigger_input(context: BindingContext): num = context.trigger.value if num == 1:
]), core.Button('click sum', identity='click-sum'), core.Container(identity='sum-output'), core.Container(identity='shaped-output'), ]) ) async def bind_click(ctx: BindingContext): await ctx.set_aspect( f'{ctx.trigger.identity}-output', children=f'Click {ctx.trigger.identity}: {ctx.trigger.value}' ) page.bind(Trigger('single', 'clicks'))(bind_click) page.bind(Trigger('shaped', 'clicks'))(bind_click) async def bind_array_value(ctx: BindingContext): await ctx.set_aspect( f'output-{ctx.trigger.identity}', children=f'{ctx.trigger.identity} value: {ctx.trigger.value}' ) for i in arr: page.bind(Trigger(f'array-{i}', 'value'))(bind_array_value) @page.bind(
from dazzler import Dazzler from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page(name='page', url='/', layout=core.Container([ core.Button('click', identity='clicker'), core.Container('output', identity='output') ])) app = Dazzler(__name__) app.add_page(page) @page.bind(Trigger('clicker', 'clicks')) async def on_click(context: BindingContext): await context.set_aspect('output', children=core.Container('from binding', id='from-binding')) if __name__ == '__main__': app.start('-v --debug=1 --port=8151'.split())
core.Button('Click me', identity='clicker'), core.Container(children='Not clicked', identity='output'), core.DataList([{ 'value': 'hello', 'label': 'world' }, { 'value': 'foo', 'label': 'Foo' }], identity='dropdown'), core.Container( 'No data', identity='datalist-output', ), ])) @page.bind(Trigger('clicker', 'clicks'), State('dropdown', 'data_value')) async def on_click(context: BindingContext): await context.set_aspect('output', children=f'Clicked {context.trigger.value}', style={ 'backgroundColor': 'blue' if context.trigger.value % 2 == 0 else 'red' }) data_value = context.states['dropdown']['data_value'] if data_value: await context.set_aspect('datalist-output', children=f'Data {data_value}')
""" Page same_identity of dazzler Created 2019-06-17 """ from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext, State page = Page( __name__, core.Container([ core.Container( core.Input(value=0, type='number', identity='same'), identity='container' ), core.Button('click', identity='click') ]) ) @page.bind(Trigger('click', 'clicks'), State('container', 'children')) async def on_click(ctx: BindingContext): component = ctx.states['container']['children'] component.value = ctx.trigger.value await ctx.set_aspect( 'container', children=component )
from dazzler import Dazzler from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext app = Dazzler(__name__) page = Page(name='home', url='/', layout=core.Container([ core.Button('click', identity='click'), core.Container(identity='output'), core.Container(identity='output2') ])) app.add_page(page) @page.bind(Trigger('click', 'clicks')) async def on_click(context: BindingContext): await context.set_aspect('output', children=core.Button('click twice', identity='generated')) @page.bind(Trigger('generated', 'clicks')) async def on_generated_click(context: BindingContext): await context.set_aspect('output2', children='Generated') if __name__ == '__main__': app.start('-v --debug=1 --port=8159'.split())
""" Page checklist of dazzler Created 2019-06-19 """ import json from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page( __name__, core.Container([ core.CheckList(identity='checklist', options=[{ 'label': f'option {x}', 'value': x } for x in range(1, 12)]), core.Container(identity='output') ]), ) @page.bind(Trigger('checklist', 'values')) async def on_values(ctx: BindingContext): await ctx.set_aspect('output', children=json.dumps(ctx.trigger.value))
""" Page modal of dazzler Created 2019-07-07 """ from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page( __name__, core.Container([ core.Modal( core.Container('modal body', identity='modal-body'), header='modal header', footer='modal footer', identity='modal', close_button=False, ), core.Button('Show modal', identity='show') ])) @page.bind(Trigger('show', 'clicks')) async def on_show(ctx: BindingContext): await ctx.set_aspect('modal', active=True)
__name__, core.Container([ lb_component, core.Container([ core.Button('append', identity='append-btn'), core.Button('prepend', identity='prepend-btn'), core.Button('concat', identity='concat-btn'), core.Button('insert', identity='insert-btn'), core.Input(identity='index-input', type='number'), core.Button('delete', identity='delete-btn') ]) ])) # Add an element to the end. @page.bind(Trigger('append-btn', 'clicks')) async def on_append(ctx: BindingContext): await ctx.set_aspect('list-box', append=core.Container('appended', class_name='item append')) # Add an element to the start of the list. @page.bind(Trigger('prepend-btn', 'clicks')) async def on_prepend(ctx: BindingContext): await ctx.set_aspect('list-box', prepend=core.Container('prepended', class_name='item prepend')) # Add multiple elements to the end of the list.
""" Page button of dazzler Created 2019-07-06 """ from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page( __name__, core.Container([ core.Button('Click me', identity='button', rounded=True), core.Container(identity='output') ])) @page.bind(Trigger('button', 'clicks')) async def on_click(ctx: BindingContext): await ctx.set_aspect('output', children=f'clicked: {ctx.trigger.value}')
from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page( 'removed-component', core.Container([ core.Container(core.Container(identity='set-me'), identity='remove-inner'), core.Button('remover', identity='remover'), core.Button('setter', identity='setter'), core.Container(identity='done') ])) @page.bind(Trigger('remover', 'clicks')) async def remover(context: BindingContext): await context.set_aspect('remove-inner', children=f'removed {context.trigger.value}') @page.bind(Trigger('setter', 'clicks')) async def on_set(context: BindingContext): await context.set_aspect('set-me', children='set') await context.set_aspect('done', children=f'done {context.trigger.value}')
""" from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page( __name__, core.Container( [ core.Container(style={'marginTop': '20px'}), core.Container([ core.Container('start', identity='start'), core.Slider(-100, 100, identity='slider', value=-20, style={'width': '80%'}), core.Container('stop', identity='stop') ], style={'padding': '3rem'}, class_name='row'), core.Container(identity='output') ], style={'width': '100%'}, )) @page.bind(Trigger('slider', 'value')) async def on_value(ctx: BindingContext): await ctx.set_aspect( 'output', children=f'{ctx.trigger.identity}: {ctx.trigger.value}')
""" Page pager of dazzler Created 2019-09-03 """ from dazzler.components import core, extra from dazzler.system import Page, Trigger, BindingContext items = list(range(1, 200)) page = Page( __name__, core.Container([ core.Grid([], columns=2, identity='output'), extra.Pager(total_items=len(items), items_per_page=10, identity='pager'), core.Container(identity='num_pages'), ])) @page.bind(Trigger('pager', 'current_page')) async def on_page(ctx: BindingContext): start = await ctx.get_aspect('pager', 'start_offset') stop = await ctx.get_aspect('pager', 'end_offset') await ctx.set_aspect('output', children=items[start:stop]) @page.bind(Trigger('pager', 'total_pages')) async def on_total(ctx: BindingContext): await ctx.set_aspect('num_pages', children=ctx.trigger.value)
""" Page datalist of dazzler Created 2019-06-13 """ from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page( 'datalist', core.Container([ core.DataList([{ 'value': 'foo', 'label': 'Foo' }, { 'value': 'bar', 'label': 'Bar' }], identity='datalist'), core.Container(identity='output') ]), ) @page.bind(Trigger('datalist', 'data_value')) async def on_list(ctx: BindingContext): await ctx.set_aspect('output', children=ctx.trigger.value)
core.Container([ core.Store(identity='empty-store'), core.Store(data={'foo': 'bar'}, identity='initial-store'), core.Button('click', identity='click'), core.Container(identity='click-output'), core.Container(identity='initial-output'), core.Button('type-click', identity='type-click'), core.Store(identity='type-store'), core.Container(identity='type-output'), core.Button('get-aspect', identity='get-aspect-click'), core.Container(identity='get-aspect-output') ]) ) @page.bind(Trigger('initial-store', 'data')) async def initial(ctx: BindingContext): await ctx.set_aspect( 'initial-output', children=json.dumps(ctx.trigger.value) ) @page.bind(Trigger('click', 'clicks'), State('empty-store', 'data')) async def click_store(ctx: BindingContext): data = ctx.states['empty-store']['data'] or {'clicks': 0} data['clicks'] += 1 await ctx.set_aspect('empty-store', data=data)
from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page( 'get-aspect', core.Container([ core.Input(value=0, type='number', identity='input'), core.Button('Start', identity='starter'), core.Button('Updater', identity='updater'), core.Container(identity='done'), core.Container(identity='done-output') ])) @page.bind(Trigger('starter', 'clicks')) async def starter(ctx: BindingContext): value = 0 values = set() while value < 100: value = await ctx.get_aspect('input', 'value') values.add(value) await asyncio.sleep(0.05) await ctx.set_aspect( 'done', children='done', ) await ctx.set_aspect('done-output', children=json.dumps(list(values)))
""" Page initial_trigger of dazzler Created 2019-06-15 """ from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext, State page = Page( 'initial-trigger', core.Container([ core.Input(value=10, identity='input'), core.Container(identity='output'), core.Input(value=88, identity='state'), core.Container(identity='state-output') ])) @page.bind(Trigger('input', 'value'), State('state', 'value')) async def on_value(context: BindingContext): await context.set_aspect('output', children=f'Input {context.trigger.value}') await context.set_aspect( 'state-output', children=F'State {context.states["state"]["value"]}')
])), identity='nested-components'), core.Container(identity='nested-output'), core.Button('get-aspect-click', identity='get-aspect-trigger'), core.Container( core.Input(value='input-value'), identity='input' ), core.Container(core.Input(value=4747), identity='as-state'), core.Container(identity='get-aspect-output'), core.Container(identity='as-state-output') ]) ) @page.bind(Trigger('component', 'children')) async def trigger(ctx: BindingContext): await ctx.set_aspect( 'output', children=f'From component: {ctx.trigger.value.children}' ) @page.bind(Trigger('array-components', 'children')) async def trigger_array_components(ctx: BindingContext): # The value is an array of container. value = sum(int(x.children) for x in ctx.trigger.value) await ctx.set_aspect( 'array-output', children=f'Sum: {value}' )
""" Page get_aspect_error of dazzler Created 2019-06-15 """ from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext from dazzler.errors import GetAspectError page = Page( __name__, core.Container([ core.Button('click error', identity='click-error'), core.Container(identity='error-output') ])) @page.bind(Trigger('click-error', 'clicks')) async def trigger_error(ctx: BindingContext): try: await ctx.get_aspect('invalid', 'error') except GetAspectError as err: await ctx.set_aspect('error-output', children=err.args[0])
from dazzler.system import Page, Trigger, BindingContext, State page = Page( __name__, core.Container([ core.Button('btn1', identity='btn1'), core.Button('btn2', identity='btn2'), core.Container(identity='output1'), core.Container(identity='output2'), core.Input(identity='state1'), core.Store(data='store', identity='state2'), core.Container(identity='state-output') ])) @page.bind(Trigger(r'btn\d', 'clicks', regex=True), State(r'state\d', '(value|data)', regex=True)) async def on_any_click(ctx: BindingContext): await ctx.set_aspect( re.compile(r'output\d'), children=f'clicked from button {ctx.trigger.identity}') output = [] for identity, aspects in ctx.states.items(): for aspect_name, aspect_value in aspects.items(): output.append( core.Container(f'{aspect_name}@{identity}: {aspect_value}', identity=f'{aspect_name}-{identity}-output')) # FIXME Setting the array directly on children trigger # the same identity bug #53
import functools from dazzler.components import core from dazzler.system import Page, Trigger, BindingContext page = Page( 'binding-chain', core.Container([ core.Button(x, identity=f'trigger-{x}') for x in range(1, 21) ] + [core.Container(identity='output')]) ) async def update_next(context: BindingContext, num: int = 0): await context.set_aspect( f'trigger-{num+1}', clicks=1, ) @page.bind(Trigger('trigger-20', 'clicks')) async def last_trigger(context: BindingContext): await context.set_aspect('output', children='output generated') for i in range(1, 20): page.bind(Trigger(f'trigger-{i}', 'clicks'))( functools.partial(update_next, num=i) )
'fontSize': 777 }, 'json': True, }, } button_ids = ['set-{}'.format(y) for y in aspect_types] output_ids = ['out-{}'.format(y) for y in aspect_types] layout = core.Container([ core.Container([core.Button(x, identity=x) for x in button_ids]), spec.TestComponent('', identity='spec-output', id='spec-output'), ]) page = Page('page', url='/', layout=layout) app.add_page(page) async def on_click_render_type(context: BindingContext): identity = context.trigger.identity.replace('set-', '') await context.set_aspect( 'spec-output', **{f'{identity}_prop': aspect_types[identity]['value']}) for button in button_ids: page.bind(Trigger(button, 'clicks'))(on_click_render_type) if __name__ == '__main__': app.start('-v --debug=1 --port=8155'.split())