# Webapps and security[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#webapps-and-security "Permalink to this headline")

* Authentication of webapp users

* Run-as-user

* Identifying users from within a webapp

+ Standard webapp

+ Bokeh webapp

+ Dash webapp

+ Shiny webapp

+ Access to secrets

* Impersonating users from within a webapp

+ Standard webapps

+ Bokeh webapps

+ Dash webapps

+ Shiny webapps

## Authentication of webapp users[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#authentication-of-webapp-users "Permalink to this headline")

By default, webapps require users to be authenticated. For more details and options, please see Public webapps.

## Run-as-user[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#run-as-user "Permalink to this headline")

The code of the webapp itself always runs as a single user, the “run-as-user” of the webapp. By default, a webapp runs as the identity of the last DSS user who modified the user.

An administrator can modify the DSS user name under which the webapp runs. This is done in the settings of each individual webapp.

## Identifying users from within a webapp[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#identifying-users-from-within-a-webapp "Permalink to this headline")

When a logged-in DSS user accesses a webapp, the webapp’s code can identify which user is accessing the webapp. The webapp can use this information in order to customize the behavior for the user, to access user-specific information, or to deny access to some features, for example.

The exact way to do that depends on the webapp kind:

### Standard webapp[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#standard-webapp "Permalink to this headline")

Please see https://github.com/dataiku/dss-code-samples/tree/master/webapps/flask/authenticate-calls

### Bokeh webapp[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#bokeh-webapp "Permalink to this headline")

Please see Authentication information and impersonation. In order to retrieve the request headers, you need the following:

§ from bokeh.io import curdoc as bokeh\_curdoc

§ session\_id = bokeh\_curdoc().session\_context.id

§ from dataiku.webapps.run\_bokeh import get\_session\_headers as get\_bokeh\_session\_headers

§ headers = get\_bokeh\_session\_headers(session\_id)

§ auth\_info = dataiku.api\_client().get\_auth\_info\_from\_browser\_headers(request\_headers)

### Dash webapp[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#dash-webapp "Permalink to this headline")

This work the same as standard webapp. Just be careful to only access the request.header in a callback, because there’s no active HTTP request initialization code.

§ from flask import request

§ @app.callback(

§ Output(component\_id='my-output', component\_property='children'),

§ [Input(component\_id='my-input', component\_property='value')]

§ )

§ def update\_output\_div(input\_value):

§ request\_headers = dict(request.headers)

§ auth\_info\_brower = dataiku.api\_client().get\_auth\_info\_from\_browser\_headers(request\_headers)

§ return auth\_info\_brower["authIdentifier"]

### Shiny webapp[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#shiny-webapp "Permalink to this headline")

Please see Authentication information

### Access to secrets[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#access-to-secrets "Permalink to this headline")

The `get\_auth\_info\_from\_browser\_headers` can be called with `with\_secrets=True` in order to get decrypted user secrets (Please see User secrets for more details).

This is possible because the end-user who is browsing the webapp has a DSS session cookie that the `get\_auth\_info\_from\_browser\_headers` calls reads to retrieve information and secrets. If you want to block that behavior, you need to enable “Hide access tokens” in the Webapps security settings (Administration > Settings > Login & Security).

## Impersonating users from within a webapp[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#impersonating-users-from-within-a-webapp "Permalink to this headline")

As indicated earlier, the backend code of a webapp runs as single user. However, the backend will very often perform calls to the Dataiku API, in order to read datasets, set variables, run scenarios, …

It is possible for these calls to the Dataiku API to be *impersonated* in the name of the user currently viewing the webapp.

In order for a webapp to be able to impersonate other users in the Dataiku API, the run-as-user of the webapp must be granted the “Impersonation in webapps” permission to impersonate the *target* users, i.e. end-users.

These settings are done at the group level. If the webapp runs as user RU1 (which belongs to group G1), and the end-users to impersonate, EU1 and EU2, who belong to group G2, you need to:

* Go to the settings of G1

* In “Impersonation in webapps”, put G2 as the allowed group.

This now allows webapps running as users of the G1 group to perform impersonated API calls in the name of users of the G2 group.

To actually perform impersonated calls, you need to modify your code this way:

### Standard webapps[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#standard-webapps "Permalink to this headline")

§ @app.route('/example')

§ def example\_call():

§ # Calls performed using this client will be done as the run-as-user

§ client = dataiku.api\_client()

§ # D1 will be read as the run-as-user

§ df = dataiku.Dataset("d1").get\_dataframe()

§ with dataiku.WebappImpersonationContext() as ctx:

§ # Calls performed using this client will be done as the end-user

§ end\_user\_client = dataiku.api\_client()

§ # D2 will be read as the end-user

§ df = dataiku.Dataset("d2").get\_dataframe()

### Bokeh webapps[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#bokeh-webapps "Permalink to this headline")

§ def update\_data(attrname, old, new):

§ # Calls performed using this client will be done as the run-as-user

§ client = dataiku.api\_client()

§ # D1 will be read as the run-as-user

§ df = dataiku.Dataset("d1").get\_dataframe()

§ with dataiku.WebappImpersonationContext() as ctx:

§ # Calls performed using this client will be done as the end-user

§ end\_user\_client = dataiku.api\_client()

§ # D2 will be read as the end-user

§ df = dataiku.Dataset("d2").get\_dataframe()

### Dash webapps[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#dash-webapps "Permalink to this headline")

§ @app.callback(

§ Output(component\_id='my-output', component\_property='children'),

§ [Input(component\_id='my-input', component\_property='value')]

§ )

§ def update\_output\_div(input\_value):

§ # Calls performed using this client will be done as the run-as-user

§ client = dataiku.api\_client()

§ # D1 will be read as the run-as-user

§ df = dataiku.Dataset("d1").get\_dataframe()

§ with dataiku.WebappImpersonationContext() as ctx:

§ # Calls performed using this client will be done as the end-user

§ end\_user\_client = dataiku.api\_client()

§ # D2 will be read as the end-user

§ df = dataiku.Dataset("d2").get\_dataframe()

### Shiny webapps[¶](https://doc.dataiku.com/dss/latest/webapps/security.html#shiny-webapps "Permalink to this headline")

§ output$myPlot <- renderPlot({

§ # D1 will be read as the run-as-user

§ dkuReadDataset("d1")

§ dkuImpersonateShinyCalls(session$request, {

§ # D2 will be read as the end-user

§ dkuReadDataset("d2")

§ })

§ ...

§ })
