Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
30 changes: 30 additions & 0 deletions Migrations/20240625_AddShiftRatings.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
public partial class AddShiftRatings : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "ShiftRatings",
columns: table => new
{
ShiftId = table.Column<int>(nullable: false),
FacilityId = table.Column<int>(nullable: false),
WorkerId = table.Column<int>(nullable: false),
Score = table.Column<int>(nullable: false)
},
constraints: table =>
{
table.PrimaryKey("PK_ShiftRatings", x => new { x.ShiftId, x.WorkerId });

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should the FacilityId be included as a part of the PK?

table.ForeignKey("FK_ShiftRatings_Shifts_ShiftId", x => x.ShiftId, "Shifts", "Id", onDelete: ReferentialAction.Cascade);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Remove extra spaces

table.ForeignKey("FK_ShiftRatings_Facilities_FacilityId", x => x.FacilityId, "Facilities", "Id", onDelete: ReferentialAction.Cascade);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Remove extra spaces

table.ForeignKey("FK_ShiftRatings_Workers_WorkerId", x => x.WorkerId, "Workers", "Id", onDelete: ReferentialAction.Cascade);
});

migrationBuilder.CreateIndex("IX_ShiftRatings_FacilityId", "ShiftRatings", "FacilityId");
migrationBuilder.CreateIndex("IX_ShiftRatings_WorkerId", "ShiftRatings", "WorkerId");
}

protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable("ShiftRatings");
}
}
29 changes: 26 additions & 3 deletions src/Controllers/FacilitiesController.cs
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,31 @@
public class FacilitiesController : ControllerBase
{
private readonly AppDbContext _dbContext;
public FacilitiesController(AppDbContext dbContext) => _dbContext = dbContext;
private readonly RateWorkerHandler _rateWorkerHandler;
private readonly BlockWorkerHandler _blockWorkerHandler;

[HttpGet]
public IActionResult GetFacilities() => Ok(_dbContext.Facilities.ToList());
public FacilitiesController(AppDbContext dbContext, RateWorkerHandler rateWorkerHandler, BlockWorkerHandler blockWorkerHandler)
{
_dbContext = dbContext;
_rateWorkerHandler = rateWorkerHandler;
_blockWorkerHandler = blockWorkerHandler;
}

[HttpGet("facilities/list")]

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Route is duplicating the "facilities" part.

public async Task<IActionResult> GetFacilities([FromBody] RateWorkerRequest request)

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a get method. Request should not have a body.

{
return await _dbContext.Facilities.ToListAsync();
Copy link

@EscobarMirandaK EscobarMirandaK Nov 20, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To follow the standard as the rest of the code, this should be moved to the repository, a handler and return the appropriate type.

}

[HttpPost("facilities/rate-worker")]

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Route is duplicating the "facilities" part.

public async Task<IActionResult> RateWorker([FromBody] RateWorkerRequest request)
{
return await _rateWorkerHandler.HandleAsync(request);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No validations in any part of the code to make sure the data will be properly saved.

}

[HttpPost("facilities/block-worker")]

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Route is duplicating the "facilities" part.

public async Task<IActionResult> BlockWorker([FromBody] BlockWorkerRequest request)
{
return await _blockWorkerHandler.HandleAsync(request);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No validations in any part of the code to make sure the data will be properly saved.

}
}
21 changes: 21 additions & 0 deletions src/Handlers/BlockWorkerHandler.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
public class BlockWorkerHandler
{
private readonly WorkerRepository _workerRepository;

public BlockWorkerHandler(WorkerRepository workerRepository)
{
_workerRepository = workerRepository;
}

public async Task<IActionResult> HandleAsync(BlockWorkerRequest request)
{
try
{
_workerRepository.BlockWorker(request.WorkerId, request.FacilityId);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A return needs to be added in the try statement.
if the BlockWorker is async, an await needs to be added.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A validation needs to be added to avoid duplicate records.

}
catch (Exception e)
{
return new JsonResult(new { error = e.Message });

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Logs need to be added for debugging purposes.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Depends on the complexity of the API and how public it is, this error message should not be returned.
A GUID or an identifier should be returned and saved anywhere using the identifier to search it.

}
}
}
32 changes: 32 additions & 0 deletions src/Handlers/RateWorkerHandler.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
public class RateWorkerHandler
{
private readonly AppDbContext _dbContext;

public RateWorkerHandler(AppDbContext dbContext)
{
_dbContext = dbContext;
}

public async Task<IActionResult> HandleAsync(RateWorkerRequest request)
{
try
{
var shiftRating = new ShiftRating
{
ShiftId = request.ShiftId,
FacilityId = request.FacilityId,
WorkerId = request.WorkerId,
Score = request.Score
};

_dbContext.ShiftRatings.Add(shiftRating);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is calling the DB directly instead following the structure of the BlockWorkerHandler that uses a repository.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A validation needs to be added to avoid duplicate records.

await _dbContext.SaveChangesAsync();

return new JsonResult(shiftRating);
}
catch (Exception e)
{
return new JsonResult(new { error = e.Message });

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Logs need to be added for debugging purposes.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Depends on the complexity of the API and how public it is, this error message should not be returned.
A GUID or an identifier should be returned and saved anywhere using the identifier to search it.

}
}
}
13 changes: 13 additions & 0 deletions src/Models/ShiftRating.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
public class ShiftRating
{
public int ShiftId { get; set; }
public Shift Shift { get; set; }

public int FacilityId { get; set; }
public Facility Facility { get; set; }

public int WorkerId { get; set; }
public Worker Worker { get; set; }

public int Score { get; set; }
}
1 change: 1 addition & 0 deletions src/Models/Worker.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,6 @@ public class Worker
{
public int Id { get; set; }
public string FullName { get; set; }
public string Email { get; set; }
public List<Shift> Shifts { get; set; }
}