大量消息收件箱完成第一层性能优化
This commit is contained in:
@@ -58,6 +58,7 @@ public sealed class NotificationsController(
|
||||
var total = await source.CountAsync(cancellationToken);
|
||||
var items = await source
|
||||
.OrderByDescending(x => x.CreatedAt)
|
||||
.ThenByDescending(x => x.Id)
|
||||
.Skip((page - 1) * pageSize)
|
||||
.Take(pageSize)
|
||||
.Select(x => new
|
||||
|
||||
@@ -1475,8 +1475,11 @@ public sealed class AppDbContext(DbContextOptions<AppDbContext> options)
|
||||
entity.Property(x => x.Title).HasMaxLength(200);
|
||||
entity.Property(x => x.Content).HasColumnType("longtext");
|
||||
entity.Property(x => x.LinkUrl).HasMaxLength(300);
|
||||
entity.HasIndex(x => new { x.UserId, x.IsRead });
|
||||
entity.HasIndex(x => new { x.UserId, x.Category, x.CreatedAt });
|
||||
// Each inbox query starts with its recipient. Keep the selected
|
||||
// sort fields in the index so large inboxes do not need a filesort.
|
||||
entity.HasIndex(x => new { x.UserId, x.CreatedAt, x.Id });
|
||||
entity.HasIndex(x => new { x.UserId, x.IsRead, x.CreatedAt, x.Id });
|
||||
entity.HasIndex(x => new { x.UserId, x.Category, x.CreatedAt, x.Id });
|
||||
entity.HasIndex(x => x.MessageDispatchId);
|
||||
entity.HasIndex(x => x.CreatedAt);
|
||||
entity.HasOne(x => x.MessageDispatch)
|
||||
|
||||
@@ -102,6 +102,8 @@ public sealed class DevelopmentSqliteMigrator(
|
||||
"20260809_53_course_grade_statistics_refresh_settings";
|
||||
private const string ExperimentCourseGradesMigration =
|
||||
"20260809_54_experiment_course_grades";
|
||||
private const string NotificationInboxIndexesMigration =
|
||||
"20260810_55_notification_inbox_indexes";
|
||||
|
||||
public async Task MigrateAsync(CancellationToken cancellationToken = default)
|
||||
{
|
||||
@@ -731,6 +733,10 @@ public sealed class DevelopmentSqliteMigrator(
|
||||
ExperimentCourseGradesMigration,
|
||||
experimentCourseGradesExist ? [] : ExperimentCourseGradesStatements,
|
||||
cancellationToken);
|
||||
await ApplyMigrationAsync(
|
||||
NotificationInboxIndexesMigration,
|
||||
NotificationInboxIndexesStatements,
|
||||
cancellationToken);
|
||||
}
|
||||
|
||||
private async Task ApplyMigrationAsync(
|
||||
@@ -2999,6 +3005,15 @@ public sealed class DevelopmentSqliteMigrator(
|
||||
"""CREATE UNIQUE INDEX IF NOT EXISTS "IX_CourseGradeStatisticsRefreshSettings_Key" ON "CourseGradeStatisticsRefreshSettings" ("Key");"""
|
||||
];
|
||||
|
||||
private static readonly string[] NotificationInboxIndexesStatements =
|
||||
[
|
||||
"""DROP INDEX "IX_Notifications_UserId_IsRead";""",
|
||||
"""DROP INDEX "IX_Notifications_UserId_Category_CreatedAt";""",
|
||||
"""CREATE INDEX "IX_Notifications_UserId_CreatedAt_Id" ON "Notifications" ("UserId", "CreatedAt", "Id");""",
|
||||
"""CREATE INDEX "IX_Notifications_UserId_IsRead_CreatedAt_Id" ON "Notifications" ("UserId", "IsRead", "CreatedAt", "Id");""",
|
||||
"""CREATE INDEX "IX_Notifications_UserId_Category_CreatedAt_Id" ON "Notifications" ("UserId", "Category", "CreatedAt", "Id");"""
|
||||
];
|
||||
|
||||
private static readonly string[] ExperimentCourseGradesStatements =
|
||||
[
|
||||
"""
|
||||
|
||||
+6936
File diff suppressed because it is too large
Load Diff
+63
@@ -0,0 +1,63 @@
|
||||
using Microsoft.EntityFrameworkCore.Migrations;
|
||||
|
||||
#nullable disable
|
||||
|
||||
namespace Jiaowu.Api.Infrastructure.Persistence.Migrations.MySql
|
||||
{
|
||||
/// <inheritdoc />
|
||||
public partial class OptimizeNotificationInboxIndexes : Migration
|
||||
{
|
||||
/// <inheritdoc />
|
||||
protected override void Up(MigrationBuilder migrationBuilder)
|
||||
{
|
||||
migrationBuilder.DropIndex(
|
||||
name: "IX_Notifications_UserId_Category_CreatedAt",
|
||||
table: "Notifications");
|
||||
|
||||
migrationBuilder.DropIndex(
|
||||
name: "IX_Notifications_UserId_IsRead",
|
||||
table: "Notifications");
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
name: "IX_Notifications_UserId_Category_CreatedAt_Id",
|
||||
table: "Notifications",
|
||||
columns: new[] { "UserId", "Category", "CreatedAt", "Id" });
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
name: "IX_Notifications_UserId_CreatedAt_Id",
|
||||
table: "Notifications",
|
||||
columns: new[] { "UserId", "CreatedAt", "Id" });
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
name: "IX_Notifications_UserId_IsRead_CreatedAt_Id",
|
||||
table: "Notifications",
|
||||
columns: new[] { "UserId", "IsRead", "CreatedAt", "Id" });
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override void Down(MigrationBuilder migrationBuilder)
|
||||
{
|
||||
migrationBuilder.DropIndex(
|
||||
name: "IX_Notifications_UserId_Category_CreatedAt_Id",
|
||||
table: "Notifications");
|
||||
|
||||
migrationBuilder.DropIndex(
|
||||
name: "IX_Notifications_UserId_CreatedAt_Id",
|
||||
table: "Notifications");
|
||||
|
||||
migrationBuilder.DropIndex(
|
||||
name: "IX_Notifications_UserId_IsRead_CreatedAt_Id",
|
||||
table: "Notifications");
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
name: "IX_Notifications_UserId_Category_CreatedAt",
|
||||
table: "Notifications",
|
||||
columns: new[] { "UserId", "Category", "CreatedAt" });
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
name: "IX_Notifications_UserId_IsRead",
|
||||
table: "Notifications",
|
||||
columns: new[] { "UserId", "IsRead" });
|
||||
}
|
||||
}
|
||||
}
|
||||
+4
-2
@@ -3417,9 +3417,11 @@ namespace Jiaowu.Api.Infrastructure.Persistence.Migrations.MySql
|
||||
|
||||
b.HasIndex("MessageDispatchId");
|
||||
|
||||
b.HasIndex("UserId", "IsRead");
|
||||
b.HasIndex("UserId", "CreatedAt", "Id");
|
||||
|
||||
b.HasIndex("UserId", "Category", "CreatedAt");
|
||||
b.HasIndex("UserId", "Category", "CreatedAt", "Id");
|
||||
|
||||
b.HasIndex("UserId", "IsRead", "CreatedAt", "Id");
|
||||
|
||||
b.ToTable("Notifications");
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user