diff --git a/CHANGELOG.md b/CHANGELOG.md index 5d7b14eec2..1fadfb1f27 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +0.18.1 - 2017-09-07 +## Fixed +- 🐛 If `app.layout` was supplied a function, then it used to be called excessively. Now it is called just once on startup and just once on page load. https://github.com/plotly/dash/pull/128 + 0.18.0 - 2017-09-07 ## Changed - 🔒 Removes the `/static/` folder and endpoint that is implicitly initialized by flask. This is too implicit for my comfort level: I worry that users will not be aware that their files in their `static` folder are accessible @@ -13,7 +17,7 @@ - ✏️ Fix a typo in an exception - 🔧 Replaced all illegal characters in environment variable -## Maintenance +##🔧 Maintenance - 📝 Update README.md - ✅ Fix CircleCI tests. Note that the the [`dash-renderer`](https://github.com/plotly/dash-renderer) contains the bulk of the integration tests. - 💄 Flake8 fixes and tests (fixes #99 ) diff --git a/dash/dash.py b/dash/dash.py index 3abee05689..f02bb0a09f 100644 --- a/dash/dash.py +++ b/dash/dash.py @@ -108,6 +108,7 @@ def __init__( self.server.before_first_request(self._setup_server) self._layout = None + self._cached_layout = None self.routes = [] class config: @@ -119,9 +120,10 @@ def layout(self): def _layout_value(self): if isinstance(self._layout, collections.Callable): - return self._layout() + self._cached_layout = self._layout() else: - return self._layout + self._cached_layout = self._layout + return self._cached_layout @layout.setter def layout(self, value): @@ -134,8 +136,10 @@ def layout(self, value): 'a dash component.') self._layout = value - self.css._update_layout(value) - self.scripts._update_layout(value) + + layout_value = self._layout_value() + self.css._update_layout(layout_value) + self.scripts._update_layout(layout_value) self._collect_and_register_resources( self.scripts.get_all_scripts() ) @@ -324,7 +328,8 @@ def react(self, *args, **kwargs): 'so make sure to call `help(app.callback)` to learn more.') def _validate_callback(self, output, inputs, state, events): - layout = self._layout_value() + layout = self._cached_layout or self._layout_value() + if (layout is None and not self.config.supress_callback_exceptions): # Without a layout, we can't do validation on the IDs and diff --git a/dash/resources.py b/dash/resources.py index 1756b9f671..80ba81bebe 100644 --- a/dash/resources.py +++ b/dash/resources.py @@ -1,7 +1,6 @@ from copy import copy import json import warnings -import collections from .development.base_component import Component @@ -64,10 +63,7 @@ def get_all_resources(self): def get_inferred_resources(self): namespaces = [] resources = [] - if isinstance(self.layout, collections.Callable): - layout = self.layout() - else: - layout = self.layout + layout = self.layout def extract_resource_from_component(component): if (isinstance(component, Component) and diff --git a/dash/version.py b/dash/version.py index 5ec52a922c..5877c8d040 100644 --- a/dash/version.py +++ b/dash/version.py @@ -1 +1 @@ -__version__ = '0.18.0' +__version__ = '0.18.1'