LgInputFile
LgInputFile is the Lagoon component for file selection, upload, download, and deletion of linked files. It supports multiple file selection, folder selection, drag-and-drop, file extension or MIME type restrictions, automatic, button-triggered, or manual upload modes, as well as form modification tracking.
<LgInputFile Label="Pièces jointes"
UploadUri="api/InputFile/Upload"
LinkedFilesUri="api/InputFile/Files"
Authenticate="false" />
- Namespace :
Lagoon.UI.Components - Inherits from :
LgAriaComponentBase→LgComponentBase - Interfaces :
IFormTrackerComponent - NuGet package :
Lagoon.UI
UploadMode.Automatic launches the transfer immediately after selection. UploadMode.Button displays an internal button. UploadMode.Manual lets the page call DoUploadAsync() via @ref.
Usage
Demonstration
Try this component in the Lagoon showcase.
Endpoint contract
LgInputFile uses UploadUri for sending files and LinkedFilesUri as the base for listing, downloading, and deleting files. The routes below correspond to UploadUri="api/documents/upload" and LinkedFilesUri="api/documents/files".
POST — File reception (UploadUri)
The component sends a multipart/form-data. Files are available in Request.Form.Files.
[ApiController]
[Route("api/documents")]
public class DocumentController : LgControllerBase
{
// Contexte applicatif utilisé pour persister les métadonnées des fichiers.
private readonly ApplicationDbContext _db;
// Répertoire racine configuré côté serveur pour ne jamais exposer un chemin fourni par le client.
private readonly string _storagePath;
// Initialise les dépendances nécessaires au stockage des fichiers et de leurs métadonnées.
public DocumentController(ApplicationDbContext db, IConfiguration configuration)
{
_db = db;
_storagePath = configuration["Documents:StoragePath"];
}
// Reçoit les fichiers envoyés par LgInputFile sur UploadUri.
[HttpPost("upload")]
public IActionResult Upload()
{
Directory.CreateDirectory(_storagePath);
foreach (IFormFile file in Request.Form.Files)
{
// Crée un identifiant serveur afin de ne jamais réutiliser directement un chemin fourni par le client.
Document document = new()
{
Id = Guid.NewGuid(),
Name = file.FileName,
ContentType = string.IsNullOrEmpty(file.ContentType) ? "application/octet-stream" : file.ContentType,
Size = file.Length
};
// Stocke le fichier dans un répertoire configuré et conserve uniquement les métadonnées en base.
string path = Path.Combine(_storagePath, $"{document.Id}_{document.Name}");
using FileStream stream = new(path, FileMode.Create, FileAccess.Write);
file.CopyTo(stream);
_db.Documents.Add(document);
}
_db.SaveChanges();
return NoContent();
}
}
GET — File list (LinkedFilesUri)
The list must return LinkedFile objects. CanDownload and CanDelete control the display of actions in the component.
// Retourne les fichiers liés que LgInputFile doit afficher dans sa zone de téléchargement.
[HttpGet("files")]
public IEnumerable<LinkedFile> GetFiles()
{
// Charge seulement les métadonnées nécessaires à l'affichage pour éviter de rapatrier les contenus binaires.
return _db.Documents.Select(document => new LinkedFile
{
Id = document.Id,
Name = document.Name,
Size = document.Size,
ContentType = document.ContentType,
CanDownload = true,
CanDelete = true
});
}
LinkedFile property | Client-side role |
|---|---|
Id | Appended to LinkedFilesUri to download or delete the file. |
Name | Display name and suggested name for download. |
Size | Size displayed in the list. |
ContentType | MIME type returned by the server. |
CanDownload | Shows or hides the download action. |
CanDelete | Shows or hides the delete action. |
GET — Download (LinkedFilesUri/{id})
In DownloadMode.Direct or DownloadMode.NewTab, the endpoint returns the file stream. In DownloadMode.PresignedUrl, it returns a URL as a string.
// Retourne le contenu d'un fichier demandé par LgInputFile depuis LinkedFilesUri/{id}.
[HttpGet("files/{id:guid}")]
public IActionResult GetFile(Guid id)
{
Document document = _db.Documents.FirstOrDefault(item => item.Id == id);
if (document is null)
{
return NotFound();
}
// Reconstruit le chemin depuis l'identifiant serveur ; le client ne transmet jamais de chemin physique.
string path = Path.Combine(_storagePath, $"{document.Id}_{document.Name}");
return FileContent(path, document.Name);
}
DELETE — Deletion (LinkedFilesUri/{id})
// Supprime un fichier lié lorsque l'utilisateur clique sur l'action de suppression du composant.
[HttpDelete("files/{id:guid}")]
public IActionResult DeleteFile(Guid id)
{
Document document = _db.Documents.FirstOrDefault(item => item.Id == id);
if (document is null)
{
return NotFound();
}
// Supprime d'abord les métadonnées, puis le fichier physique s'il existe encore.
_db.Documents.Remove(document);
_db.SaveChanges();
string path = Path.Combine(_storagePath, $"{document.Id}_{document.Name}");
if (System.IO.File.Exists(path))
{
System.IO.File.Delete(path);
}
return NoContent();
}
Never expose an endpoint that receives a physical path as a parameter. The client must only manipulate an identifier (LinkedFile.Id) and the server reconstructs the path from its own data.
Selection and automatic upload
UploadMode.Automatic sends files immediately after selection if UploadUri is set and MaxUploadSize is respected.
@inherits LgPage
<LgInputFile Label="#Attachments"
UploadUri="api/documents/upload"
LinkedFilesUri="api/documents/files"
UploadMode="UploadMode.Automatic"
AllowMultipleFiles="true"
ShowFileList="true" />
Choosing the upload mode
| Mode | Behavior |
|---|---|
UploadMode.Automatic | Immediate send after selection. |
UploadMode.Button | Displays an internal launch button. |
UploadMode.Manual | Lets the page call DoUploadAsync() via @ref. |
@inherits LgPage
<LgInputFile @ref="_inputFile"
Label="#Attachments"
UploadUri="api/documents/upload"
UploadMode="UploadMode.Manual"
OnChange="OnFilesChangedAsync"
OnUploadComplete="OnUploadCompleteAsync" />
<LgButton Text="#Upload" IconName="@IconNames.All.Upload" OnClick="UploadAsync" />
public partial class DocumentPage : LgPage
{
// Référence au composant nécessaire uniquement en mode manuel pour déclencher l'envoi par code.
private LgInputFile _inputFile;
// Mémorise la taille sélectionnée afin d'afficher ou de contrôler l'état d'un bouton externe.
private long _selectedSize;
// Met à jour les informations locales après chaque changement de sélection.
private Task OnFilesChangedAsync(IFileListEntry[] files)
{
_selectedSize = files.Sum(file => file.Size);
return Task.CompletedTask;
}
// Lance l'upload manuel et intercepte les erreurs via le mécanisme standard de la page.
private async Task UploadAsync(ActionEventArgs args)
{
try
{
await _inputFile.DoUploadAsync();
}
catch (Exception ex)
{
ShowException(ex);
}
}
// Rafraîchit explicitement la liste liée après un upload réussi si d'autres données de la page en dépendent.
private Task OnUploadCompleteAsync()
{
ShowSuccess("#UploadCompleted");
return Task.CompletedTask;
}
}
Restrict accepted files
Restrictions populate the accept attribute and component-side filtering. They do not replace server-side validation.
@inherits LgPage
<LgInputFile Label="#Documents"
UploadUri="api/documents/upload"
AllowedFileExtensions="@(new List<string> { ".pdf", ".docx" })"
MaxUploadSize="10485760"
AllowDuplicate="false" />
<LgInputFile Label="#Images"
UploadUri="api/documents/upload"
AllowedFileTypes="@(new List<string> { "image/*" })"
AllowMultipleFiles="true" />
<LgInputFile Label="#FolderImport"
UploadUri="api/documents/upload"
AllowDirectories="true"
AllowMultipleFiles="true" />
Customize the selected file card
FileCardTemplate receives each IFileListEntry before upload. Use it to display size, an icon, or project information.
@inherits LgPage
<LgInputFile Label="#Images"
UploadUri="api/documents/upload"
AllowedFileTypes="@(new List<string> { "image/*" })"
ShowFileList="true">
<FileCardTemplate Context="file">
<LgIcon IconName="@IconNames.All.Image" />
<span>@file.Name</span>
<span>@Tools.BytesToHumanReadable(file.Size)</span>
</FileCardTemplate>
</LgInputFile>
Display only linked files
Disable ShowUpload to use the component as a download/delete list, for example on an already-validated record.
@inherits LgPage
<LgInputFile Label="#LinkedFiles"
LinkedFilesUri="api/documents/files"
ShowUpload="false"
FileListLabel="#LinkedFileCount"
DownloadMode="DownloadMode.NewTab"
VerticalDisplay="false"
OnDeleteComplete="OnDeleteCompleteAsync" />
public partial class DocumentPage : LgPage
{
// Notifie la page après suppression serveur pour mettre à jour d'autres compteurs ou états métier.
private Task OnDeleteCompleteAsync(LinkedFile file)
{
ShowSuccess("#FileDeleted");
return Task.CompletedTask;
}
}
Manage authentication and error handling
By default, requests use a Bearer token. OnTokenRequested allows you to provide the token explicitly; OnErrorHandling allows you to intercept an upload or download error.
@inherits LgPage
<LgInputFile Label="#SecureAttachments"
UploadUri="api/documents/upload"
LinkedFilesUri="api/documents/files"
Authenticate="true"
OnTokenRequested="GetUploadTokenAsync"
OnErrorHandling="HandleUploadErrorAsync" />
public partial class DocumentPage : LgPage
{
// Fournit un jeton spécifique lorsque les endpoints de fichiers n'utilisent pas le jeton applicatif par défaut.
private Task<string> GetUploadTokenAsync()
{
return App.GetAccessTokenValueAsync();
}
// Centralise l'affichage des erreurs de transfert pour ajouter un message métier ou une télémétrie.
private Task HandleUploadErrorAsync(Exception ex)
{
ShowException(ex);
return Task.CompletedTask;
}
}
If the server returns a 413 error (RequestEntityTooLarge), also increase the limit on the hosting side (IIS, reverse proxy, or application server). MaxUploadSize controls only client-side selection.
Properties
All [Parameter] properties of the component, including inherited ones.
| Name | Type | Default | Declared in | Description |
|---|---|---|---|---|
ActionMessage | string | "#lgFileUploadDragAndDropMessage" | LgInputFile | Message displayed in the selection area. The value is translated with CheckTranslate(). |
AllowDirectories | bool | false | LgInputFile | Allows folder selection via the webkitdirectory attribute. |
AllowDuplicate | bool | true | LgInputFile | Allows multiple files with the same name in the current selection. |
AllowMultipleFiles | bool | false | LgInputFile | Allows multiple file selection. |
AllowedFileExtensions | List<string> | new List<string>() | LgInputFile | Allowed extensions, used for the accept attribute and component-side filtering (e.g., .docx). |
AllowedFileTypes | List<string> | new List<string>() | LgInputFile | Allowed MIME types, added to the accept attribute (e.g., image/*). |
Authenticate | bool | true | LgInputFile | Adds a Bearer token to transfer and list requests if true. |
CssClass | string | null | LgInputFile | Additional CSS classes applied to the lg-input-file container. |
DownloadMode | DownloadMode | DownloadMode.Direct | LgInputFile | Download mode for linked files. |
FileCardTemplate | RenderFragment<IFileListEntry> | null | LgInputFile | Custom template to display each selected file before transfer. |
FileListLabel | string | "#lgFileUploadLinkedFileList" | LgInputFile | Text displayed before the linked file list; receives the file count. |
IgnoreFormTracking | bool | false | LgInputFile | Ignores modification tracking provided by a parent LgFormTracker. |
Label | string | null | LgInputFile | Label associated with the selection field. |
LabelContent | RenderFragment | null | LgInputFile | Custom label content. |
LinkedFilesUri | string | null | LgInputFile | URI of the endpoint listing already-linked files; also serves as the base for downloading or deleting a file by ID. |
MaxUploadSize | long | -1 | LgInputFile | Maximum total size, in bytes, for the selection to transfer. -1 disables the limit. |
OnChange | EventCallback<IFileListEntry[]> | — | LgInputFile | Callback triggered after modification of the local selection. |
OnDeleteComplete | EventCallback<LinkedFile> | — | LgInputFile | Callback triggered after successful deletion of a linked file. |
OnErrorHandling | EventCallback<Exception> | — | LgInputFile | Callback triggered when an error occurs during transfer; if absent, the error is displayed by ShowException. |
OnTokenRequested | Func<Task<string>> | null | LgInputFile | Optional callback that provides the Bearer token when Authenticate is true. |
OnUploadComplete | EventCallback | — | LgInputFile | Callback triggered after successful upload. |
ShowFileList | bool | true | LgInputFile | Displays the list of selected files in the upload area. |
ShowUpload | bool | true | LgInputFile | Enables and displays the selection/upload area. |
ShowUploadSpeed | bool | false | LgInputFile | Displays the transfer rate in the progress label if JavaScript provides it. |
UploadedFailureMessage | string | "lgFileUploadUploadedFailureMessage".Translate() | LgInputFile | Message displayed when transfer fails. |
UploadingMessage | string | "lgFileUploadUploadingMessage".Translate() | LgInputFile | Progress message during transfer. |
UploadIconName | string | IconNames.UploadBoxIcon | LgInputFile | Icon displayed in the selection area. |
UploadMode | UploadMode | UploadMode.Automatic | LgInputFile | Upload launch behavior. |
UploadUri | string | null | LgInputFile | URI of the endpoint receiving selected files. Required to upload. |
VerticalDisplay | bool | true | LgInputFile | Displays the upload area and linked file list vertically; false places them side by side. |
AriaLabel | string | null | LgAriaComponentBase | Value of the aria-label attribute of the group. |
AriaLabelledBy | string | null | LgAriaComponentBase | Value of the aria-labelledby attribute of the group. |
LgInputFile also consumes FormTracker (LgFormTracker) when an ancestor provides form tracking. This parameter is automatic: use IgnoreFormTracking to disable the component's participation in modification tracking.
Events
| Event | Type | Description |
|---|---|---|
OnChange | EventCallback<IFileListEntry[]> | Triggered after selection or removal of a local file. |
OnDeleteComplete | EventCallback<LinkedFile> | Triggered after server deletion of a linked file. |
OnErrorHandling | EventCallback<Exception> | Triggered when an upload or download error should be intercepted by the page. |
OnUploadComplete | EventCallback | Triggered after successful upload and reset of the selection. |
Public methods
| Method | Signature | Description |
|---|---|---|
CancelUploadAsync | Task CancelUploadAsync() | Cancels the ongoing direct JavaScript transfer, clears the local selection, and resets the state to ReadyToUpload. |
CheckUploadSize | bool CheckUploadSize() | Indicates whether the total selected size respects MaxUploadSize. |
DoUploadAsync | Task<bool> DoUploadAsync() | Launches the upload of the selected files. Returns true if the direct transfer succeeds. |
GetTotalSizeToUpload | long GetTotalSizeToUpload() | Returns the sum of the sizes of the selected files, in bytes. |
RefreshFilesListAsync | Task RefreshFilesListAsync() | Reloads the list of linked files from LinkedFilesUri and refreshes the display. |
Associated enumerations
UploadMode
| Value | Description |
|---|---|
Automatic | Uploads files immediately after selection. |
Button | Displays an internal button to trigger upload. |
Manual | Requires an explicit call to DoUploadAsync(). |
DownloadMode
| Value | Description |
|---|---|
Direct | The endpoint returns the file stream; the component downloads via JavaScript. |
PresignedUrl | The endpoint returns a presigned URL opened by the browser. |
NewTab | The document is opened in a new tab. |
Accessibility
- The component renders a group (
role="group") witharia-labelandaria-labelledbyfromAriaLabelandAriaLabelledBy. - Provide
Label,LabelContent,AriaLabel, orAriaLabelledByto clearly describe the drop zone. - Selected and linked files are rendered as lists (
role="list"/role="listitem") and size errors userole="alert". - The restrictions
AllowedFileExtensionsandAllowedFileTypesdo not replace a clear user message about expected formats.
Related components
LgButton— used for internal transfer, retry, and cancel actions.LgLabelAction— associates a displayed value with a contextual action.