# Multi-User Session Management

{% hint style="info" %}
Supervisely SDK version ≥ **v6.73.454**

Supervisely instance version ≥ **v6.15.2**
{% endhint %}

## Introduction

In Supervisely SDK version 6.73.454, multi-user session management was introduced, allowing each user's interactions with app widgets to be isolated from others. This means that when one user interacts with a widget, it does not affect what other users see.

This is particularly useful for applications that can be used by a large number of users simultaneously, as it optimizes resource usage by avoiding the need to run separate app sessions for each user.

**Enable Multi-User Mode**

At the beginning of your app code, enable multi-user session management by calling:

```python
sly.env.enable_multiuser_app_mode()
```

This ensures that the app operates in a multi-user context.

**Session-Specific Data Handling**

Then, ensure that your callbacks and widget interactions are designed to work with session-specific data.

{% hint style="warning" %}
Avoid using global variables to store user-specific information, as this can lead to data leakage between sessions.
{% endhint %}

Instead of using global variables to store user-specific information (like filter states), retrieve user-specific data within the callbacks or use session-specific storage if available. This prevents data leakage between sessions.

* **Get Current User ID**: `user_id = sly.env.user_from_multiuser_app()`
* **Get API Instance**: `user_api = sly.app.session_user_api()`. It provides an [API](https://supervisely.readthedocs.io/en/latest/sdk/supervisely.api.api.Api.html#supervisely.api.api.Api) instance scoped to the current user's permissions. So you can perform actions on behalf of the user.

For example:

```python
@widget.value_changed
def on_value_change(value):
    # Retrieve session-specific data
    # Process the value based on the current user's session
    user_id = sly.env.user_from_multiuser_app()
    user_api = sly.app.session_user_api()  # Get API instance for the current user
    user_info = user_api.user.get_my_info()  # Example of using the user-specific API instance
    # Perform actions on behalf of the user with user's permissions
```

{% hint style="info" %}
Note: This function works only when the app is running in multi-user mode on the Supervisely platform. It may not return a valid user ID when running the app locally. For local testing, you might need to use advanced debugging mode or mock user data.
{% endhint %}

### Example Application

Here is a simple example of a multi-user app that generates a random number for each user when they press a button. Each user will see their own random number without affecting others.

```python
import os
from random import randint

from dotenv import load_dotenv

import supervisely as sly
import supervisely.app.development as sly_app_development
from supervisely.app.widgets import Button, Card, Container, Text

load_dotenv(os.path.expanduser("~/supervisely.env"))
load_dotenv("local.env")

sly.env.enable_multiuser_app_mode()  # Enable multi-user session management
team_id = sly.env.team_id()
workspace_id = sly.env.workspace_id()

if sly.is_development():
    sly_app_development.enable_advanced_debug(team_id=team_id)

api = sly.Api.from_env()
info_widget = Text(status="info")
generate_random_number_button = Button("Generate random number", widget_id="mb")
card = Card(
    "Random number",
    "Press the button to show a random number.",
    content=Container([info_widget, generate_random_number_button]),
)


# Creating a callback function, which will be change the text of the Text widget
@generate_random_number_button.click
def generate_random_number():
    random_number = randint(1, 100)
    info_widget.text = f"Random number: {random_number}" # each user will see their own value
    api = sly.app.session_user_api()  # Get API instance for the current user
    api.user.get_my_info()  # Example of using the user-specific API instance
    # You can use `api` to perform actions on behalf of the user with user's permissions

app = sly.Application(layout=card)
```

![Example App](/files/tJm8nWmVWx5wEmlm3jOZ)

## Advanced Debugging in Multi-User Apps

When developing multi-user apps, you might want to test how the app behaves for different users. You can use the advanced debugging mode to simulate multiple users. Check the [Advanced Debugging](/app-development/advanced/advanced-debugging.md) documentation for detailed instructions on setting up and using advanced debugging mode.

## Recap

In this guide, we covered the basics of implementing multi-user session management in your Supervisely apps. By enabling multi-user mode and designing your app to handle session-specific data, you can create a more efficient and user-friendly experience for all users.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://developer.supervisely.com/app-development/advanced/multi_user_session.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
