Skip to content

Commit 20277ee

Browse files
author
Mark Gibbs
committed
Added access control to views through an arbitrary function
1 parent 9040365 commit 20277ee

File tree

5 files changed

+80
-1
lines changed

5 files changed

+80
-1
lines changed

demo/demo/settings.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,8 @@
130130
"insert_demo_migrations" : True, # Insert model instances used by the demo
131131

132132
"http_poke_enabled" : True, # Flag controlling availability of direct-to-messaging http endpoint
133+
134+
"view_decorator" : None, # Specify a function to be used to wrap each of the dpd view functions
133135
}
134136

135137
# Static files (CSS, JavaScript, Images)

django_plotly_dash/access.py

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
'''
2+
Control url access based on user and other state
3+
4+
Copyright (c) 2018 Gibbs Consulting and others - see CONTRIBUTIONS.md
5+
6+
Permission is hereby granted, free of charge, to any person obtaining a copy
7+
of this software and associated documentation files (the "Software"), to deal
8+
in the Software without restriction, including without limitation the rights
9+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10+
copies of the Software, and to permit persons to whom the Software is
11+
furnished to do so, subject to the following conditions:
12+
13+
The above copyright notice and this permission notice shall be included in all
14+
copies or substantial portions of the Software.
15+
16+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22+
SOFTWARE.
23+
'''
24+
25+
from django.conf import settings
26+
27+
from django.contrib.auth.decorators import login_required as login_required_decorator
28+
29+
def login_required(view_function, **kwargs):
30+
'Wrap all DPD calls with login_required'
31+
return login_required_decorator(view_function)
32+
33+
try:
34+
dash_view_decorator_name = settings.PLOTLY_DASH['view_decorator']
35+
try:
36+
dash_view_decorator = locals()[dash_view_decorator_name]
37+
except:
38+
mod_name, func_name = dash_view_decorator_name.rsplit('.',1)
39+
if len(mod_name):
40+
mod = importlib.import_module(mod_name)
41+
dash_view_decorator = getattr(mod, func_name)
42+
else:
43+
dash_view_decorator = locals()[func_name]
44+
except:
45+
dash_view_decorator = None
46+
47+
def process_view_function(view_function, **kwargs):
48+
'Process view function and wrap according to settings'
49+
50+
if dash_view_decorator:
51+
return dash_view_decorator(view_function,**kwargs)
52+
53+
return view_function

django_plotly_dash/urls.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,8 @@
3131

3232
from .app_name import app_name, main_view_label
3333

34+
from .access import process_view_function
35+
3436
urlpatterns = []
3537

3638
for base_type, args, name_prefix, url_ending, name_suffix in [('instance', {}, '', '', '', ),
@@ -48,7 +50,11 @@
4850
]:
4951

5052
route_name = '%s%s%s' % (name_prefix, name, name_suffix)
53+
wrapped_view_function = process_view_function(view_function,
54+
route_name=route_name,
55+
url_part=url_part,
56+
name=name)
5157
urlpatterns.append(path('%s/<slug:ident>%s/%s%s' % (base_type, url_ending, url_part, url_suffix),
52-
view_function,
58+
wrapped_view_function,
5359
args,
5460
name=route_name))

docs/configuration.rst

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,11 +24,16 @@ below.
2424
2525
# Timeout for caching of initial arguments in seconds
2626
"cache_timeout_initial_arguments": 60,
27+
28+
# Name of view wrapping function
29+
"view_decorator": None,
2730
}
2831
2932
Defaults are inserted for missing values. It is also permissible to not have any ``PLOTLY_DASH`` entry in
3033
the Django settings file.
3134

35+
.. _endpoints:
36+
3237
Endpoints
3338
---------
3439

@@ -44,3 +49,11 @@ two requirements
4449
as part of the public API.
4550

4651
A reverse proxy front end, such as ``nginx``, can route appropriately according to URL.
52+
53+
.. _view_decoration:
54+
55+
View decoration
56+
---------------
57+
58+
Each view delegated through to ``plotly_dash`` can be wrapped using a view decoration function. This enables access to be restricted to
59+
logged-in users, or using a desired conditions based on the user and session state.

docs/faq.rst

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,3 +27,8 @@ In general, the only constraint on the files containing these functions is that
2727
the ``DjangoDash`` instantiation. This is discussed in
2828
the :ref:`installation` section and also
2929
in this github `issue <https://github.com/GibbsConsulting/django-plotly-dash/issues/58>`_.
30+
31+
* Can per-user or other fine-grained access control be used?
32+
33+
Yes. See the :ref:`view_decoration` configuration setting.
34+

0 commit comments

Comments
 (0)