Update DataTable content

Hello,

I am having trouble to update the content of a DataTable. When some user action takes place (e.g. a radio button is clicked) the datatable should update its content accordingly.

Any ideas, why this example code is working not correctly? The table changes only once, no matter how often the buttons are clicked.

from datetime import date
from random import randint
from bokeh.client import push_session
from bokeh.models import ColumnDataSource
from bokeh.models.widgets import RadioButtonGroup, DataTable, DateFormatter, TableColumn
from bokeh.plotting import curdoc
from bokeh.layouts import layout

Starting bokeh server from here

import subprocess
import time
args = [‘python’, ‘-m’, ‘bokeh’, ‘serve’]
p = subprocess.Popen(args)
time.sleep(1) # time to wait might be longer on other PC

data1 = dict(
dates=[date(2014, 3, i+1) for i in range(10)],
downloads=[randint(0, 100) for i in range(10)],
)
source1 = ColumnDataSource(data1)

columns switched

data2 = dict(
dates=[date(2017, 3, i+1) for i in range(10)],
downloads=[randint(100, 200) for i in range(10)],
)
source2 = ColumnDataSource(data2)

defining initial CDS and initial table

source = source1
columns = [TableColumn(field=“dates”, title=“Date”, formatter=DateFormatter()),
TableColumn(field=“downloads”, title=“Downloads”)]
data_table = DataTable(source=source, columns=columns, width=400, height=280)

callback for RadioButtonGroup

def select_data(attr, old, new):
print(‘callback’)
print(‘RadioButtonGroup - active is button {}’.format(new))
if new == 0:
source.data = source1.data
print(‘Action for button 0’)
else:
source.data = source2.data
print(‘Action for button 1’)

button = RadioButtonGroup(labels=[“Option 0”, “Option 1”], active=0)
button.on_change(‘active’, select_data)

mylayout = layout([[button], [data_table]])

session = push_session(curdoc())
session.show(mylayout)
session.loop_until_closed()

``

I’ve done something similar.

It worked when I added: data_table.update()

···

On Wed, Mar 1, 2017 at 11:31 AM ‘Daniel Krause’ via Bokeh Discussion - Public [email protected] wrote:

Hello,

I am having trouble to update the content of a DataTable. When some user action takes place (e.g. a radio button is clicked) the datatable should update its content accordingly.

Any ideas, why this example code is working not correctly? The table changes only once, no matter how often the buttons are clicked.

from datetime import date
from random import randint
from bokeh.client import push_session
from bokeh.models import ColumnDataSource
from bokeh.models.widgets import RadioButtonGroup, DataTable, DateFormatter, TableColumn
from bokeh.plotting import curdoc
from bokeh.layouts import layout

Starting bokeh server from here

import subprocess
import time
args = [‘python’, ‘-m’, ‘bokeh’, ‘serve’]
p = subprocess.Popen(args)
time.sleep(1) # time to wait might be longer on other PC

data1 = dict(
dates=[date(2014, 3, i+1) for i in range(10)],
downloads=[randint(0, 100) for i in range(10)],
)
source1 = ColumnDataSource(data1)

columns switched

data2 = dict(
dates=[date(2017, 3, i+1) for i in range(10)],
downloads=[randint(100, 200) for i in range(10)],
)
source2 = ColumnDataSource(data2)

defining initial CDS and initial table

source = source1
columns = [TableColumn(field=“dates”, title=“Date”, formatter=DateFormatter()),
TableColumn(field=“downloads”, title=“Downloads”)]
data_table = DataTable(source=source, columns=columns, width=400, height=280)

callback for RadioButtonGroup

def select_data(attr, old, new):
print(‘callback’)
print(‘RadioButtonGroup - active is button {}’.format(new))
if new == 0:
source.data = source1.data
print(‘Action for button 0’)
else:
source.data = source2.data
print(‘Action for button 1’)

button = RadioButtonGroup(labels=[“Option 0”, “Option 1”], active=0)
button.on_change(‘active’, select_data)

mylayout = layout([[button], [data_table]])

session = push_session(curdoc())
session.show(mylayout)
session.loop_until_closed()

``

You received this message because you are subscribed to the Google Groups “Bokeh Discussion - Public” group.

To unsubscribe from this group and stop receiving emails from it, send an email to [email protected].

To post to this group, send email to [email protected].

To view this discussion on the web visit https://groups.google.com/a/continuum.io/d/msgid/bokeh/fd1ec3d4-43a2-40f2-80c1-77aa1344a959%40continuum.io.

For more options, visit https://groups.google.com/a/continuum.io/d/optout.

Jacques, thanks for the idea. I changed the callback and added two lines in the end:

callback for RadioButtonGroup

def select_data(attr, old, new):
print(‘callback’)
print(‘RadioButtonGroup - active is button {}’.format(new))
if new == 0:
source.data = source1.data
print(‘Action for button 0’)
else:
source.data = source2.data
print(‘Action for button 1’)
global data_table
data_table.update()

``

Unfortunately it did not solve my problem. It still works only ones, then the table is not changing any more.

···

Am Mittwoch, 1. März 2017 21:06:37 UTC+1 schrieb Jacques Roy:

I’ve done something similar.

It worked when I added: data_table.update()

On Wed, Mar 1, 2017 at 11:31 AM ‘Daniel Krause’ via Bokeh Discussion - Public [email protected] wrote:

Hello,

I am having trouble to update the content of a DataTable. When some user action takes place (e.g. a radio button is clicked) the datatable should update its content accordingly.

Any ideas, why this example code is working not correctly? The table changes only once, no matter how often the buttons are clicked.

from datetime import date
from random import randint
from bokeh.client import push_session
from bokeh.models import ColumnDataSource
from bokeh.models.widgets import RadioButtonGroup, DataTable, DateFormatter, TableColumn
from bokeh.plotting import curdoc
from bokeh.layouts import layout

Starting bokeh server from here

import subprocess
import time
args = [‘python’, ‘-m’, ‘bokeh’, ‘serve’]
p = subprocess.Popen(args)
time.sleep(1) # time to wait might be longer on other PC

data1 = dict(
dates=[date(2014, 3, i+1) for i in range(10)],
downloads=[randint(0, 100) for i in range(10)],
)
source1 = ColumnDataSource(data1)

columns switched

data2 = dict(
dates=[date(2017, 3, i+1) for i in range(10)],
downloads=[randint(100, 200) for i in range(10)],
)
source2 = ColumnDataSource(data2)

defining initial CDS and initial table

source = source1
columns = [TableColumn(field=“dates”, title=“Date”, formatter=DateFormatter()),
TableColumn(field=“downloads”, title=“Downloads”)]
data_table = DataTable(source=source, columns=columns, width=400, height=280)

callback for RadioButtonGroup

def select_data(attr, old, new):
print(‘callback’)
print(‘RadioButtonGroup - active is button {}’.format(new))
if new == 0:
source.data = source1.data
print(‘Action for button 0’)
else:
source.data = source2.data
print(‘Action for button 1’)

button = RadioButtonGroup(labels=[“Option 0”, “Option 1”], active=0)
button.on_change(‘active’, select_data)

mylayout = layout([[button], [data_table]])

session = push_session(curdoc())
session.show(mylayout)
session.loop_until_closed()

``

You received this message because you are subscribed to the Google Groups “Bokeh Discussion - Public” group.

To unsubscribe from this group and stop receiving emails from it, send an email to [email protected].

To post to this group, send email to [email protected].

To view this discussion on the web visit https://groups.google.com/a/continuum.io/d/msgid/bokeh/fd1ec3d4-43a2-40f2-80c1-77aa1344a959%40continuum.io.

For more options, visit https://groups.google.com/a/continuum.io/d/optout.

Hi Daniel,

I am also quite new to Bokeh so I maybe wrong.

However, I believe you need to update the source1 and source2 within the select_data() function.

If I copy

data1 = dict(
dates=[date(2014, 3, i+1) for i in range(10)],
downloads=[randint(0, 100) for i in range(10)],
)
source1 = ColumnDataSource(data1)

columns switched

data2 = dict(
dates=[date(2017, 3, i+1) for i in range(10)],
downloads=[randint(100, 200) for i in range(10)],
)
source2 = ColumnDataSource(data2)

into the function it works for me.

Fred

···

Am Mittwoch, 1. März 2017 20:31:33 UTC+1 schrieb Daniel Krause:

Hello,

I am having trouble to update the content of a DataTable. When some user action takes place (e.g. a radio button is clicked) the datatable should update its content accordingly.

Any ideas, why this example code is working not correctly? The table changes only once, no matter how often the buttons are clicked.

from datetime import date
from random import randint
from bokeh.client import push_session
from bokeh.models import ColumnDataSource
from bokeh.models.widgets import RadioButtonGroup, DataTable, DateFormatter, TableColumn
from bokeh.plotting import curdoc
from bokeh.layouts import layout

Starting bokeh server from here

import subprocess
import time
args = [‘python’, ‘-m’, ‘bokeh’, ‘serve’]
p = subprocess.Popen(args)
time.sleep(1) # time to wait might be longer on other PC

data1 = dict(
dates=[date(2014, 3, i+1) for i in range(10)],
downloads=[randint(0, 100) for i in range(10)],
)
source1 = ColumnDataSource(data1)

columns switched

data2 = dict(
dates=[date(2017, 3, i+1) for i in range(10)],
downloads=[randint(100, 200) for i in range(10)],
)
source2 = ColumnDataSource(data2)

defining initial CDS and initial table

source = source1
columns = [TableColumn(field=“dates”, title=“Date”, formatter=DateFormatter()),
TableColumn(field=“downloads”, title=“Downloads”)]
data_table = DataTable(source=source, columns=columns, width=400, height=280)

callback for RadioButtonGroup

def select_data(attr, old, new):
print(‘callback’)
print(‘RadioButtonGroup - active is button {}’.format(new))
if new == 0:
source.data = source1.data
print(‘Action for button 0’)
else:
source.data = source2.data
print(‘Action for button 1’)

button = RadioButtonGroup(labels=[“Option 0”, “Option 1”], active=0)
button.on_change(‘active’, select_data)

mylayout = layout([[button], [data_table]])

session = push_session(curdoc())
session.show(mylayout)
session.loop_until_closed()

``

Hi Fred,

thanks, that helped a lot. To avoid the same code in two different places I use now separate function to create the column data sources. This function is called once at initialization of the table, and than each time the callback is used.

This is my working final code:

from datetime import date
from random import randint
from bokeh.client import push_session
from bokeh.models import ColumnDataSource
from bokeh.models.widgets import RadioButtonGroup, DataTable, DateFormatter, TableColumn
from bokeh.plotting import curdoc
from bokeh.layouts import layout

Starting bokeh server from here

import subprocess
import time
args = [‘python’, ‘-m’, ‘bokeh’, ‘serve’]
p = subprocess.Popen(args)
time.sleep(1) # time to wait might be longer on other PC

def create_cds():
‘’‘Create two different column data sources’‘’

data1 = dict(dates=[date(2014, 3, i+1) for i in range(10)],
             downloads=[randint(0, 100) for i in range(10)])
source1 = ColumnDataSource(data1)
 
data2 = dict(dates=[date(2017, 3, i+1) for i in range(15)],
             downloads=[randint(100, 200) for i in range(15)])
source2 = ColumnDataSource(data2)

return source1, source2

defining initial CDS and initial table

source1, source2 = create_cds()
source = source1
columns = [TableColumn(field=“dates”, title=“Date”, formatter=DateFormatter()),
TableColumn(field=“downloads”, title=“Downloads”)]
data_table = DataTable(source=source, columns=columns, width=400, height=280)

callback for RadioButtonGroup

def select_data(attr, old, new):
print(‘callback’)
print(‘RadioButtonGroup - active is button {}’.format(new))
source1, source2 = create_cds()

if new == 0:
    source.data = source1.data
    print('Action for button 0')
else:
    source.data = source2.data
    print('Action for button 1')
global data_table
data_table.update()

button = RadioButtonGroup(labels=[“Option 0”, “Option 1”], active=0)
button.on_change(‘active’, select_data)

mylayout = layout([[button], [data_table]])

session = push_session(curdoc())
session.show(mylayout)
session.loop_until_closed()

``

Daniel

···

Am Donnerstag, 2. März 2017 16:14:14 UTC+1 schrieb FredMaster:

Hi Daniel,

I am also quite new to Bokeh so I maybe wrong.

However, I believe you need to update the source1 and source2 within the select_data() function.

If I copy

data1 = dict(
dates=[date(2014, 3, i+1) for i in range(10)],
downloads=[randint(0, 100) for i in range(10)],
)
source1 = ColumnDataSource(data1)

columns switched

data2 = dict(
dates=[date(2017, 3, i+1) for i in range(10)],
downloads=[randint(100, 200) for i in range(10)],
)
source2 = ColumnDataSource(data2)

into the function it works for me.

Fred

Am Mittwoch, 1. März 2017 20:31:33 UTC+1 schrieb Daniel Krause:

Hello,

I am having trouble to update the content of a DataTable. When some user action takes place (e.g. a radio button is clicked) the datatable should update its content accordingly.

Any ideas, why this example code is working not correctly? The table changes only once, no matter how often the buttons are clicked.

from datetime import date
from random import randint
from bokeh.client import push_session
from bokeh.models import ColumnDataSource
from bokeh.models.widgets import RadioButtonGroup, DataTable, DateFormatter, TableColumn
from bokeh.plotting import curdoc
from bokeh.layouts import layout

Starting bokeh server from here

import subprocess
import time
args = [‘python’, ‘-m’, ‘bokeh’, ‘serve’]
p = subprocess.Popen(args)
time.sleep(1) # time to wait might be longer on other PC

data1 = dict(
dates=[date(2014, 3, i+1) for i in range(10)],
downloads=[randint(0, 100) for i in range(10)],
)
source1 = ColumnDataSource(data1)

columns switched

data2 = dict(
dates=[date(2017, 3, i+1) for i in range(10)],
downloads=[randint(100, 200) for i in range(10)],
)
source2 = ColumnDataSource(data2)

defining initial CDS and initial table

source = source1
columns = [TableColumn(field=“dates”, title=“Date”, formatter=DateFormatter()),
TableColumn(field=“downloads”, title=“Downloads”)]
data_table = DataTable(source=source, columns=columns, width=400, height=280)

callback for RadioButtonGroup

def select_data(attr, old, new):
print(‘callback’)
print(‘RadioButtonGroup - active is button {}’.format(new))
if new == 0:
source.data = source1.data
print(‘Action for button 0’)
else:
source.data = source2.data
print(‘Action for button 1’)

button = RadioButtonGroup(labels=[“Option 0”, “Option 1”], active=0)
button.on_change(‘active’, select_data)

mylayout = layout([[button], [data_table]])

session = push_session(curdoc())
session.show(mylayout)
session.loop_until_closed()

``

The code did not work for me with Bokeh 0.12.9 so I changed it a little bit:

from datetime import date

from random import randint

from bokeh.client import push_session

from bokeh.models import ColumnDataSource

from bokeh.models.widgets import RadioButtonGroup, DataTable, DateFormatter, TableColumn

from bokeh.plotting import curdoc

from bokeh.layouts import layout

import subprocess

import time

args = [‘python’, ‘-m’, ‘bokeh’, ‘serve’]

p = subprocess.Popen(args)

time.sleep(1) # time to wait might be longer on other PC

data1 = dict(dates = [date(2014, 3, i + 1) for i in range(10)], downloads = [randint(0, 100) for i in range(10)])

source1 = ColumnDataSource(data1)

data2 = dict(dates = [date(2017, 3, i + 1) for i in range(10)], downloads = [randint(100, 200) for i in range(10)])

source2 = ColumnDataSource(data2)

columns = [TableColumn(field = “dates”, title = “Date”, formatter = DateFormatter()),

       TableColumn(field = "downloads", title = "Downloads")]

data_table = DataTable(source = source1, columns = columns, reorderable = False, width = 400, height = 280)

def select_data(attr, old, new):

global data_table

global data1

global data2

update_data = None

print('RadioButtonGroup - active is button {}'.format(new))

if new == 0:

    data_table.source.data.update(data1)

    print('Action for button 0')

else:

    data_table.source.data.update(data2)

    print('Action for button 1')

button = RadioButtonGroup(labels = [“Option 0”, “Option 1”], active = 0)

button.on_change(‘active’, select_data)

mylayout = layout([[button], [data_table]])

session = push_session(curdoc())

session.show(mylayout)

session.loop_until_closed()

``

···

On Thursday, March 2, 2017 at 7:09:14 PM UTC+1, Daniel Krause wrote:

Hi Fred,

thanks, that helped a lot. To avoid the same code in two different places I use now separate function to create the column data sources. This function is called once at initialization of the table, and than each time the callback is used.

This is my working final code:

from datetime import date
from random import randint
from bokeh.client import push_session
from bokeh.models import ColumnDataSource
from bokeh.models.widgets import RadioButtonGroup, DataTable, DateFormatter, TableColumn
from bokeh.plotting import curdoc
from bokeh.layouts import layout

Starting bokeh server from here

import subprocess
import time
args = [‘python’, ‘-m’, ‘bokeh’, ‘serve’]
p = subprocess.Popen(args)
time.sleep(1) # time to wait might be longer on other PC

def create_cds():
‘’‘Create two different column data sources’‘’

data1 = dict(dates=[date(2014, 3, i+1) for i in range(10)],
             downloads=[randint(0, 100) for i in range(10)])
source1 = ColumnDataSource(data1)
 
data2 = dict(dates=[date(2017, 3, i+1) for i in range(15)],
             downloads=[randint(100, 200) for i in range(15)])
source2 = ColumnDataSource(data2)

return source1, source2

defining initial CDS and initial table

source1, source2 = create_cds()
source = source1
columns = [TableColumn(field=“dates”, title=“Date”, formatter=DateFormatter()),
TableColumn(field=“downloads”, title=“Downloads”)]
data_table = DataTable(source=source, columns=columns, width=400, height=280)

callback for RadioButtonGroup

def select_data(attr, old, new):
print(‘callback’)
print(‘RadioButtonGroup - active is button {}’.format(new))
source1, source2 = create_cds()

if new == 0:
    source.data = source1.data
    print('Action for button 0')
else:
    source.data = source2.data
    print('Action for button 1')
global data_table
data_table.update()

button = RadioButtonGroup(labels=[“Option 0”, “Option 1”], active=0)
button.on_change(‘active’, select_data)

mylayout = layout([[button], [data_table]])

session = push_session(curdoc())
session.show(mylayout)
session.loop_until_closed()

``

Daniel

Am Donnerstag, 2. März 2017 16:14:14 UTC+1 schrieb FredMaster:

Hi Daniel,

I am also quite new to Bokeh so I maybe wrong.

However, I believe you need to update the source1 and source2 within the select_data() function.

If I copy

data1 = dict(
dates=[date(2014, 3, i+1) for i in range(10)],
downloads=[randint(0, 100) for i in range(10)],
)
source1 = ColumnDataSource(data1)

columns switched

data2 = dict(
dates=[date(2017, 3, i+1) for i in range(10)],
downloads=[randint(100, 200) for i in range(10)],
)
source2 = ColumnDataSource(data2)

into the function it works for me.

Fred

Am Mittwoch, 1. März 2017 20:31:33 UTC+1 schrieb Daniel Krause:

Hello,

I am having trouble to update the content of a DataTable. When some user action takes place (e.g. a radio button is clicked) the datatable should update its content accordingly.

Any ideas, why this example code is working not correctly? The table changes only once, no matter how often the buttons are clicked.

from datetime import date
from random import randint
from bokeh.client import push_session
from bokeh.models import ColumnDataSource
from bokeh.models.widgets import RadioButtonGroup, DataTable, DateFormatter, TableColumn
from bokeh.plotting import curdoc
from bokeh.layouts import layout

Starting bokeh server from here

import subprocess
import time
args = [‘python’, ‘-m’, ‘bokeh’, ‘serve’]
p = subprocess.Popen(args)
time.sleep(1) # time to wait might be longer on other PC

data1 = dict(
dates=[date(2014, 3, i+1) for i in range(10)],
downloads=[randint(0, 100) for i in range(10)],
)
source1 = ColumnDataSource(data1)

columns switched

data2 = dict(
dates=[date(2017, 3, i+1) for i in range(10)],
downloads=[randint(100, 200) for i in range(10)],
)
source2 = ColumnDataSource(data2)

defining initial CDS and initial table

source = source1
columns = [TableColumn(field=“dates”, title=“Date”, formatter=DateFormatter()),
TableColumn(field=“downloads”, title=“Downloads”)]
data_table = DataTable(source=source, columns=columns, width=400, height=280)

callback for RadioButtonGroup

def select_data(attr, old, new):
print(‘callback’)
print(‘RadioButtonGroup - active is button {}’.format(new))
if new == 0:
source.data = source1.data
print(‘Action for button 0’)
else:
source.data = source2.data
print(‘Action for button 1’)

button = RadioButtonGroup(labels=[“Option 0”, “Option 1”], active=0)
button.on_change(‘active’, select_data)

mylayout = layout([[button], [data_table]])

session = push_session(curdoc())
session.show(mylayout)
session.loop_until_closed()

``