feat(attachments): data layer for task file attachments
TaskAttachmentEntity (+config, cascade FK), TaskAttachmentRepository, and an AttachmentStore that writes files under ~/.todo-app/attachments/<taskId>/ with a path-traversal guard and a 5 MB cap. TaskPromptComposer gains an optional read-only 'Reference files' section. Migration AddTaskAttachments.
This commit is contained in:
@@ -0,0 +1,45 @@
|
||||
using ClaudeDo.Data.Models;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
|
||||
namespace ClaudeDo.Data.Repositories;
|
||||
|
||||
public sealed class TaskAttachmentRepository
|
||||
{
|
||||
private readonly ClaudeDoDbContext _context;
|
||||
|
||||
public TaskAttachmentRepository(ClaudeDoDbContext context) => _context = context;
|
||||
|
||||
public async Task AddAsync(TaskAttachmentEntity entity, CancellationToken ct = default)
|
||||
{
|
||||
_context.TaskAttachments.Add(entity);
|
||||
await _context.SaveChangesAsync(ct);
|
||||
}
|
||||
|
||||
public async Task<List<TaskAttachmentEntity>> ListByTaskIdAsync(string taskId, CancellationToken ct = default)
|
||||
{
|
||||
return await _context.TaskAttachments
|
||||
.Where(a => a.TaskId == taskId)
|
||||
.OrderBy(a => a.CreatedAt)
|
||||
.ToListAsync(ct);
|
||||
}
|
||||
|
||||
public async Task<TaskAttachmentEntity?> GetAsync(string taskId, string fileName, CancellationToken ct = default)
|
||||
{
|
||||
return await _context.TaskAttachments
|
||||
.FirstOrDefaultAsync(a => a.TaskId == taskId && a.FileName == fileName, ct);
|
||||
}
|
||||
|
||||
public async Task DeleteAsync(string taskId, string fileName, CancellationToken ct = default)
|
||||
{
|
||||
await _context.TaskAttachments
|
||||
.Where(a => a.TaskId == taskId && a.FileName == fileName)
|
||||
.ExecuteDeleteAsync(ct);
|
||||
}
|
||||
|
||||
public async Task DeleteAllForTaskAsync(string taskId, CancellationToken ct = default)
|
||||
{
|
||||
await _context.TaskAttachments
|
||||
.Where(a => a.TaskId == taskId)
|
||||
.ExecuteDeleteAsync(ct);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user