Skip to content

Commit

Permalink
Merge pull request #120 from rdkelley/mqtt
Browse files Browse the repository at this point in the history
Add forgot password routes, onboarding links for inactive accounts
  • Loading branch information
EdrianI committed Apr 23, 2021
2 parents 8ccbe51 + aa09dda commit 429da39
Show file tree
Hide file tree
Showing 8 changed files with 263 additions and 65 deletions.
66 changes: 49 additions & 17 deletions web/api/rest/routes.js
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,9 @@ module.exports = (app) => {
*/
app.post('/api/verification', apiKeyAuth, async (req, res) => {
const { email, givenName, familyName } = req.body;
let link;
let results;
let user;

if (!email || !validator.validate(email)) {
return res.status(400).json({ message: 'Email missing' });
Expand All @@ -57,20 +59,16 @@ module.exports = (app) => {

// If no user, create user
if (results.totalResults === 0) {
const user = await AppIdManagement.createUser(
email,
givenName,
familyName,
);

const token = await jwt.encode({ id: user.id });
user = await AppIdManagement.createUser(email, givenName, familyName);

const link = `${dashboardURL}/onboard?${qs.stringify({
token,
link = `${dashboardURL}/onboard?${qs.stringify({
token: await jwt.encode({ id: user.id }),
})}`;

return res.json({
verified: false,
new: true,
active: false,
givenName,
familyName,
email,
Expand All @@ -79,17 +77,26 @@ module.exports = (app) => {
});
}

user = results.Resources[0];

// If user has account, but has not finished
// onboarding, generate new link & token
if (!user.active) {
link = `${dashboardURL}/onboard?${qs.stringify({
token: await jwt.encode({ id: user.id }),
})}`;
}

await jwt.encode({ id: user.id });
return res.json({
verified: true,
givenName: results.Resources[0].name
? results.Resources[0].name.givenName
: null,
familyName: results.Resources[0].name
? results.Resources[0].name.familyName
: null,
uuid: results.Resources[0].id,
new: false,
active: user.active,
givenName: user.name ? user.name.givenName : null,
familyName: user.name ? user.name.familyName : null,
uuid: user.id,
email,
link: null,
link: !user.active ? link : null,
});
} catch (e) {
return res.status(500).json({ message: 'Error verifying user' });
Expand Down Expand Up @@ -255,6 +262,31 @@ module.exports = (app) => {
})(req, res, next);
});

app.post('/api/forgot-password', async (req, res) => {
const { email } = req.body;

if (!email) {
return res.status(400).json({ message: 'Missing email.' });
}

try {
await AppIdManagement.forgotPassword(email);

return res.json({ success: true });
} catch (e) {
// To not indicate whether a user exists in db,
// a success message is returned if the user is not found
if (e.message === 'user_not_found') {
return res.json({ success: true });
}

return res.status(500).json({
message: 'Error processing forgot password.',
clientCode: 'error_forgot_password',
});
}
});

app.post('/api/logout', (req, res) => {
req.session.destroy((err) => {
if (err) {
Expand Down
36 changes: 36 additions & 0 deletions web/api/services/appId.js
Original file line number Diff line number Diff line change
Expand Up @@ -242,6 +242,42 @@ class AppIdManagement {
return json;
}

async forgotPassword(email) {
const iam = await this.iamAuth;

const data = JSON.stringify({
user: email,
});

const response = await fetch(
`https://us-south.appid.cloud.ibm.com/management/v4/${TENET_ID}/cloud_directory/forgot_password`,
{
method: 'POST',
headers: {
// eslint-disable-next-line quote-props
Accept: 'application/json',
// eslint-disable-next-line quote-props
Authorization: `Bearer ${iam.token}`,
'Content-Type': 'application/json',
},
body: data,
},
);

if (!response.ok) {
const error = await response.json();
console.error(error);

if (error.error === 'user not found') {
throw new Error('user_not_found');
}

throw new Error('forgot_password_fail');
}

return response.ok;
}

async removeUser(id) {
const iam = await this.iamAuth;

Expand Down
12 changes: 12 additions & 0 deletions web/client/src/components/LoginInput/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ const LoginInput = ({
initLogin,
loginId,
setError,
setForgotPassword,
forgotPassword,
}) => {
const { t } = useContext(AppContext)
const [attemptedSubmit, setAttemptedSubmit] = useState(false)
Expand All @@ -27,6 +29,12 @@ const LoginInput = ({
const returnToEmail = () => {
setError('')
setStep(1)
setForgotPassword({
email: '',
request: false,
success: false,
error: '',
})
}

useEffect(() => {
Expand All @@ -52,6 +60,10 @@ const LoginInput = ({
onSubmit={(values, { setSubmitting }) => {
if (step === 1) {
setLoginId(values.openeewId)
setForgotPassword({
...forgotPassword,
email: values.openeewId,
})

setStep(2)
} else {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,22 +4,22 @@
bottom: 0;
right: 0;
padding: $layout-02 $layout-03;
background-color: #2C2C2C;
background-color: #2c2c2c;
border-left: 1px solid #515151;

.bx--toast-notification {
width: 100%;
color: #fff;
background-color: #393939;

border-left: 3px solid #6D96DD;
border-left: 3px solid #6d96dd;

.bx--toast-notification__icon {
fill: #6D96DD;
fill: #6d96dd;
}

a {
color: #6D96DD;
color: #6d96dd;
}
}

Expand All @@ -33,7 +33,7 @@
}
}
.tag-owner {
margin-Left: 40px;
margin-left: 40px;
}
}

Expand Down Expand Up @@ -78,9 +78,9 @@
text-align: left;
cursor: pointer;

&[data-testing-sensor="true"] {
color: #FF5D5D;
border: 1px solid #FF5D5D;
&[data-testing-sensor='true'] {
color: #ff5d5d;
border: 1px solid #ff5d5d;
}
}

Expand All @@ -91,10 +91,10 @@
.sensors-side-panel__restarting {
display: flex;
align-items: center;
position:absolute;
position: absolute;
left: calc(24px);
margin-top: 10px;
color: #9C9C9C;
color: #9c9c9c;

p {
margin-left: $spacing-02;
Expand Down
17 changes: 16 additions & 1 deletion web/client/src/content/Login/Login.scss
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,8 @@
min-height: 1.5rem;
}

.login__container .bx--inline-notification--error {
.login__container .bx--inline-notification--error,
.login__container .bx--inline-notification--success {
background: #393939;
color: white;
}
Expand All @@ -50,6 +51,16 @@
margin-right: $spacing-03;
}

.login__forgotPasswordLoading {
position: relative;
left: -5px;
}

.login__forgotPasswordSuccess span {
@include carbon--type-style('body-short-01');
color: #5ec07a;
}

.login__supportingContainer {
min-height: $layout-05;
}
Expand Down Expand Up @@ -105,4 +116,8 @@
.login__supportingContainer {
min-height: $layout-06 / 2;
}

.bx--inline-notification {
max-width: none;
}
}
Loading

0 comments on commit 429da39

Please sign in to comment.