Unable to programmatically get the keys for Azure Storage Account - azure

I am trying to get the keys for all the Storage Accounts in my subscription. But I am getting this exception on one of the Storage Account using Azure Java SDK.
com.microsoft.azure.CloudException: Status code 403, {"error":{"code":"AuthorizationFailed","message":"The client '5c79ee27-#########-######91f8e3' with object id '5c79ee27-###########-#####91f8e3' does not have authorization to perform action 'Microsoft.Storage/storageAccounts/listKeys/action' over scope '/subscriptions/758ad253-#######f07/resourceGroups/spcwestus/providers/Microsoft.Storage/storageAccounts/grsstorag'."}}: The client '5c79ee27-###########-#####91f8e3' with object id '5c79ee27-###########-#####91f8e3' does not have authorization to perform action 'Microsoft.Storage/storageAccounts/listKeys/action' over scope '/subscriptions/758ad253-#######f07/resourceGroups/spcwestus/providers/Microsoft.Storage/storageAccounts/grsstorag'.
For most of the Storage Accounts I manage to get the keys. But for some of them the same error gets repeated. What does this mean?

From the error you encountered, the server responded to your requests with HTTP 403 status code indicates that your request is Forbidden by the server.
HTTP 403 Status Code
A server that receives valid credentials that are not adequate to
gain access ought to respond with the 403 (Forbidden) status code
(Section 6.5.3 of [RFC7231]).
This is most probably caused by some Role-Based Access Controls that are in place to prevent your account to perform the list storage account key actions for certain storage accounts based on your assigned role.
You can use the Azure PowerShell cmdlet below to verify whether the role assigned to your specific object under the specific scope has the permission to list the storage account keys.
Get-AzureRmRoleAssignment -Scope "/subscriptions/758ad253-#######f07/resourceGroups/spcwestus/providers/Microsoft.Storage/storageAccounts/grsstorag" -ObjectId 5c79ee27-###########-#####91f8e3
More information please refer to the link below:
Use Role-Based Access Control to manage access to your Azure subscription resources

Maybe as addition above. Azure has the Storage Account Key Operator Service Role which is describes at the following:
Storage Account Key Operators are allowed to list and regenerate keys on Storage Accounts
Granting you this role should allow to list the keys.

Related

Download Azure Blob using HTTP Basic Auth using Azure AD Credentials

I have an Azure Storage Account with public access disabled. Inside the storage account are a few Blob Storage Containers. Each container has access managed with AzureAD with varying permissions for each user/group to different Blob Containers.
I want to be able to download items inside the Blob Storage using tools like wget or curl using HTTP Basic Auth or specifying user information in the request.
I'm aware that AzCopy can be used to download Blobs from the containers, but previously we have used http requests to download artifacts and would like to continue using that method.
This question from 2016 Makes it seem like that its possible to do this with Shared Access Signature, which makes me believe that its possible to use with User Delegation SAS, but I have not found a way to set this up, and it requires a lot of parameters, more than a username/password or token.
Does Azure Blob Storage have a way where a user can access blob storage without AzCopy or any other specialized tools and authenticate via a method that does not require additional resources?
No. You must make a separate request for a token to send to Blob.
When a security principal (a user, group, or application) attempts to
access a blob resource, the request must be authorized, unless it is a
blob available for anonymous access. With Azure AD, access to a
resource is a two-step process. First, the security principal's
identity is authenticated and an OAuth 2.0 token is returned. Next,
the token is passed as part of a request to the Blob service and used
by the service to authorize access to the specified resource.
The authentication step requires that an application request an OAuth
2.0 access token at runtime.
Overview of Azure AD for blobs

Get access to Azure Blob storage and Key Vault from Azure ad B2C account

i'm new in Azure. And if the question is stupid don't punish me.
I made an App in Azure to get access to storage blob and key vault.
I used Azure AD tenant(with AD users) and user_impersonation scopes like https://storage.azure.com/user_impersonation and https://vault.azure.net/user_impersonation
All I need from that App is:
Upload file to Blob
Download file from Blob
Delete file from Blob
Generate SAS
Get value of secret from Key Vault.
In Azure AD tenant it works fine. I can request to login.microsoftonline.com enter credentials and get token to my back-end to do all this things listed above.But later customer desided to use custom UX(to hide Microsoft login page) and only one way to get this is to use B2C and local accounts.
I made a B2C tenant like here tutorial-create-tenant
Registered App like here tutorial-register-applications and add Api permissions to Azure Storage from APIs my organization uses tab
Created user-flows like here user-flows
All local users in one group with Owner policy
Using this request i got a token
https:/<domain_name>.b2clogin.com/<domain_name>.onmicrosoft.com/oauth2/v2.0/authorize?
p=B2C_1_signin&
client_id=<App_ID>&
nonce=defaultNonce&
redirect_uri=https%3A%2F%2Fjwt.ms%2F& // https://jwt.ms/
scope=https%3A%2F%2Fstorage.azure.com%2Fuser_impersonation& // https://storage.azure.com/user_impersonation
response_type=token&
prompt=login
In decoded token claim "aud" has id the same as Azure Storage API from APIs my organization uses tab when I register App, "scp" is "user_impersonation". But using this token i can't get access to storage using Postman (I use it as Bearer token)
For example GET request to https://.blob.core.windows.net/?comp=list must return json with list of containers(and in Azure AD it work) but with this token got an error
<Error>
<Code>AuthenticationFailed</Code>
<Message>Server failed to authenticate the request. Make sure the value of Authorization header is formed correctly including the signature.
RequestId:49873755-401e-0065-0dd0-386211000000
Time:2020-06-02T11:24:57.3079213Z</Message>
<AuthenticationErrorDetail>Signature validation failed. Signature key not found.</AuthenticationErrorDetail>
</Error>
May be I need to add additional Api access to Storage app some how?
What should I set up yet?
Or maybe there is a way to connect Ad B2C tenant to AD tenant?
Will appreciate any help.
Upd: as #juunas noiced I had differernt subscriptions for B2C tenant and Storage account. Now b2c and storage in one sub(i created new b2c, link subscription and move it inside b2c tenant, after that i made a storage account in moved subscription)
But the problem still exist.
I tried to change scope in request. On Api Permissions page in Azure Storage user_impersonation option you can see link like
https://*.dfs.core.windows.net/user_impersonation
when I used this link as a scope I've got an error
AADB2C90117: The scope
'https://*.dfs.core.windows.net/user_impersonation'
provided in the request is not supported.
After replacing of asterisk by name of storage account in link I've got the next message
AADB2C90205: This application does not have sufficient permissions
against this web resource to perform the operation.
It looks like I need to get additional permissions for App?
Does it make sense? Or trying to get access to particular storage account is wrong?

Azure Maps 403 "Permission, capacity, or authentication issues."

I am trying to call Azure Maps with OAuth access tokens but it is throwing me 403 Forbidden with the message "Permission, capacity, or authentication issues.". I have followed procedure mentioned here: https://learn.microsoft.com/en-us/azure/azure-maps/azure-maps-authentication
Created App Registration in AD, generated secret
Added API permission to Azure Maps
In Azure Maps > IAM > added the application as Map Data Reader
Got the Access token from https://login.microsoftonline.com//oauth2/token with resource=https://atlas.microsoft.com/
Calling https://atlas.microsoft.com/route/directions/json?api-version=1.0&query=52.50931,13.42936:52.50274,13.43872 with x-ms-client-id and Authorization=Bearer
Same procedure works correctly for my personal free subscription but not in my company's subscription. Don't know how to debug.
For reference on how Azure RBAC works.
Ensure you have no deny assignments possibly enforced from management groups on the particular role.
Make sure the role assignment is applied to the correct scope. Meaning on the scope of an Azure Maps Account or a parent of the account such as the resource group or subscription.
If you have security principals assigned to the correct scope but still receiving 403. It usually means you have assigned or authenticating with the wrong security principal.
Example:
"App only" token for an App Registration requires the service principal App to be assigned at the scope.
If you as user authenticate as a user to the App Registration that would mean the user security principal should be assigned to the scope; Not the app.
If you are using Azure AD groups it could mean that the security principal may not be part of the group which is assigned access.
I don't think it's common to add service principals to security groups though. But it is a possibility which should be confirmed. There is also a possibility of delay before the permissions are propagated but this usually shouldn't take more than a few minutes.
Just to be thorough but may not apply here. Certain REST APIs require S1 sku to be selected on the account. This will result in the same error response.
We raised the ticket with Microsoft and they told us it was caused by:
longer synchronization times regarding the RBAC configurations
worldwide

Azure KeyVault Managed Storage Account

I am trying to implement KeyVault managed Storage Account in Azure to rotate storage keys using KeyVault. I did follow the documentation, which uses both "ServicePrincipalID" and "UserPrincipalID", but in my case i am provisioning my resources and implementing all the steps involved using my service principal (as we deploy using VSTS with service principal) and using "ServicePrincipalID" as ObjectID in place of "UserPrincipalID" (as there is no user intervention during provisioning and post-provisioning process). I did give my service principal "Owner" role and all required permissions for keyvault to access storage. But when i do "Add-AzureKeyVaultManagedStorageAccount" i get the below error which says "KeyVault is unable to perform the action on behalf of the caller". So i am not sure what access i am still missing, even after making my principal as Owner. Please find my screenshots below for more details. Would be glad to hear any suggestions to cross this hurdle.
Error
KeyVault details
Thanks
Chaitanya Alladi.
i get the below error which says "KeyVault is unable to perform the action on behalf of the caller". So i am not sure what access i am still missing, even after making my principal as Owner.
Unfortunly, we can't do that with service principle now.
AAD doesn't support get OBO(OnBehalfOf) token for service principle caller tokens.
We need to use the user credentials instead of Service Principal credentials. There are some operations that are only possible on behalf of the user and not Service Principal when it comes to storage account keys as of now.

Regenerating access keys in Azure by REST API

For Azure there is an API Endpoint that allows to regenerate key.
The endpoint looks like
POST https://management.azure.com/subscriptions/{subscriptionId}/resourceGroups/{resourceGroupName}/providers/Microsoft.Storage/storageAccounts/{accountName}/regenerateKey?api-version=2017-06-01
Documentation states
When you have code that needs to access or modify resources, you must set up an Azure Active Directory (AD) application.
However, when I use it (i.e. create POST request) I'm getting error Authentication failed. The 'Authorization' header is missing. I tried to follow this tutorial and I did all the steps except Assign application to role What role should I select to be able to regenerate password? How do I do that? Am I getting this correct?
I think you could use Storage Account Key Operator Service Role.
The Storage Account Key Operators are allowed to list and regenerate keys on Storage Account.
Storage Account Contributor: Lets you manage storage accounts, but not access to them.
Contributor:Lets you manage everything except access to resources.
If you have some more action to operate, you could use more powerful roles, but if you only want to regenerate key, I suggest that you could use Storage Account Key Operator Service Role.

Resources