Skip to content
Merged
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
Original file line number Diff line number Diff line change
Expand Up @@ -191,6 +191,18 @@ public AccessorResponse<ResetPassword> answerResetPassword(ResetPassword resetPa
throw new AccessorMethodNotImplementedException();
}

/**
* Reset password - Version 20260428
*
* @param resetPassword
* @return
*/
@GatewayAPI
@API(description = "Reset Password version 20260428")
public AccessorResponse<com.mx.path.model.mdx.model.id.v20260428.ResetPassword> resetPassword20260428(com.mx.path.model.mdx.model.id.v20260428.ResetPassword resetPassword) {
throw new AccessorMethodNotImplementedException();
}

/**
* Unlock user
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -270,6 +270,7 @@ public static void registerResources(GsonBuilder builder) {
}.getType(), new ModelWrappableSerializer("mfa_challenges"));
// ResetPassword
builder.registerTypeAdapter(ResetPassword.class, new ModelWrappableSerializer("reset_password"));
builder.registerTypeAdapter(com.mx.path.model.mdx.model.id.v20260428.ResetPassword.class, new ModelWrappableSerializer("reset_password"));
// ForgotUsername
builder.registerTypeAdapter(ForgotUsername.class, new ModelWrappableSerializer("forgot_username"));
// UnlockUser
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package com.mx.path.model.mdx.model.id.v20260428;

import java.util.List;

import lombok.Data;
import lombok.EqualsAndHashCode;

import com.mx.path.model.mdx.model.MdxBase;
import com.mx.path.model.mdx.model.challenges.Challenge;

@EqualsAndHashCode(callSuper = true)
@Data
public final class ResetPassword extends MdxBase<ResetPassword> {
private String username;
private List<Challenge> challenges;

public ResetPassword() {
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package com.mx.path.model.mdx.accessor.id

import com.mx.path.core.common.accessor.AccessorMethodNotImplementedException
import com.mx.path.core.common.accessor.PathResponseStatus

import spock.lang.Specification
Expand All @@ -23,4 +24,11 @@ class IdBaseAccessorTest extends Specification {
then:
response.status == PathResponseStatus.NO_CONTENT
}

def "resetPassword20260428 throws"() {
when:
subject.resetPassword20260428(null)
then:
thrown(AccessorMethodNotImplementedException)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -254,7 +254,9 @@ public final ResponseEntity<?> start(@PathVariable("clientId") String clientId,
* Always creates a new session, discards old session
*
* @return
* @deprecated Use {@link #resetPassword20260428(com.mx.path.model.mdx.model.id.v20260428.ResetPassword)}
*/
@Deprecated
@RequestMapping(value = "/reset_password", method = RequestMethod.POST)
public final ResponseEntity<ResetPassword> resetPassword() {
//This endpoint always creates a new session when it called even if there is an existing session being passed
Expand All @@ -268,6 +270,12 @@ public final ResponseEntity<ResetPassword> resetPassword() {
return new ResponseEntity<>(response.getResult().wrapped(), createMultiMapForResponse(response.getHeaders(), headers), HttpStatus.OK);
}

/**
* @param resetPasswordAuthentication
* @return
* @deprecated Use {@link #resetPassword20260428(com.mx.path.model.mdx.model.id.v20260428.ResetPassword)}
*/
@Deprecated
@RequestMapping(value = "/reset_password/challenges/{challengeId}", method = RequestMethod.PUT, consumes = MDX_MEDIA)
public final ResponseEntity<ResetPassword> resetPassword(@RequestBody ResetPassword resetPasswordAuthentication) {
AccessorResponse<ResetPassword> response = gateway().id().answerResetPassword(resetPasswordAuthentication);
Expand All @@ -281,6 +289,34 @@ public final ResponseEntity<ResetPassword> resetPassword(@RequestBody ResetPassw
return new ResponseEntity<>(result.wrapped(), createMultiMapForResponse(response.getHeaders()), status);
}

/**
* Initiates and answers the reset password workflow - Version 20260428
*
* Always creates a new session, discards old session
*
* @param resetPasswordRequest
* @return
*/
@RequestMapping(value = "/reset_password", method = RequestMethod.PUT, consumes = MDX_MEDIA)
public final ResponseEntity<com.mx.path.model.mdx.model.id.v20260428.ResetPassword> resetPassword20260428(@RequestBody com.mx.path.model.mdx.model.id.v20260428.ResetPassword resetPasswordRequest) {
//This endpoint always creates a new session when it called even if there is an existing session being passed
Session.deleteCurrent();
Session.createSession();

AccessorResponse<com.mx.path.model.mdx.model.id.v20260428.ResetPassword> response = gateway().id().resetPassword20260428(resetPasswordRequest);
com.mx.path.model.mdx.model.id.v20260428.ResetPassword result = response.getResult();

HttpHeaders headers = new HttpHeaders();
headers.add("mx-session-key", Session.current().getId());

// Return 202 returning challenge questions
HttpStatus status = HttpStatus.NO_CONTENT;
if (result.getChallenges() != null && !result.getChallenges().isEmpty()) {
status = HttpStatus.ACCEPTED;
}
return new ResponseEntity<>(result.wrapped(), createMultiMapForResponse(response.getHeaders(), headers), status);
}

@RequestMapping(value = "/forgot_username", method = RequestMethod.POST)
public final ResponseEntity<ForgotUsername> forgotUsername() {
AccessorResponse<ForgotUsername> response = gateway().id().forgotUsername();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -677,6 +677,56 @@ class AuthenticationControllerTest extends Specification implements WithMockery
response.statusCode == HttpStatus.NO_CONTENT
}

def "resetPassword20260428 - ACCEPTED"() {
given:
AuthenticationController.setGateway(gateway)
def resetPasswordRequest = new com.mx.path.model.mdx.model.id.v20260428.ResetPassword().tap {
setUsername("USER-1234")
}
def challenge = new Challenge().tap {
setId("CHALLENGE_ID_1")
setPrompt("Your password has been reset.")
setQuestions([
new Question().tap {
setId("QUESTION_ID_1")
setPrompt("Please enter your new password")
}
])
}
def expected = new com.mx.path.model.mdx.model.id.v20260428.ResetPassword().tap {
setUsername("USER-1234")
setChallenges([challenge])
}
doReturn(new AccessorResponse<com.mx.path.model.mdx.model.id.v20260428.ResetPassword>().withResult(expected).withStatus(PathResponseStatus.ACCEPTED)).when(id).resetPassword20260428(resetPasswordRequest)

when:
def response = subject.resetPassword20260428(resetPasswordRequest)

then:
verify(gateway).id() || true
verify(id).resetPassword20260428(resetPasswordRequest) || true
response.statusCode == HttpStatus.ACCEPTED
Session.current().getId() == response.getHeaders().getFirst("mx-session-key")
}

def "resetPassword20260428 - NO_CONTENT"() {
given:
AuthenticationController.setGateway(gateway)
def resetPasswordRequest = new com.mx.path.model.mdx.model.id.v20260428.ResetPassword().tap {
setUsername("USER-1234")
}
doReturn(new AccessorResponse<com.mx.path.model.mdx.model.id.v20260428.ResetPassword>().withResult(new com.mx.path.model.mdx.model.id.v20260428.ResetPassword()).withStatus(PathResponseStatus.NO_CONTENT)).when(id).resetPassword20260428(resetPasswordRequest)

when:
def response = subject.resetPassword20260428(resetPasswordRequest)

then:
verify(gateway).id() || true
verify(id).resetPassword20260428(resetPasswordRequest) || true
response.statusCode == HttpStatus.NO_CONTENT
Session.current().getId() == response.getHeaders().getFirst("mx-session-key")
}

def "unlockUser - ACCEPTED"() {
given:
AuthenticationController.setGateway(gateway)
Expand Down
Loading
Loading