Add pattern to all service methods for security purposes.
public async Task<Answer?> UpdateAsync(int id, UpdateAnswerDto updateAnswerDto)
{
var userId = int.Parse(_httpContextAccessor.HttpContext?.User.FindFirst("id")?.Value ?? "0");
if (userId <= 0)
throw new UnauthorizedAccessException("User not authenticated");
Answer? answer = await _lifeTrackerContext.Answer
.Include(a => a.Submission)
.FirstOrDefaultAsync(a => a.Id == id);
if (answer == null)
{
_logger.LogError("Could not find answer of id {answer}", id);
return null;
}
// Verify user owns the submission
if (answer.Submission?.UserId != userId)
throw new UnauthorizedAccessException("User does not own this submission");
answer.Text = updateAnswerDto.Text;
answer.Points = updateAnswerDto.Points;
await _lifeTrackerContext.SaveChangesAsync();
return answer;
}
With test pattern:
private static Mock<Microsoft.AspNetCore.Http.IHttpContextAccessor> CreateMockHttpContextAccessor(int userId)
{
var mockHttpContextAccessor = new Mock<Microsoft.AspNetCore.Http.IHttpContextAccessor>();
var mockHttpContext = new Mock<Microsoft.AspNetCore.Http.HttpContext>();
var mockUser = new Mock<System.Security.Claims.ClaimsPrincipal>();
mockUser.Setup(u => u.FindFirst("id")).Returns(new System.Security.Claims.Claim("id", userId.ToString()));
mockHttpContext.Setup(c => c.User).Returns(mockUser.Object);
mockHttpContextAccessor.Setup(a => a.HttpContext).Returns(mockHttpContext.Object);
return mockHttpContextAccessor;
}
// Helper to initialize services with a specific user
private void InitializeServicesWithUser(User user)
{
var mockAccessor = CreateMockHttpContextAccessor(user.Id).Object;
_questionnaireService = new EFQuestionnaireService(_context, _questionnaireLogger, mockAccessor);
_submissionService = new EFSubmissionService(_context, _submissionLogger, mockAccessor);
}
Add pattern to all service methods for security purposes.
With test pattern:
// Helper to initialize services with a specific user
private void InitializeServicesWithUser(User user)
{
var mockAccessor = CreateMockHttpContextAccessor(user.Id).Object;
_questionnaireService = new EFQuestionnaireService(_context, _questionnaireLogger, mockAccessor);
_submissionService = new EFSubmissionService(_context, _submissionLogger, mockAccessor);
}