示例代码: https://download.csdn.net/download/hefeng_aspnet/90138968
介绍
我们将在 IFormFile 接口和 .NET 提供的其他接口的帮助下,逐步讨论单个和多个文件上传。
- .NET 提供了一个 IFormFile 接口,代表 HTTP 请求中传输的文件。
- 此外,它还提供许多属性,如 ContentDisposition、ContentType、FileName、Headers、Name 和 Length。
- IFormFile还提供了许多方法,如复制请求流内容,打开请求流进行读取等等。
先决条件
- .NET Core 6 SDK
- Visual Studio 2022
- SQL Server
- Postman
逐步实施
步骤 1.创建一个新的 .NET Core Web API。
第 2 步。安装以下 NuGet 包。
步骤3.创建以下文件实体。
FileDetails.cs
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace FileUpload.Entities
{
[Table("FileDetails")]
public class FileDetails
{
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int ID { get; set; }
public string FileName { get; set; }
public byte[] FileData { get; set; }
public FileType FileType { get; set; }
}
}
FileUploadModel.cs
namespace FileUpload.Entities
{
public class FileUploadModel
{
public IFormFile FileDetails { get; set; }
public FileType FileType { get; set; }
}
}
FileType
namespace FileUpload.Entities
{
public enum FileType
{
PDF = 1,
DOCX = 2
}
}
步骤4.接下来,Data文件夹内的DbContextClass.cs类。
using FileUpload.Entities;
using Microsoft.EntityFrameworkCore;
namespace FileUpload.Data
{
public class DbContextClass : DbContext
{
protected readonly IConfiguration Configuration;
public DbContextClass(IConfiguration configuration)
{
Configuration = configuration;
}
protected override void OnConfiguring(DbContextOptionsBuilder options)
{
options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection"));
}
public DbSet<FileDetails> FileDetails { get; set; }
}
}
步骤5.创建IFileService和FileService文件。
IFileService.cs
using FileUpload.Entities;
namespace FileUpload.Services
{
public interface IFileService
{
public Task PostFileAsync(IFormFile fileData, FileType fileType);
public Task PostMultiFileAsync(List<FileUploadModel> fileData);
public Task DownloadFileById(int fileName);
}
}
FileService.cs
using FileUpload.Data;
using FileUpload.Entities;
using Microsoft.EntityFrameworkCore;
namespace FileUpload.Services
{
public class FileService : IFileService
{
private readonly DbContextClass dbContextClass;
public FileService(DbContextClass dbContextClass)
{
this.dbContextClass = dbContextClass;
}
public async Task PostFileAsync(IFormFile fileData, FileType fileType)
{
try
{
var fileDetails = new FileDetails()
{
ID = 0,
FileName = fileData.FileName,
FileType = fileType,
};
using (var stream = new MemoryStream())
{
fileData.CopyTo(stream);
fileDetails.FileData = stream.ToArray();
}
var result = dbContextClass.FileDetails.Add(fileDetails);
await dbContextClass.SaveChangesAsync();
}
catch (Exception)
{
throw;
}
}
public async Task PostMultiFileAsync(List<FileUploadModel> fileData)
{
try
{
foreach(FileUploadModel file in fileData)
{
var fileDetails = new FileDetails()
{
ID = 0,
FileName = file.FileDetails.FileName,
FileType = file.FileType,
};
using (var stream = new MemoryStream())
{
file.FileDetails.CopyTo(stream);
fileDetails.FileData = stream.ToArray();
}
var result = dbContextClass.FileDetails.Add(fileDetails);
}
await dbContextClass.SaveChangesAsync();
}
catch (Exception)
{
throw;
}
}
public async Task DownloadFileById(int Id)
{
try
{
var file = dbContextClass.FileDetails.Where(x => x.ID == Id).FirstOrDefaultAsync();
var content = new System.IO.MemoryStream(file.Result.FileData);
var path = Path.Combine(
Directory.GetCurrentDirectory(), "FileDownloaded",
file.Result.FileName);
await CopyStream(content, path);
}
catch (Exception)
{
throw;
}
}
public async Task CopyStream(Stream stream, string downloadPath)
{
using (var fileStream = new FileStream(downloadPath, FileMode.Create, FileAccess.Write))
{
await stream.CopyToAsync(fileStream);
}
}
}
}
步骤6.在控制器部分内创建FilesController.cs。
FilesController.cs
using FileUpload.Entities;
using FileUpload.Services;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
namespace FileUpload.Controllers
{
[Route("api/[controller]")]
[ApiController]
public class FilesController : ControllerBase
{
private readonly IFileService _uploadService;
public FilesController(IFileService uploadService)
{
_uploadService = uploadService;
}
/// <summary>
/// Single File Upload
/// </summary>
/// <param name="file"></param>
/// <returns></returns>
[HttpPost("PostSingleFile")]
public async Task<ActionResult> PostSingleFile([FromForm] FileUploadModel fileDetails)
{
if(fileDetails == null)
{
return BadRequest();
}
try
{
await _uploadService.PostFileAsync(fileDetails.FileDetails, fileDetails.FileType);
return Ok();
}
catch (Exception)
{
throw;
}
}
/// <summary>
/// Multiple File Upload
/// </summary>
/// <param name="file"></param>
/// <returns></returns>
[HttpPost("PostMultipleFile")]
public async Task<ActionResult> PostMultipleFile([FromForm] List<FileUploadModel> fileDetails)
{
if (fileDetails == null)
{
return BadRequest();
}
try
{
await _uploadService.PostMultiFileAsync(fileDetails);
return Ok();
}
catch (Exception)
{
throw;
}
}
/// <summary>
/// Download File
/// </summary>
/// <param name="file"></param>
/// <returns></returns>
[HttpGet("DownloadFile")]
public async Task<ActionResult> DownloadFile(int id)
{
if (id < 1)
{
return BadRequest();
}
try
{
await _uploadService.DownloadFileById(id);
return Ok();
}
catch (Exception)
{
throw;
}
}
}
}
第七步,在程序类和DI容器内配置一些服务。
using FileUpload.Data;
using FileUpload.Services;
var builder = WebApplication.CreateBuilder(args);
// Add services to the container.
builder.Services.AddControllers();
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
builder.Services.AddDbContext < DbContextClass > ();
builder.Services.AddScoped < IFileService, FileService > ();
var app = builder.Build();
// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment()) {
app.UseSwagger();
app.UseSwaggerUI();
}
app.UseAuthorization();
app.MapControllers();
app.Run();
步骤8.在SQL Server中创建一个新的数据库并将其命名为FileUploadDemo。
步骤9.接下来,使用以下脚本创建FileDetails表。
USE [FileUploadDemo]
GO
/****** Object: Table [dbo].[FileDetails] Script Date: 10/1/2022 5:51:22 PM ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[FileDetails](
[ID] [int] IDENTITY(1,1) NOT NULL,
[FileName] [nvarchar](80) NOT NULL,
[FileData] [varbinary](max) NOT NULL,
[FileType] [int] NULL,
CONSTRAINT [PK_FileDetails] PRIMARY KEY CLUSTERED
(
[ID] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON, OPTIMIZE_FOR_SEQUENTIAL_KEY = OFF) ON [PRIMARY]
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
GO
第十步. 将数据库连接放入 appsettings.json 文件中。
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft.AspNetCore": "Warning"
}
},
"AllowedHosts": "*",
"ConnectionStrings": {
"DefaultConnection": "Data Source=DESKTOP-****;;Initial Catalog=FileUploadDemo;User Id=sa;Password=database;"
}
}
第 11 步. 最后,我们运行该应用程序。
第 12 步。 现在,我们将使用 swagger 上传单个文件,并根据枚举 id 提供文件和文件类型。
第 13 步。 此外,对于上传多个文件,我们使用 Postman。在这里您可以看到我们使用数组索引来发送文件及其类型,并且它可以正常工作。
第14步。 稍后,我们可以根据文件ID在本地系统上的指定路径位置下载文件。
第 15 步。 您可以在这里在指定位置看到下载的文件。
此外,在数据库中,我们可以看到使用上述端点已经上传的所有文件。
结论
在本文中,我们讨论了使用 IFormFile 进行单个和多个文件上传以及使用 .NET Core Web API 的分步 i.ahat,并从数据库读取文件并将其保存到指定位置。
如果您喜欢此文章,请收藏、点赞、评论,谢谢,祝您快乐每一天。