-
Notifications
You must be signed in to change notification settings - Fork 2.6k
Add Azure Blob Storage Gen2 (ADLS HNS) support to BlobFileStore #19014
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from 7 commits
2b469e4
1f5d2a0
06a1192
7be25b8
71ced65
256835f
121557d
03c0980
8504bb4
7d16f4f
858be10
d8c9ebb
aa477e6
56b294a
89e7656
7c01e5c
3a44b79
c0c186b
08c3cf8
f0e47b9
fb6bcb6
d3442fc
fa2c62f
d91f49b
f572bd2
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -41,6 +41,46 @@ public interface IFileStore | |
| /// </remarks> | ||
| IAsyncEnumerable<IFileStoreEntry> GetDirectoryContentAsync(string path = null, bool includeSubDirectories = false); | ||
|
|
||
| /// <summary> | ||
| /// Enumerates only the files (not directories) in a given directory within the file store. | ||
| /// </summary> | ||
| /// <param name="path">The path of the directory to enumerate, or <c>null</c> to enumerate the root of the file store.</param> | ||
| /// <returns>The list of files in the given directory.</returns> | ||
| /// <remarks> | ||
| /// Default implementation filters <see cref="GetDirectoryContentAsync"/>. Implementations | ||
| /// may override this to avoid enumerating directories for better performance. | ||
| /// </remarks> | ||
| async IAsyncEnumerable<IFileStoreEntry> GetFilesAsync(string path = null) | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is supposed to be optimized in the implementations. For instance if a storage contains 1M files and 1 folder , we can now get the folder without listing the files. However this is not implemented in concrete implementations.
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I added the implementation details that are different in a table on the PR description. It will be easier for you to review that way. |
||
| { | ||
| await foreach (var entry in GetDirectoryContentAsync(path)) | ||
| { | ||
| if (!entry.IsDirectory) | ||
| { | ||
| yield return entry; | ||
| } | ||
| } | ||
| } | ||
|
|
||
| /// <summary> | ||
| /// Enumerates only the subdirectories in a given directory within the file store. | ||
| /// </summary> | ||
| /// <param name="path">The path of the directory to enumerate, or <c>null</c> to enumerate the root of the file store.</param> | ||
| /// <returns>The list of subdirectories in the given directory.</returns> | ||
| /// <remarks> | ||
| /// Default implementation filters <see cref="GetDirectoryContentAsync"/>. Implementations | ||
| /// may override this to avoid enumerating files for better performance. | ||
| /// </remarks> | ||
| async IAsyncEnumerable<IFileStoreEntry> GetDirectoriesAsync(string path = null) | ||
| { | ||
| await foreach (var entry in GetDirectoryContentAsync(path)) | ||
| { | ||
| if (entry.IsDirectory) | ||
| { | ||
| yield return entry; | ||
| } | ||
| } | ||
| } | ||
|
|
||
| /// <summary> | ||
| /// Creates a directory in the file store if it doesn't already exist. | ||
| /// </summary> | ||
|
|
@@ -113,6 +153,11 @@ public interface IFileStore | |
| /// </summary> | ||
| /// <returns>The usable space in bytes, or <see langword="null"/> if the space is unlimited.</returns> | ||
| Task<long?> GetPermittedStorageAsync() => Task.FromResult<long?>(null); | ||
|
|
||
| /// <summary> | ||
| /// Gets the capabilities supported by this file store. | ||
| /// </summary> | ||
| IFileStoreCapabilities Capabilities => FileStoreCapabilities.Default; | ||
|
Skrypt marked this conversation as resolved.
Outdated
|
||
| } | ||
|
|
||
| public static class IFileStoreExtensions | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,52 @@ | ||
| namespace OrchardCore.FileStorage; | ||
|
|
||
| /// <summary> | ||
| /// Describes the capabilities supported by a specific <see cref="IFileStore"/> implementation. | ||
| /// </summary> | ||
| public interface IFileStoreCapabilities | ||
| { | ||
| /// <summary> | ||
| /// Gets a value indicating whether the store has a true hierarchical namespace | ||
| /// (i.e. directories are first-class objects, not simulated via path prefixes). | ||
| /// </summary> | ||
| bool HasHierarchicalNamespace { get; } | ||
|
|
||
| /// <summary> | ||
| /// Gets a value indicating whether the store supports atomic (server-side) move / rename | ||
| /// that does not require a copy-then-delete round-trip. | ||
| /// </summary> | ||
| bool SupportsAtomicMove { get; } | ||
|
|
||
| /// <summary> | ||
| /// Gets a human-readable name identifying the storage provider (e.g. "Local", "Azure Blob"). | ||
| /// </summary> | ||
| string StorageProvider => "Unknown"; | ||
|
Skrypt marked this conversation as resolved.
Outdated
|
||
| } | ||
|
|
||
| /// <summary> | ||
| /// Provides a default <see cref="IFileStoreCapabilities"/> instance where all capabilities are <c>false</c>. | ||
| /// </summary> | ||
| public sealed class FileStoreCapabilities : IFileStoreCapabilities | ||
| { | ||
| /// <summary> | ||
| /// A shared instance that returns <c>false</c> for every capability. | ||
| /// </summary> | ||
| public static readonly IFileStoreCapabilities Default = new FileStoreCapabilities(); | ||
|
|
||
| public FileStoreCapabilities() | ||
| { | ||
| } | ||
|
|
||
| public FileStoreCapabilities(bool hasHierarchicalNamespace, bool supportsAtomicMove, string storageProvider = "Unknown") | ||
| { | ||
| HasHierarchicalNamespace = hasHierarchicalNamespace; | ||
| SupportsAtomicMove = supportsAtomicMove; | ||
| StorageProvider = storageProvider; | ||
| } | ||
|
|
||
| public bool HasHierarchicalNamespace { get; } | ||
|
|
||
| public bool SupportsAtomicMove { get; } | ||
|
|
||
| public string StorageProvider { get; } = "Unknown"; | ||
| } | ||
Uh oh!
There was an error while loading. Please reload this page.