TaskEntity.Number is a global, monotonically increasing, never-reused integer (displayed as #123), allocated from AppSettingsEntity.NextTaskNumber via a single UPDATE...RETURNING statement rather than MAX(number)+1, which would reissue a deleted task's number. Both insert paths (TaskRepository. AddAsync and CreateChildAsync) route through the new TaskNumberAllocator, with a bounded retry on a unique-index collision. One migration adds the columns, backfills existing rows in creation order, and creates the unique index afterwards. Data-layer only; MCP/UI wiring is later slices.
73 lines
3.6 KiB
C#
73 lines
3.6 KiB
C#
using ClaudeDo.Data.Models;
|
|
using Microsoft.EntityFrameworkCore;
|
|
using Microsoft.EntityFrameworkCore.Metadata.Builders;
|
|
|
|
namespace ClaudeDo.Data.Configuration;
|
|
|
|
public class AppSettingsEntityConfiguration : IEntityTypeConfiguration<AppSettingsEntity>
|
|
{
|
|
public void Configure(EntityTypeBuilder<AppSettingsEntity> builder)
|
|
{
|
|
builder.ToTable("app_settings");
|
|
|
|
builder.HasKey(s => s.Id);
|
|
builder.Property(s => s.Id).HasColumnName("id").ValueGeneratedNever();
|
|
|
|
builder.Property(s => s.NextTaskNumber)
|
|
.HasColumnName("next_task_number").IsRequired().HasDefaultValue(1);
|
|
|
|
builder.Property(s => s.DefaultClaudeInstructions)
|
|
.HasColumnName("default_claude_instructions").IsRequired().HasDefaultValue(string.Empty);
|
|
builder.Property(s => s.DefaultModel)
|
|
.HasColumnName("default_model").IsRequired().HasDefaultValue("sonnet");
|
|
builder.Property(s => s.DefaultMaxTurns)
|
|
.HasColumnName("default_max_turns").IsRequired().HasDefaultValue(40);
|
|
builder.Property(s => s.DefaultPermissionMode)
|
|
.HasColumnName("default_permission_mode").IsRequired().HasDefaultValue("bypassPermissions");
|
|
|
|
builder.Property(s => s.MaxTurnsCeiling)
|
|
.HasColumnName("max_turns_ceiling").IsRequired().HasDefaultValue(80);
|
|
|
|
builder.Property(s => s.MaxParallelExecutions)
|
|
.HasColumnName("max_parallel_executions").IsRequired().HasDefaultValue(1);
|
|
|
|
builder.Property(s => s.WorktreeStrategy)
|
|
.HasColumnName("worktree_strategy").IsRequired().HasDefaultValue("sibling");
|
|
builder.Property(s => s.CentralWorktreeRoot)
|
|
.HasColumnName("central_worktree_root");
|
|
builder.Property(s => s.WorktreeAutoCleanupEnabled)
|
|
.HasColumnName("worktree_auto_cleanup_enabled").IsRequired().HasDefaultValue(false);
|
|
builder.Property(s => s.WorktreeAutoCleanupDays)
|
|
.HasColumnName("worktree_auto_cleanup_days").IsRequired().HasDefaultValue(7);
|
|
|
|
builder.Property(s => s.RepoImportFolders)
|
|
.HasColumnName("repo_import_folders");
|
|
|
|
builder.Property(s => s.ReportExcludedPaths).HasColumnName("report_excluded_paths");
|
|
builder.Property(s => s.StandupWeekday).HasColumnName("standup_weekday")
|
|
.IsRequired().HasDefaultValue((int)DayOfWeek.Wednesday);
|
|
|
|
builder.Property(s => s.DailyPrepMaxTasks)
|
|
.HasColumnName("daily_prep_max_tasks").IsRequired().HasDefaultValue(5);
|
|
|
|
builder.Property(s => s.SessionSkills).HasColumnName("session_skills");
|
|
builder.Property(s => s.ModelPresets).HasColumnName("model_presets");
|
|
|
|
builder.Property(s => s.UsageGateFiveHourPct)
|
|
.HasColumnName("usage_gate_five_hour_pct").IsRequired().HasDefaultValue(80);
|
|
builder.Property(s => s.UsageGateSevenDayPct)
|
|
.HasColumnName("usage_gate_seven_day_pct").IsRequired().HasDefaultValue(90);
|
|
|
|
builder.Property(s => s.UsageThrottleFiveHourSoftPct)
|
|
.HasColumnName("usage_throttle_five_hour_soft_pct").IsRequired().HasDefaultValue(50);
|
|
builder.Property(s => s.UsageThrottleFiveHourHardPct)
|
|
.HasColumnName("usage_throttle_five_hour_hard_pct").IsRequired().HasDefaultValue(65);
|
|
builder.Property(s => s.UsageThrottleSevenDaySoftPct)
|
|
.HasColumnName("usage_throttle_seven_day_soft_pct").IsRequired().HasDefaultValue(50);
|
|
builder.Property(s => s.UsageThrottleSevenDayHardPct)
|
|
.HasColumnName("usage_throttle_seven_day_hard_pct").IsRequired().HasDefaultValue(65);
|
|
|
|
builder.HasData(new AppSettingsEntity { Id = AppSettingsEntity.SingletonId });
|
|
}
|
|
}
|