最近我们将 ASP.NET 5 Web API 以及所有 nuget 包升级到 .NET 6,一切正常,直到我们注意到新图像不再保存到我们的 MySQL 数据库中。
任何小于 40kb 的图像似乎仍然保存得很好,但一旦超过该大小,它们就无法保存。没有抛出任何错误,也没有表明任何错误的日志。
当我们检查数据库时,mediumblob 并不像我们预期的那样为空,而是一个空的 blob。告诉我“东西”被保存了。
我的直觉告诉我,在将
byte[]
交给 Entity Framework 之后,转换过程中发生了一些事情。可能与序列化有关。我知道 .NET 6 有一个新的 System.Test.Json
转换器,但我们没有使用它,我们使用的是 Newtonsoft。
我尝试过的事情:
System.Text.Json
代替,不幸的是,这不是直截了当的,并导致了大量其他问题DbContext
._dbContext.SaveChangesAsync()
之前使用断点,向我展示了 byte[]
仍然存在,并且没有任何问题。但是在SaveChanges
之后,数据库中的blob是空的。正确保存对数据库的所有其他更改。我不确定我能在这里展示什么代码。
有谁知道 .NET 6 上发生的任何更改会造成这样的问题?
文档没有列出任何重大更改,我们不得不升级,因为不再支持 .NET 5。
Startup.cs
services
.AddControllers()
.AddNewtonsoftJson(options =>
{
options.SerializerSettings.ReferenceLoopHandling = ReferenceLoopHandling.Ignore;
options.SerializerSettings.Formatting = Formatting.None;
options.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver();
options.SerializerSettings.MaxDepth = 64;
});
CampaignService.cs
:
campaignToUpdate.CampaignName = campaign.CampaignName;
campaignToUpdate.CampaignDescription = campaign.CampaignDescription;
campaignToUpdate.StartDate = campaign.StartDate;
campaignToUpdate.EndDate = campaign.EndDate;
campaignToUpdate.PrizeDescription = campaign.PrizeDescription;
campaignToUpdate.PrizeImage = campaign.PrizeImage;
campaignToUpdate.IsIndividualCampaign = campaign.IsIndividualCampaign;
campaignToUpdate.IsTeamCampaign = campaign.IsTeamCampaign;
await _dbContext.SaveChangesAsync();
DbContext.cs
:
entity.Property(e => e.PrizeImage).HasColumnType("mediumblob");
编辑1:
只要我在一个新的应用程序中更新这两个 Nuget 包,我就会得到同样的错误:
不确定这是否相关,但我们的 MySQL 服务器仍在 V5.7 上运行
编辑2:
在我的本地安装了 MySQL 8.0.27,但仍然得到相同的结果。
编辑3代码:
UpdateCampaignImageRequest
:
public class UpdateCampaignImageRequest
{
public int CampaignId { get; set; }
public byte[] Image { get; set; }
}
TestController.cs
:
[HttpPost]
public async Task<IActionResult> UpdateAsync([FromBody] UpdateCampaignImageRequest request)
{
await _dbContext.Database.BeginTransactionAsync();
var campaign = await _dbContext.Campaigns.SingleOrDefaultAsync(x => x.CampaignId == request.CampaignId);
if (campaign == null)
{
return NotFound();
}
campaign.PrizeImage = request.Image;
await _dbContext.SaveChangesAsync();
await _dbContext.Database.CommitTransactionAsync();
return Ok();
}
Campaign.cs
:
public class Campaign
{
public int CampaignId { get; set; }
public int? CompanyId { get; set; }
public int? ChallengeId { get; set; }
public string CampaignName { get; set; }
public string CampaignDescription { get; set; }
public DateTime StartDate { get; set; }
public DateTime EndDate { get; set; }
public string PrizeDescription { get; set; }
public byte[] PrizeImage { get; set; }
public string PrizeImageName { get; set; }
public string UniqueCampaignCode { get; set; }
public bool IsIndividualCampaign { get; set; }
public bool IsTeamCampaign { get; set; }
[NotMapped]
public int? TotalParticipants { get; set; }
[NotMapped]
public string CurrentLeader { get; set; }
[NotMapped]
public bool HasInviteEmailSent { get; set; }
}
Context.cs
:
public partial class Context : DbContext
{
public Context()
{
}
public Context(DbContextOptions<Context> options)
: base(options)
{
}
public virtual DbSet<Campaign> Campaigns { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Campaign>(entity =>
{
entity.HasIndex(e => e.CompanyId, "Campaigns_ibfk_1");
entity.HasIndex(e => e.ChallengeId, "Campaigns_ibfk_2_idx");
entity.HasIndex(e => new { e.StartDate, e.EndDate }, "StartDate");
entity.HasIndex(e => e.UniqueCampaignCode, "UniqueCampaignCode")
.IsUnique();
entity.Property(e => e.CampaignId).HasColumnType("int(11)");
entity.Property(e => e.CampaignDescription).HasMaxLength(128);
entity.Property(e => e.CampaignName).HasMaxLength(30);
entity.Property(e => e.ChallengeId).HasColumnType("int(11)");
entity.Property(e => e.CompanyId).HasColumnType("int(11)");
entity.Property(e => e.PrizeDescription).HasMaxLength(500);
entity.Property(e => e.PrizeImage).HasColumnType("mediumblob");
entity.Property(e => e.PrizeImageName).HasMaxLength(64);
entity.Property(e => e.UniqueCampaignCode)
.HasMaxLength(6)
.IsFixedLength(true);
});
OnModelCreatingPartial(modelBuilder);
}
partial void OnModelCreatingPartial(ModelBuilder modelBuilder);
}
使用: