Limiting account SAS permission to specific files in Azure Storage - azure

I'm developing a web application which users can upload their files and each user can set permissions for the uploaded file to access to other users.
I want to use Azure Blob Storage of Azure File Storage for the uploaded files to be saved.
I need to check and validate the uploaded files before saving them, though users should upload their files on web server and then the web server will validate the files and save them to Azure Storage using Access Key.
To get accessed the files using explained method in SAS - Shared Access Signatures, Part 1: Understanding the SAS model, I want to create account SAS and generate URL on the web server and then user can download their accessible files directly from the Azure Storage.
Here is the access model (just to read data):
And here is the sample SAS url:
https://myaccount.blob.core.windows.net/sascontainer/sasblob.txt?sv=2015-04-05&st=2015-04-29T22%3A18%3A26Z&se=2015-04-30T02%3A23%3A26Z&sr=b&sp=rw&sip=168.1.5.60-168.1.5.70&spr=https&sig=Z%2FRHIX5Xcg0Mq2rqI3OlWTjEg2tYkboXr1P9ZUXDtkk%3D
But, what if user share the URL with anonymous users directly: they can access the file before expiration date, or maybe they can use the URL to access other files (or not?).
Can account SAS limit access to specific files or folders?
Can I expire the SAS server side?
What would be the best solution on this scenario?

Account SAS is for account level, Azure File Storage supports file share level SAS or file level SAS as well, please use them instead.
To revoke SAS in server side, you'll need to set up Shared Access Policy for them. By removing the corresponding Shared Access Policy, the related SAS can be revoked. However, server can only store 5 Shared Access Policies at most, which may not satisfy your requirement. What's more, Shared Access Policy doesn't support Account SAS currently. Anyway, technically there is still one way to revoke ad hoc SAS, but I don't think it's a valid option: to regenerate the corresponding storage account key on SAS Provider Service which was used to generate the ad hoc SAS.
In my opinion, SAS is not the good solution for your scenario, since SAS is designed for sharing links in plain text among anonymous users. In order to achieve your requirement, you need to set up your own authentication and authorization on your website. All the users must upload/download the files via your website, and Azure Storage is just the storage back end of your website, which shouldn't be exposed to users directly.

We can use SAS to set the file permission, use SAS policy to set the start data and expire date. However if you have very complex logic about the file. I would suggest you use role permission to do this.

Related

How to generate SAS Token to connect to Azure Storage Account - File Share?

In order to connect to Azure Shared Storage(in particularly File Share) to perform tasks like copying/removing/modifying files from remote to azure storage, we need either SAS(Shared Access Signature) or Active Directory Settings Enabled (and then assign roles based on requirement).
I wanted to implement the access using SAS approach, I tried generating SAS from UI, tried generating SAS by making use of Access Keys(Present Inside Storage Account - Confidential and most important key for storage account) both worked. But UI approach isn't conducive in my case, and Access token can't be given to anyone apart from the administrator.
So is there a way to generate SAS using Azure AD credentials or some service where we can create an account and password/key and that account can be used to create SAS token via curl(REST call) and not generating SAS via access keys(admin key).
The tricky part is to let your users create a sas token for the file share without granting them permissions on the whole storage account.
You can use a middle tier application that creates the SAS token and allow the users to use that app. An azure function with an HTTP trigger can be used for example. You grant the azure function access to the storage account using a Managed Service Identity and secure the access to the Azure function either with Active Directory or a function key, that you distribute to your users.
You can try with this approach:
A SAS token for access to a container, directory, or blob may be secured by using either Azure AD credentials or an account key.
Microsoft recommends that you use Azure AD credentials when possible as a security best practice, rather than using the account key, which can be more easily compromised. When your application design requires shared access signatures, use Azure AD credentials to create a user delegation SAS for superior security.
Create a User delegation SAS
Generate a User Delegation Key:
POST https://myaccount.blob.core.windows.net/?restype=service&comp=userdelegationkey

How to get user details who accessed azure blob container from .log files in $logs directory

I am trying to find out user details who accessed a blob storage in an Azure container
Can I find out details from .log files in $logs directory or is there any other way ?
Any help is much appreciated
I assume you already have Azure AD authentication and configured 2.0 logs already, in that case you can use UserPrincipalName column to identify the user and parse the column with JSON AuthorizationDetail.action to identify the action of the user on storage either write,read etc
Storage Analytics log format version 2.0 has the information, which needs OAuth 2.0 token which must be provided by Azure Active Directory. You must make sure you call the Storage operations with OAuth Tokens before you start.
Or by generating the SAS(Shared Access Signature) Token which is an URl that grants restricted access to the Azure Storage resources, by distributing the shared access signature which can be for a specific period of time.

Write to Azure Blob with username and password

I need to write to an azure blob store using my app that is running on a customer's network. I would like to use a network username and password to secure the blob location. I have been reading MANY articles but I cannot see how to use a username and password to connect to the azure blob store.
It is a WPF app, so I do not want to store my key (or any secrets) in a config file or hard code it as it will be too easy to get with a decompiler. I would prefer to issue the user with a network username and password. That way I can change the password or disable the username when needed.
Can anyone point me in the right direction here please, I just keep looping back to the same documentation over and over
There are three ways to get connected to Azure Storage:
Using account name/key
Using Azure Active Directory (Azure AD) authentication
Using Shared Access Signature
1st option is automatically ruled out as you don't want to store the secrets in the application (wise decision BTW).
You can use Azure AD authentication to connect to Blob Storage. Your users would need to be present in Azure AD for this though. Whenever a user launches your application, you will redirect them to Azure AD for authentication and once they are authenticated, they will be able to use the application. You can read more about it here: https://learn.microsoft.com/en-us/azure/storage/common/storage-auth-aad
3rd option is to use Shared Access Signature (SAS) which basically is a URL that has a time-bound/permission driven access to your storage. The way this would work is that your application will authenticate the users by asking them to provide their network username/password. Once they are authenticated, they will get access to the application. In the application, you can make a call to an API that will return a SAS URL using which a user will be able to upload data into blob storage. You can read more about it here: https://learn.microsoft.com/en-us/azure/storage/common/storage-sas-overview?toc=%2fazure%2fstorage%2fblobs%2ftoc.json

Micorsoft Azure blob storage secruity

We are using MS Azure and developing SAAS based Multi-Tenant Application.
For each Tenant we have BLOB Container Private and assigned to each Tenant.
Also there is a requirement that Client can share files with other client users.
Eg.
Client C1 has Container "C1" and it has files "C1f1", "C1f2" and "C1f3".
User U1 and U2. U1 has access permission for C1f1 and U2 has C1f2 access only.
How can we do this in MS Azure Permission or Security? This needs to be done RUNTtime?
Please suggest How can this be done - What is BEST way to do
I believe you have two options.
Either generate and use SAS tokens per client/user with the right permissions. With a SAS token you can provide access to a specific resource up to a specific point in time. The disadvantage is that SAS tokens cannot be revoked on a per token basis. You can only revoke all tokens by rolling the storage access key that was used to generate the SAS token. Another disadvantage is that you have to provide a SAS token per item you want to grant access to. (For more info see also https://azure.microsoft.com/nl-nl/documentation/articles/storage-dotnet-shared-access-signature-part-1/)
Create a Web Service that encapsulates the Azure storage and serves files to your customers. In this service implement authorization management yourself.

how to revoke Shared Access Signature in Azure SDK

I could not find any code sample for revoking the created Shared Access Signature access on blob, can anyone provide me link or reference for removing the Shared Access Signature access created earlier.
Even if shared access signature (SAS) is based on a stored access policy (SAP), you can only revoke SAP, not individual SAS.
Azure Storage security guide has good details:
https://learn.microsoft.com/en-us/azure/storage/common/storage-security-guide#revocation
SAS not based on SAP - can't be revoked:
If you are using ad hoc URIs, you have three options. You can issue SAS tokens with short expiration policies and wait for the SAS to expire. You can rename or delete the resource (assuming the token was scoped to a single object). You can change the storage account keys. This last option can have a significant impact, depending on how many services are using that storage account, and probably isn't something you want to do without some planning.
SAS based on SAP - can be revoked by revoking SAP:
If you are using a SAS derived from a Stored Access Policy, you can remove access by revoking the Stored Access Policy – you can just change it so it has already expired, or you can remove it altogether. This takes effect immediately, and invalidates every SAS created using that Stored Access Policy. Updating or removing the Stored Access Policy may impact people accessing that specific container, file share, table, or queue via SAS, but if the clients are written so they request a new SAS when the old one becomes invalid, this will work fine.
Best practice:
Because using a SAS derived from a Stored Access Policy gives you the ability to revoke that SAS immediately, it is the recommended best practice to always use Stored Access Policies when possible.
Context
MSFT Azure storage account (live version as of 2019-11-26)
MSFT Azure storage permissions as managed by Shared Access Signature (SAS)
Problem
User user145610 wants to immediately revoke a deployed SAS
(e.g., because SAS allows authentication into Blob Storage, and the SAS has been compromised, requiring immediate remediation to prevent unauthorized data breach)
Workarounds already mentioned
Other answers already appear in this thread discussing the use of Shared Access Policy (aka Stored Access Policy) (SAP)
SAS generated based on SAP has limitations, only five SAPs can be attached to a a blob container within a storage account.
Workaround: Regenerating Account Keys
One workaround that does not appear in this thread (at the time of this posting) is the ability to regenerate the account key used to originally create the SAS, as documented in one of the links in the see also section of this answer.
Regenerating an account key will cause all application components using that key to fail to authorize until they're updated to use either the other valid account key or the newly regenerated account key. Regenerating the account key is the only way to immediately revoke an ad hoc SAS.
Consequently, one potential workaround is to generate and deploy SASs based on the secondary account key, and have the expectation that you will routinely regenerate the secondary account key whenever immediate revocation of one or more SASs becomes necessary.
(Obviously, this is not a desirable circumstance where many SAS tokens are deployed and dependent on the secondary account key, because they will all be rendered invalid upon regeneration of the key)
Solution
The inability to deploy a large number of SAPs, combined with the potentially unfavorable side-effects of having to regenerate account keys suggests that a potential solution is to re-engineer the architecture of your project to use ActiveDirectory for controlling authorization and access control, and the generation of SAS tokens.
SASs based on SAPs may be better suited for cases where there are only few clients requiring access, and the probability of the SASs getting compromised is extremely low.
As of this writing, MSFT Azure storage supports the generation and use of SAS tokens based on ActiveDirectory accounts.
See also
How many access policies can I create and add on the same one Azure container?
https://learn.microsoft.com/en-us/azure/storage/common/storage-auth
https://learn.microsoft.com/en-us/rest/api/storageservices/create-service-sas#revocation-of-a-sas
https://learn.microsoft.com/en-us/azure/storage/common/storage-sas-overview#types-of-shared-access-signatures
https://learn.microsoft.com/en-us/rest/api/storageservices/create-user-delegation-sas
https://learn.microsoft.com/en-us/azure/storage/common/storage-sas-overview#best-practices-for-using-sas
You can't revoke a shared access signature unless it is based on a stored access policy. See https://learn.microsoft.com/en-us/rest/api/storageservices/define-stored-access-policy#modifying-or-revoking-a-stored-access-policy for more information:
To revoke a stored access policy, you can either delete it, or rename
it by changing the signed identifier. Changing the signed identifier
breaks the associations between any existing signatures and the stored
access policy. Deleting or renaming the stored access policy
immediately effects all of the shared access signatures associated
with it.
Came across this topic too. As per highlighted by #IlyaBerdichevsky on the top, Best practice is to use a SAS derived from a Stored Access Policy.
TLDR;
Watch this youtube tutorial
(Step by step) How to create a SAS Derived from Store Access Policy?
First, setup Stored Access Policy
Go to your Azure Storage Resource
Click on containers (left panel under Data Storage), choose your container (because different container may setup different policy).
Click on Access Policy (left panel under Settings)
Click on Add policy
Here you may specify the desired policy you want (Sample in screenshot)
Click on OK
Tap on Save button on top (it reflects quickly actually, although it claimed to take about 30 seconds)
Second, generate SAS based on the SAP (Stored Access Policy) created
Back to Azure Storage Resource
Click on Storage Explorer (preview)
In my case I'm using Blob container, so I'll expand my blob container and click on the container I want. You shall see your file inside the container, once you've selected.
Right click on the file, click on Get Shared Access Signature.
Select the policy you have just created under the dropdown.
Tap on create
DONE! You've gotten your token now :)
How to revoke/extend the SAS token created for client?
Back to the policy you have setup
Update the expiry time
Save
TAAA-DAHH! Same link with the SAS token should expired/work now.
I had the same problem and this is how I solved it:
The communication between the redacted service and Azure Blob Storage is done through the SDK v8.0.

Resources