Skip to content

Commit

Permalink
Fixed Azure.Storage.SecureTransfer #2414
Browse files Browse the repository at this point in the history
  • Loading branch information
BernieWhite committed Sep 2, 2023
1 parent 9a1297b commit 9dce51d
Show file tree
Hide file tree
Showing 6 changed files with 83 additions and 57 deletions.
3 changes: 3 additions & 0 deletions docs/CHANGELOG-v1.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,9 @@ What's changed since pre-release v1.30.0-B0047:
- Engineering:
- Bump Microsoft.NET.Test.Sdk to v17.7.2.
[#2407](https://github.com/Azure/PSRule.Rules.Azure/pull/2407)
- Bug fixes:
- Fixed false positive with `Azure.Storage.SecureTransfer` on new API versions by @BernieWhite.
[#2414](https://github.com/Azure/PSRule.Rules.Azure/issues/2414)

## v1.30.0-B0047 (pre-release)

Expand Down
65 changes: 41 additions & 24 deletions docs/en/rules/Azure.Storage.SecureTransfer.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
---
reviewed: 2023-09-02
severity: Important
pillar: Security
category: Encryption
Expand All @@ -23,6 +24,9 @@ To do this set the _Secure transfer required_ option.
When _secure transfer required_ is enabled,
attempts to connect to storage using HTTP or unencrypted SMB connections are rejected.

Storage Accounts that are deployed with a newer API version will have this option enabled by default.
However, this does not prevent the option from being disabled.

## RECOMMENDATION

Storage accounts should only accept secure traffic.
Expand All @@ -35,59 +39,72 @@ Also consider using Azure Policy to audit or enforce this configuration.

To deploy Storage Accounts that pass this rule:

- Set the `properties.supportsHttpsTrafficOnly` property to `true`.
- For API versions older then _2019-04-01_, set the `properties.supportsHttpsTrafficOnly` property to `true`.
- For API versions _2019-04-01_ and newer:
- Omit the `properties.supportsHttpsTrafficOnly` property OR
- Explicitly set the `properties.supportsHttpsTrafficOnly` property to `true`.

For example:

```json
{
"comments": "Storage Account",
"type": "Microsoft.Storage/storageAccounts",
"apiVersion": "2019-06-01",
"name": "st0000001",
"location": "[parameters('location')]",
"sku": {
"name": "Standard_GRS",
"tier": "Standard"
},
"kind": "StorageV2",
"properties": {
"supportsHttpsTrafficOnly": true,
"minimumTlsVersion": "TLS1_2",
"allowBlobPublicAccess": false,
"accessTier": "Hot"
"type": "Microsoft.Storage/storageAccounts",
"apiVersion": "2023-01-01",
"name": "[parameters('name')]",
"location": "[parameters('location')]",
"sku": {
"name": "Standard_GRS"
},
"kind": "StorageV2",
"properties": {
"allowBlobPublicAccess": false,
"supportsHttpsTrafficOnly": true,
"minimumTlsVersion": "TLS1_2",
"accessTier": "Hot",
"allowSharedKeyAccess": false,
"networkAcls": {
"defaultAction": "Deny"
}
}
}
```

### Configure with Bicep

To deploy Storage Accounts that pass this rule:

- Set the `properties.supportsHttpsTrafficOnly` property to `true`.
- For API versions older then _2019-04-01_, set the `properties.supportsHttpsTrafficOnly` property to `true`.
- For API versions _2019-04-01_ and newer:
- Omit the `properties.supportsHttpsTrafficOnly` property OR
- Explicitly set the `properties.supportsHttpsTrafficOnly` property to `true`.

For example:

```bicep
resource st0000001 'Microsoft.Storage/storageAccounts@2021-04-01' = {
name: 'st0000001'
resource storageAccount 'Microsoft.Storage/storageAccounts@2023-01-01' = {
name: name
location: location
sku: {
name: 'Standard_GRS'
}
kind: 'StorageV2'
properties: {
supportsHttpsTrafficOnly: true
accessTier: 'Hot'
allowBlobPublicAccess: false
supportsHttpsTrafficOnly: true
minimumTlsVersion: 'TLS1_2'
accessTier: 'Hot'
allowSharedKeyAccess: false
networkAcls: {
defaultAction: 'Deny'
}
}
}
```

## LINKS

- [Data encryption in Azure](https://learn.microsoft.com/azure/architecture/framework/security/design-storage-encryption#data-in-transit)
- [Require secure transfer in Azure Storage](https://docs.microsoft.com/azure/storage/common/storage-require-secure-transfer)
- [Sample policy for ensuring https traffic](https://docs.microsoft.com/azure/governance/policy/samples/ensure-https-stor-acct)
- [Azure deployment reference](https://docs.microsoft.com/azure/templates/microsoft.storage/storageaccounts)
- [Require secure transfer in Azure Storage](https://learn.microsoft.com/azure/storage/common/storage-require-secure-transfer)
- [DP-3: Encrypt sensitive data in transit](https://learn.microsoft.com/security/benchmark/azure/baselines/storage-security-baseline#dp-3-encrypt-sensitive-data-in-transit)
- [Sample policy for ensuring https traffic](https://learn.microsoft.com/azure/governance/policy/samples/built-in-policies#storage)
- [Azure deployment reference](https://learn.microsoft.com/azure/templates/microsoft.storage/storageaccounts)
10 changes: 5 additions & 5 deletions docs/examples-storage.bicep
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ var containerName = 'data'
var shareName = 'group'

// An example Storage Account
resource storageAccount 'Microsoft.Storage/storageAccounts@2021-06-01' = {
resource storageAccount 'Microsoft.Storage/storageAccounts@2023-01-01' = {
name: name
location: location
sku: {
Expand All @@ -36,7 +36,7 @@ resource storageAccount 'Microsoft.Storage/storageAccounts@2021-06-01' = {
}

// Configure blob services
resource blobService 'Microsoft.Storage/storageAccounts/blobServices@2021-06-01' = {
resource blobService 'Microsoft.Storage/storageAccounts/blobServices@2023-01-01' = {
parent: storageAccount
name: 'default'
properties: {
Expand All @@ -52,7 +52,7 @@ resource blobService 'Microsoft.Storage/storageAccounts/blobServices@2021-06-01'
}

// An example container
resource container 'Microsoft.Storage/storageAccounts/blobServices/containers@2021-06-01' = {
resource container 'Microsoft.Storage/storageAccounts/blobServices/containers@2023-01-01' = {
parent: blobService
name: containerName
properties: {
Expand All @@ -61,7 +61,7 @@ resource container 'Microsoft.Storage/storageAccounts/blobServices/containers@20
}

// Configure file services
resource fileServices 'Microsoft.Storage/storageAccounts/fileServices@2021-06-01' = {
resource fileServices 'Microsoft.Storage/storageAccounts/fileServices@2023-01-01' = {
parent: storageAccount
name: 'default'
properties: {
Expand All @@ -72,7 +72,7 @@ resource fileServices 'Microsoft.Storage/storageAccounts/fileServices@2021-06-01
}
}

resource share 'Microsoft.Storage/storageAccounts/fileServices/shares@2021-06-01' = {
resource share 'Microsoft.Storage/storageAccounts/fileServices/shares@2023-01-01' = {
parent: fileServices
name: shareName
properties: {
Expand Down
40 changes: 20 additions & 20 deletions docs/examples-storage.json
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
{
"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
"languageVersion": "1.10-experimental",
"contentVersion": "1.0.0.0",
"metadata": {
"_EXPERIMENTAL_WARNING": "Symbolic name support in ARM is experimental, and should be enabled for testing purposes only. Do not enable this setting for any production usage, or you may be unexpectedly broken at any time!",
"_generator": {
"name": "bicep",
"version": "0.4.1124.51302",
"templateHash": "4901265845278602446"
"version": "0.20.4.51522",
"templateHash": "6814134128727565933"
}
},
"parameters": {
Expand All @@ -27,10 +29,10 @@
"containerName": "data",
"shareName": "group"
},
"resources": [
{
"resources": {
"storageAccount": {
"type": "Microsoft.Storage/storageAccounts",
"apiVersion": "2021-06-01",
"apiVersion": "2023-01-01",
"name": "[parameters('name')]",
"location": "[parameters('location')]",
"sku": {
Expand All @@ -48,9 +50,9 @@
}
}
},
{
"blobService": {
"type": "Microsoft.Storage/storageAccounts/blobServices",
"apiVersion": "2021-06-01",
"apiVersion": "2023-01-01",
"name": "[format('{0}/{1}', parameters('name'), 'default')]",
"properties": {
"deleteRetentionPolicy": {
Expand All @@ -63,24 +65,23 @@
}
},
"dependsOn": [
"[resourceId('Microsoft.Storage/storageAccounts', parameters('name'))]"
"storageAccount"
]
},
{
"container": {
"type": "Microsoft.Storage/storageAccounts/blobServices/containers",
"apiVersion": "2021-06-01",
"apiVersion": "2023-01-01",
"name": "[format('{0}/{1}/{2}', parameters('name'), 'default', variables('containerName'))]",
"properties": {
"publicAccess": "None"
},
"dependsOn": [
"[resourceId('Microsoft.Storage/storageAccounts/blobServices', parameters('name'), 'default')]",
"[resourceId('Microsoft.Storage/storageAccounts', parameters('name'))]"
"blobService"
]
},
{
"fileServices": {
"type": "Microsoft.Storage/storageAccounts/fileServices",
"apiVersion": "2021-06-01",
"apiVersion": "2023-01-01",
"name": "[format('{0}/{1}', parameters('name'), 'default')]",
"properties": {
"shareDeleteRetentionPolicy": {
Expand All @@ -89,20 +90,19 @@
}
},
"dependsOn": [
"[resourceId('Microsoft.Storage/storageAccounts', parameters('name'))]"
"storageAccount"
]
},
{
"share": {
"type": "Microsoft.Storage/storageAccounts/fileServices/shares",
"apiVersion": "2021-06-01",
"apiVersion": "2023-01-01",
"name": "[format('{0}/{1}/{2}', parameters('name'), 'default', variables('shareName'))]",
"properties": {
"accessTier": "TransactionOptimized"
},
"dependsOn": [
"[resourceId('Microsoft.Storage/storageAccounts/fileServices', parameters('name'), 'default')]",
"[resourceId('Microsoft.Storage/storageAccounts', parameters('name'))]"
"fileServices"
]
}
]
}
}
19 changes: 13 additions & 6 deletions src/PSRule.Rules.Azure/rules/Azure.Storage.Rule.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -54,17 +54,24 @@ metadata:
name: Azure.Storage.SecureTransfer
ref: AZR-000196
tags:
release: 'GA'
ruleSet: '2020_06'
Azure.WAF/pillar: 'Security'
release: GA
ruleSet: 2020_06
Azure.WAF/pillar: Security
labels:
Azure.MCSB.v1/control: 'DP-3'
Azure.MCSB.v1/control: DP-3
spec:
type:
- Microsoft.Storage/storageAccounts
condition:
field: properties.supportsHttpsTrafficOnly
equals: true
anyOf:
- allOf:
- field: apiVersion
apiVersion: '>=2019-04-01'
- field: properties.supportsHttpsTrafficOnly
hasDefault: true
- allOf:
- field: properties.supportsHttpsTrafficOnly
equals: true

---
# Synopsis: Disallow blob containers with public access types.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,7 @@
{
"comments": "Storage Account",
"type": "Microsoft.Storage/storageAccounts",
"apiVersion": "2019-06-01",
"apiVersion": "2022-09-01",
"name": "[parameters('storageAccountName')]",
"location": "[parameters('location')]",
"sku": {
Expand All @@ -116,7 +116,6 @@
],
"defaultAction": "Deny"
},
"supportsHttpsTrafficOnly": true,
"encryption": {
"services": {
"file": {
Expand Down

0 comments on commit 9dce51d

Please sign in to comment.