This commit is contained in:
Bernie White 2020-05-18 16:56:54 +10:00 коммит произвёл GitHub
Родитель 62545b570e
Коммит c74456f8ac
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: 4AEE18F83AFDEB23
14 изменённых файлов: 260 добавлений и 22 удалений

Просмотреть файл

@ -2,6 +2,11 @@
## Unreleased
- New rules:
- SQL Database:
- Check SQL Database uses TDE. [#379](https://github.com/Microsoft/PSRule.Rules.Azure/issues/379)
- Check SQL Database uses AAD authentication. [#378](https://github.com/Microsoft/PSRule.Rules.Azure/issues/378)
## v0.12.0-B2005019 (pre-release)
- New rules:

Просмотреть файл

@ -0,0 +1,30 @@
---
severity: Critical
category: Security configuration
resource: SQL Database
online version: https://github.com/Microsoft/PSRule.Rules.Azure/blob/master/docs/rules/en/Azure.SQL.AAD.md
---
# Use AAD authentication with SQL databases
## SYNOPSIS
Use Azure Active Directory (AAD) authentication with Azure SQL databases.
## DESCRIPTION
Azure SQL Database offer two authentication models, Azure Active Directory (AAD) and SQL logins.
AAD authentication provides additional features over SQL logins that improve authentication security.
When using AAD authentication, Azure Multi-Factor Authentication (MFA) and Conditional Access are available.
## RECOMMENDATION
Consider using Azure Active Directory (AAD) authentication with SQL databases.
## LINKS
- [Configure and manage Azure Active Directory authentication with SQL](https://docs.microsoft.com/en-us/azure/sql-database/sql-database-aad-authentication-configure)
- [Azure template reference](https://docs.microsoft.com/en-us/azure/templates/microsoft.sql/2014-04-01/servers/administrators)
- [Using Multi-factor AAD authentication with Azure SQL Database](https://docs.microsoft.com/en-us/azure/sql-database/sql-database-ssms-mfa-authentication)
- [Conditional Access (MFA) with Azure SQL Database](https://docs.microsoft.com/en-us/azure/sql-database/sql-database-conditional-access)

Просмотреть файл

@ -1,7 +1,7 @@
---
severity: Important
category: Security configuration
resource: Azure SQL Database
resource: SQL Database
online version: https://github.com/Microsoft/PSRule.Rules.Azure/blob/master/docs/rules/en/Azure.SQL.AllowAzureAccess.md
ms-content-id: 30a551f6-54e0-4e51-b068-f9695d891a89
---

Просмотреть файл

@ -1,7 +1,7 @@
---
severity: Important
category: Security configuration
resource: Azure SQL Database
resource: SQL Database
online version: https://github.com/Microsoft/PSRule.Rules.Azure/blob/master/docs/rules/en/Azure.SQL.Auditing.md
ms-content-id: d6084913-9ff9-40b6-a65b-30fcd4d49251
---

Просмотреть файл

@ -1,7 +1,7 @@
---
severity: Important
category: Security configuration
resource: Azure SQL Database
resource: SQL Database
online version: https://github.com/Microsoft/PSRule.Rules.Azure/blob/master/docs/rules/en/Azure.SQL.FirewallIPRange.md
ms-content-id: a25b1927-f04c-4a6a-8a3d-42d59d4722ff
---

Просмотреть файл

@ -1,7 +1,7 @@
---
severity: Awareness
category: Operations management
resource: Azure SQL Database
resource: SQL Database
online version: https://github.com/Microsoft/PSRule.Rules.Azure/blob/master/docs/rules/en/Azure.SQL.FirewallRuleCount.md
ms-content-id: b877a8ba-bc56-4bfe-9674-4b52b75cd13b
---

Просмотреть файл

@ -0,0 +1,27 @@
---
severity: Critical
category: Security configuration
resource: SQL Database
online version: https://github.com/Microsoft/PSRule.Rules.Azure/blob/master/docs/rules/en/Azure.SQL.TDE.md
---
# Use SQL database TDE
## SYNOPSIS
Use Transparent Data Encryption (TDE) with Azure SQL Database.
## DESCRIPTION
TDE helps protect Azure SQL Databases against malicious offline access by encrypting data at rest.
SQL Databases perform real-time encryption and decryption of the database, backups, and log files.
Encryption is perform at rest without requiring changes to the application.
## RECOMMENDATION
Consider enable Transparent Data Encryption (TDE) for Azure SQL Databases to perform encryption at rest.
## LINKS
- [Transparent data encryption for SQL Database](https://docs.microsoft.com/en-us/azure/sql-database/transparent-data-encryption-azure-sql)
- [Azure template reference](https://docs.microsoft.com/en-us/azure/templates/microsoft.sql/2014-04-01/servers/databases/transparentdataencryption)

Просмотреть файл

@ -1,7 +1,7 @@
---
severity: Important
category: Security configuration
resource: Azure SQL Database
resource: SQL Database
online version: https://github.com/Microsoft/PSRule.Rules.Azure/blob/master/docs/rules/en/Azure.SQL.ThreatDetection.md
ms-content-id: 720e560d-4ad3-41ca-93dd-69c5783b9dbe
---

Просмотреть файл

@ -159,9 +159,11 @@ Name | Synopsis | Severity
[Azure.PostgreSQL.UseSSL](Azure.PostgreSQL.UseSSL.md) | Enforce encrypted PostgreSQL connections. | Critical
[Azure.Redis.MinTLS](Azure.Redis.MinTLS.md) | Redis Cache should reject TLS versions older then 1.2. | Critical
[Azure.Redis.NonSslPort](Azure.Redis.NonSslPort.md) | Redis Cache should only accept secure connections. | Critical
[Azure.SQL.AAD](Azure.SQL.AAD.md) | Use Azure Active Directory (AAD) authentication with Azure SQL databases. | Critical
[Azure.SQL.AllowAzureAccess](Azure.SQL.AllowAzureAccess.md) | Determine if access from Azure services is required. | Important
[Azure.SQL.Auditing](Azure.SQL.Auditing.md) | Enable auditing for Azure SQL logical server. | Important
[Azure.SQL.FirewallIPRange](Azure.SQL.FirewallIPRange.md) | Determine if there is an excessive number of permitted IP addresses. | Important
[Azure.SQL.TDE](Azure.SQL.TDE.md) | Use Transparent Data Encryption (TDE) with Azure SQL Database. | Critical
[Azure.SQL.ThreatDetection](Azure.SQL.ThreatDetection.md) | Enable Advanced Thread Protection for Azure SQL logical server. | Important
[Azure.Storage.BlobAccessType](Azure.Storage.BlobAccessType.md) | Storage Accounts use containers configured with an access type other than Private. | Important
[Azure.Storage.SecureTransfer](Azure.Storage.SecureTransfer.md) | Storage accounts should only accept encrypted connections. | Important

Просмотреть файл

@ -90,16 +90,6 @@ Name | Synopsis | Severity
[Azure.AKS.UseRBAC](Azure.AKS.UseRBAC.md) | Deploy AKS cluster with role-based access control (RBAC) enabled. | Important
[Azure.AKS.Version](Azure.AKS.Version.md) | AKS control plane and nodes pools should use a current stable release. | Important
### Azure SQL Database
Name | Synopsis | Severity
---- | -------- | --------
[Azure.SQL.AllowAzureAccess](Azure.SQL.AllowAzureAccess.md) | Determine if access from Azure services is required. | Important
[Azure.SQL.Auditing](Azure.SQL.Auditing.md) | Enable auditing for Azure SQL logical server. | Important
[Azure.SQL.FirewallIPRange](Azure.SQL.FirewallIPRange.md) | Determine if there is an excessive number of permitted IP addresses. | Important
[Azure.SQL.FirewallRuleCount](Azure.SQL.FirewallRuleCount.md) | Determine if there is an excessive number of firewall rules. | Awareness
[Azure.SQL.ThreatDetection](Azure.SQL.ThreatDetection.md) | Enable Advanced Thread Protection for Azure SQL logical server. | Important
### Container Registry
Name | Synopsis | Severity
@ -215,6 +205,18 @@ Name | Synopsis | Severity
---- | -------- | --------
[Azure.SignalR.Name](Azure.SignalR.Name.md) | SignalR service instance names should meet naming requirements. | Awareness
### SQL Database
Name | Synopsis | Severity
---- | -------- | --------
[Azure.SQL.AAD](Azure.SQL.AAD.md) | Use Azure Active Directory (AAD) authentication with Azure SQL databases. | Critical
[Azure.SQL.AllowAzureAccess](Azure.SQL.AllowAzureAccess.md) | Determine if access from Azure services is required. | Important
[Azure.SQL.Auditing](Azure.SQL.Auditing.md) | Enable auditing for Azure SQL logical server. | Important
[Azure.SQL.FirewallIPRange](Azure.SQL.FirewallIPRange.md) | Determine if there is an excessive number of permitted IP addresses. | Important
[Azure.SQL.FirewallRuleCount](Azure.SQL.FirewallRuleCount.md) | Determine if there is an excessive number of firewall rules. | Awareness
[Azure.SQL.TDE](Azure.SQL.TDE.md) | Use Transparent Data Encryption (TDE) with Azure SQL Database. | Critical
[Azure.SQL.ThreatDetection](Azure.SQL.ThreatDetection.md) | Enable Advanced Thread Protection for Azure SQL logical server. | Important
### Storage
Name | Synopsis | Severity

Просмотреть файл

@ -529,14 +529,42 @@ function VisitSqlServer {
$resources = @();
# Get SQL Server firewall rules
$resources += Get-AzResource -Name $resource.Name -ResourceType 'Microsoft.Sql/servers/firewallRules' -ResourceGroupName $resource.ResourceGroupName -DefaultProfile $Context -ApiVersion '2015-05-01-preview' -ExpandProperties;
$resources += Get-AzResource -Name $resource.Name -ResourceType 'Microsoft.Sql/servers/securityAlertPolicies' -ResourceGroupName $resource.ResourceGroupName -DefaultProfile $Context -ApiVersion '2017-03-01-preview' -ExpandProperties;
# $resources += Get-AzResource -Name $resource.Name -ResourceType 'Microsoft.Sql/servers/vulnerabilityAssessments' -ResourceGroupName $resource.ResourceGroupName -DefaultProfile $Context -ApiVersion '2018-06-01-preview' -ExpandProperties;
$resources += Get-AzResource -Name $resource.Name -ResourceType 'Microsoft.Sql/servers/auditingSettings' -ResourceGroupName $resource.ResourceGroupName -DefaultProfile $Context -ApiVersion '2017-03-01-preview' -ExpandProperties;
$resources += GetSubResource @PSBoundParameters -ResourceType 'Microsoft.Sql/servers/firewallRules' -ApiVersion '2015-05-01-preview';
$resources += GetSubResource @PSBoundParameters -ResourceType 'Microsoft.Sql/servers/administrators' -ApiVersion '2014-04-01';
$resources += GetSubResource @PSBoundParameters -ResourceType 'Microsoft.Sql/servers/securityAlertPolicies' -ApiVersion '2017-03-01-preview';
$resources += GetSubResource @PSBoundParameters -ResourceType 'Microsoft.Sql/servers/vulnerabilityAssessments' -ApiVersion '2018-06-01-preview';
$resources += GetSubResource @PSBoundParameters -ResourceType 'Microsoft.Sql/servers/auditingSettings' -ApiVersion '2017-03-01-preview';
$sqlServer | Add-Member -MemberType NoteProperty -Name resources -Value $resources -PassThru;
}
}
function VisitSqlDatabase {
[CmdletBinding()]
param (
[Parameter(Mandatory = $True, ValueFromPipeline = $True)]
[PSObject]$Resource,
[Parameter(Mandatory = $True)]
[Microsoft.Azure.Commands.Common.Authentication.Abstractions.Core.IAzureContextContainer]$Context
)
process {
$resources = @();
$getParams = @{
ResourceGroupName = $Resource.ResourceGroupName
DefaultProfile = $Context
ErrorAction = 'SilentlyContinue'
}
$idParts = $Resource.ResourceId.Split('/');
$serverName = $idParts[-3];
$resourceName = "$serverName/$($Resource.Name)";
$resources += Get-AzResource @getParams -Name $resourceName -ResourceType 'Microsoft.Sql/servers/databases/dataMaskingPolicies' -ApiVersion '2014-04-01' -ExpandProperties
$resources += Get-AzResource @getParams -Name $resourceName -ResourceType 'Microsoft.Sql/servers/databases/transparentDataEncryption' -ApiVersion '2014-04-01' -ExpandProperties;
$resources += Get-AzResource @getParams -Name $resourceName -ResourceType 'Microsoft.Sql/servers/databases/connectionPolicies' -ApiVersion '2014-04-01' -ExpandProperties;
$resources += Get-AzResource @getParams -Name $resourceName -ResourceType 'Microsoft.Sql/servers/databases/geoBackupPolicies' -ApiVersion '2014-04-01' -ExpandProperties;
$Resource | Add-Member -MemberType NoteProperty -Name resources -Value $resources -PassThru;
}
}
function VisitPostgreSqlServer {
[CmdletBinding()]
param (
@ -607,9 +635,8 @@ function VisitAutomationAccount {
process {
$aa = $Resource
$resources = @();
$resources += Get-AzResource -Name $resource.Name -ResourceType 'Microsoft.Automation/AutomationAccounts/variables' -ResourceGroupName $resource.ResourceGroupName -DefaultProfile $Context -ApiVersion '2015-10-31' -ExpandProperties;
$resources += Get-AzResource -Name $resource.Name -ResourceType 'Microsoft.Automation/AutomationAccounts/webhooks' -ResourceGroupName $resource.ResourceGroupName -DefaultProfile $Context -ApiVersion '2015-10-31' -ExpandProperties;
$resources += GetSubResource @PSBoundParameters -ResourceType 'Microsoft.Automation/AutomationAccounts/variables' -ApiVersion '2015-10-31';
$resources += GetSubResource @PSBoundParameters -ResourceType 'Microsoft.Automation/AutomationAccounts/webhooks' -ApiVersion '2015-10-31';
$aa | Add-Member -MemberType NoteProperty -Name resources -Value $resources -PassThru;
}
}
@ -858,6 +885,7 @@ function ExpandResource {
'Microsoft.ApiManagement/service' { VisitAPIManagement @PSBoundParameters; }
'Microsoft.Automation/automationAccounts' { VisitAutomationAccount @PSBoundParameters; }
'Microsoft.Sql/servers' { VisitSqlServer @PSBoundParameters; }
'Microsoft.Sql/servers/databases' { VisitSqlDatabase @PSBoundParameters; }
'Microsoft.DBforPostgreSQL/servers' { VisitPostgreSqlServer @PSBoundParameters; }
'Microsoft.DBforMySQL/servers' { VisitMySqlServer @PSBoundParameters; }
# 'Microsoft.Sql/managedInstances' { VisitSqlManagedInstance @PSBoundParameters; }

Просмотреть файл

@ -40,8 +40,38 @@ Rule 'Azure.SQL.Auditing' -Type 'Microsoft.Sql/servers' -Tag @{ release = 'GA' }
$policy | Within 'Properties.state' 'Enabled'
}
# Synopsis: Use Azure AD administrators
Rule 'Azure.SQL.AAD' -Type 'Microsoft.Sql/servers' -Tag @{ release = 'GA' } {
$config = GetSubResources -ResourceType 'Microsoft.Sql/servers/administrators';
$Assert.HasFieldValue($config, 'Properties.administratorType', 'ActiveDirectory');
}
# Synopsis: Enable transparent data encryption
Rule 'Azure.SQL.TDE' -Type 'Microsoft.Sql/servers/databases' -If { !(IsMasterDatabase) } -Tag @{ release = 'GA' } {
$config = GetSubResources -ResourceType 'Microsoft.Sql/servers/databases/transparentDataEncryption';
$Assert.HasFieldValue($config, 'Properties.status', 'Enabled');
}
#endregion SQL Database
#region SQL Managed Instance
#endregion SQL Managed Instance
#region Helper functions
function global:IsMasterDatabase {
[CmdletBinding()]
[OutputType([System.Boolean])]
param ()
process {
return (
$PSRule.TargetType -eq 'Microsoft.Sql/servers/databases' -and (
$PSRule.TargetName -like '*/master' -or
$PSRule.TargetName -eq 'master'
)
);
}
}
#endregion Helper functions

Просмотреть файл

@ -114,5 +114,37 @@ Describe 'Azure.SQL' {
$ruleResult.Length | Should -Be 1;
$ruleResult.TargetName | Should -Be 'server-A';
}
It 'Azure.SQL.AAD' {
$filteredResult = $result | Where-Object { $_.RuleName -eq 'Azure.SQL.AAD' };
# Fail
$ruleResult = @($filteredResult | Where-Object { $_.Outcome -eq 'Fail' });
$ruleResult | Should -Not -BeNullOrEmpty;
$ruleResult.Length | Should -Be 2;
$ruleResult.TargetName | Should -BeIn 'server-B', 'server-C';
# Pass
$ruleResult = @($filteredResult | Where-Object { $_.Outcome -eq 'Pass' });
$ruleResult | Should -Not -BeNullOrEmpty;
$ruleResult.Length | Should -Be 1;
$ruleResult.TargetName | Should -Be 'server-A';
}
It 'Azure.SQL.TDE' {
$filteredResult = $result | Where-Object { $_.RuleName -eq 'Azure.SQL.TDE' };
# Fail
$ruleResult = @($filteredResult | Where-Object { $_.Outcome -eq 'Fail' });
$ruleResult | Should -Not -BeNullOrEmpty;
$ruleResult.Length | Should -Be 1;
$ruleResult.TargetName | Should -BeIn 'server-A/database-A';
# Pass
$ruleResult = @($filteredResult | Where-Object { $_.Outcome -eq 'Pass' });
$ruleResult | Should -Not -BeNullOrEmpty;
$ruleResult.Length | Should -Be 1;
$ruleResult.TargetName | Should -Be 'server-A/database-B';
}
}
}

Просмотреть файл

@ -94,6 +94,32 @@
"Type": "Microsoft.Sql/servers/auditingSettings",
"ResourceType": "Microsoft.Sql/servers/auditingSettings",
"SubscriptionId": "00000000-0000-0000-0000-000000000000"
},
{
"ResourceId": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test-rg/providers/Microsoft.Sql/servers/server-A/administrators/ActiveDirectory",
"Id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test-rg/providers/Microsoft.Sql/servers/server-A/administrators/ActiveDirectory",
"Identity": null,
"Kind": null,
"Location": "region",
"ManagedBy": null,
"ResourceName": "ActiveDirectory",
"Name": "ActiveDirectory",
"ExtensionResourceName": null,
"ParentResource": null,
"Plan": null,
"Properties": {
"administratorType": "ActiveDirectory",
"login": "sa@contoso.com",
"sid": "00000000-0000-0000-0000-000000000000",
"tenantId": "00000000-0000-0000-0000-000000000000"
},
"ResourceGroupName": "test-rg",
"Type": "Microsoft.Sql/servers/administrators",
"ResourceType": "Microsoft.Sql/servers/administrators",
"ExtensionResourceType": null,
"Sku": null,
"Tags": null,
"SubscriptionId": "00000000-0000-0000-0000-000000000000"
}
]
},
@ -402,5 +428,61 @@
"zoneRedundant": false,
"isUpgradeRequested": false
}
},
{
"Name": "database-B",
"ResourceId": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test-rg/providers/Microsoft.Sql/servers/server-A/databases/database-B",
"ResourceName": "server-A/database-B",
"ResourceType": "Microsoft.Sql/servers/databases",
"Kind": "v12.0,user",
"ResourceGroupName": "test-rg",
"Location": "region",
"SubscriptionId": "00000000-0000-0000-0000-000000000000",
"Properties": {
"edition": "Standard",
"status": "Online",
"serviceLevelObjective": "S2",
"collation": "SQL_Latin1_General_CP1_CI_AS",
"maxSizeBytes": "268435456000",
"requestedServiceObjectiveName": "S2",
"sampleName": null,
"defaultSecondaryLocation": "region-B",
"earliestRestoreDate": "2019-01-01T00:00:00Z",
"elasticPoolName": null,
"containmentState": 2,
"readScale": "Disabled",
"failoverGroupId": null,
"zoneRedundant": false,
"isUpgradeRequested": false
},
"resources": [
{
"ResourceId": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test-rg/providers/Microsoft.Sql/servers/server-A/databases/database-B/transparentDataEncryption/current",
"Id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/test-rg/providers/Microsoft.Sql/servers/server-A/databases/database-B/transparentDataEncryption/current",
"Identity": null,
"Kind": null,
"Location": "region",
"ManagedBy": null,
"ResourceName": "current",
"Name": "current",
"ExtensionResourceName": null,
"ParentResource": null,
"Plan": null,
"Properties": {
"status": "Enabled"
},
"ResourceGroupName": "test-rg",
"Type": "Microsoft.Sql/servers/databases/transparentDataEncryption",
"ResourceType": "Microsoft.Sql/servers/databases/transparentDataEncryption",
"ExtensionResourceType": null,
"Sku": null,
"Tags": null,
"TagsTable": null,
"SubscriptionId": "00000000-0000-0000-0000-000000000000",
"CreatedTime": null,
"ChangedTime": null,
"ETag": null
}
]
}
]