# import the and use function you created in step 1
from .roles import is_admin, is_member, is_moderator


def team_moderator_required(view_func):
    return _get_decorated_function(view_func, is_moderator)
```

#### 4. Use the role

[Section titled “4. Use the role”](#4-use-the-role)

You’ll need to update any views or logic that handle role-based permissions, by calling the helper functions and decorators you’ve defined above.

The specifics here will depend on the role you’ve added and the goals you’re trying to achieve with it.

## Cookbooks

[Section titled “Cookbooks”](#cookbooks)

### Strict team access

[Section titled “Strict team access”](#strict-team-access)

If you want to ensure that your data models are only ever accessible in the context of a team, you can change the declaration of the manager classes on `BaseTeamModel` as follows:

```python
class BaseTeamModel(BaseModel):
    """
    Abstract model for objects that are part of a team.
    """


    team = models.ForeignKey(Team, verbose_name=gettext("Team"),
                             on_delete=models.CASCADE)


    # rename the global manager to `all_objects`.
    # This will be used in the Django admin, but any calling code
    # using `.objects` will automatically filter by team.
    all_objects = models.Manager()


    # Override `.objects` with the TeamScopedManager to always filter
    # queries by the current team.
    objects = TeamScopedManager()




    class Meta:
        abstract = True
```

You can also set `settings.STRICT_TEAM_CONTEXT = True` to fail hard if `.objects` is ever called without a valid team set.

If you make this change, you never need to add `.filter(team=team)` to any of your queries, as the filter will be applied automatically anytime you reference `TeamModel.objects`.

### Partially using teams

[Section titled “Partially using teams”](#partially-using-teams)

Many projects might want to use teams in the background but hide them from users. This can be useful in certain scenarios:

* If you know you want to use teams eventually, but haven’t built out support for them yet.
* If your application has different user types, some of which belong to teams and some of which don’t.

The recommended way to handle this situation is to **enable teams in Pegasus, but hide/restrict them in the UI**. In this world, all users will still belong to a default team (which is created for them automatically), and all models are associated with teams. However, the concept of teams will be hidden from users until you decide to make them visible.

This allows you to easily “turn on” teams when you are ready, or migrate a user from a “non-team” to a “team” account, while being able to use the same underlying business logic and not have to deal with complicated data migrations.

To achieve this, you should do something like the following:

1. Build your application with teams enabled. This will provide the data models and URL scaffolding to work with teams, and make using teams later much easier.
2. Hide the `team_name` field from the signup form (`signup.html`), and let teams be auto-created for new users.
3. Hide the team-related items from the application navigation (entry point is `app_nav.html`).
4. (Optional) Hide/remove out the team-based url mappings (entry point is `teams/urls.py`). Do this if you don’t want people to be able to access team-related functionality even if they navigate to the right URL in the browser.
5. Continue building your application using the team-based models and URL patterns, but don’t expose them to the user.

If you follow these steps it should be relatively easy to expose teams down the line instead of having to deal with a complicated migration. That process will mostly involve un-hidng the team functionality that was hidden.

Supporting team and non-team users

If you have different categories of users, some on teams and some not, then instead of hiding the functionality mentioned above, you should instead conditionally enable it based on the type of user that is logged in.