Note
Access to this page requires authorization. You can try signing in or changing directories.
Access to this page requires authorization. You can try changing directories.
Role-based access control refers to a method to manage access to resources in Azure. This method is based on specific identities being assigned roles that manage what level of access they have to one or more resources. Role-based access control provides a flexible system of fine-grained access management that ensures identities only have the least privileged level of access they need to perform their task.
For more information, see role-based access control.
Prerequisites
An Azure account with an active subscription. Create an account for free.
An existing Azure Cosmos DB for NoSQL account.
One or more existing identities in Microsoft Entra ID.
Use the Bash environment in Azure Cloud Shell. For more information, see Get started with Azure Cloud Shell.
If you prefer to run CLI reference commands locally, install the Azure CLI. If you're running on Windows or macOS, consider running Azure CLI in a Docker container. For more information, see How to run the Azure CLI in a Docker container.
If you're using a local installation, sign in to the Azure CLI by using the az login command. To finish the authentication process, follow the steps displayed in your terminal. For other sign-in options, see Authenticate to Azure using Azure CLI.
When you're prompted, install the Azure CLI extension on first use. For more information about extensions, see Use and manage extensions with the Azure CLI.
Run az version to find the version and dependent libraries that are installed. To upgrade to the latest version, run az upgrade.
- If you choose to use Azure PowerShell locally:
- Install the latest version of the Az PowerShell module.
- Connect to your Azure account using the Connect-AzAccount cmdlet.
- If you choose to use Azure Cloud Shell:
- See Overview of Azure Cloud Shell for more information.
Disable key-based authentication
Disabling key-based authorization prevents your account from being used without the more secure Microsoft Entra ID authentication method. This procedure is a step that should be performed on new accounts in secure workloads. Alternatively, perform this procedure on existing accounts being migrated to a secure workload pattern.
First, disable key-based authentication to your existing account so that applications are required to use Microsoft Entra ID authentication. Use az resource update
to modify properties.disableLocalAuth
of the existing account.
az resource update \
--resource-group "<name-of-existing-resource-group>" \
--name "<name-of-existing-account>" \
--resource-type "Microsoft.DocumentDB/databaseAccounts" \
--set properties.disableLocalAuth=true
First, create a new account with key-based authentication disabled so that applications are required to use Microsoft Entra authentication.
Create a new Bicep file to deploy your new account with key-based authentication disabled. Name the file deploy-new-account.bicep.
metadata description = 'Deploys a new Azure Cosmos DB account with key-based auth disabled.' @description('Name of the Azure Cosmos DB account.') param name string = 'csms-${uniqueString(resourceGroup().id)}' @description('Primary ___location for the Azure Cosmos DB account.') param ___location string = resourceGroup().___location resource account 'Microsoft.DocumentDB/databaseAccounts@2024-05-15' = { name: name ___location: ___location kind: 'GlobalDocumentDB' properties: { databaseAccountOfferType: 'Standard' locations: [ { locationName: ___location } ] disableLocalAuth: true } }
Use
az deployment group create
to deploy the Bicep file with the new account.az deployment group create \ --resource-group "<name-of-existing-resource-group>" \ --template-file deploy-new-account.bicep
First, disable key-based authentication to your existing account so that applications are required to use Microsoft Entra authentication. Use Get-AzResource
and Set-AzResource
to respectively read and update the existing account.
$parameters = @{
ResourceGroupName = "<name-of-existing-resource-group>"
ResourceName = "<name-of-existing-account>"
ResourceType = "Microsoft.DocumentDB/databaseAccounts"
}
$resource = Get-AzResource @parameters
$resource.Properties.DisableLocalAuth = $true
$resource | Set-AzResource -Force
Use these steps to create a new Azure Cosmos DB for NoSQL account with key-based authentication disabled so that applications are required to only use Microsoft Entra authentication.
When setting up a new Azure Cosmos DB for NoSQL account, navigate to the Security section of the account creation process.
Then, select Disable for the Key-based authentication option.
Important
Modifying an Azure Cosmos DB account requires an Azure role with at least the Microsoft.DocumentDb/databaseAccounts/*/write
permission. For more information, see permissions for Azure Cosmos DB.
Validate that key-based authentication is disabled
To validate that key-based access is disabled, attempt to use the Azure SDK to connect to Azure Cosmos DB for NoSQL using a resource-owner password credential (ROPC). This attempt should fail. If necessary, code samples for common programming languages are provided here.
using Microsoft.Azure.Cosmos;
string connectionString = "AccountEndpoint=<nosql-endpoint>;AccountKey=<key>;";
CosmosClient client = new(connectionString);
const { CosmosClient } = require('@azure/cosmos');
const connectionString = 'AccountEndpoint=<nosql-endpoint>;AccountKey=<key>;';
const client = new CosmosClient(connectionString);
import { CosmosClient } from '@azure/cosmos'
let connectionString: string = 'AccountEndpoint=<nosql-endpoint>;AccountKey=<key>;';
const client: CosmosClient = new CosmosClient(connectionString);
from azure.cosmos import CosmosClient
connection_string = "AccountEndpoint=<nosql-endpoint>;AccountKey=<key>;"
client = CosmosClient(connection_string)
package main
import (
"github.com/Azure/azure-sdk-for-go/sdk/data/azcosmos"
)
const connectionString = "AccountEndpoint=<nosql-endpoint>;AccountKey=<key>;"
func main() {
client, _ := azcosmos.NewClientFromConnectionString(connectionString, nil)
}
import com.azure.cosmos.CosmosClient;
import com.azure.cosmos.CosmosClientBuilder;
public class NoSQL{
public static void main(String[] args){
CosmosClient client = new CosmosClientBuilder()
.endpoint("<nosql-endpoint>")
.key("<key>")
.buildClient();
}
}
use azure_data_cosmos::CosmosClient;
fn main() {
let client = CosmosClient::new_with_access_key(
"<account-endpoint>",
"<account-key>",
None,
).unwrap();
let container = client.database_client("<database-name>").container_client("<container-name>");
let response = container.read_item("<partition-key>", "<item-id>", None);
tokio::runtime::Runtime::new().unwrap().block_on(response).unwrap();
}
Grant control plane role-based access
Control plane access refers to the ability to manage resources for an Azure service without managing data. For example, Azure Cosmos DB control plane access could include the ability to:
- Read all account and resource metadata
- Read and regenerate account keys and connection strings
- Perform account backups and restore
- Start and track data transfer jobs
- Manage databases and containers
- Modify account properties
Important
In Azure Cosmos DB, you need control plane access to manage native data-plane role-based access control definitions and assignments. Since Azure Cosmos DB's data plane role-based access control mechanism is native, you need control plane access to create definitions and assignments and store them as resources within an Azure Cosmos DB account.
First, you must prepare a role definition with a list of actions
to grant access to manage account resources in Azure Cosmos DB. In this guide, you prepare a built-in and custom role. Then, assign the newly defined role[s] to an identity so that your applications can access resources in Azure Cosmos DB.
List all of the role definitions associated with your Azure Cosmos DB account using
az role definition list
.az role definition list \ --name "Cosmos DB Operator"
Review the output and locate the role definition named Cosmos DB Operator. The output contains the unique identifier of the role definition in the
id
property. Record this value as it is required to use in the assignment step later in this guide.[ { "assignableScopes": [ "/" ], "description": "Lets you manage Azure Cosmos DB accounts, but not access data in them. Prevents access to account keys and connection strings.", "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/providers/Microsoft.Authorization/roleDefinitions/230815da-be43-4aae-9cb4-875f7bd000aa", "name": "230815da-be43-4aae-9cb4-875f7bd000aa", "permissions": [ { "actions": [ "Microsoft.DocumentDb/databaseAccounts/*", "Microsoft.Insights/alertRules/*", "Microsoft.Authorization/*/read", "Microsoft.ResourceHealth/availabilityStatuses/read", "Microsoft.Resources/deployments/*", "Microsoft.Resources/subscriptions/resourceGroups/read", "Microsoft.Support/*", "Microsoft.Network/virtualNetworks/subnets/joinViaServiceEndpoint/action" ], "condition": null, "conditionVersion": null, "dataActions": [], "notActions": [ "Microsoft.DocumentDB/databaseAccounts/dataTransferJobs/*", "Microsoft.DocumentDB/databaseAccounts/readonlyKeys/*", "Microsoft.DocumentDB/databaseAccounts/regenerateKey/*", "Microsoft.DocumentDB/databaseAccounts/listKeys/*", "Microsoft.DocumentDB/databaseAccounts/listConnectionStrings/*", "Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions/write", "Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions/delete", "Microsoft.DocumentDB/databaseAccounts/sqlRoleAssignments/write", "Microsoft.DocumentDB/databaseAccounts/sqlRoleAssignments/delete", "Microsoft.DocumentDB/databaseAccounts/mongodbRoleDefinitions/write", "Microsoft.DocumentDB/databaseAccounts/mongodbRoleDefinitions/delete", "Microsoft.DocumentDB/databaseAccounts/mongodbUserDefinitions/write", "Microsoft.DocumentDB/databaseAccounts/mongodbUserDefinitions/delete" ], "notDataActions": [] } ], "roleName": "Cosmos DB Operator", "roleType": "BuiltInRole", "type": "Microsoft.Authorization/roleDefinitions", } ]
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/providers/Microsoft.Authorization/roleDefinitions/230815da-be43-4aae-9cb4-875f7bd000aa
. This example uses fictitious data and your identifier would be distinct from this example. However, the identifier (230815da-be43-4aae-9cb4-875f7bd000aa
) is globally unique across all role definitions in Azure.Use
az group show
to get the metadata for your current resource group.az group show \ --name "<name-of-existing-resource-group>"
Observe the output of the previous command. Record the value of the
id
property for this resource group as it is required to use in the next step.{ "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example", "___location": "westus", "name": "msdocs-identity-example", "type": "Microsoft.Resources/resourceGroups" }
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example
. This example uses fictitious data and your identifier would be distinct from this example. This string is a truncated example of the output.Create a new JSON file named role-definition.json. In the file, create this resource definition specifying the values listed here. For the
AssignableScopes
list, add theid
property of the resource group recorded in the previous step.{ "Name": "Azure Cosmos DB Control Plane Owner", "IsCustom": true, "Description": "Can perform all control plane actions for an Azure Cosmos DB account.", "Actions": [ "Microsoft.DocumentDb/*" ], "AssignableScopes": [ "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example" ] }
Note
This example uses the
/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example
value recorded from the previous step. Your actual resource identifier could be different.Create a new role definition using
az role definition create
. Use the role-definition.json file as the input for the--role-definition
argument.az role definition create \ --role-definition role-definition.json
Review the output from the definition creation command. The output contains the unique identifier of the role definition in the
id
property. Record this value as it is required to use in the assignment step later in this guide.{ "assignableScopes": [ "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example" ], "description": "Can perform all control plane actions for an Azure Cosmos DB account.", "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleDefinitions/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1", "name": "e4e4e4e4-ffff-aaaa-bbbb-c5c5c5c5c5c5", "permissions": [ { "actions": [ "Microsoft.DocumentDb/*" ] } ], "roleName": "Azure Cosmos DB Control Plane Owner", "roleType": "CustomRole" }
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleDefinitions/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1
. This example uses fictitious data and your identifier would be distinct from this example. This example is a subset of the typical JSON outputted from the deployment for clarity.Use
az group show
to get the metadata for your current resource group again.az group show \ --name "<name-of-existing-resource-group>"
Observe the output of the previous command. Record the value of the
id
property for this resource group as it is required to use in the next step.{ "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example", "___location": "westus", "name": "msdocs-identity-example", "type": "Microsoft.Resources/resourceGroups" }
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example
. This example uses fictitious data and your identifier would be distinct from this example. This string is a truncated example of the output.Assign the new role using
az role assignment create
. Use your resource group's identifier for the--scope
argument, the role's identifier for the-role
argument, and the unique identifier for your identity to the--assignee
argument.az role assignment create \ --assignee "<your-principal-identifier>" \ --role "subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleDefinitions/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1" \ --scope "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example"
Note
In this example command, the
scope
was set to the fictitious example/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example
from the previous step's example. Your resource group's identifier would be distinct from this example. Therole
was also set to the fictitious/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleDefinitions/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1
. Again, your role identifier would be distinct.Observe the output from the command. The output includes a unique identifier for the assignment in the
id
property.{ "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleAssignments/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1", "name": "ffffffff-5555-6666-7777-aaaaaaaaaaaa", "principalId": "aaaaaaaa-bbbb-cccc-1111-222222222222", "resourceGroup": "msdocs-identity-example", "roleDefinitionId": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleDefinitions/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1", "scope": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example", "type": "Microsoft.Authorization/roleAssignments" }
Note
In this example, the
id
property is/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleAssignments/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1
, which is another fictitious example.Repeat these steps to grant access to the account from any other identities you would like to use.
Tip
You can repeat these steps for as many identities as you'd like. Typically, these steps are at least repeated to allow developers access to an account using their human identity and to allow applications access to the data using a managed identity.
List all of the role definitions associated with your Azure Cosmos DB account using
az role definition list
.az role definition list \ --name "Cosmos DB Operator"
Review the output and locate the role definition named Cosmos DB Operator. The output contains the unique identifier of the role definition in the
id
property. Record this value as it is required to use in the assignment step later in this guide.[ { "assignableScopes": [ "/" ], "description": "Lets you manage Azure Cosmos DB accounts, but not access data in them. Prevents access to account keys and connection strings.", "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/providers/Microsoft.Authorization/roleDefinitions/230815da-be43-4aae-9cb4-875f7bd000aa", "name": "230815da-be43-4aae-9cb4-875f7bd000aa", "permissions": [ { "actions": [ "Microsoft.DocumentDb/databaseAccounts/*", "Microsoft.Insights/alertRules/*", "Microsoft.Authorization/*/read", "Microsoft.ResourceHealth/availabilityStatuses/read", "Microsoft.Resources/deployments/*", "Microsoft.Resources/subscriptions/resourceGroups/read", "Microsoft.Support/*", "Microsoft.Network/virtualNetworks/subnets/joinViaServiceEndpoint/action" ], "condition": null, "conditionVersion": null, "dataActions": [], "notActions": [ "Microsoft.DocumentDB/databaseAccounts/dataTransferJobs/*", "Microsoft.DocumentDB/databaseAccounts/readonlyKeys/*", "Microsoft.DocumentDB/databaseAccounts/regenerateKey/*", "Microsoft.DocumentDB/databaseAccounts/listKeys/*", "Microsoft.DocumentDB/databaseAccounts/listConnectionStrings/*", "Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions/write", "Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions/delete", "Microsoft.DocumentDB/databaseAccounts/sqlRoleAssignments/write", "Microsoft.DocumentDB/databaseAccounts/sqlRoleAssignments/delete", "Microsoft.DocumentDB/databaseAccounts/mongodbRoleDefinitions/write", "Microsoft.DocumentDB/databaseAccounts/mongodbRoleDefinitions/delete", "Microsoft.DocumentDB/databaseAccounts/mongodbUserDefinitions/write", "Microsoft.DocumentDB/databaseAccounts/mongodbUserDefinitions/delete" ], "notDataActions": [] } ], "roleName": "Cosmos DB Operator", "roleType": "BuiltInRole", "type": "Microsoft.Authorization/roleDefinitions", } ]
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/providers/Microsoft.Authorization/roleDefinitions/230815da-be43-4aae-9cb4-875f7bd000aa
. This example uses fictitious data and your identifier would be distinct from this example. However, the identifier (230815da-be43-4aae-9cb4-875f7bd000aa
) is globally unique across all role definitions in Azure.Create a new Bicep file to define your role definition. Name the file control-plane-role-definition.bicep. Add these
actions
to the definition:Description Microsoft.DocumentDb/*
Enables all possible actions. metadata description = 'Create RBAC definition for control plane access to Azure Cosmos DB.' @description('Name of the role definition.') param roleDefinitionName string = 'Azure Cosmos DB Control Plane Owner' @description('Description of the role definition.') param roleDefinitionDescription string = 'Can perform all control plane actions for an Azure Cosmos DB account.' resource definition 'Microsoft.Authorization/roleDefinitions@2022-04-01' = { name: guid(subscription().id, resourceGroup().id, roleDefinitionName) scope: resourceGroup() properties: { roleName: roleDefinitionName description: roleDefinitionDescription type: 'CustomRole' permissions: [ { actions: [ 'Microsoft.DocumentDb/*' ] } ] assignableScopes: [ resourceGroup().id ] } } output definitionId string = definition.id
Deploy the Bicep template using
az deployment group create
. Specify the name of the Bicep template and Azure resource group.az deployment group create \ --resource-group "<name-of-existing-resource-group>" \ --template-file control-plane-role-definition.bicep
Review the output from the deployment. The output contains the unique identifier of the role definition in the
properties.outputs.definitionId.value
property. Record this value as it is required to use in the assignment step later in this guide.{ "properties": { "outputs": { "definitionId": { "type": "String", "value": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleDefinitions/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1" } } } }
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleDefinitions/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1
. This example uses fictitious data and your identifier would be distinct from this example. This example is a subset of the typical JSON outputted from the deployment for clarity.Create a new Bicep file to define your role assignment. Name the file control-plane-role-assignment.bicep.
metadata description = 'Assign RBAC role for control plane access to Azure Cosmos DB.' @description('Id of the role definition to assign to the targeted principal in the context of the account.') param roleDefinitionId string @description('Id of the identity/principal to assign this role in the context of the account.') param identityId string resource assignment 'Microsoft.Authorization/roleAssignments@2022-04-01' = { name: guid(subscription().id, resourceGroup().id, roleDefinitionId, identityId) scope: resourceGroup() properties: { roleDefinitionId: roleDefinitionId principalId: identityId } }
Create a new Bicep parameters file named control-plane-role-assignment.
bicepparam
. In this parameters file; assign the previously recorded role definition identifiers to theroleDefinitionId
parameter, and the unique identifier for your identity to theidentityId
parameter.using './control-plane-role-assignment.bicep' param roleDefinitionId = '<id-of-new-role-definition>' param identityId = '<id-of-existing-identity>'
Deploy this Bicep template using
az deployment group create
.az deployment group create \ --resource-group "<name-of-existing-resource-group>" \ --parameters control-plane-role-assignment.bicepparam \ --template-file control-plane-role-assignment.bicep
Repeat these steps to grant access to the account from any other identities you would like to use.
Tip
You can repeat these steps for as many identities as you'd like. Typically, these steps are at least repeated to allow developers access to an account using their human identity and to allow applications access to the data using a managed identity.
Sign in to the Azure portal (https://portal.azure.com).
Enter Resource group in the global search bar.
Within Services, select Resource groups.
In the Resource groups pane, select your existing resource group.
Note
This example screenshot includes the
msdocs-identity-example
resource group. Your actual resource group name could be different.Within the pane for the resource group, select Access control (IAM) in the service menu.
In the Access control (IAM) pane, select Roles.
In the Roles section, use the search phrase Cosmos DB and locate the Cosmos DB Operator role definition. Then, select the View option associated with that definition.
In the Cosmos DB Operator role definition dialog, observe the actions assigned as part of this role definition.
Close the Cosmos DB Operator role definition dialog.
Back in the Access control (IAM) pane, select Add. Then select Add custom role.
Within the Basics pane, configure the following options, and then select Next:
Value Custom role name Azure Cosmos DB Control Plane Owner
Description Can perform all control plane actions for an Azure Cosmos DB account.
Baseline permissions Start from scratch In the Permissions pane, select Add permissions. Then, search for
DocumentDB
in the permissions dialog. Finally, select the Microsoft.DocumentDB option.In the permissions dialog, select all Actions for
Microsoft.DocumentDB
. Then, select Add to return to the *Permissions pane.Back in the Permissions pane, observe the list of permissions. Then, select Review + create.
In the Review + create pane, review the specified options for the new role definition. Finally, select Create.
Wait for the portal to finish creating the role definition.
In the Access control (IAM) pane, select Add and then Add role assignment.
In the Role pane, search for
Azure Cosmos DB
and then select the Azure Cosmos DB Control Plane Owner role created earlier in this guide. Then, select Next.Tip
You can optionally filter the list of roles to only include custom roles.
In the Members pane, select the Select members option. In the members dialog, select the identity you wish to grant this level of access for your Azure Cosmos DB account and then use the Select option to confirm your choice.
Note
This screenshot illustrates an example user named "Kai Carter" with a principal of
kai@adventure-works.com
.Back in the Members pane, review the selected member[s] and then select Review + assign.
In the Review + assign pane, review the specified options for the new role assignment. Finally, select Review + assign.
Wait for the portal to finish creating the role assignment.
Use
Get-AzRoleDefinition
to list all of the role definitions associated with your Azure Cosmos DB account.$parameters = @{ Name = "Cosmos DB Operator" } Get-AzRoleDefinition @parameters
Review the output and locate the role definition named Cosmos DB Built-in Data Contributor. The output contains the unique identifier of the role definition in the
Id
property. Record this value as it is required to use in the assignment step later in this guide.Name : Cosmos DB Operator Id : 230815da-be43-4aae-9cb4-875f7bd000aa IsCustom : False Description : Lets you manage Azure Cosmos DB accounts, but not access data in them. Prevents access to account keys and connection strings. Actions : {Microsoft.DocumentDb/databaseAccounts/*, Microsoft.Insights/alertRules/*, Microsoft.Authorization/*/read, Microsoft.ResourceHealth/availabilityStatuses/read…} NotActions : {Microsoft.DocumentDB/databaseAccounts/dataTransferJobs/*, Microsoft.DocumentDB/databaseAccounts/readonlyKeys/*, Microsoft.DocumentDB/databaseAccounts/regenerateKey/*, Microsoft.DocumentDB/databaseAccounts/listKeys/*…} DataActions : {} NotDataActions : {} AssignableScopes : {/}
Note
In this example, the
Id
value would be230815da-be43-4aae-9cb4-875f7bd000aa
. The identifier is globally unique across all role definitions in Azure.Use
Get-AzResourceGroup
to get the metadata for your current resource group.$parameters = @{ Name = "<name-of-existing-resource-group>" } Get-AzResourceGroup @parameters
Observe the output of the previous command. Record the value of the
ResourceId
property for this resource group as it is required to use in the next step.ResourceGroupName : msdocs-identity-example Location : westus ProvisioningState : Succeeded ResourceId : /subscriptions/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1/resourcegroups/msdocs-identity-example
Note
In this example, the
ResourceId
value would be/subscriptions/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1/resourcegroups/msdocs-identity-example
. This example uses fictitious data and your identifier would be distinct from this example. This string is a truncated example of the typical output.First, import the
Az.Resources
module. Then, Create a newMicrosoft.Azure.Commands.Resources.Models.Authorization.PSRoleDefinition
object. In the object, create this resource definition specifying the values listed here. For theAssignableScopes
list, add theResourceId
property of the resource group recorded in the previous step. Finally, use the role definition object as the input for the-Role
parameter ofNew-AzRoleDefinition
.Import-Module Az.Resources $parameters = @{ TypeName = "Microsoft.Azure.Commands.Resources.Models.Authorization.PSRoleDefinition" Property = @{ Name = "Azure Cosmos DB Control Plane Owner" Description = "Can perform all control plane actions for an Azure Cosmos DB account." IsCustom = $true Actions = @( "Microsoft.DocumentDb/*" ) AssignableScopes = @( "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example" ) } } $role = New-Object @parameters New-AzRoleDefinition -Role $role
Note
This example uses the
/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example
value recorded from the previous step. Your actual resource identifier could be different.Review the output from the definition creation command. The output contains the unique identifier of the role definition in the
Name
property. Record this value as it is required to use in the assignment step later in this guide.Name : Azure Cosmos DB Control Plane Owner Id : e4e4e4e4-ffff-aaaa-bbbb-c5c5c5c5c5c5 IsCustom : True Description : Can perform all control plane actions for an Azure Cosmos DB account. Actions : {Microsoft.DocumentDb/*} AssignableScopes : {/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example}
Note
In this example, the
Name
value would beAzure Cosmos DB Control Plane Owner
. This example is a subset of the typical output of the deployment for clarity.Assign the new role using
New-AzRoleAssignment
. Use the role's name for theRoleDefinitionName
parameter and the unique identifier for your identity to theObjectId
parameter.$parameters = @{ ResourceGroupName = "<name-of-existing-resource-group>" ObjectId = "<your-principal-identifier>" RoleDefinitionName = "Azure Cosmos DB Control Plane Owner" } New-AzRoleAssignment @parameters
Observe the output from the command. The output includes a unique identifier for the assignment in the
RoleAssignmentId
property.RoleAssignmentName : ffffffff-5555-6666-7777-aaaaaaaaaaaa RoleAssignmentId : /subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleAssignments/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1 Scope : /subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example DisplayName : Kai Carter SignInName : <kai@adventure-works.com> RoleDefinitionName : Azure Cosmos DB Control Plane Owner RoleDefinitionId : e4e4e4e4-ffff-aaaa-bbbb-c5c5c5c5c5c5
Note
In this example, the
RoleAssignmentId
property is/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.Authorization/roleAssignments/a0a0a0a0-bbbb-cccc-dddd-e1e1e1e1e1e1
, which is another fictitious example. This example is a subset of the typical output of the deployment for clarity.Repeat these steps to grant access to the account from any other identities you would like to use.
Tip
You can repeat these steps for as many identities as you'd like. Typically, these steps are at least repeated to allow developers access to an account using their human identity and to allow applications access to the data using a managed identity.
Important
Assigning a role definition requires you to already have the unique identifier of any identity you want to grant role-based access control permissions.
Validate control plane role-based access in code
Validate that you correctly granted access using application code and the Azure Management SDK.
using Azure.Identity;
using Azure.ResourceManager;
DefaultAzureCredential credential = new();
ArmClient client = new(credential);
const { CosmosDBManagementClient } = require('@azure/arm-cosmosdb');
const { DefaultAzureCredential } = require('@azure/identity');
const subscriptionId = "<subscription-id>";
const credential = new DefaultAzureCredential();
const client = new CosmosDBManagementClient(credential, subscriptionId);
import { CosmosDBManagementClient } from '@azure/arm-cosmosdb';
import { TokenCredential, DefaultAzureCredential } from '@azure/identity';
let subscriptionId: string = "<subscription-id>";
let credential: TokenCredential = new DefaultAzureCredential();
const client: CosmosDBManagementClient = new CosmosDBManagementClient(credential, subscriptionId);
from azure.mgmt.cosmosdb import CosmosDBManagementClient
from azure.identity import DefaultAzureCredential
subscription_id = "<subscription-id>"
credential = DefaultAzureCredential()
client = CosmosDBManagementClient(credential=credential, subscription=subscription_id)
package main
import (
"github.com/Azure/azure-sdk-for-go/sdk/azidentity"
"github.com/Azure/azure-sdk-for-go/sdk/resourcemanager/cosmos/armcosmos"
)
const subscriptionId = "<subscription-id>"
func main() {
credential, _ := azidentity.NewDefaultAzureCredential(nil)
client, _ := armcosmos.NewDatabaseClient(subscriptionId, credential, nil)
}
package com.example;
import com.azure.core.management.profile.AzureProfile;
import com.azure.core.management.AzureEnvironment;
import com.azure.identity.DefaultAzureCredential;
import com.azure.identity.DefaultAzureCredentialBuilder;
import com.azure.resourcemanager.cosmos.CosmosManager;
public class CosmosDB {
public static void main(String[] args) {
AzureProfile profile = new AzureProfile(AzureEnvironment.AZURE);
DefaultAzureCredential credential = new DefaultAzureCredentialBuilder()
.build();
CosmosManager manager = CosmosManager.authenticate(credential, profile);
}
}
Grant data plane role-based access
Data plane access refers to the ability to read and write data within an Azure service without the ability to manage resources in the account. For example, Azure Cosmos DB data plane access could include the ability to:
- Read some account and resource metadata
- Create, read, update, patch, and delete items
- Execute NoSQL queries
- Read from a container's change feed
- Execute stored procedures
- Manage conflicts in the conflict feed
First, you must prepare a role definition with a list of dataActions
to grant access to read, query, and manage data in Azure Cosmos DB for NoSQL. In this guide, you prepare a built-in and custom role. Then, assign the newly defined role[s] to an identity so that your applications can access data in Azure Cosmos DB for NoSQL.
Important
Obtaining an existing data plane role definition requires these control plane permissions:
Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions/read
Creating a new data plane role definition requires these control plane permissions:
Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions/read
Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions/write
Creating a new data plane role assignment requires these control plane permissions:
Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions/read
Microsoft.DocumentDB/databaseAccounts/sqlRoleAssignments/read
Microsoft.DocumentDB/databaseAccounts/sqlRoleAssignments/write
Warning
Azure Cosmos DB for NoSQL's native role-based access control doesn't support the notDataActions
property. Any action that isn't specified as an allowed dataAction
is excluded automatically.
List all of the role definitions associated with your Azure Cosmos DB for NoSQL account using
az cosmosdb sql role definition list
.az cosmosdb sql role definition list \ --resource-group "<name-of-existing-resource-group>" \ --account-name "<name-of-existing-nosql-account>"
Review the output and locate the role definition named Cosmos DB Built-in Data Contributor. The output contains the unique identifier of the role definition in the
id
property. Record this value as it is required to use in the assignment step later in this guide.[ ..., { "assignableScopes": [ "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql" ], "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/00000000-0000-0000-0000-000000000002", "name": "00000000-0000-0000-0000-000000000002", "permissions": [ { "dataActions": [ "Microsoft.DocumentDB/databaseAccounts/readMetadata", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*" ], "notDataActions": [] } ], "resourceGroup": "msdocs-identity-example", "roleName": "Cosmos DB Built-in Data Contributor", "type": "Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions", "typePropertiesType": "BuiltInRole" } ... ]
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/00000000-0000-0000-0000-000000000002
. This example uses fictitious data and your identifier would be distinct from this example.Create a new JSON file named role-definition.json. In this file, create a resource definition specifying the data actions listed here:
Description Microsoft.DocumentDB/databaseAccounts/readMetadata
Can read account-level metadata Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*
Can perform any container-level data operations Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*
Can perform any operation on items with containers { "RoleName": "Azure Cosmos DB for NoSQL Data Plane Owner", "Type": "CustomRole", "AssignableScopes": [ "/" ], "Permissions": [ { "DataActions": [ "Microsoft.DocumentDB/databaseAccounts/readMetadata", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*" ] } ] }
Next, use
az cosmosdb sql role definition create
to create the role definition. Use the role-definition.json as the input for the--body
argument.az cosmosdb sql role definition create \ --resource-group "<name-of-existing-resource-group>" \ --account-name "<name-of-existing-nosql-account>" \ --body "@role-definition.json"
Now, list all of the role definitions associated with your Azure Cosmos DB for NoSQL account using
az cosmosdb sql role definition list
.az cosmosdb sql role definition list \ --resource-group "<name-of-existing-resource-group>" \ --account-name "<name-of-existing-nosql-account>"
Review the output from the previous command. Locate the role definition you just created named Azure Cosmos DB for NOSQL Data Plane Owner. The output contains the unique identifier of the role definition in the
id
property. Record this value as it is required to use in the assignment step later in this guide.{ "assignableScopes": [ "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql" ], "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/bbbbbbbb-1111-2222-3333-cccccccccccc", "name": "bbbbbbbb-1111-2222-3333-cccccccccccc", "permissions": [ { "dataActions": [ "Microsoft.DocumentDB/databaseAccounts/readMetadata", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*" ], "notDataActions": [] } ], "resourceGroup": "msdocs-identity-example", "roleName": "Azure Cosmos DB for NoSQL Data Plane Owner", "type": "Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions", "typePropertiesType": "CustomRole" }
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/bbbbbbbb-1111-2222-3333-cccccccccccc
. This example uses fictitious data and your identifier would be distinct from this example.Use
az cosmosdb show
to get the unique identifier for your current account.az cosmosdb show \ --resource-group "<name-of-existing-resource-group>" \ --name "<name-of-existing-nosql-account>" \ --query "{id:id}"
Observe the output of the previous command. Record the value of the
id
property for this account as it is required to use in the next step.{ "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql" }
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql
. This example uses fictitious data and your identifier would be distinct from this example.Assign the new role using
az cosmosdb sql role assignment create
. Use the previously recorded role definition identifiers to the--role-definition-id
argument, and the unique identifier for your identity to the--principal-id
argument. Finally, use your account's identifier for the--scope
argument.az cosmosdb sql role assignment create \ --resource-group "<name-of-existing-resource-group>" \ --account-name "<name-of-existing-nosql-account>" \ --role-definition-id "<id-of-new-role-definition>" \ --principal-id "<id-of-existing-identity>" \ --scope "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql"
Tip
If you're attempting to grant data plane role-based access control to your own identity, you can use this command to get the identity:
az ad signed-in-user show
For more information, see
az ad signed-in-user
.Tip
In Azure Cosmos DB's native implementation of role-based access control, scope refers to the granularity of resources within an account for which you want permission applied. At the highest level, you can scope a data plane role-based access control assignment to the entire account using the largest scope. This scope includes all databases and containers within the account:
/subscriptions/<subscription-id>/resourcegroups/<resource-group-name>/providers/Microsoft.DocumentDB/databaseAccounts/<account-name>/
Or, you can scope your data plane role assignment to a specific database:
/subscriptions/<subscription-id>/resourcegroups/<resource-group-name>/providers/Microsoft.DocumentDB/databaseAccounts/<account-name>/dbs/<database-name>
Finally, you can scope the assignment to a single container, the most granular scope:
/subscriptions/<subscription-id>/resourcegroups/<resource-group-name>/providers/Microsoft.DocumentDB/databaseAccounts/<account-name>/dbs/<database-name>/colls/<container-name>
In many cases, you can use the relative scope instead of the fully qualified scope. For example, you can use this relative scope to grant data plane role-based access control permissions to a specific database and container from an Azure CLI command:
/dbs/<database-name>/colls/<container-name>
You can also grant universal access to all databases and containers using the relative scope:
/
Use
az cosmosdb sql role assignment list
to list all role assignments for your Azure Cosmos DB for NoSQL account. Review the output to ensure your role assignment was created.az cosmosdb sql role assignment list \ --resource-group "<name-of-existing-resource-group>" \ --account-name "<name-of-existing-nosql-account>"
List all of the role definitions associated with your Azure Cosmos DB for NoSQL account using
az cosmosdb sql role definition list
.az cosmosdb sql role definition list \ --resource-group "<name-of-existing-resource-group>" \ --account-name "<name-of-existing-nosql-account>"
Review the output and locate the role definition named Cosmos DB Built-in Data Contributor. The output contains the unique identifier of the role definition in the
id
property. Record this value as it is required to use in the assignment step later in this guide.[ ..., { "assignableScopes": [ "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql" ], "id": "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/00000000-0000-0000-0000-000000000002", "name": "00000000-0000-0000-0000-000000000002", "permissions": [ { "dataActions": [ "Microsoft.DocumentDB/databaseAccounts/readMetadata", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*" ], "notDataActions": [] } ], "resourceGroup": "msdocs-identity-example", "roleName": "Cosmos DB Built-in Data Contributor", "type": "Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions", "typePropertiesType": "BuiltInRole" } ... ]
Note
In this example, the
id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/00000000-0000-0000-0000-000000000002
. This example uses fictitious data and your identifier would be distinct from this example.Create a new Bicep file to define your role definition. Name the file data-plane-role-definition.bicep. Add these
dataActions
to the definition:Description Microsoft.DocumentDB/databaseAccounts/readMetadata
Can read account-level metadata Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*
Can perform any container-level data operations Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*
Can perform any operation on items with containers metadata description = 'Create RBAC definition for data plane access to Azure Cosmos DB for NoSQL.' @description('Name of the Azure Cosmos DB for NoSQL account.') param accountName string @description('Name of the role definition.') param roleDefinitionName string = 'Azure Cosmos DB for NoSQL Data Plane Owner' resource account 'Microsoft.DocumentDB/databaseAccounts@2024-05-15' existing = { name: accountName } resource definition 'Microsoft.DocumentDB/databaseAccounts/sqlRoleDefinitions@2024-05-15' = { name: guid(account.id, roleDefinitionName) parent: account properties: { roleName: roleDefinitionName type: 'CustomRole' assignableScopes: [ account.id ] permissions: [ { dataActions: [ 'Microsoft.DocumentDB/databaseAccounts/readMetadata' 'Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*' 'Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*' ] } ] } } output definitionId string = definition.id
Tip
In Azure Cosmos DB's native implementation of role-based access control, scope refers to the granularity of resources within an account for which you want permission applied. At the highest level, you can scope a data plane role-based access control assignment to the entire account using the largest scope. This scope includes all databases and containers within the account:
/subscriptions/<subscription-id>/resourcegroups/<resource-group-name>/providers/Microsoft.DocumentDB/databaseAccounts/<account-name>/
Or, you can scope your data plane role assignment to a specific database:
/subscriptions/<subscription-id>/resourcegroups/<resource-group-name>/providers/Microsoft.DocumentDB/databaseAccounts/<account-name>/dbs/<database-name>
Finally, you can scope the assignment to a single container, the most granular scope:
/subscriptions/<subscription-id>/resourcegroups/<resource-group-name>/providers/Microsoft.DocumentDB/databaseAccounts/<account-name>/dbs/<database-name>/colls/<container-name>
In many cases, you can use the relative scope instead of the fully qualified scope. For example, you can use this relative scope to grant data plane role-based access control permissions to a specific database and container from an Azure CLI command:
/dbs/<database-name>/colls/<container-name>
You can also grant universal access to all databases and containers using the relative scope:
/
Create a new Bicep parameters file named data-plane-role-definition.
bicepparam
. In this parameters file, assign the name of your existing Azure Cosmos DB for NoSQL account to theaccountName
parameter.using './data-plane-role-definition.bicep' param accountName = '<name-of-existing-nosql-account>'
Deploy the Bicep template using
az deployment group create
.az deployment group create \ --resource-group "<name-of-existing-resource-group>" \ --parameters data-plane-role-definition.bicepparam \ --template-file data-plane-role-definition.bicep
Create a new Bicep file to define your role assignment. Name the file data-plane-role-assignment.bicep.
metadata description = 'Assign RBAC role for data plane access to Azure Cosmos DB for NoSQL.' @description('Name of the Azure Cosmos DB for NoSQL account.') param accountName string @description('Id of the role definition to assign to the targeted principal in the context of the account.') param roleDefinitionId string @description('Id of the identity/principal to assign this role in the context of the account.') param identityId string = deployer().objectId resource account 'Microsoft.DocumentDB/databaseAccounts@2024-05-15' existing = { name: accountName } resource assignment 'Microsoft.DocumentDB/databaseAccounts/sqlRoleAssignments@2024-05-15' = { name: guid(roleDefinitionId, identityId, account.id) parent: account properties: { principalId: identityId roleDefinitionId: roleDefinitionId scope: account.id } } output assignmentId string = assignment.id
Create a new Bicep parameters file named data-plane-role-assignment.
bicepparam
. In this parameters file, assign the name of your existing Azure Cosmos DB for NoSQL account to theaccountName
parameter, the previously recorded role definition identifiers to theroleDefinitionId
parameter, and the unique identifier for your identity to theidentityId
parameter.using './data-plane-role-assignment.bicep' param accountName = '<name-of-existing-nosql-account>' param roleDefinitionId = '<id-of-new-role-definition>' param identityId = '<id-of-existing-identity>'
Tip
If you're attempting to grant data plane role-based access control to your own identity, you can omit the
identityId
parameter. The Bicep template then usesdeployer().objectId
to get the identity of the principal that deployed the template. For more information, seedeployer
.Deploy the Bicep template using
az deployment group create
.az deployment group create \ --resource-group "<name-of-existing-resource-group>" \ --parameters data-plane-role-assignment.bicepparam \ --template-file data-plane-role-assignment.bicep
Repeat these steps to grant access to the account from any other identities you would like to use.
Tip
You can repeat these steps for as many identities as you'd like. Typically, these steps are at least repeated to allow developers access to an account using their human identity. You can also repeat these steps to allow applications to access resources using a managed identity.
Use
Get-AzCosmosDBSqlRoleDefinition
to list all of the role definitions associated with your Azure Cosmos DB for NoSQL account.$parameters = @{ ResourceGroupName = "<name-of-existing-resource-group>" AccountName = "<name-of-existing-nosql-account>" } Get-AzCosmosDBSqlRoleDefinition @parameters
Review the output and locate the role definition named Cosmos DB Built-in Data Contributor. The output contains the unique identifier of the role definition in the
Id
property. Record this value as it is required to use in the assignment step later in this guide.Id : /subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/00000000-0000-0000-0000-000000000002 RoleName : Cosmos DB Built-in Data Contributor Type : BuiltInRole AssignableScopes : {/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccountsmsdocs-identity-example-nosql} Permissions.DataActions : {Microsoft.DocumentDB/databaseAccounts/readMetadata, Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*, Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*} Permissions.NotDataActions :
Note
In this example, the
Id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/00000000-0000-0000-0000-000000000002
. This example uses fictitious data and your identifier would be distinct from this example. However, the identifier (00000000-0000-0000-0000-000000000002
) is unique across all role definitions in your account.Create a new role definition using
New-AzCosmosDBSqlRoleDefinition
. For theDataAction
parameter, specify the data actions listed here:Description Microsoft.DocumentDB/databaseAccounts/readMetadata
Can read account-level metadata Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*
Can perform any container-level data operations Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*
Can perform any operation on items with containers $parameters = @{ ResourceGroupName = "<name-of-existing-resource-group>" AccountName = "<name-of-existing-nosql-account>" RoleName = "Azure Cosmos DB for NoSQL Data Plane Owner" Type = "CustomRole" AssignableScope = @( "/" ) DataAction = @( "Microsoft.DocumentDB/databaseAccounts/readMetadata", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*", "Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*" ) } New-AzCosmosDBSqlRoleDefinition @parameters
Tip
In Azure Cosmos DB's native implementation of role-based access control, scope refers to the granularity of resources within an account for which you want permission applied. At the highest level, you can scope a data plane role-based access control assignment to the entire account using the largest scope. This scope includes all databases and containers within the account:
/subscriptions/<subscription-id>/resourcegroups/<resource-group-name>/providers/Microsoft.DocumentDB/databaseAccounts/<account-name>/
Or, you can scope your data plane role assignment to a specific database:
/subscriptions/<subscription-id>/resourcegroups/<resource-group-name>/providers/Microsoft.DocumentDB/databaseAccounts/<account-name>/dbs/<database-name>
Finally, you can scope the assignment to a single container, the most granular scope:
/subscriptions/<subscription-id>/resourcegroups/<resource-group-name>/providers/Microsoft.DocumentDB/databaseAccounts/<account-name>/dbs/<database-name>/colls/<container-name>
In many cases, you can use the relative scope instead of the fully qualified scope. For example, you can use this relative scope to grant data plane role-based access control permissions to a specific database and container from an Azure CLI command:
/dbs/<database-name>/colls/<container-name>
You can also grant universal access to all databases and containers using the relative scope:
/
Use
Get-AzCosmosDBSqlRoleDefinition
to list all of the role definitions associated with your Azure Cosmos DB for NoSQL account.$parameters = @{ ResourceGroupName = "<name-of-existing-resource-group>" AccountName = "<name-of-existing-nosql-account>" } Get-AzCosmosDBSqlRoleDefinition @parameters
Review the output from the previous command. Locate the role definition you just created named Azure Cosmos DB for NOSQL Data Plane Owner. The output contains the unique identifier of the role definition in the
Id
property. Record this value as it is required to use in the assignment step later in this guide.Id : /subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/bbbbbbbb-1111-2222-3333-cccccccccccc RoleName : Azure Cosmos DB for NoSQL Data Plane Owner Type : CustomRole AssignableScopes : {/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql} Permissions.DataActions : {Microsoft.DocumentDB/databaseAccounts/readMetadata, Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/items/*, Microsoft.DocumentDB/databaseAccounts/sqlDatabases/containers/*} Permissions.NotDataActions :
Note
In this example, the
Id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourcegroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql/sqlRoleDefinitions/bbbbbbbb-1111-2222-3333-cccccccccccc
. This example uses fictitious data and your identifier would be distinct from this example.Use
Get-AzCosmosDBAccount
to get the metadata for your current account.$parameters = @{ ResourceGroupName = "<name-of-existing-resource-group>" Name = "<name-of-existing-nosql-account>" } Get-AzCosmosDBAccount @parameters | Select -Property Id
Observe the output of the previous command. Record the value of the
Id
property for this account as it is required to use in the next step.Id -- /subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql
Note
In this example, the
Id
value would be/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql
. This example uses fictitious data and your identifier would be distinct from this example.Use
New-AzCosmosDBSqlRoleAssignment
to assign the new role. Use the previously recorded role definition identifiers to theRoleDefinitionId
parameter, and the unique identifier for your identity to thePrincipalId
parameter. Finally, use your account's identifier for theScope
parameter.$parameters = @{ ResourceGroupName = "<name-of-existing-resource-group>" AccountName = "<name-of-existing-nosql-account>" RoleDefinitionId = "<id-of-new-role-definition>" PrincipalId = "<id-of-existing-identity>" Scope = "/subscriptions/aaaa0a0a-bb1b-cc2c-dd3d-eeeeee4e4e4e/resourceGroups/msdocs-identity-example/providers/Microsoft.DocumentDB/databaseAccounts/msdocs-identity-example-nosql" } New-AzCosmosDBSqlRoleAssignment @parameters
Tip
If you're attempting to grant data plane role-based access control to your own identity, you can use this command to get the identity:
Get-AzADUser -SignedIn | Format-List ` -Property Id, DisplayName, Mail, UserPrincipalName
For more information, see
Get-AzADUser
.List all role assignments for your Azure Cosmos DB for NoSQL account using
Get-AzCosmosDBSqlRoleAssignment
. Review the output to ensure your role assignment was created.$parameters = @{ ResourceGroupName = "<name-of-existing-resource-group>" AccountName = "<name-of-existing-nosql-account>" } Get-AzCosmosDBSqlRoleAssignment @parameters
Warning
Managing data plane role-based access control isn't supported in the Azure portal.
Validate data plane role-based access in code
Validate that you correctly granted access using application code and the Azure SDK.
using Azure.Core;
using Azure.Identity;
using Microsoft.Azure.Cosmos;
string endpoint = "<account-endpoint>";
TokenCredential credential = new DefaultAzureCredential();
CosmosClient client = new(endpoint, credential);
Container container = client.GetContainer("<database-name>", "<container-name>");
await container.ReadItemAsync<dynamic>("<item-id>", new PartitionKey("<partition-key>"));
const { CosmosClient } = require('@azure/cosmos');
const { DefaultAzureCredential } = require('@azure/identity');
const endpoint = '<account-endpoint>';
const credential = new DefaultAzureCredential();
const client = new CosmosClient({ endpoint, aadCredentials:credential});
const container = client.database('<database-name>').container('<container-name>');
await container.item('<item-id>', '<partition-key>').read<String>();
import { Container, CosmosClient, CosmosClientOptions } from '@azure/cosmos'
import { TokenCredential, DefaultAzureCredential } from '@azure/identity'
let endpoint: string = '<account-endpoint>';
let credential: TokenCredential = new DefaultAzureCredential();
let options: CosmosClientOptions = {
endpoint: endpoint,
aadCredentials: credential
};
const client: CosmosClient = new CosmosClient(options);
const container: Container = client.database('<database-name>').container('<container-name>');
await container.item('<item-id>', '<partition-key>').read<String>();
from azure.cosmos import CosmosClient
from azure.identity import DefaultAzureCredential
endpoint = "<account-endpoint>"
credential = DefaultAzureCredential()
client = CosmosClient(endpoint, credential=credential)
container = client.get_database_client("<database-name>").get_container_client("<container-name>")
container.read_item(
item="<item-id>",
partition_key="<partition-key>",
)
import (
"context"
"github.com/Azure/azure-sdk-for-go/sdk/azidentity"
"github.com/Azure/azure-sdk-for-go/sdk/data/azcosmos"
)
const endpoint = "<account-endpoint>"
func main() {
credential, _ := azidentity.NewDefaultAzureCredential(nil)
client, _ := azcosmos.NewClient(endpoint, credential, nil)
database, _ := client.NewDatabase("<database-name>")
container, _ := database.NewContainer("<container-name>")
_, err := container.ReadItem(context.TODO(), azcosmos.NewPartitionKeyString("<partition-key>"), "<item-id>", nil)
if err != nil {
panic(err)
}
}
import com.azure.cosmos.CosmosClient;
import com.azure.cosmos.CosmosClientBuilder;
import com.azure.cosmos.CosmosContainer;
import com.azure.cosmos.models.PartitionKey;
import com.azure.identity.DefaultAzureCredential;
import com.azure.identity.DefaultAzureCredentialBuilder;
public class NoSQL {
public static void main(String[] args) {
DefaultAzureCredential credential = new DefaultAzureCredentialBuilder()
.build();
CosmosClient client = new CosmosClientBuilder()
.endpoint("<account-endpoint>")
.credential(credential)
.buildClient();
CosmosContainer container = client.getDatabase("<database-name>").getContainer("<container-name>");
container.readItem("<item-id>", new PartitionKey("<partition-key>"), Object.class);
}
}
use azure_data_cosmos::CosmosClient;
use azure_identity::DefaultAzureCredential;
fn main() {
let credential = DefaultAzureCredential::new().unwrap();
let client = CosmosClient::new("<account-endpoint>", credential, None).unwrap();
let container = client.database_client("<database-name>").container_client("<container-name>");
let response = container.read_item("<partition-key>", "<item-id>", None);
tokio::runtime::Runtime::new().unwrap().block_on(response).unwrap();
}