Skip to content

[BE] PR 3/3: GET Endpoint for User Points History (#217)#1116

Open
Lucy-SD wants to merge 8 commits intodevelopfrom
feature/190-3/new-endpoint-Get-userScoreHistory
Open

[BE] PR 3/3: GET Endpoint for User Points History (#217)#1116
Lucy-SD wants to merge 8 commits intodevelopfrom
feature/190-3/new-endpoint-Get-userScoreHistory

Conversation

@Lucy-SD
Copy link
Collaborator

@Lucy-SD Lucy-SD commented Feb 23, 2026

Feature: GET endpoint for authenticated student progress

closes sub-issue IT-Academy-BCN/ita-challenges#217

📝Description

Exposes the final REST endpoint GET /itachallenge/api/v1/gamification/users/{userId}/history. This PR implements the endpoint to query a user's points history, using a reactive architecture and persistence in MongoDB, which allows efficient retrieval of activity breakdowns and total points balances.

✅ Acceptance Criteria

  • Accessible Endpoint: The resource must respond at the path ´/itachallenge/api/v1/gamification/users/{userId}/history´.
  • Identifier Handling: The system must process the userId as a java.util.UUID.
  • Point Calculation: The totalPoints field in the response must be the arithmetic sum of all the user's pointsEarned in the database.
  • Sort: The points history must be presented chronologically (from most recent to oldest).
  • Documentation: Swagger UI must display the endpoint with its response models and 200 (success) and 400 (validation error) codes.

🔧 Technical Details

  • Controller: UserScoreHistoryController injects UserScoreService.
  • Sorting: Data is sorted by createdAt in descending order to provide a clear timeline for the frontend.
  • Global Exception Handling: Integration with common.exception.GlobalExceptionHandler.
  • Users with no Points: We don't need to return a 404 response if an existing user has no points. We'll return an object with totalPoints = 0 and an empty Array [ ] with a
    Ok response (since this is the expected situation for a new student).

💰 Value Provided

  • Progress Visibility: It allows users to transparently view their progress and accumulated achievements within the platform.
  • Technical Decoupling: By using UUIDs as identifiers in the path, robust integration with other microservices is ensured without relying on session states or complex tokens for this specific query.

🔓 Unlocks

Unblocks QA Testing and Frontend Integration.

🔗 Dependencies

Chained to #1118

🧪 Test Implementations

  • Controller Integration Tests: Unit and Integration Testing strategy was followed using WebTestClient and Mockito.
  • Success Path: Verification that a valid UUID with records returns a 200 OK, the totalPoints are calculated correctly, and the history list is serialized in JSON.
  • Edge Case: Verification that a valid UUID with no records in the database returns a 200 OK with a default DTO (points at 0 and an empty list).
  • Error Path: Verification that a text string that does not conform to the UUID format triggers the GlobalExceptionHandler, returning a 400 Bad Request.
  • Mapping Verification: Verification that the fields in the MongoDB document (UserScoreDocument) are correctly transformed into the properties of the DTO (PointHistoryEntryDto).

🔄 Acceptance Criteria (DoD)

  • Clean Code: The code follows the project's naming and structure standards.
  • Test Coverage: The minimum test coverage required by SonarCloud for the controller and service has been achieved.
  • API Documentation: The OpenAPI/Swagger annotations have been updated and reflect actual behavior.
  • Security Review: No sensitive information (PII) is exposed in the logs; only the technical UUID is used.

👨‍💻 Technical Debts

  • Filters: Filtering by date range or transaction type is not implemented.

  • Username: Currently, the username is retrieved from the history. If the history is empty, the field returns an empty string.

  • Pagination: The history returns all records. For users with high long-term activity, pagination or date filtering should be implemented.

  • Audit Logs: Point source differentiation is currently not exposed in the API, although the data model supports it via challengeId.

  • Debt Log: Implementation of 404 errors have been formally documented in the backlog board.

@Lucy-SD
Copy link
Collaborator Author

Lucy-SD commented Feb 23, 2026

All tests passing = )

All tests pass after PR3

@Lucy-SD Lucy-SD force-pushed the feature/190-2/point-history-retrival-logic branch from a01284c to 21b48e3 Compare February 24, 2026 10:55
@Lucy-SD Lucy-SD force-pushed the feature/190-3/new-endpoint-Get-userScoreHistory branch from 3bfd607 to 5c381f4 Compare February 24, 2026 11:08
@Lucy-SD Lucy-SD force-pushed the feature/190-2/point-history-retrival-logic branch from 21b48e3 to 084f044 Compare February 24, 2026 12:05
@Lucy-SD Lucy-SD force-pushed the feature/190-3/new-endpoint-Get-userScoreHistory branch from 5c381f4 to 5de6a97 Compare February 24, 2026 22:33
Copy link
Collaborator

Choose a reason for hiding this comment

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

Align with #1118: In PR #1118 the gamification API was aligned to UserScoreService (renamed from PointsService per Iván's suggestion). For consistency across the module, this controller should inject UserScoreService instead of PointsService.
Change the import to com.itachallenge.gamification.service.UserScoreService
Replace the field and constructor parameter with UserScoreService userScoreService
Call userScoreService.getUserPointsHistory(userId) in the handler

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Done.

}

@Test
void getUserPointsHistory_WhenNoTokenProvided_Returns400BadRequest() {
Copy link
Collaborator

Choose a reason for hiding this comment

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

The AC state "Returns 401 Unauthorized if the token is missing or invalid". This test currently expects 400 Bad Request. Consider renaming the test to e.g. getUserPointsHistory_WhenNoTokenProvided_Returns401Unauthorized and asserting .expectStatus().isUnauthorized() so the behaviour and test name match the criteria.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Updated.

@pantalois pantalois force-pushed the feature/190-2/point-history-retrival-logic branch from fce0295 to ced6d51 Compare February 25, 2026 11:53
# Conflicts:
#	itachallenge-challenge/src/main/java/com/itachallenge/gamification/service/UserScoreServiceImpl.java
@Lucy-SD Lucy-SD force-pushed the feature/190-3/new-endpoint-Get-userScoreHistory branch from 5de6a97 to c9f69e8 Compare February 25, 2026 16:02
@Lucy-SD Lucy-SD changed the base branch from feature/190-2/point-history-retrival-logic to develop February 25, 2026 16:04
@Lucy-SD Lucy-SD requested a review from carlosPc1987 February 26, 2026 00:19
@Lucy-SD
Copy link
Collaborator Author

Lucy-SD commented Feb 26, 2026

All test still passing = )

image

@sonarqubecloud
Copy link

Copy link
Collaborator

@carlosPc1987 carlosPc1987 left a comment

Choose a reason for hiding this comment

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

good job Lucy

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants