fix: align backend APIs and upload flow

This commit is contained in:
2026-09-15 14:10:55 +08:00
parent 32177a7293
commit 53e6195938
149 changed files with 4791 additions and 435 deletions
@@ -11,6 +11,9 @@ namespace GroupService.Infrastructure.Configs
builder.ToTable("group_join_requests");
builder.HasKey(x => x.Id);
builder.HasKey(x => new { x.GroupId, x.UserId });
builder.HasIndex(x => x.Id).IsUnique();
builder.HasIndex(x => new { x.GroupId, x.State, x.CreationTime });
builder.HasIndex(x => new { x.UserId, x.CreationTime });
builder.ComplexProperty(x => x.UserProfile, u =>
{
@@ -9,6 +9,8 @@ namespace GroupService.Infrastructure.Configs
public void Configure(EntityTypeBuilder<GroupMember> builder)
{
builder.ToTable("group_members");
builder.HasIndex(x => new { x.UserId, x.IsDeleted, x.GroupId });
builder.HasIndex(x => new { x.GroupId, x.IsDeleted, x.Role });
}
}
}
@@ -0,0 +1,48 @@
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Migrations;
namespace GroupService.Infrastructure.Migrations
{
[DbContext(typeof(GroupDbContext))]
[Migration("20260909000200_ApiAlignmentFixes")]
public partial class ApiAlignmentFixes : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateIndex(
name: "IX_group_members_UserId_IsDeleted_GroupId",
table: "group_members",
columns: new[] { "UserId", "IsDeleted", "GroupId" });
migrationBuilder.CreateIndex(
name: "IX_group_members_GroupId_IsDeleted_Role",
table: "group_members",
columns: new[] { "GroupId", "IsDeleted", "Role" });
migrationBuilder.CreateIndex(
name: "IX_group_join_requests_Id",
table: "group_join_requests",
column: "Id",
unique: true);
migrationBuilder.CreateIndex(
name: "IX_group_join_requests_GroupId_State_CreationTime",
table: "group_join_requests",
columns: new[] { "GroupId", "State", "CreationTime" });
migrationBuilder.CreateIndex(
name: "IX_group_join_requests_UserId_CreationTime",
table: "group_join_requests",
columns: new[] { "UserId", "CreationTime" });
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropIndex("IX_group_members_UserId_IsDeleted_GroupId", "group_members");
migrationBuilder.DropIndex("IX_group_members_GroupId_IsDeleted_Role", "group_members");
migrationBuilder.DropIndex("IX_group_join_requests_Id", "group_join_requests");
migrationBuilder.DropIndex("IX_group_join_requests_GroupId_State_CreationTime", "group_join_requests");
migrationBuilder.DropIndex("IX_group_join_requests_UserId_CreationTime", "group_join_requests");
}
}
}
@@ -0,0 +1,19 @@
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Migrations;
namespace GroupService.Infrastructure.Migrations;
[DbContext(typeof(GroupDbContext))]
[Migration("20260915000100_ManagementReceipts")]
public class ManagementReceipts : Migration
{
protected override void Up(MigrationBuilder m) => m.Sql("""
CREATE TABLE IF NOT EXISTS management_receipts (
Owner varchar(64) NOT NULL,
Id char(36) NOT NULL,
Payload longtext NOT NULL,
CreatedAt datetime(6) NOT NULL,
PRIMARY KEY (Owner, Id)
) CHARACTER SET utf8mb4;
""");
// Receipts are retained on rollback: losing idempotency history can repeat a previously applied action.
protected override void Down(MigrationBuilder m) { }
}
@@ -227,6 +227,13 @@ namespace GroupService.Infrastructure.Migrations
b.HasKey("GroupId", "UserId");
b.HasIndex("Id")
.IsUnique();
b.HasIndex("GroupId", "State", "CreationTime");
b.HasIndex("UserId", "CreationTime");
b.ToTable("group_join_requests", (string)null);
});
@@ -266,6 +273,10 @@ namespace GroupService.Infrastructure.Migrations
b.HasKey("Id");
b.HasIndex("GroupId", "IsDeleted", "Role");
b.HasIndex("UserId", "IsDeleted", "GroupId");
b.ToTable("group_members", (string)null);
});
#pragma warning restore 612, 618
@@ -36,5 +36,19 @@ namespace GroupService.Infrastructure.Reposities
x.UserId == userId || x.OperatorId == userId
).ToListAsync();
}
public async Task<IEnumerable<GroupJoinRequest>> FindVisibleToUserAsync(Guid userId)
{
var managedGroupIds = db.GroupMembers
.Where(member => member.UserId == userId &&
(member.Role == Domain.Enums.GroupMemberRole.Administrator ||
member.Role == Domain.Enums.GroupMemberRole.Master))
.Select(member => member.GroupId);
return await db.GroupJoinRequests
.Where(request => request.UserId == userId || managedGroupIds.Contains(request.GroupId))
.OrderByDescending(request => request.CreationTime)
.ToListAsync();
}
}
}
@@ -29,6 +29,18 @@ namespace GroupService.Infrastructure.Reposities
return await db.Groups.Where(x => x.GroupMaster == userId).ToListAsync();
}
public async Task<IEnumerable<Group>> FindByMemberIdAsync(Guid userId)
{
var groupIds = db.GroupMembers
.Where(member => member.UserId == userId)
.Select(member => member.GroupId);
return await db.Groups
.Where(group => groupIds.Contains(group.Id))
.OrderByDescending(group => group.ModificationTime ?? group.CreationTime)
.ToListAsync();
}
public async Task<IEnumerable<Group>> FindByNameAsync(string name)
{
return await db.Groups.Where(x => x.Name == name).ToListAsync();