-
Notifications
You must be signed in to change notification settings - Fork 10.5k
InputFile Component #24640
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
InputFile Component #24640
Conversation
src/Components/test/testassets/BasicTestApp/InputFileComponent.razor
Outdated
Show resolved
Hide resolved
src/Components/WebAssembly/WebAssembly/src/Hosting/WebAssemblyHostBuilder.cs
Outdated
Show resolved
Hide resolved
src/Components/Web.Extensions/src/InputFile/InputFileJsCallbacksRelay.cs
Outdated
Show resolved
Hide resolved
|
This looks really great, @MackinnonBuck! Let us know when you want another round of review. |
src/Components/Web.Extensions/src/InputFile/RemoteFileListEntryStream.cs
Outdated
Show resolved
Hide resolved
| // - Or, failing that, at least use something like System.IO.Pipelines to manage | ||
| // the supply/consumption of byte data with less custom code. | ||
|
|
||
| internal class RemoteFileListEntryStream : FileListEntryStream |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@javiercn You spoke before about doing a security review on the new file upload feature. I don't know if you had something else in mind, but one thing that occurs to me is reviewing this kind of logic to see if we can see any way it could be misused to make the server allocate arbitrary amounts of memory, or to leak memory, to get into an infinite loop, or anything like that.
Do you think that's something we should do directly within this PR review, or schedule something separate (maybe with Levi giving it a look over)?
|
Again, this looks great 👍 I see there are still a couple of API changes due (e.g., your |
src/Components/Web.Extensions/src/InputFile/FileListEntryStream.cs
Outdated
Show resolved
Hide resolved
src/Components/Web.Extensions/src/InputFile/FileListEntryStream.cs
Outdated
Show resolved
Hide resolved
src/Components/Web.Extensions/src/InputFile/FileListEntryStream.cs
Outdated
Show resolved
Hide resolved
| /// <summary> | ||
| /// Represents the data of a file selected from an <see cref="InputFile"/> component. | ||
| /// </summary> | ||
| public interface IFileListEntry |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we call this IBrowserFile? The browser API is called File: https://developer.mozilla.org/en-US/docs/Web/API/File
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is there a reason we have an interface and implementation? Do we expect users to implement this contract?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I believe properties that can be deserialized from JSON must have public setters - correct me if I'm wrong on this. If that's the case, we probably don't need users to be able to tinker with the various properties, hence the internal FileListEntry and the public IFileListEntry that describes those properties as read-only.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
IBrowserFile sounds fine to me. In most cases people won't see the type name in their code anyway since they will receive the InputFileChangeEventArgs then just iterate over its Files collection.
I believe properties that can be deserialized from JSON must have public setters - correct me if I'm wrong on this. If that's the case, we probably don't need users to be able to tinker with the various properties, hence the internal FileListEntry and the public IFileListEntry that describes those properties as read-only.
Yes, I agree. However if we wanted we could swap the "public interface, internal class" pair with a "public abstract class, internal concrete subclass" pair. That has the benefit of letting us add more members in the future non-breakingly.
Not a big deal though. Do either of you feel strongly either way?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not partial to keeping the interface - I'll go ahead and swap it for an abstract class.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actually, @SteveSandersonMS, I just want to clarify my understanding of what you had in mind. Is the change to enable us to add more properties to IBrowserFile without forcing our customers to modify their own types implementing IBrowserFile? If so, wouldn't default interface implementations solve this? The challenge with turning IBrowserFile into an abstract class is that we can't define properties in the abstract class as read-only but define them in the internal class as read-write. There are workarounds of course, but that seemed messier to me than using default interface implementation.
Yes, but do we stop reading after we reach the Size of the file in the implementation? So if I told you I had 1MB of data and tried to send you 2MB, would we stop at Size when we are pulling data from the stream within CopyToAsync? |
|
@javiercn Ah, I see what you mean now - I'll add a check for this! |
Nevermind, I think it's already covered https://github.com/dotnet/aspnetcore/pull/24640/files#diff-288a225ef1a4f388d11bacb6bbb83334R49 |
src/Components/Web.Extensions/src/InputFile/RemoteBrowserFileStream.cs
Outdated
Show resolved
Hide resolved
src/Components/Web.Extensions/src/InputFile/RemoteBrowserFileStream.cs
Outdated
Show resolved
Hide resolved
pranavkm
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Feel free to respond to my comments in a follow up PR
src/Components/Web.Extensions/src/InputFile/RemoteBrowserFileStreamOptions.cs
Show resolved
Hide resolved
src/Components/Web.Extensions/src/InputFile/RemoteBrowserFileStreamOptions.cs
Show resolved
Hide resolved
| /// security reasons, will never be supported for .NET code that runs on the server. | ||
| /// This is an advanced mechanism that should only be used in performance-critical scenarios. | ||
| /// </summary> | ||
| public interface IJSUnmarshalledRuntime |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could we mark this as [SupportedOSPlatform('browser")]? Previously you were unable to get to this contract from a Blazor server app. We have a way to indicate this is never useful in it.
src/Components/Web.Extensions/src/InputFile/RemoteBrowserFileStreamOptions.cs
Show resolved
Hide resolved
| /// This only has an effect when using Blazor Server. | ||
| /// </para> | ||
| /// </summary> | ||
| public TimeSpan SegmentFetchTimeout { get; set; } = TimeSpan.FromSeconds(3); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Consider increasing the timeout.
|
API changes are being included as part of #25248. |
|
looking for deep explanation, why imageFile.OpenReadStream(512000,cancellationToken) is limited? |
|
@hannespreishuber Sorry, I don't understand the question. If you think there's a problem or some unexplained behavior, could you please post a new issue detailing repro steps, what you expect to happen, and what happens instead? Thanks! |
|
The upload limit of 512KB as parameter size. No bigger files? or do I miss something (as there is no doc on it) |
|
What's stopping you from changing the parameter? Is it being called internally somewhere where maxAllowedSize is not configurable? The doc comments look good to me, but I don't think docs.microsoft.com has been updated yet. |
|
ah my fault. Read that Doc comment as internal limit |
Summary
InputFilefrom https://github.com/SteveSandersonMS/BlazorInputFile toM.A.C.Web.ExtensionsIJSUnmarshalledRuntimeto allowRemoteFileListEntryStreamto make unmarshalled JS invocations without reflection.RemoteFileListEntryStreamto useSystem.IO.Pipelines.Addresses #12205