Skip to content

Commit c9c93d9

Browse files
authored
[Storage] Support share soft delete (Azure#11779)
* [Storage] Support share soft delete * fix CI failure * Remove GetShareUsage parameter since server issue * [Storage] Fix a CI failure
1 parent b7c5d21 commit c9c93d9

23 files changed

+3250
-63
lines changed

src/Storage/Storage.Management.Test/ScenarioTests/StorageFileTests.cs

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,13 @@ public StorageFileTests(ITestOutputHelper output)
3636
public void TestStorageFileShare()
3737
{
3838
TestController.NewInstance.RunPsTest(_logger, "Test-StorageFileShare");
39-
}
39+
}
40+
41+
[Fact]
42+
[Trait(Category.AcceptanceType, Category.CheckIn)]
43+
public void TestShareSoftDeletee()
44+
{
45+
TestController.NewInstance.RunPsTest(_logger, "Test-ShareSoftDelete");
46+
}
4047
}
4148
}

src/Storage/Storage.Management.Test/ScenarioTests/StorageFileTests.ps1

Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,5 +99,106 @@ function Test-StorageFileShare
9999
}
100100
}
101101

102+
<#
103+
.SYNOPSIS
104+
Test Storage File Share Soft Delete
105+
.DESCRIPTION
106+
SmokeTest
107+
#>
108+
function Test-ShareSoftDelete
109+
{
110+
# Setup
111+
$rgname = Get-StorageManagementTestResourceName;
112+
113+
try
114+
{
115+
# Test
116+
$stoname = 'sto' + $rgname;
117+
$stotype = 'Standard_LRS';
118+
$loc = Get-ProviderLocation ResourceManagement;
119+
$kind = 'StorageV2'
120+
$shareName1 = "share1"+ $rgname
121+
$shareName2 = "share2"+ $rgname
122+
123+
Write-Verbose "RGName: $rgname | Loc: $loc"
124+
New-AzResourceGroup -Name $rgname -Location $loc;
125+
126+
$loc = Get-ProviderLocation_Stage ResourceManagement;
127+
New-AzStorageAccount -ResourceGroupName $rgname -Name $stoname -Location $loc -Type $stotype -Kind $kind
128+
$stos = Get-AzStorageAccount -ResourceGroupName $rgname;
129+
130+
# Enable Share Soft delete
131+
Update-AzStorageFileServiceProperty -ResourceGroupName $rgname -StorageAccountName $stoname -EnableShareDeleteRetentionPolicy $true -ShareRetentionDays 5
132+
$servicePropertie = Get-AzStorageFileServiceProperty -ResourceGroupName $rgname -StorageAccountName $stoname
133+
Assert-AreEqual $true $servicePropertie.ShareDeleteRetentionPolicy.Enabled
134+
Assert-AreEqual 5 $servicePropertie.ShareDeleteRetentionPolicy.Days
135+
136+
#create Shares
137+
New-AzRmStorageShare -ResourceGroupName $rgname -StorageAccountName $stoname -Name $shareName1
138+
$share = Get-AzRmStorageShare -ResourceGroupName $rgname -StorageAccountName $stoname -Name $shareName1
139+
Assert-AreEqual $rgname $share.ResourceGroupName
140+
Assert-AreEqual $stoname $share.StorageAccountName
141+
Assert-AreEqual $shareName1 $share.Name
142+
New-AzRmStorageShare -ResourceGroupName $rgname -StorageAccountName $stoname -Name $shareName2
143+
144+
#delete share
145+
Remove-AzRmStorageShare -ResourceGroupName $rgname -StorageAccountName $stoname -Name $shareName1 -Force
146+
147+
#list share check
148+
$share = Get-AzRmStorageShare -ResourceGroupName $rgname -StorageAccountName $stoname -IncludeDeleted
149+
$deletedShareVersion = $share[0].Version
150+
Assert-AreEqual 2 $share.Count
151+
Assert-AreEqual $shareName1 $share[0].Name
152+
Assert-AreEqual $null $share[0].ShareUsageBytes
153+
Assert-AreEqual $true $share[0].Deleted
154+
Assert-AreNotEqual $null $share[0].DeletedTime
155+
Assert-AreNotEqual $null $share[0].Version
156+
Assert-AreEqual $shareName2 $share[1].Name
157+
Assert-AreEqual $null $share[1].Deleted
158+
Assert-AreEqual $null $share[1].DeletedTime
159+
Assert-AreEqual $null $share[1].Version
160+
161+
$share = Get-AzRmStorageShare -ResourceGroupName $rgname -StorageAccountName $stoname
162+
Assert-AreEqual 1 $share.Count
163+
Assert-AreEqual $shareName2 $share[0].Name
164+
Assert-AreEqual $null $share[0].Deleted
165+
Assert-AreEqual $null $share[0].DeletedTime
166+
Assert-AreEqual $null $share[0].Version
167+
168+
# restore share and check
169+
if ($env:AZURE_TEST_MODE -eq "Record")
170+
{
171+
# sleep 1 miniute if record. Don't need sleep in replay
172+
sleep 60
173+
}
174+
Restore-AzRmStorageShare -ResourceGroupName $rgname -StorageAccountName $stoname -Name $shareName1 -DeletedShareVersion $deletedShareVersion
175+
176+
$share = Get-AzRmStorageShare -ResourceGroupName $rgname -StorageAccountName $stoname
177+
Assert-AreEqual 2 $share.Count
178+
Assert-AreEqual $shareName1 $share[0].Name
179+
Assert-AreEqual $null $share[0].Deleted
180+
Assert-AreEqual $null $share[0].DeletedTime
181+
Assert-AreEqual $null $share[0].Version
182+
Assert-AreEqual $shareName2 $share[1].Name
183+
Assert-AreEqual $null $share[1].Deleted
184+
Assert-AreEqual $null $share[1].DeletedTime
185+
Assert-AreEqual $null $share[1].Version
186+
187+
$share = Get-AzRmStorageShare -ResourceGroupName $rgname -StorageAccountName $stoname -IncludeDeleted
188+
Assert-AreEqual 2 $share.Count
189+
190+
# Disable Share Soft delete
191+
Update-AzStorageFileServiceProperty -ResourceGroupName $rgname -StorageAccountName $stoname -EnableShareDeleteRetentionPolicy $false
192+
$servicePropertie = Get-AzStorageFileServiceProperty -ResourceGroupName $rgname -StorageAccountName $stoname
193+
Assert-AreEqual $false $servicePropertie.ShareDeleteRetentionPolicy.Enabled
194+
195+
Remove-AzStorageAccount -Force -ResourceGroupName $rgname -Name $stoname;
196+
}
197+
finally
198+
{
199+
# Cleanup
200+
Clean-ResourceGroup $rgname
201+
}
202+
}
102203

103204

src/Storage/Storage.Management.Test/SessionRecords/Microsoft.Azure.Commands.Management.Storage.Test.ScenarioTests.StorageFileTests/TestShareSoftDeletee.json

Lines changed: 1797 additions & 0 deletions
Large diffs are not rendered by default.

src/Storage/Storage.Management/Az.Storage.psd1

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -163,6 +163,8 @@ CmdletsToExport = 'Get-AzStorageAccount', 'Get-AzStorageAccountKey',
163163
'Get-AzStorageFileHandle', 'Close-AzStorageFileHandle',
164164
'New-AzRmStorageShare', 'Remove-AzRmStorageShare',
165165
'Get-AzRmStorageShare', 'Update-AzRmStorageShare',
166+
'Update-AzStorageFileServiceProperty',
167+
'Get-AzStorageFileServiceProperty', 'Restore-AzRmStorageShare',
166168
'Get-AzDataLakeGen2ChildItem', 'Get-AzDataLakeGen2Item',
167169
'New-AzDataLakeGen2Item', 'Move-AzDataLakeGen2Item',
168170
'Remove-AzDataLakeGen2Item', 'Update-AzDataLakeGen2Item',

src/Storage/Storage.Management/ChangeLog.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,13 @@
1818
- Additional information about change #1
1919
-->
2020
## Upcoming Release
21+
* Support enable/disable/get share soft delete properties on file Service of a Storage account
22+
- `Update-AzStorageFileServiceProperty`
23+
- `Get-AzStorageFileServiceProperty`
24+
* Support list file shares include the deleted ones of a Storage account, and Get single file share usage
25+
- `Get-AzRmStorageShare`
26+
* Support restore a deleted file share
27+
- `Restore-AzRmStorageShare`
2128
* Support enable/disable versioning on Blob Service of a Storage account
2229
- `Update-AzStorageBlobServiceProperty`
2330
* Support Set/Get/Remove Object Replication Policy on Storage accounts
Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
// ----------------------------------------------------------------------------------
2+
//
3+
// Copyright Microsoft Corporation
4+
// Licensed under the Apache License, Version 2.0 (the "License");
5+
// you may not use this file except in compliance with the License.
6+
// You may obtain a copy of the License at
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
// Unless required by applicable law or agreed to in writing, software
9+
// distributed under the License is distributed on an "AS IS" BASIS,
10+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11+
// See the License for the specific language governing permissions and
12+
// limitations under the License.
13+
// ----------------------------------------------------------------------------------
14+
15+
namespace Microsoft.Azure.Commands.Management.Storage
16+
{
17+
using Microsoft.Azure.Commands.Management.Storage.Models;
18+
using Microsoft.Azure.Management.Storage;
19+
using Microsoft.Azure.Management.Storage.Models;
20+
using System;
21+
using System.Collections.Generic;
22+
using System.Management.Automation;
23+
using Microsoft.Azure.Commands.ResourceManager.Common.ArgumentCompleters;
24+
using Microsoft.Azure.Management.Internal.Resources.Utilities.Models;
25+
26+
/// <summary>
27+
/// Modify Azure Storage service properties
28+
/// </summary>
29+
[Cmdlet("Get", ResourceManager.Common.AzureRMConstants.AzureRMPrefix + StorageFileServiceProperty, DefaultParameterSetName = AccountNameParameterSet), OutputType(typeof(PSFileServiceProperties))]
30+
public class GetAzStorageFileServicePropertyCommand : StorageFileBaseCmdlet
31+
{
32+
33+
/// <summary>
34+
/// AccountName Parameter Set
35+
/// </summary>
36+
private const string AccountNameParameterSet = "AccountName";
37+
38+
/// <summary>
39+
/// Account object parameter set
40+
/// </summary>
41+
private const string AccountObjectParameterSet = "AccountObject";
42+
43+
/// <summary>
44+
/// BlobServiceProperties ResourceId parameter set
45+
/// </summary>
46+
private const string PropertiesResourceIdParameterSet = "FileServicePropertiesResourceId";
47+
48+
[Parameter(
49+
Position = 0,
50+
Mandatory = true,
51+
HelpMessage = "Resource Group Name.",
52+
ParameterSetName = AccountNameParameterSet)]
53+
[ResourceGroupCompleter]
54+
[ValidateNotNullOrEmpty]
55+
public string ResourceGroupName { get; set; }
56+
57+
[Parameter(
58+
Position = 1,
59+
Mandatory = true,
60+
HelpMessage = "Storage Account Name.",
61+
ParameterSetName = AccountNameParameterSet)]
62+
[ResourceNameCompleter("Microsoft.Storage/storageAccounts", nameof(ResourceGroupName))]
63+
[Alias(AccountNameAlias, NameAlias)]
64+
[ValidateNotNullOrEmpty]
65+
public string StorageAccountName { get; set; }
66+
67+
[Parameter(Mandatory = true,
68+
HelpMessage = "Storage account object",
69+
ValueFromPipeline = true,
70+
ParameterSetName = AccountObjectParameterSet)]
71+
[ValidateNotNullOrEmpty]
72+
public PSStorageAccount StorageAccount { get; set; }
73+
74+
[Parameter(
75+
Position = 0,
76+
Mandatory = true,
77+
ValueFromPipelineByPropertyName = true,
78+
HelpMessage = "Input a Storage account Resource Id, or a File service properties Resource Id.",
79+
ParameterSetName = PropertiesResourceIdParameterSet)]
80+
[ValidateNotNullOrEmpty]
81+
public string ResourceId { get; set; }
82+
83+
public override void ExecuteCmdlet()
84+
{
85+
base.ExecuteCmdlet();
86+
switch (ParameterSetName)
87+
{
88+
case AccountObjectParameterSet:
89+
this.ResourceGroupName = StorageAccount.ResourceGroupName;
90+
this.StorageAccountName = StorageAccount.StorageAccountName;
91+
break;
92+
case PropertiesResourceIdParameterSet:
93+
ResourceIdentifier blobServicePropertiesResource = new ResourceIdentifier(ResourceId);
94+
this.ResourceGroupName = blobServicePropertiesResource.ResourceGroupName;
95+
this.StorageAccountName = PSBlobServiceProperties.GetStorageAccountNameFromResourceId(ResourceId);
96+
break;
97+
default:
98+
// For AccountNameParameterSet, the ResourceGroupName and StorageAccountName can get from input directly
99+
break;
100+
}
101+
FileServiceProperties serviceProperties = this.StorageClient.FileServices.GetServiceProperties(this.ResourceGroupName, this.StorageAccountName);
102+
103+
WriteObject(new PSFileServiceProperties(serviceProperties));
104+
}
105+
}
106+
}

src/Storage/Storage.Management/File/GetAzureStorageShare.cs

Lines changed: 55 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
using Microsoft.Azure.Management.Internal.Resources.Utilities.Models;
1717
using Microsoft.Azure.Management.Storage;
1818
using Microsoft.Azure.Management.Storage.Models;
19+
using Microsoft.Rest.Azure;
1920
using System;
2021
using System.Collections.Generic;
2122
using System.Management.Automation;
@@ -26,20 +27,34 @@ namespace Microsoft.Azure.Commands.Management.Storage
2627
public class GetAzureStorageShareCommand : StorageFileBaseCmdlet
2728
{
2829
/// <summary>
29-
/// AccountName Parameter Set
30+
/// AccountName list Parameter Set
3031
/// </summary>
3132
private const string AccountNameParameterSet = "AccountName";
3233

3334
/// <summary>
34-
/// Account object parameter set
35+
/// Account object list parameter set
3536
/// </summary>
3637
private const string AccountObjectParameterSet = "AccountObject";
38+
/// <summary>
39+
/// AccountName Parameter Set
40+
/// </summary>
41+
private const string AccountNameSingleParameterSet = "AccountNameSingle";
42+
43+
/// <summary>
44+
/// Account object parameter set
45+
/// </summary>
46+
private const string AccountObjectSingleParameterSet = "AccountObjectSingle";
3747

3848
/// <summary>
3949
/// Share ResourceId parameter set
4050
/// </summary>
4151
private const string ShareResourceIdParameterSet = "ShareResourceId";
4252

53+
[Parameter(
54+
Position = 0,
55+
Mandatory = true,
56+
HelpMessage = "Resource Group Name.",
57+
ParameterSetName = AccountNameSingleParameterSet)]
4358
[Parameter(
4459
Position = 0,
4560
Mandatory = true,
@@ -48,6 +63,11 @@ public class GetAzureStorageShareCommand : StorageFileBaseCmdlet
4863
[ValidateNotNullOrEmpty]
4964
public string ResourceGroupName { get; set; }
5065

66+
[Parameter(
67+
Position = 1,
68+
Mandatory = true,
69+
HelpMessage = "Storage Account Name.",
70+
ParameterSetName = AccountNameSingleParameterSet)]
5171
[Parameter(
5272
Position = 1,
5373
Mandatory = true,
@@ -57,6 +77,10 @@ public class GetAzureStorageShareCommand : StorageFileBaseCmdlet
5777
[ValidateNotNullOrEmpty]
5878
public string StorageAccountName { get; set; }
5979

80+
[Parameter(Mandatory = true,
81+
HelpMessage = "Storage account object",
82+
ValueFromPipeline = true,
83+
ParameterSetName = AccountObjectSingleParameterSet)]
6084
[Parameter(Mandatory = true,
6185
HelpMessage = "Storage account object",
6286
ValueFromPipeline = true,
@@ -75,15 +99,28 @@ public class GetAzureStorageShareCommand : StorageFileBaseCmdlet
7599

76100
[Alias("N", "ShareName")]
77101
[Parameter(HelpMessage = "Share Name",
78-
Mandatory = false)]
102+
Mandatory = true,
103+
ParameterSetName = AccountObjectSingleParameterSet)]
104+
[Parameter(HelpMessage = "Share Name",
105+
Mandatory = false,
106+
ParameterSetName = AccountNameSingleParameterSet)]
79107
public string Name { get; set; }
80108

109+
[Parameter(Mandatory = false,
110+
HelpMessage = "Include deleted shares, by default list shares won't include deleted shares",
111+
ParameterSetName = AccountNameParameterSet)]
112+
[Parameter(Mandatory = false,
113+
HelpMessage = "Include deleted shares, by default list shares won't include deleted shares",
114+
ParameterSetName = AccountObjectParameterSet)]
115+
public SwitchParameter IncludeDeleted { get; set; }
116+
81117
public override void ExecuteCmdlet()
82118
{
83119
base.ExecuteCmdlet();
84120

85121
switch (ParameterSetName)
86122
{
123+
case AccountObjectSingleParameterSet:
87124
case AccountObjectParameterSet:
88125
this.ResourceGroupName = StorageAccount.ResourceGroupName;
89126
this.StorageAccountName = StorageAccount.StorageAccountName;
@@ -95,7 +132,7 @@ public override void ExecuteCmdlet()
95132
this.Name = shareResource.ResourceName;
96133
break;
97134
default:
98-
// For AccountNameParameterSet, the ResourceGroupName and StorageAccountName can get from input directly
135+
// For AccountNameSingleParameterSet, the ResourceGroupName and StorageAccountName can get from input directly
99136
break;
100137
}
101138

@@ -109,10 +146,21 @@ public override void ExecuteCmdlet()
109146
}
110147
else
111148
{
112-
var Shares = this.StorageClient.FileShares.List(
149+
ListSharesExpand? listSharesExpand = null;
150+
if (this.IncludeDeleted.IsPresent)
151+
{
152+
listSharesExpand = ListSharesExpand.Deleted;
153+
}
154+
IPage<FileShareItem> shares = this.StorageClient.FileShares.List(
113155
this.ResourceGroupName,
114-
this.StorageAccountName);
115-
WriteShareList(Shares);
156+
this.StorageAccountName,
157+
expand: listSharesExpand);
158+
WriteShareList(shares);
159+
while (shares.NextPageLink != null)
160+
{
161+
shares = this.StorageClient.FileShares.ListNext(shares.NextPageLink);
162+
WriteShareList(shares);
163+
}
116164
}
117165
}
118166
}

0 commit comments

Comments
 (0)