Skip to content

Commit 5fe8e95

Browse files
committed
- Address CR feedback: createUserAndSendEmail now throws MessagingException | ConfigurationException; callers handle exception.
- verifyCaptcha no longer clears the session attribute. Captcha stays valid for retry if a later step fails (matching LoginController's RegisterUserAction pattern) - Added new clearCaptcha() that is called only after the full operation succeeds in BeginAction and SignUpApiAction - validateSignupForm uses equalsIgnoreCase for email/emailConfirm comparison - signupPage.jsp: restored explicit action URL (urlFor(BeginAction.class)) lost in the rewrite Co-Authored-By: Claude <[email protected]>
1 parent 3e1101f commit 5fe8e95

2 files changed

Lines changed: 52 additions & 30 deletions

File tree

signup/src/org/labkey/signup/SignUpController.java

Lines changed: 50 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -591,11 +591,22 @@ public boolean handlePost(SignupForm signupForm, BindException errors) throws Ex
591591
return false;
592592
}
593593

594-
if (!createUserAndSendEmail(signupForm, email, errors))
594+
try
595595
{
596+
createUserAndSendEmail(signupForm, email);
597+
}
598+
catch (MessagingException | ConfigurationException e)
599+
{
600+
errors.reject(ERROR_MSG, sendEmailErrorMessage(getContainer()));
601+
if (e.getMessage() != null)
602+
{
603+
errors.reject(ERROR_MSG, e.getMessage());
604+
}
596605
return false;
597606
}
598607

608+
clearCaptcha();
609+
599610
// Re-render the JSP with the CONFIRMATION_SENT message.
600611
signupForm.setNewSignUp(false);
601612
return false;
@@ -635,14 +646,15 @@ private void validateSignupForm(SignupForm form, Errors errors)
635646
{
636647
errors.reject(ERROR_MSG, "Confirm email cannot be blank.");
637648
}
638-
else if(form.getEmail() != null && !form.getEmail().equals(form.getEmailConfirm()))
649+
else if(!StringUtils.isBlank(form.getEmail()) && !form.getEmail().equalsIgnoreCase(form.getEmailConfirm()))
639650
{
640651
errors.reject(ERROR_MSG, "Email addresses do not match.");
641652
}
642653
}
643654

644-
// On success returns null and clears the session attribute so the captcha cannot be replayed.
645-
// On failure return a user-facing error message.
655+
// On success returns null. On failure returns a user-facing error message.
656+
// Does not clear the session attribute — callers clear it after the full operation
657+
// succeeds so the user can retry with the same captcha if a later step fails.
646658
// Logging matches LoginController's RegisterUserAction.
647659
private String verifyCaptcha(String submittedText, String emailForLogging)
648660
{
@@ -658,10 +670,14 @@ private String verifyCaptcha(String submittedText, String emailForLogging)
658670
_log.warn("Captcha text did not match for signup attempt for {}", emailForLogging);
659671
return "Verification text does not match, please retry.";
660672
}
661-
session.removeAttribute(LabKeyKaptchaServlet.SESSION_KEY_VALUE);
662673
return null;
663674
}
664675

676+
private void clearCaptcha()
677+
{
678+
getViewContext().getRequest().getSession(true).removeAttribute(LabKeyKaptchaServlet.SESSION_KEY_VALUE);
679+
}
680+
665681
// Returns a parsed ValidEmail, or null if the address is invalid (errors populated).
666682
// Uses EmailValidator first because ValidEmail's constructor does not throw on bare
667683
// strings like "foo" - it silently appends the server's default domain.
@@ -685,34 +701,21 @@ private ValidEmail parseAndValidateEmail(SignupForm form, Errors errors)
685701
}
686702

687703
// Creates (or reuses) a TempUser row and sends the confirmation email in a single
688-
// transaction. On send failure the transaction is rolled back so a freshly inserted
689-
// TempUser row does not persist when the user never received a confirmation link.
690-
private boolean createUserAndSendEmail(SignupForm form, ValidEmail email, Errors errors) throws java.sql.SQLException
704+
// transaction. On send failure the exception propagates and the transaction rolls back
705+
// automatically so a freshly inserted TempUser row does not persist.
706+
private void createUserAndSendEmail(SignupForm form, ValidEmail email)
707+
throws MessagingException, ConfigurationException, java.sql.SQLException
691708
{
692709
try (DbScope.Transaction transaction = SignUpManager.getSchema().getScope().ensureTransaction())
693710
{
694711
TempUser tempUser = getTempUser(form, email);
695712
ActionURL confirmationUrl = getConfirmationURL(getContainer(), email, tempUser.getKey());
696-
try
697-
{
698-
User mockUser = new User();
699-
mockUser.setEmail(email.getEmailAddress());
700-
SecurityManager.sendEmail(getContainer(), mockUser,
701-
SecurityManager.getRegistrationMessage(null, false),
702-
email.getEmailAddress(), confirmationUrl);
703-
}
704-
catch (MessagingException | ConfigurationException e)
705-
{
706-
String systemEmail = LookAndFeelProperties.getInstance(getContainer()).getSystemEmailAddress();
707-
errors.reject(ERROR_MSG, "Could not send new user registration email. Please contact your server administrator at " + systemEmail);
708-
if (e.getMessage() != null)
709-
{
710-
errors.reject(ERROR_MSG, e.getMessage());
711-
}
712-
return false;
713-
}
713+
User mockUser = new User();
714+
mockUser.setEmail(email.getEmailAddress());
715+
SecurityManager.sendEmail(getContainer(), mockUser,
716+
SecurityManager.getRegistrationMessage(null, false),
717+
email.getEmailAddress(), confirmationUrl);
714718
transaction.commit();
715-
return true;
716719
}
717720
}
718721

@@ -723,6 +726,12 @@ private static List<String> errorsToMessages(Errors errors)
723726
.toList();
724727
}
725728

729+
private static String sendEmailErrorMessage(Container container)
730+
{
731+
return "Could not send new user registration email. Please contact your server administrator at "
732+
+ LookAndFeelProperties.getInstance(container).getSystemEmailAddress();
733+
}
734+
726735
public static ActionURL getConfirmationURL(Container c, ValidEmail email, String key)
727736
{
728737
ActionURL url = new ActionURL(ConfirmAction.class, c);
@@ -911,13 +920,25 @@ public ApiResponse execute(SignupForm signupForm, BindException errors) throws E
911920
return response;
912921
}
913922

914-
if (!createUserAndSendEmail(signupForm, email, errors))
923+
try
924+
{
925+
createUserAndSendEmail(signupForm, email);
926+
}
927+
catch (MessagingException | ConfigurationException e)
915928
{
916929
response.put("status", "ERROR");
917-
response.put("error_message", errorsToMessages(errors));
930+
List<String> messages = new ArrayList<>();
931+
messages.add(sendEmailErrorMessage(getContainer()));
932+
if (e.getMessage() != null)
933+
{
934+
messages.add(e.getMessage());
935+
}
936+
response.put("error_message", messages);
918937
return response;
919938
}
920939

940+
clearCaptcha();
941+
921942
response.put("status", "USER_ADDED");
922943
return response;
923944
}

signup/src/org/labkey/signup/signupPage.jsp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
<%@ page import="org.labkey.api.view.HttpView" %>
2+
<%@ page import="org.labkey.signup.SignUpController.BeginAction" %>
23
<%@ page import="org.labkey.signup.SignUpController.SignupForm" %>
34
<%@ page extends="org.labkey.api.jsp.JspBase" %>
45
<%@ taglib prefix="labkey" uri="http://www.labkey.org/taglib" %>
@@ -9,7 +10,7 @@
910

1011
<labkey:errors/>
1112

12-
<labkey:form method="post" layout="horizontal" autoComplete="off" style="max-width:600px;">
13+
<labkey:form method="post" action="<%=urlFor(BeginAction.class)%>" layout="horizontal" autoComplete="off" style="max-width:600px;">
1314
<labkey:input name="firstName" id="firstName" label="First Name" isRequired="true" size="50" value="<%=form.getFirstName()%>"/>
1415
<labkey:input name="lastName" id="lastName" label="Last Name" isRequired="true" size="50" value="<%=form.getLastName()%>"/>
1516
<labkey:input name="organization" id="organization" label="Organization" isRequired="true" size="50" value="<%=form.getOrganization()%>"/>

0 commit comments

Comments
 (0)