Skip to content

Commit

Permalink
Fix #11001: [Storage] Inconsistencies when working with Azure file ac…
Browse files Browse the repository at this point in the history
…cess providers and BaseDirectory property

- Changed way FileItem paths are calculated
- Added more tests for both scenarios: with or without BaseDirectory
value
  • Loading branch information
sescalada committed Jul 3, 2024
1 parent 7e89235 commit 4dfaecd
Show file tree
Hide file tree
Showing 10 changed files with 568 additions and 199 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,14 @@
<PropertyGroup>
<TargetFramework>net6.0</TargetFramework>
<IsPackable>false</IsPackable>
<UserSecretsId>f4e51bff-77ff-475a-9e12-2a79b49ae2ab</UserSecretsId>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Microsoft.Extensions.Configuration" Version="6.0.1" />
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="6.0.0" />
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="6.0.0" />
<PackageReference Include="Microsoft.Extensions.Configuration.UserSecrets" Version="6.0.1" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.1.0" />
<PackageReference Include="Moq" Version="4.18.2" />
<PackageReference Include="xunit" Version="2.4.1" />
Expand Down
Original file line number Diff line number Diff line change
@@ -1,27 +1,27 @@
using System.IO;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;
using Evergine.Xrv.Core.Storage;
using Evergine.Xrv.Core.Utils;
using Xunit;

namespace Evergine.Xrv.Core.Tests.Storage
{
public class ApplicationDataFileAccessShould
public class ApplicationDataFileAccessShould : IAsyncLifetime
{
private const string TestDirectory = "test";
private readonly ApplicationDataFileAccess fileAccess;

public ApplicationDataFileAccessShould()
{
this.fileAccess = new ApplicationDataFileAccess()
{
BaseDirectory = TestDirectory,
};
this.CleanTestFolder();
string roothPath = Path.Combine(DeviceHelper.GetLocalApplicationFolderPath(), "tests");
this.fileAccess = new ApplicationDataFileAccess(roothPath);
}

Task IAsyncLifetime.InitializeAsync() => this.fileAccess.ClearAsync();

Task IAsyncLifetime.DisposeAsync() => Task.CompletedTask;

[Fact]
public async Task CreateADirectory()
{
Expand Down Expand Up @@ -62,7 +62,7 @@ public async Task EnumerateDirectoryStructure()
await TestHelpers.PrepareTestFileSystemAsync(this.fileAccess, numberOfDirectories, numberOfFilesPerDirectory);

var rootFolderFiles = await this.fileAccess.EnumerateFilesAsync();
Assert.Single(rootFolderFiles);
Assert.Equal(numberOfFilesPerDirectory, rootFolderFiles.Count());

var rootFolderDirectories = await this.fileAccess.EnumerateDirectoriesAsync();
Assert.Equal(numberOfDirectories, rootFolderDirectories.Count());
Expand Down Expand Up @@ -94,6 +94,56 @@ public async Task DeleteADirectory()
Assert.False(exists);
}

[Fact]
public async Task EnsureOnlyBaseDirectoryItemsAreEnumerated()
{
this.fileAccess.BaseDirectory = "base";

await TestHelpers.CreateTestFileAsync(this.fileAccess, "file.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "file2.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "folder/file.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "folder/file2.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "folder2/file1.txt");

var files = await this.fileAccess.EnumerateFilesAsync();
var directories = await this.fileAccess.EnumerateDirectoriesAsync();

Assert.Equal(2, files.Count());
Assert.Equal(2, directories.Count());
}

[Fact]
public async Task EnsureOnlySpecificDirectoryItemsAreEnumerated()
{
await TestHelpers.CreateTestFileAsync(this.fileAccess, "file1.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "folder/file.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "folder/file2.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "folder/folder/file.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "folder/folder/file2.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "folder/folder2/file1.txt");

var files = await this.fileAccess.EnumerateFilesAsync("folder");
var directories = await this.fileAccess.EnumerateDirectoriesAsync("folder");

Assert.Equal(2, files.Count());
Assert.Equal(2, directories.Count());
}

[Fact]
public async Task DeleteADirectoryInDepth()
{
const string directoryName = "todelete";
await TestHelpers.CreateTestFileAsync(this.fileAccess, "todelete1/file.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "todelete1/file2.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "todelete1/folder/file.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "todelete1/folder/file2.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "todelete1/folder2/file1.txt");
await this.fileAccess.DeleteDirectoryAsync(directoryName);

bool exists = await fileAccess.ExistsDirectoryAsync(directoryName);
Assert.False(exists);
}

[Fact]
public async Task RetrieveDirectoryDates()
{
Expand All @@ -114,27 +164,89 @@ public async Task RetrieveFileDates()
Assert.True(files.All(file => file.ModificationTime != null));
}

[Fact]
public async Task RetrieveFileMetadata()
{
this.fileAccess.BaseDirectory = "base";
string filePath = await TestHelpers.CreateTestFileAsync(this.fileAccess, "file.txt");
var targetFile = await fileAccess.GetFileItemAsync("file.txt");

Assert.NotNull(targetFile);
Assert.Equal("file.txt", targetFile.Name);
Assert.Equal("file.txt", targetFile.Path);
Assert.NotNull(targetFile.CreationTime);
Assert.NotNull(targetFile.ModificationTime);
Assert.NotNull(targetFile.Size);
}

[Fact]
public async Task RetrieveFileItem()
{
this.fileAccess.BaseDirectory = "base";

string filePath = await TestHelpers.CreateTestFileAsync(this.fileAccess, "file.txt");
var file = await this.fileAccess.GetFileItemAsync(filePath);
Assert.NotNull(file);
Assert.True(file.CreationTime != null);
Assert.True(file.ModificationTime != null);
Assert.NotNull(file.Size);
Assert.Equal("file.txt", file.Name);
Assert.Equal("file.txt", file.Path);
}

[Fact]
public async Task RetrieveFileItemInDeepFolder()
{
this.fileAccess.BaseDirectory = "base";

const string filePath = "path/to/the/file.txt";
await TestHelpers.CreateTestFileAsync(this.fileAccess, filePath);
var file = await this.fileAccess.GetFileItemAsync(filePath);
Assert.NotNull(file);
Assert.True(file.CreationTime != null);
Assert.True(file.ModificationTime != null);
Assert.NotNull(file.Size);
Assert.Equal("file.txt", file.Name);
Assert.Equal(filePath, file.Path);
}

private void CleanTestFolder()
[Fact]
public async Task CreateDirectoriesStructureBySingleCall()
{
var executingFolderPath = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);
var testFolderPath = Path.Combine(executingFolderPath, TestDirectory);
if (Directory.Exists(testFolderPath))
await TestHelpers.CreateTestFileAsync(this.fileAccess, "level1_1/level2/file.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "level1_2/level2/file.txt");

var directories = await this.fileAccess.EnumerateDirectoriesAsync();
Assert.Equal(2, directories.Count());

for (int i = 1; i <= directories.Count(); i++)
{
Directory.Delete(testFolderPath, true);
var directory = directories.ElementAt(i - 1);
Assert.Equal($"level1_{i}", directory.Path);
var subDirectories = await this.fileAccess.EnumerateDirectoriesAsync(directory.Path);
Assert.Single(subDirectories);
Assert.Equal($"level1_{i}/level2", subDirectories.ElementAt(0).Path);
}
}

Directory.CreateDirectory(testFolderPath);
[Fact]
public async Task CreateDirectoriesStructureWithBasePathBySingleCall()
{
this.fileAccess.BaseDirectory = "base";
await TestHelpers.CreateTestFileAsync(this.fileAccess, "level1_1/level2/file.txt");
await TestHelpers.CreateTestFileAsync(this.fileAccess, "level1_2/level2/file.txt");

var directories = await this.fileAccess.EnumerateDirectoriesAsync();
Assert.Equal(2, directories.Count());

for (int i = 1; i <= directories.Count(); i++)
{
var directory = directories.ElementAt(i - 1);
Assert.Equal($"level1_{i}", directory.Path);
var subDirectories = await this.fileAccess.EnumerateDirectoriesAsync(directory.Path);
Assert.Single(subDirectories);
Assert.Equal($"level1_{i}/level2", subDirectories.ElementAt(0).Path);
}
}
}
}
Loading

0 comments on commit 4dfaecd

Please sign in to comment.