Edit

Share via


Entities

Configuration settings for database entities.

Health

Property Description
entities.entity-name.health.enabled Enables the health check endpoint for the entity
entities.entity-name.health.first Number of rows returned in health check query
entities.entity-name.health.threshold-ms Maximum duration in milliseconds for health check query

Source

Property Description
entities.entity-name.source.type Object type: table, view, or stored-procedure
entities.entity-name.source.object Name of the database object
entities.entity-name.source.parameters Parameters for stored procedures or functions
entities.entity-name.source.key-fields List of primary key fields for views
entities.entity-name.mappings Maps API field names to database columns

REST

Property Description
entities.entity-name.rest.enabled Enables REST for this entity
entities.entity-name.rest.path Custom route for REST endpoint
entities.entity-name.rest.methods Allowed REST methods: get, post, put, patch, delete

GraphQL

Property Description
entities.entity-name.graphql.type Type name or object with singular and plural
entities.entity-name.graphql.operation Operation type: query or mutation
entities.entity-name.graphql.enabled Enables GraphQL for this entity

Permissions

Property Description
entities.entity-name.permissions[].role Role name string
entities.entity-name.permissions[].actions One or more of: create, read, update, delete, execute

Relationships

Property Description
entities.entity-name.relationships.relationship-name.cardinality one or many
entities.entity-name.relationships.relationship-name.target.entity Name of the target entity
entities.entity-name.relationships.relationship-name.source.fields Fields from this entity used in the relationship
entities.entity-name.relationships.relationship-name.target.fields Fields from target entity
entities.entity-name.relationships.relationship-name.linking.object Join object used for many-to-many relationships
entities.entity-name.relationships.relationship-name.linking.source.fields Fields from source entity used in join
entities.entity-name.relationships.relationship-name.linking.target.fields Fields from target entity used in join

Cache

Property Description
entities.entity-name.cache.enabled Enables response caching for the entity
entities.entity-name.cache.ttl-seconds Cache time-to-live in seconds

Format overview

{
  "entities": {
    "{entity-name}": {
      "rest": {
        "enabled": <boolean> // default: true
        "path": <string> // default: "{entity-name}"
        "methods": ["GET", "POST"] // default: ["GET", "POST"]
      },
      "graphql": {
        "enabled": <boolean> // default: true
        "type": {
          "singular": <string>,
          "plural": <string>
        },
        "operation": "query" | "mutation" // default: "query"
      },
      "source": {
        "object": <string>,
        "type": "view" | "stored-procedure" | "table",
        "key-fields": [<string>], // primary keys for the view
        "parameters": { // only for stored-procedure
          "<parameter-name>": <string | number | boolean>,
          "<parameter-name>": <string | number | boolean>
        }
      },
      "mappings": {
        "<database-field-name>": <string>
      },
      "relationships": {
        "<relationship-name>": {
          "cardinality": "one" | "many",
          "target.entity": <string>,
          "source.fields": [<string>],
          "target.fields": [<string>],
          "linking.object": <string>,
          "linking.source.fields": [<string>],
          "linking.target.fields": [<string>]
        }
      },
      "permissions": [
        {
          "role": "anonymous" | "authenticated" | <custom-role>,
          "actions": ["create", "read", "update", "delete", "execute", "*"],
          "fields": {
            "include": [<string>],
            "exclude": [<string>]
          },
          "policy": {
            "database": <string>
          }
        }
      ]
    }
  }
}

Source (entity-name entities)

Parent Property Type Required Default
entities.{entity-name} source object ✔️ Yes None

The database source details of the entity.

Nested properties

Parent Property Type Required Default
entities.{entity-name}.source object string ✔️ Yes None
entities.{entity-name}.source type enum (table, view, stored-procedure) ✔️ Yes None
entities.{entity-name}.source key-fields string array ✔️ Yes* None
entities.{entity-name}.source parameters object ✔️ Yes** None
  • key-fields is only required when type is view. The value represents the primary keys.

** parameters is only required when type is stored-procedure. Optional parameters may be omitted.

Tip

If the object belongs to the dbo schema, specifying the schema is optional. Additionally, square brackets around object names (for example, dbo.Users vs. [dbo].[Users]) can be used when required.

Supported parameter data types:

  1. string—includes ANSI and Unicode; also used for JSON/Date/DateTime types
  2. number—includes integral and decimal
  3. booleantrue or false

Format

{
  "entities": {
    "{entity-name}": {
      "source": {
        "object": <string>,
        "type": <"view" | "stored-procedure" | "table">,
        "key-fields": [ <string> ], // primary keys of the view
        "parameters": { // only for stored-procedure
          "<parameter-name-1>": <string | number | boolean>,
          "<parameter-name-2>": <string | number | boolean>
        }
      }
    }
  }
}

Permissions (entity-name entities)

Parent Property Type Required Default
entities.permissions role string ✔️ Yes None

A string specifying the name of the role to which permissions apply.

Format

{
  "entities": {
    "{entity-name}": {
      "permissions": [
        {
          "role": <"anonymous" | "authenticated" | "custom-role">
        }
      ]
    }
  }
}

Example

This example defines the role custom-role with only read permissions on the User entity.

{
  "entities": {
    "User": {
      "permissions": [
        {
          "role": "custom-role",
          "actions": ["read"]
        }
      ]
    }
  }
}

Usage examples

GET https://localhost:5001/api/User
Authorization: Bearer <your_access_token>
X-MS-API-ROLE: custom-role

Actions (string-array Permissions entity-name entities)

Parent Property Type Required Default
entities.permissions actions oneOf [string, array] ✔️ Yes None

A string array detailing what operations are allowed for the associated role.

Action SQL Operation
* All actions
create Insert one or more* rows
read Select one or more rows
update Modify one or more* rows
delete Delete one or more* rows
execute Runs a stored procedure

* Multiple operations are currently only supported in GraphQL.

Note

For stored procedures, the wildcard (*) action expands to only the execute action. For tables and views, it expands to create, read, update, and delete.

Format

{
  "entities": {
    "{entity-name}": {
      "permissions": [
        {
          "actions": [ <string> ]
        }
      ]
    }
  }
}

Example

{
  "entities": {
    "{entity-name}": {
      "permissions": [
        {
          "actions": [ "*" ] // equivalent to create, read, update, delete
        }
      ]
    }
  }
}

Alternate format (string-only, when type=stored-procedure)

{
  "entities": {
    "{entity-name}": {
      "permissions": [
        {
          "actions": <string>
        }
      ]
    }
  }
}

Example

{
  "entities": {
    "{entity-name}": {
      "permissions": [
        {
          "actions": "*" // equivalent to execute
        }
      ]
    }
  }
}

Actions (object-array Permissions entity-name entities)

Parent Property Type Required Default
entities.{entity-name}.permissions actions string array ✔️ Yes None

An object array detailing what operations are allowed for the associated role.

Note

For stored procedures, the wildcard (*) action expands to only execute. For tables/views, it expands to create, read, update, and delete.

Nested properties

Parent Property Type Required Default
entities.{entity-name}.permissions.actions[] action string ✔️ Yes None
entities.{entity-name}.permissions.actions[] fields object ❌ No None
entities.{entity-name}.permissions.actions[] policy object ❌ No None
entities.{entity-name}.permissions.actions[].policy database string ✔️ Yes None

Format

{
  "entities": {
    "{entity-name}": {
      "permissions": [
        {
          "role": <string>,
          "actions": [
            {
              "action": <string>,
              "fields": <array of strings>,
              "policy": <object>
            }
          ]
        }
      ]
    }
  }

Example

This grants read permission to auditor on the User entity, with field and policy restrictions.

{
  "entities": {
    "User": {
      "permissions": [
        {
          "role": "auditor",
          "actions": [
            {
              "action": "read",
              "fields": {
                "include": ["*"],
                "exclude": ["last_login"]
              },
              "policy": {
                "database": "@item.IsAdmin eq false"
              }
            }
          ]
        }
      ]
    }
  }
}

Policy notes

  • Policies support OData operators like eq.
  • Policies support compound predicates using and and or.
  • Only supported for actions: create, read, update, and delete. (Not execute)
  • Policies filter results but don't prevent query execution in the database.
  • Field must use the field alias, if mapped.

Type (GraphQL entity-name entities)

Parent Property Type Required Default
entities.{entity-name}.graphql type object ❌ No {entity-name}

Sets the naming convention for an entity within the GraphQL schema.

Format

{
  "entities": {
    "{entity-name}": {
      "graphql": {
        "type": {
          "singular": "<string>",
          "plural": "<string>"
        }
      }
    }
  }
}

Nested properties

Parent Property Required Type Default
entities.{entity-name}.graphql.type singular ❌ No string None
entities.{entity-name}.graphql.type plural ❌ No string N/A (defaults to singular value)

Example

Configuration

{
  "entities": {
    "User": {
      "graphql": {
        "type": {
          "singular": "User",
          "plural": "Users"
        }
      }
    }
  }
}

GraphQL query

{
  Users {
    items {
      id
      name
      age
      isAdmin
    }
  }
}

GraphQL response

{
  "data": {
    "Users": {
      "items": [
        {
          "id": 1,
          "name": "Alice",
          "age": 30,
          "isAdmin": true
        },
        {
          "id": 2,
          "name": "Bob",
          "age": 25,
          "isAdmin": false
        }
        // ...
      ]
    }
  }
}

Operation (GraphQL entity-name entities)

Parent Property Type Required Default
entities.{entity-name}.graphql operation enum string ❌ No mutation

Designates whether the stored-procedure operation appears under the Query or Mutation.

Note

When {entity-name}.type is set to stored-procedure, a new GraphQL type executeXXX is automatically created. This operation property controls where this type is placed in the GraphQL schema. There's no functional impact, just schema hygiene.

Format

{
  "entities": {
    "{entity-name}": {
      "graphql": {
        "operation": "query" | "mutation"
      }
    }
  }
}

Example: operation

When operation is set to query

type Query {
  executeGetUserDetails(userId: Int!): GetUserDetailsResponse
}

When operation is set to mutation

type Mutation {
  executeGetUserDetails(userId: Int!): GetUserDetailsResponse
}

Enabled (GraphQL entity-name entities)

Parent Property Type Required Default
entities.{entity-name}.graphql enabled boolean ❌ No True

Lets developers selectively include entities in the GraphQL schema.

Format

{
  "entities": {
    "{entity-name}": {
      "graphql": {
        "enabled": <true> (default) | <false>
      }
    }
  }
}

REST (entity-name entities)

Parent Property Type Required Default
entities.{entity-name}.rest enabled boolean ❌ No True
entities.rest path string ❌ No /{entity-name}
entities.{entity-name}.rest methods string array ❌ No* POST

* The methods property is only for stored-procedure endpoints.

Format

{
  "entities": {
    "{entity-name}": {
      "rest": {
        "enabled": <true> (default) | <false>,
        "path": <string; default: "{entity-name}">
      }
    }
  }
}

Mappings (entity-name entities)

Parent Property Type Required Default
entities.{entity-name} mappings object ❌ No None

Enables custom aliases, or exposed names, for database object fields.

Important

For entities with GraphQL enabled, the configured exposed name must meet the GraphQL name requirements.

Format

{
  "entities": {
    "{entity-name}": {
      "mappings": {
        "<field-1-name>": "<field-1-alias>",
        "<field-2-name>": "<field-2-alias>",
        "<field-3-name>": "<field-3-alias>"
      }
    }
  }
}

Examples

Database Table

CREATE TABLE Books
(
  id INT,
  sku_title VARCHAR(50),
  sku_status VARCHAR(50),
)

Configuration

{
  "entities": {
    "Books": {
      ...
      "mappings": {
        "sku_title": "title",
        "sku_status": "status"
      }
    }
  }
}

Cache (entity-name entities)

Parent Property Type Required Default
entities.{entity-name} cache object ❌ No None

Enables and configures caching for the entity.

Nested properties

Parent Property Type Required Default
entities.{entity-name}.cache enabled boolean ❌ No False
entities.{entity-name}.cache ttl-seconds integer ❌ No -

Format

{
  "entities": {
    "{entity-name}": {
      "cache": {
        "enabled": <true> (default) | <false>,
        "ttl-seconds": <integer; default: 5>
      }
    }
  }
}

Note

When not specified, ttl-seconds inherits the global value set under runtime.cache.

Example

{
  "entities": {
    "Author": {
      "cache": {
        "enabled": true,
        "ttl-seconds": 30
      }
    }
  }
}

Relationships (entity-name entities)

Parent Property Type Required Default
entities.{entity-name} relationships object ❌ No None

Configures how GraphQL entities are related to other exposed entities. For more information, see Data API builder relationships breakdown.

Note

The relationship-name property for each relationship must be unique across all relationships for that entity.

Nested properties

These properties are used in different combinations depending on the relationship cardinality.

Parent Property Type Required Default
entities.{entity-name}.relationships cardinality string ✔️ Yes None
entities.{entity-name}.relationships target.entity string ✔️ Yes None
entities.{entity-name}.relationships target.fields string array ❌ No None
entities.{entity-name}.relationships source.fields string array ❌ No None
entities.{entity-name}.relationships linking.object string ❌ No None
entities.{entity-name}.relationships linking.source.fields string array ❌ No None
entities.{entity-name}.relationships linking.target.fields string array ❌ No None

Format

{
  "entities": {
    "{entity-name}": {
      "relationships": {
        "<relationship-name>": {
          "cardinality": "one" | "many",
          "target.entity": "<string>",
          "source.fields": ["<string>"],
          "target.fields": ["<string>"],
          "linking.object": "<string>",
          "linking.source.fields": ["<string>"],
          "linking.target.fields": ["<string>"]
        }
      }
    }
  }
}
Relationship Cardinality Example
one-to-many many One category entity can relate to many todo entities
many-to-one one Many todo entities can relate to one category entity
many-to-many many One todo entity can relate to many user entities, and one user entity can relate to many todo entities

Example: One-to-one cardinality

Each Profile is related to exactly one User, and each User has exactly one related Profile.

{
  "entities": {
    "User": {
      "relationships": {
        "user_profile": {
          "cardinality": "one",
          "target.entity": "Profile",
          "source.fields": [ "id" ],
          "target.fields": [ "user_id" ]
        }
      }
    },
    "Profile": {
      ...
    }
  }
}

GraphQL schema

type User
{
  id: Int!
  ...
  profile: Profile
}

Command-line

dab update User \
  --relationship profile \
  --target.entity Profile \
  --cardinality one \
  --relationship.fields "id:user_id"

Example: One-to-many cardinality

A Category can have one or more related Book entities, while each Book can have one related Category.

{
  "entities": {
    "Book": {
      ...
    },
    "Category": {
      "relationships": {
        "category_books": {
          "cardinality": "many",
          "target.entity": "Book",
          "source.fields": [ "id" ],
          "target.fields": [ "category_id" ]
        }
      }
    }
  }
}

GraphQL schema

type Category
{
  id: Int!
  ...
  books: [BookConnection]!
}

Command line

dab update Category \
  --relationship category_books \
  --target.entity Book \
  --cardinality many \
  --relationship.fields "id:category_id"

Example: Many-to-one cardinality

Many Book entities can have one related Category, while a Category can have one or more related Book entries.

{
  "entities": {
    "Book": {
      "relationships": {
        "books_category": {
          "cardinality": "one",
          "target.entity": "Category",
          "source.fields": [ "category_id" ],
          "target.fields": [ "id" ]
        }
      },
      "Category": {
        ...
      }
    }
  }
}

GraphQL schema

type Book
{
  id: Int!
  ...
  category: Category
}

Command line

dab update Book \
  --relationship books_category \
  --target.entity "Category" \
  --cardinality one \
  --relationship.fields "category_id:id"

Example: Many-to-many cardinality

Many Book entities can have many related Author entities, while many Author entities can have many related Book entries.

Note

This relationship is possible with a third table, dbo.books_authors, which we refer to as the linking object.

{
  "entities": {
    "Book": {
      "relationships": {
        ...,
        "books_authors": {
          "cardinality": "many",
          "target.entity": "Author",
          "source.fields": [ "id" ],
          "target.fields": [ "id" ],
          "linking.object": "dbo.books_authors",
          "linking.source.fields": [ "book_id" ],
          "linking.target.fields": [ "author_id" ]
        }
      },
      "Category": {
        ...
      },
      "Author": {
        ...
      }
    }
  }
}

GraphQL schema

type Book
{
  id: Int!
  ...
  authors: [AuthorConnection]!
}

type Author
{
  id: Int!
  ...
  books: [BookConnection]!
}

Command line

dab update Book \
  --relationship books_authors \
  --target.entity "Author" \
  --cardinality many \
  --relationship.fields "id:id" \
  --linking.object "dbo.books_authors" \
  --linking.source.fields "book_id" \
  --linking.target.fields "author_id"

Health (entity-name entities)

Parent Property Type Required Default
entities.{entity-name} health object ❌ No None

Enables and configures health checks for the entity.

Nested properties

Parent Property Type Required Default
entities.{entity-name}.health enabled boolean ❌ No True
entities.{entity-name}.health first integer ❌ No 1
entities.{entity-name}.health threshold-ms integer ❌ No 5

Format

{
  "entities": {
    "{entity-name}": {
      "health": {
        "enabled": true,
        "first": 5,
        "threshold-ms": 2000
      }
    }
  }
}

Example

{
  "entities": {
    "Book": {
      "health": {
        "enabled": true,
        "first": 3,
        "threshold-ms": 500
      }
    }
  }
}