> ## Documentation Index
> Fetch the complete documentation index at: https://docs.fga.dev/llms.txt
> Use this file to discover all available pages before exploring further.

# Direct Relationships

> Modeling Concepts: Direct Relationships

In this guide you'll learn how to model relationships that may or may not be assigned directly to individual users.

**When to use**

Disabling *direct relationships* for a certain relation on an objects are useful especially in cases where you are trying to model some permissions that are not usually granted individually to a user.

This is useful when:

* For security reason, not permitting permissions assigned directly to individuals without associating roles

## Before you start

To better understand this guide, you should be familiar with some [Auth0 FGA Concepts](https://docs.fga.dev/fga-concepts.md) and know how to develop the things listed below.

<details>
  <summary>
    You will need to know the following:

    * Direct Access
    * Auth0 FGA Concepts
  </summary>

  ### Direct access

  You need to know how to create an authorization model and create a relationship tuple to grant a user access to an object. [Learn more →](https://docs.fga.dev/modeling/basics/modeling-basics.md)

  ### Auth0 FGA Concepts

  * A [Type](https://docs.fga.dev/fga-concepts.md#what-is-a-type): a class of objects that have similar characteristics
  * A [User](https://docs.fga.dev/fga-concepts.md#what-is-a-user): an entity in the system that can be related to an object
  * A [Relation](https://docs.fga.dev/fga-concepts.md#what-is-a-relation): is a string defined in the type definition of an authorization model that defines the possibility of a relationship between an object of the same type as the type definition and a user in the system
  * An [Object](https://docs.fga.dev/fga-concepts.md#what-is-an-object): represents an entity in the system. Users' relationships to it can be define through relationship tuples and the authorization model
  * A [Relationship Tuple](https://docs.fga.dev/fga-concepts.md#what-is-a-relationship-tuple): a grouping consisting of a user, a relation and an object stored in Auth0 FGA
  * [Direct Relationship Type Restrictions](https://docs.fga.dev/modeling/configuration-language.md#direct-relationship-type-restrictions): used in the context of the relation definition can be used to allow direct relationships to the objects of this type
</details>

[The Playground
Try this guide out on the Auth0 FGA Playground](https://play.fga.dev/)

## What are direct relationships?

Direct relationships are relationships where a user has a relationship to an [object](https://docs.fga.dev/fga-concepts.md#what-is-an-object) that is not dependent on any other relationship they have with that object.

When checking for a relationship, a direct relationship exists if a *[relationship tuple](https://docs.fga.dev/fga-concepts.md#what-is-a-relationship-tuple)* is present in the system with the exact same object and relation that were in the query and where the user is one of:

* the same user ID as that in the query
* type bound public access (`<type>:*`)
* a set of users that contains the user ID present in the query

## Enable or disable direct relationships

Direct relationships can be enabled for a specific relation on an *[object type](https://docs.fga.dev/fga-concepts.md#what-is-a-type)* by adding [direct relationship type restrictions](https://docs.fga.dev/modeling/configuration-language.md#direct-relationship-type-restrictions) from that [relation's definition](https://docs.fga.dev/fga-concepts.md#what-is-a-relation-definition). Likewise, they can be disabled by removing the direct relationship type restrictions.

> [!NOTE]
>
> The [authorization model](https://docs.fga.dev/fga-concepts.md#what-is-an-authorization-model) describes two [object types](https://docs.fga.dev/fga-concepts.md#what-is-a-type): `document` and `team`.
>
> The `document` [type definition](https://docs.fga.dev/fga-concepts.md#what-is-a-type-definition) has two [relations](https://docs.fga.dev/fga-concepts.md#what-is-a-relation), `editor` and `viewer`. Both relations allow a direct relationship; `viewer` also allows an [indirect relationship](https://docs.fga.dev/fga-concepts.md#what-are-direct-and-implied-relationships) through `editor`.
>
> In the `team` type definition, there is a single `member` relation that only allows direct relationships.

## How it affects your system

To illustrate the effect enabling or disabling direct relationships on a specific relation has, we'll investigate several situations.

### 1. With direct relationships enabled

Let us start with the authorization model we had above:

Now choose the type of relation to see how it affects your system:

> [tab] Direct User
>
> Assume you have a tuple that states that Anne is a `viewer` of `document:planning`
>
> ```json theme={null}
> [
>   {
>     "user": "user:anne",
>     "relation": "viewer",
>     "object": "document:planning"
>   }
> ]
> ```
>
> Now if we do a [check request](https://docs.fga.dev/fga-concepts.md#what-is-a-check-request) to see if Anne can view the planning document, we will get a response of `{"allowed": true}`.
>
> This is because:
>
> * There is a relationship tuple specifying that Anne has a `viewer` relationship with `document:planning`.
> * Direct relationships are allowed in the `viewer` relation definition in the `document` type definition.

> [tab] Type Bound Public Access
>
> Assume you have a [type bound public access](https://docs.fga.dev/fga-concepts.md#what-is-type-bound-public-access) tuple where everyone of type `user` is a `viewer` of `document:planning` (In other words, the document is public)
>
> ```json theme={null}
> [
>   {
>     "user": "user:*",
>     "relation": "viewer",
>     "object": "document:planning"
>   }
> ]
> ```
>
> Now if we do a check request to see if Beth can view the planning document, we will get a response of `{"allowed": true}`.
>
> This is because:
>
> * There is a relationship tuple specifying that everyone of type `user` has a `viewer` relationship with `document:planning`.
>
> * Direct relationships are allowed in the `viewer` relation definition in the `document` type definition.
>
> > [!NOTE]
> >
> > Note: Even though the relationship tuple stored in the system does not specify the user (`beth`), this is still considered a direct relationship.

> [tab] Userset
>
> [*Usersets*](https://docs.fga.dev/modeling/concepts/usersets.md) are the third way direct relationships apply, we will see how in this section.
>
> Assume you have two relationship tuples:
>
> * Charlie is a member of the product team.
> * Members of the product team are viewers of the planning document.
>
> ```json theme={null}
> [
>   {
>     "user": "user:charlie",
>     "relation": "member",
>     "object": "team:product"
>   },
>   {
>     "user": "team:product#member",
>     "relation": "viewer",
>     "object": "document:planning"
>   }
> ]
> ```
>
> > [!NOTE]
> >
> > Note that these two relationship tuples are specifying that:
> >
> > * `user:charlie` is a `member` of `team:product`.
> > * any `member` of `team:product` is a `viewer` of `document:planning`.
> >   * Note that this second relationship tuple is specifying that the **members** of the team have viewer access, and not the team object itself.
>
> Now if we do a *check request* to see if charlie can view the planning document, we will get a response of `{"allowed": true}`.
>
> This is because:
>
> * Charlie is a member of the product team.
> * There is a relationship tuple specifying that all members of the product team have a `viewer` relationship with `document:planning`.
> * Direct relationships are allowed in the `viewer` relation definition in the `document` type definition.
>
> Note that this is still considered a direct relationship no matter how many resolutions occur on the usersets until the user is found.
>
> For example, if our relationship tuples were the following relationship tuples:
>
> * Dany is a member of the product leads team.
> * Members of the product leads team are members of the product team.
> * Members of the product team are members of the contoso team.
> * Members of the contoso team are viewers of the planning document.
>
> ```json theme={null}
> [
>   {
>     "user": "user:dany",
>     "relation": "member",
>     "object": "team:product-leads"
>   },
>   {
>     "user": "team:product-leads#member",
>     "relation": "member",
>     "object": "team:product"
>   },
>   {
>     "user": "team:product#member",
>     "relation": "member",
>     "object": "team:contoso"
>   },
>   {
>     "user": "team:contoso#member",
>     "relation": "viewer",
>     "object": "document:planning"
>   }
> ]
> ```
>
> A subsequent *check request* to see if Dany can view the planning document will still return a response of `{"allowed": true}`.
>
> > [!NOTE]
> >
> > Note: Even though the relationship tuple stored in the system does not specify the user (`charlie` or `dany`), this is still considered a direct relationship.

> [tab] Indirect Relationship
>
> Here we will cover one example of an [indirect relationship](https://docs.fga.dev/fga-concepts.md#what-are-direct-and-implied-relationships) in order to see how they differ from direct relationships.
>
> With the same authorization model we have above, assume there is a relationship tuple that specifies that Emily is an `editor` of `document:planning`.
>
> ```json theme={null}
> [
>   {
>     "user": "user:emily",
>     "relation": "editor",
>     "object": "document:planning"
>   }
> ]
> ```
>
> A subsequent *check request* to see if emily can view the planning document will still return a response of `{"allowed": true}`.
>
> This is because:
>
> * Emily is an `editor` of the planning document.
> * The authorization model specified that anyone who is an `editor` on a `document` is also a `viewer` on that document.
>
> In this case, there is **NO** direct viewer relationship between Emily and the planning document. The only viewer relationship that exists is implied because Emily is an editor and the authorization model specified that any document's `editor` is that document's viewer.

### 2. With direct relationships disabled

In this section, we will investigate the effect of disabling *direct relationships* on the document's `viewer` relation.

> [!NOTE]
>
> Notice that in this updated authorization model, the direct relationship keyword has been removed from the document's `viewer` relation definition.

Now choose the type of relation to see how it affects your system:

> [tab] Direct User
>
> Assume you have a tuple that states that Fred is a `viewer` of `document:planning`
>
> ```json theme={null}
> [
>   {
>     "user": "user:fred",
>     "relation": "viewer",
>     "object": "document:planning"
>   }
> ]
> ```
>
> Now if we do a check request to see if Fred can view the planning document, we will get a response of `{"allowed": false}`.
>
> This is because:
>
> * Even though there is a relationship tuple specifying that Fred has a `viewer` relationship with `document:planning`.
> * Direct relationships are **NOT** allowed in the `viewer` relation definition in the `document` type definition.

> [tab] Everyone
>
> You will see the same behaviour with a relationship tuple specifying everyone of type `user` as the user.
>
> Assume you have a tuple that states that everyone of type `user` is a `viewer` of `document:planning`.
>
> ```json theme={null}
> [
>   {
>     "user": "user:*",
>     "relation": "viewer",
>     "object": "document:planning"
>   }
> ]
> ```
>
> Now if we do a check request to see if Gabriel can view the planning document, we will get a response of `{"allowed": false}`.
>
> This is because:
>
> * Even though there is a relationship tuple specifying that everyone has a `viewer` relationship with `document:planning`.
> * Direct relationships are **NOT** allowed in the `viewer` relation definition in the `document` type definition.

> [tab] Userset
>
> The same logic applies to usersets.
>
> Assume you have two relationship tuples:
>
> * Henry is a member of the product team.
> * Members of the product team are viewers of the planning document.
>
> ```json theme={null}
> [
>   {
>     "user": "user:henry",
>     "relation": "member",
>     "object": "team:product"
>   },
>   {
>     "user": "team:product#member",
>     "relation": "viewer",
>     "object": "document:planning"
>   }
> ]
> ```
>
> Now if we do a check request to see if Henry can view the planning document, we will get a response of `{"allowed": false}`.
>
> This is because although:
>
> * Henry is a member of the product team.
> * There is a relationship tuple specifying that all members of the product team have a `viewer` relationship with `document:planning`.
>
> Direct relationships are **NOT** allowed in the `viewer` relation definition in the `document` type definition.

> [tab] Indirect Relationship
>
> Indirect relationships are not affected by disabling a direct relationship on a certain relation.
>
> Assume there is a relationship tuple that specifies that Ingred is an `editor` of `document:planning`.
>
> ```json theme={null}
> [
>   {
>     "user": "user:ingred",
>     "relation": "editor",
>     "object": "document:planning"
>   }
> ]
> ```
>
> A subsequent check request to see if Ingred can view the planning document will still return a response of `{"allowed": true}`.

## Related Sections

Check the following sections for more one how direct relationships can be used. Also, take a look at the access relation in the feature type in Modeling Entitlements for another use-case.

[Modeling Roles and Permissions
Learn how to remove the direct relationship to indicate nonassignable permissions.](https://docs.fga.dev/modeling/basics/roles-and-permissions.md)

[Modeling for IoT
See how Roles and Permissions can be used in an IoT use-case.](https://docs.fga.dev/modeling/advanced/use-cases/iot.md)

[Modeling Entitlements
Take a look at the access relation in the feature type for an example of removing the direct relationship](https://docs.fga.dev/modeling/advanced/patterns/entitlements.md)
