Easily Render Flat Data in Blazor File Manager
Tags: blazor, development, filemanager, web
Published: 2024-04-19 20:54:55

---
title: Easily Render Flat Data in Blazor File Manager
published: true
date: 2024-04-15 16:53:49 UTC
tags: blazor, development, filemanager, web
canonical_url: https://www.syncfusion.com/blogs/post/render-flat-data-blazor-file-manager
cover_image: https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0pd22o6wnzc6xo6wp9ii.png
---
**TL;DR:** Discover how the Syncfusion Blazor File Manager simplifies file management. Learn to render flat data easily and handle file operations with code examples. Whether from local objects or cloud services, streamline your process and unlock Blazor File Manager’s potential!

The Syncfusion [Blazor File Manager](https://www.syncfusion.com/blazor-components/blazor-file-manager "Blazor File Manager Component") component is a graphical user interface that manages the file system. This component also provides easy navigation for browsing and selecting files and folders from the file system. Using this component, you can easily manage the file system and perform the most common file and folder operations like read, write, delete, create, rename, upload, edit, select, and sort.

From [2024 Volume 1](https://www.syncfusion.com/forums/187257/essential-studio-2024-volume-1-main-release-v25-1-35-is-available-for-download "Essential Studio 2024 Volume 1") onward, the Blazor File Manager includes support for rendering flat data objects.

Let’s see how to render flat data using the Blazor File Manager component with code examples.

## What is flat data?

[Flat data](https://en.wikipedia.org/wiki/Flat-file_database "Wikipedia Link: Flat-file database") of local objects refers to a collection of files and folders stored with a defined structure. These objects can also be defined locally or retrieved from any file service provider injected from external services.

## Why flat data?

Blazor File Manager can be populated from an injected service or local objects, eliminating the need for HTTP client requests and backend URL configuration. This allows you to utilize your required services, such as physical, Amazon, Azure, etc., through the File Manager’s action [events](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html "FileManagerEvents<TValue> class of Blazor File Manager"). This supports all file operations like delete, cut, copy, paste, new folder creation, upload, download, etc.

## Create a Blazor app with File Manager

1. First, create a Blazor app by referring to the [documentation](https://www.syncfusion.com/faq/blazor/getting-started "Creating a Blazor app").
2. Then, render the File Manager within the Blazor app by following the steps provided on the [getting started page.](https://blazor.syncfusion.com/documentation/file-manager/getting-started "Getting started with Blazor File Manager component")

## Add Blazor File Manager component

Now, add the Syncfusion Blazor File Manager component in the Razor file. Here, we’ll add the File Manager component to the **Index.razor** file under the **~/Pages** folder.

Then, import the **Syncfusion.Blazor.FileManager** NuGet package **.**

Refer to the following code example.

```xml
@using Syncfusion.Blazor.FileManager

<SfFileManager TValue="FileManagerDirectoryContent">
 <FileManagerEvents TValue="FileManagerDirectoryContent" OnRead="OnReadAsync"></FileManagerEvents>
</SfFileManager>
```

## Binding flat data with Blazor File Manager

### List of objects

The Blazor File Manager provides the option to load a list of file or folder details with [ParentId](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerDirectoryContent.html#Syncfusion_Blazor_FileManager_FileManagerDirectoryContent_ParentId "ParentId property of Blazor File Manager") mapping by assigning the response within the corresponding events. Initial data can be loaded through the [OnRead](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_OnRead "OnRead property of Blazor File Manager") event.

```csharp
@code
{
    List<FileManagerDirectoryContent> Data { get; set; }

    protected override void OnInitialized()
    {
        Data = GetData();
    }
    private async Task OnReadAsync(ReadEventArgs<FileManagerDirectoryContent> args)
    {
        string path = args.Path;
        List<FileManagerDirectoryContent> fileDetails = args.Folder;
        FileManagerResponse<FileManagerDirectoryContent> response = new FileManagerResponse<FileManagerDirectoryContent>();
        if (path == "/")
        {
            string ParentId = Data
                .Where(x => string.IsNullOrEmpty(x.ParentId))
                .Select(x => x.Id).First();
            response.CWD = Data
                .Where(x => string.IsNullOrEmpty(x.ParentId)).First();
            response.Files = Data
                .Where(x => x.ParentId == ParentId).ToList();
        }
        else
        {
            var childItem = fileDetails.Count > 0 && fileDetails[0] != null ? fileDetails[0] : Data
                .Where(x => x.FilterPath == path).First();
            response.CWD = childItem;
            response.Files = Data
                .Where(x => x.ParentId == childItem.Id).ToList();
        }
        await Task.Yield();
        args.Response = response;
    }

    private List<FileManagerDirectoryContent> GetData()
    {
        List<FileManagerDirectoryContent> data = new List<FileManagerDirectoryContent>();
        data.Add(new FileManagerDirectoryContent()
        {
            CaseSensitive = false,
            DateCreated = new DateTime(2022, 1, 2),
            DateModified = new DateTime(2022, 2, 3),
            FilterPath = "",
            FilterId = "",
            HasChild = true,
            Id = "0",
            IsFile = false,
            Name = "Files",
            ParentId = null,
            ShowHiddenItems = false,
            Size = 1779448,
            Type = "folder"
        });
        data.Add(new FileManagerDirectoryContent()
        {
            CaseSensitive = false,
            DateCreated = new DateTime(2022, 1, 2),
            DateModified = new DateTime(2022, 2, 3),
            FilterId = "0/",
            FilterPath = "/",
            HasChild = false,
            Id = "1",
            IsFile = false,
            Name = "Documents",
            ParentId = "0",
            ShowHiddenItems = false,
            Size = 680786,
            Type = "folder"
        });
        data.Add(new FileManagerDirectoryContent()
        {
            CaseSensitive = false,
            DateCreated = new DateTime(2022, 1, 2),
            DateModified = new DateTime(2022, 2, 3),
            FilterId = "0/",
            FilterPath = "/",
            HasChild = false,
            Id = "2",
            IsFile = false,
            Name = "Downloads",
            ParentId = "0",
            ShowHiddenItems = false,
            Size = 6172,
            Type = "folder"
        });
        data.Add(new FileManagerDirectoryContent()
        {
            CaseSensitive = false,
            DateCreated = new DateTime(2022, 1, 2),
            DateModified = new DateTime(2022, 2, 3),
            FilterId = "0/1/",
            FilterPath = "/Documents/",
            HasChild = false,
            Id = "5",
            IsFile = true,
            Name = "EJ2 File Manager.docx",
            ParentId = "1",
            ShowHiddenItems = false,
            Size = 12403,
            Type = ".docx"
        });
       
    }
}
```

### Injected service

Blazor File Manager can also be populated from an injected service, eliminating the need for [FileManagerAjaxSettings](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerAjaxSettings.html "FileManagerAjaxSettings class of Blazor File Manager") URL configuration. This allows you to utilize your required services, such as physical, Amazon, Azure, etc., through the File Manager’s action events.

These [events](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html "FileManagerEvents<TValue> class of Blazor File Manager") enable you to access essential item details from the event argument. Subsequently, update the File Manager’s result data by incorporating the data returned from the injected service. Assign this returned data to the **Response** property of the corresponding event argument.

To set up a locally injected physical service, create a new file with the extension **.cs** within the project. Then, include this [GitHub](https://github.com/SyncfusionExamples/blazor-filemanager-with-flat-data/blob/master/FileManagerService.cs "Rendering flat data with Blazor File Manager GitHub demo") file service code and inject the created service into the **program.cs** file.

```csharp
using Flat_Data;
using Flat_Data.Data;
using Syncfusion.Blazor;
 
...
builder.Services.AddSyncfusionBlazor();
builder.Services.AddSingleton<FileManagerService>();
```

## Handling file operations

In the File Manager service, the details of the static folder  **wwwroot** directory are fetched, and all file operations, such as reading, folder creation, renaming, getting images, cutting, copying, uploading, downloading, deleting, etc., are performed in the service end. The response is mapped to the File Manager through event actions. 

Likewise, you can inject your own service with the required file operations and bind the response to the File Manager component. Here is an example of the list of file operations that can be handled through the service and action events.

### Read

The initial set of files and folders can be retrieved from the required service and mapped to the File Manager through the [OnRead](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_OnRead "OnRead property of Blazor File Manager") event response.

```csharp
public async Task OnReadAsync(ReadEventArgs<FileManagerDirectoryContent> args)
{
    args.Response = await FileManagerService.GetFiles(args.Path, false, args.Folder.ToArray());
}
```

### Folder creation

The new folder creation can be initiated from the [FolderCreating](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_FolderCreating "FolderCreating property of Blazor File Manager") event, which triggers before the folder is created.

```csharp
public async Task FolderCreatingAsync(FolderCreateEventArgs<FileManagerDirectoryContent> args)
{
        args.Response = await FileManagerService.Create(args.Path, args.FolderName,args.ParentFolder);
}
```

### Delete

The file or folder deletion can be performed through the [ItemsDeleting](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_ItemsDeleting "ItemsDeleting property of Blazor File Manager") event, which triggers before deleting an item.

```csharp
public async Task ItemsDeletingAsync(ItemsDeleteEventArgs<FileManagerDirectoryContent> args)
{
     string[] names = args.Files.Select(x => x.Name).ToArray();
     args.Response = await FileManagerService.Delete(args.Path, names, args.Files.ToArray());
}
```

### Rename

The file or a folder can be renamed through the [ItemRenaming](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_ItemRenaming "ItemRenaming property of Blazor File Manager") event, which triggers before renaming an item.

```csharp
public async Task ItemRenamingAsync(ItemRenameEventArgs<FileManagerDirectoryContent> args)
{
        args.Response = await FileManagerService.Rename(args.Path, args.File.Name, args.NewName, false, args.ShowFileExtension, args.File);
}
```

### Search

The search action can be performed through the [searching](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_Searching "Searching property of Blazor File Manager") event.

```csharp
public async Task SearchingAsync(SearchEventArgs<FileManagerDirectoryContent> args)
{
    args.Response = await FileManagerService.Search(args.Path, args.SearchText, false, false);
}
```

### Cut, copy, and paste

Moving actions like cut, copy, and paste can be performed through the [ItemsMoving](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_ItemsMoving "ItemsMoving property of Blazor File Manager") event based on the [IsCopy](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.ItemsMoveEventArgs-1.html#Syncfusion_Blazor_FileManager_ItemsMoveEventArgs_1_IsCopy "IsCopy property of Blazor File Manager") argument value.

```csharp
public async Task ItemsMovingAsync(ItemsMoveEventArgs<FileManagerDirectoryContent> args)
{
     string[] names = args.Files.Select(x => x.Name).ToArray();
     if (args.IsCopy)
     {
         args.Response = await FileManagerService.Copy(args.Path, args.TargetPath, names, args.TargetData, args.Files.ToArray());
     }
     else
     {
         args.Response = await FileManagerService.Move(args.Path, args.TargetPath, names, args.TargetData, args.Files.ToArray());
     }
}
```

### Upload

To perform an upload action in the File Manager component with injected service, utilize the [ItemsUploaded](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_ItemsUploaded "ItemsUploaded property of Blazor File Manager") event. This event enables you to access details of the file selected in the browser, providing access to metadata such as the file name, size, and content type. To read the contents of the uploaded file, invoke the [OpenReadStream()](https://learn.microsoft.com/en-us/dotnet/api/microsoft.aspnetcore.components.forms.ibrowserfile.openreadstream?view=aspnetcore-8.0 "OpenReadStream(Int64, CancellationToken) Method") method of the [IBrowserFile](https://learn.microsoft.com/en-us/dotnet/api/microsoft.aspnetcore.components.forms.ibrowserfile?view=aspnetcore-8.0 "IBrowserFile interface") interface, which returns a stream for reading the file data.

```xml
@code{

    public async Task ItemsUploadedAsync(ItemsUploadedEventArgs<FileManagerDirectoryContent> args)
    {
        string currentPath = args.Path;
        try
        {
            foreach (var file in args.Files)
            {
                var folders = (file.FileInfo.Name).Split('/');
                if (folders.Length > 1)
                {
                    for (var i = 0; i < folders.Length - 1; i++)
                    {
                        string newDirectoryPath = Path.Combine(FileManagerService.basePath + currentPath, folders[i]);
                        if (Path.GetFullPath(newDirectoryPath) != (Path.GetDirectoryName(newDirectoryPath) + Path.DirectorySeparatorChar + folders[i]))
                        {
                            throw new UnauthorizedAccessException("Access denied for Directory-traversal");
                        }
                        if (!Directory.Exists(newDirectoryPath))
                        {
                            await FileManagerService.Create(currentPath, folders[i]);
                        }
                        currentPath += folders[i] + "/";
                    }
                }
                var fullName = Path.Combine((FileManagerService.contentRootPath + currentPath), file.File.Name);
                using (var filestream = new FileStream(fullName, FileMode.Create, FileAccess.Write))
                {
                    await file.File.OpenReadStream(long.MaxValue).CopyToAsync(filestream);
                }
            }
        }
        catch (Exception ex)
        {
            Console.WriteLine(ex.Message);
        }
    }
}
```

### Download

To perform a download action in the File Manager component with injected service, utilize the [BeforeDownload](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_BeforeDownload "BeforeDownload property of Blazor File Manager") event. This will allow you to retrieve the details of the downloaded item from the event argument. Updating the downloaded file’s stream data and name to the [FileStream](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.BeforeDownloadEventArgs-1.html#Syncfusion_Blazor_FileManager_BeforeDownloadEventArgs_1_FileStream "FileStream property of Blazor File Manager") and [DownloadFileName](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.BeforeDownloadEventArgs-1.html#Syncfusion_Blazor_FileManager_BeforeDownloadEventArgs_1_DownloadFileName "DownloadFileName property of Blazor File Manager") event arguments, respectively, completes the download action.

```xml
@code{

    public void BeforeDownload(BeforeDownloadEventArgs<FileManagerDirectoryContent> args)
    {
        var downloadData = FileManagerService.Download(args.DownloadData.Path, args.DownloadData.Names, args.DownloadData.DownloadFileDetails.ToArray());
        args.FileStream = downloadData.FileStream;
        args.DownloadFileName = downloadData.FileDownloadName;
    }
}
```

### Get image

To load an image in File Manager with an injected service, utilize the [BeforeImageLoad](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.FileManagerEvents-1.html#Syncfusion_Blazor_FileManager_FileManagerEvents_1_BeforeImageLoad "BeforeImageLoad property of Blazor File Manager") event. This will allow you to retrieve the details of the downloaded item from the event argument. Updating the image file’s stream data to the event argument [FileStream](https://help.syncfusion.com/cr/blazor/Syncfusion.Blazor.FileManager.BeforeImageLoadEventArgs-1.html#Syncfusion_Blazor_FileManager_BeforeImageLoadEventArgs_1_FileStream "FileStream property of Blazor File Manager") completes the image retrieval operation.

```xml
@code{

public async Task BeforeImageLoadAsync(BeforeImageLoadEventArgs<FileManagerDirectoryContent> args)
    {
        var result = await FileManagerService.GetImage(args.ImageUrl, false, args.FileDetails);
        result.FileStream.Position = 0;
        args.FileStream = result.FileStream;
    }
}
```

### Get data from the cloud service

To get data from cloud services like Azure, Amazon, etc., we need to provide the credentials in the File Manager service constructor. Further, file operations can be handled similarly through component events.

For example, refer to the following code to perform  **a read**  operation with the **Amazon** service.

```xml
@using Syncfusion.Blazor.FileManager
@using InjectedAmazonService.Data
@inject FileManagerAmazonService FileManagerAmazonService
<SfFileManager TValue="FileManagerDirectoryContent">
    <FileManagerEvents TValue="FileManagerDirectoryContent" OnRead="OnReadAsync"></FileManagerEvents>
</SfFileManager>
@code
{
    public async Task OnReadAsync(ReadEventArgs<FileManagerDirectoryContent> args)
    {
        args.Response = await FileManagerAmazonService.GetFiles(args.Path, false, args.Folder.ToArray());
    }
}
```

**FileManagerAmazonService**

```csharp
public FileManagerAmazonService()
{
     RegisterAmazonS3("bucket-name", "<--awsAccessKeyId-->", "<--awsSecretAccessKey-->", "bucket-region");
 
}// Register the Amazon client details
public void RegisterAmazonS3(string name, string awsAccessKeyId, string awsSecretAccessKey, string region)
{
     bucketName = name;
     RegionEndpoint bucketRegion = RegionEndpoint.GetBySystemName(region);
     client = new AmazonS3Client(awsAccessKeyId, awsSecretAccessKey, bucketRegion);
     GetBucketList();
}

public async Task<FileManagerResponse<FileManagerDirectoryContent>> GetFiles(string path, bool showHiddenItems, params FileManagerDirectoryContent[] data)
{
    FileManagerDirectoryContent cwd = new FileManagerDirectoryContent();
    List<FileManagerDirectoryContent> files = new List<FileManagerDirectoryContent>();
    List<FileManagerDirectoryContent> filesS3 = new List<FileManagerDirectoryContent>();
    FileManagerResponse<FileManagerDirectoryContent> readResponse = new FileManagerResponse<FileManagerDirectoryContent>();
    await GetBucketList();
    try
    {
        if (path == "/") await ListingObjectsAsync("/", RootName, false); else await ListingObjectsAsync("/", RootName.Replace("/", "") + path, false);
        if (path == "/")
        {
            List<FileManagerDirectoryContent> s = new List<FileManagerDirectoryContent>(); // Use a list instead of an array
            foreach (var y in response.S3Objects.Where(x => x.Key == RootName)) // Use foreach loop to iterate over the filtered S3Objects
            {
                s.Add(await CreateDirectoryContentInstanceAsync(y.Key.ToString().Replace("/", ""), false, "Folder", y.Size, y.LastModified, y.LastModified, checkChild(y.Key), string.Empty)); // Add the result of CreateDirectoryContentInstance to the list
            }
            if (s.Count > 0) cwd = s[0];
        }
        else
        {
            cwd = await CreateDirectoryContentInstanceAsync(path.Split("/")[path.Split("/").Length - 2], false, "Folder", 0, DateTime.Now, DateTime.Now, Task.FromResult(response.CommonPrefixes.Count > 0 ? true : false), path.Substring(0, path.IndexOf(path.Split("/")[path.Split("/").Length - 2])));
        }
    }
    catch (Exception ex) { throw ex; }
    try
    {
        if (response.CommonPrefixes.Count > 0)
        {
            foreach (var prefix in response.CommonPrefixes)
            {
                var file = await CreateDirectoryContentInstanceAsync(getFileName(prefix, path), false, "Folder", 0, DateTime.Now, DateTime.Now, checkChild(prefix), getFilePath(prefix));
                files.Add(file);
            }
        }
    }
    catch (Exception ex) { throw ex; }
    try
    {
        if (path == "/") ListingObjectsAsync("/", RootName, false).Wait(); else ListingObjectsAsync("/", RootName.Replace("/", "") + path, false).Wait();
        if (response.S3Objects.Count > 0)
        {
            foreach (var obj in response.S3Objects.Where(x => x.Key != RootName.Replace("/", "") + path))
            {
                var file = await CreateDirectoryContentInstanceAsync(obj.Key.ToString().Replace(RootName.Replace("/", "") + path, "").Replace("/", ""), true, Path.GetExtension(obj.Key.ToString()), obj.Size, obj.LastModified, obj.LastModified, checkChild(obj.Key), getFilterPath(obj.Key, path));
                filesS3.Add(file);
            }
        }
    }
    catch (Exception ex) { throw ex; }
    if (filesS3.Count != 0) files = files.Union(filesS3).ToList();
    readResponse.CWD = cwd;
    try
    {
        if (cwd.Permission != null && !cwd.Permission.Read)
        {
            readResponse.Files = null;
            accessMessage = cwd.Permission.Message;
            throw new UnauthorizedAccessException("'" + cwd.Name + "' is not accessible. You need permission to perform the read action.");
        }
    }
    catch (Exception e)
    {
        ErrorDetails er = new ErrorDetails();
        er.Message = e.Message.ToString();
        er.Code = er.Message.Contains("is not accessible. You need permission") ? "401" : "417";
        if (er.Code == "401" && !string.IsNullOrEmpty(accessMessage)) { er.Message = accessMessage; }
        readResponse.Error = er;
        await Task.Yield();
        return await Task.FromResult(readResponse);
    }
    readResponse.Files = files;
    await Task.Yield();
    return await Task.FromResult(readResponse);
}
 
private string getFilePath(string pathString)
{
    return pathString.Substring(0, pathString.Length - pathString.Split("/")[pathString.Split("/").Length - 2].Length - 1).Substring(RootName.Length - 1);
}
 
private string getFileName(string fileName, string path)
{
    return fileName.Replace(RootName.Replace("/", "") + path, "").Replace("/", "");
}
 
private async Task<FileManagerDirectoryContent> CreateDirectoryContentInstanceAsync(string name, bool value, string type, long size, DateTime createddate, DateTime modifieddate, Task<bool> child, string filterpath)
{
    FileManagerDirectoryContent tempFile = new FileManagerDirectoryContent();
    tempFile.Name = name;
    tempFile.IsFile = value;
    tempFile.Type = type;
    tempFile.Size = size;
    tempFile.DateCreated = createddate;
    tempFile.DateModified = modifieddate;
    tempFile.HasChild = await child;
    tempFile.FilterPath = filterpath;
    tempFile.Permission = GetPathPermission(filterpath + (value ? name : Path.GetFileNameWithoutExtension(name)), value);
    return tempFile;
}
```

## References

For more details, refer to the Rendering Blazor File Manager with Flat Data project on [GitHub](https://github.com/SyncfusionExamples/blazor-filemanager-with-flat-data "Render Blazor File Manager with flat data GitHub demo") and [web](https://blazor.syncfusion.com/demos/file-manager/flat-data?theme=fluent "Example of Flat Data in Blazor File Manager") and [documentation](https://blazor.syncfusion.com/documentation/file-manager/flat-data "Flat data rendering in Blazor File Manager").

## Conclusion

Thanks for reading! We hope you enjoyed this quick introduction to the rendering of [Blazor File Manager](https://www.syncfusion.com/blazor-components/blazor-file-manager "Blazor File Manager") with flat data objects. This feature is available in the [2024 Volume 1](https://www.syncfusion.com/forums/187257/essential-studio-2024-volume-1-main-release-v25-1-35-is-available-for-download "Essential Studio 2024 Volume 1") release. Give it a try and provide your valuable feedback.

Check out our [Release Notes](https://blazor.syncfusion.com/documentation/release-notes/25.1.35?type=all "Essential Studio Release Notes") and [What’s New](https://www.syncfusion.com/products/whatsnew "Essential Studio What’s New page") pages to see other controls and features available with this release.

The new version is available on the [License and Downloads](https://www.syncfusion.com/account/login "Essential Studio License and Downloads page") page for existing Syncfusion customers. If you’re not yet our customer, you can sign up for a [30-day free trial](https://www.syncfusion.com/downloads "Get free evaluation of Essential Studio products") to evaluate these features.

For questions, you can reach us through our [support forums](https://www.syncfusion.com/forums "Syncfusion Support Forums"), [support portal](https://support.syncfusion.com/ "Syncfusion Support Portal"), or [feedback portal](https://www.syncfusion.com/feedback/ "Syncfusion Feedback Portal").

## Related blogs

- [Easily Customize the Toolbar in Blazor PDF Viewer](https://www.syncfusion.com/blogs/post/customize-toolbar-blazor-pdf-viewer "Blog: Easily Customize the Toolbar in Blazor PDF Viewer")
- [Introducing the New Blazor Timeline Component](https://www.syncfusion.com/blogs/post/new-blazor-timeline-component "Blog: Introducing the New Blazor Timeline Component")
- [Effortless Remote Debugging with Dev Tunnel in Visual Studio 2022](https://www.syncfusion.com/blogs/post/dev-tunnel-remote-debug-vs-2022 "Blog: Effortless Remote Debugging with Dev Tunnel in Visual Studio 2022")
- [What’s New in Syncfusion Blazor: 2024 Volume 1](https://www.syncfusion.com/blogs/post/whats-new-blazor-2024-vol-1 "Blog: What’s New in Syncfusion Blazor: 2024 Volume 1")