mirror of
https://github.com/meteor/meteor.git
synced 2026-05-02 03:01:46 -04:00
Merge pull request #13214 from meteor/feature/add-addemailasync-alias
[Meteor 3] Add Accounts.addEmailAsync alias
This commit is contained in:
@@ -53,7 +53,7 @@ insensitive duplicates before updates.
|
||||
|
||||
{% apibox "Accounts.setUsername" %}
|
||||
|
||||
{% apibox "Accounts.addEmail" %}
|
||||
{% apibox "Accounts.addEmailAsync" %}
|
||||
|
||||
By default, an email address is added with `{ verified: false }`. Use
|
||||
[`Accounts.sendVerificationEmail`](#Accounts-sendVerificationEmail) to send an
|
||||
|
||||
@@ -830,7 +830,7 @@ Meteor.methods(
|
||||
});
|
||||
|
||||
/**
|
||||
* @summary Add an email asynchronously address for a user. Use this instead of directly
|
||||
* @summary Asynchronously add an email address for a user. Use this instead of directly
|
||||
* updating the database. The operation will fail if there is a different user
|
||||
* with an email only differing in case. If the specified user has an existing
|
||||
* email only differing in case however, we replace it.
|
||||
@@ -841,8 +841,7 @@ Meteor.methods(
|
||||
* be marked as verified. Defaults to false.
|
||||
* @importFromPackage accounts-base
|
||||
*/
|
||||
Accounts.addEmail =
|
||||
async (userId, newEmail, verified) => {
|
||||
Accounts.addEmailAsync = async (userId, newEmail, verified) => {
|
||||
check(userId, NonEmptyString);
|
||||
check(newEmail, NonEmptyString);
|
||||
check(verified, Match.Optional(Boolean));
|
||||
@@ -851,9 +850,8 @@ Accounts.addEmail =
|
||||
verified = false;
|
||||
}
|
||||
|
||||
const user = await getUserById(userId, {fields: {emails: 1}});
|
||||
if (!user)
|
||||
throw new Meteor.Error(403, "User not found");
|
||||
const user = await getUserById(userId, { fields: { emails: 1 } });
|
||||
if (!user) throw new Meteor.Error(403, "User not found");
|
||||
|
||||
// Allow users to change their own email to a version with a different case
|
||||
|
||||
@@ -863,32 +861,35 @@ Accounts.addEmail =
|
||||
// then we are OK and (2) if this would create a conflict with other users
|
||||
// then there would already be a case-insensitive duplicate and we can't fix
|
||||
// that in this code anyway.
|
||||
const caseInsensitiveRegExp =
|
||||
new RegExp(`^${Meteor._escapeRegExp(newEmail)}$`, 'i');
|
||||
const caseInsensitiveRegExp = new RegExp(
|
||||
`^${Meteor._escapeRegExp(newEmail)}$`,
|
||||
"i"
|
||||
);
|
||||
|
||||
// TODO: This is a linear search. If we have a lot of emails.
|
||||
// we should consider using a different data structure.
|
||||
const updatedEmail =
|
||||
async (emails = [], _id) => {
|
||||
let updated = false;
|
||||
for (const email of emails) {
|
||||
if (caseInsensitiveRegExp.test(email.address)) {
|
||||
await Meteor.users.updateAsync({
|
||||
_id: _id,
|
||||
'emails.address': email.address
|
||||
}, {
|
||||
$set: {
|
||||
'emails.$.address': newEmail,
|
||||
'emails.$.verified': verified
|
||||
}
|
||||
});
|
||||
updated = true;
|
||||
const updatedEmail = async (emails = [], _id) => {
|
||||
let updated = false;
|
||||
for (const email of emails) {
|
||||
if (caseInsensitiveRegExp.test(email.address)) {
|
||||
await Meteor.users.updateAsync(
|
||||
{
|
||||
_id: _id,
|
||||
"emails.address": email.address,
|
||||
},
|
||||
{
|
||||
$set: {
|
||||
"emails.$.address": newEmail,
|
||||
"emails.$.verified": verified,
|
||||
},
|
||||
}
|
||||
}
|
||||
return updated;
|
||||
);
|
||||
updated = true;
|
||||
}
|
||||
const didUpdateOwnEmail =
|
||||
await updatedEmail(user.emails, user._id);
|
||||
}
|
||||
return updated;
|
||||
};
|
||||
const didUpdateOwnEmail = await updatedEmail(user.emails, user._id);
|
||||
|
||||
// In the other updates below, we have to do another call to
|
||||
// checkForCaseInsensitiveDuplicates to make sure that no conflicting values
|
||||
@@ -902,32 +903,45 @@ Accounts.addEmail =
|
||||
}
|
||||
|
||||
// Perform a case insensitive check for duplicates before update
|
||||
await Accounts._checkForCaseInsensitiveDuplicates('emails.address',
|
||||
'Email', newEmail, user._id);
|
||||
await Accounts._checkForCaseInsensitiveDuplicates(
|
||||
"emails.address",
|
||||
"Email",
|
||||
newEmail,
|
||||
user._id
|
||||
);
|
||||
|
||||
await Meteor.users.updateAsync({
|
||||
_id: user._id
|
||||
}, {
|
||||
$addToSet: {
|
||||
emails: {
|
||||
address: newEmail,
|
||||
verified: verified
|
||||
}
|
||||
await Meteor.users.updateAsync(
|
||||
{
|
||||
_id: user._id,
|
||||
},
|
||||
{
|
||||
$addToSet: {
|
||||
emails: {
|
||||
address: newEmail,
|
||||
verified: verified,
|
||||
},
|
||||
},
|
||||
}
|
||||
});
|
||||
);
|
||||
|
||||
// Perform another check after update, in case a matching user has been
|
||||
// inserted in the meantime
|
||||
try {
|
||||
await Accounts._checkForCaseInsensitiveDuplicates('emails.address',
|
||||
'Email', newEmail, user._id);
|
||||
await Accounts._checkForCaseInsensitiveDuplicates(
|
||||
"emails.address",
|
||||
"Email",
|
||||
newEmail,
|
||||
user._id
|
||||
);
|
||||
} catch (ex) {
|
||||
// Undo update if the check fails
|
||||
await Meteor.users.updateAsync({_id: user._id},
|
||||
{$pull: {emails: {address: newEmail}}});
|
||||
await Meteor.users.updateAsync(
|
||||
{ _id: user._id },
|
||||
{ $pull: { emails: { address: newEmail } } }
|
||||
);
|
||||
throw ex;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @summary Remove an email address asynchronously for a user. Use this instead of updating
|
||||
|
||||
@@ -1690,10 +1690,10 @@ if (Meteor.isServer) (() => {
|
||||
});
|
||||
|
||||
const newEmail = `${ Random.id() }@turing.com`;
|
||||
await Accounts.addEmail(userId, newEmail);
|
||||
await Accounts.addEmailAsync(userId, newEmail);
|
||||
|
||||
const thirdEmail = `${ Random.id() }@turing.com`;
|
||||
await Accounts.addEmail(userId, thirdEmail, true);
|
||||
await Accounts.addEmailAsync(userId, thirdEmail, true);
|
||||
const u1 = await Accounts._findUserByQuery({ id: userId })
|
||||
test.equal(u1.emails, [
|
||||
{ address: origEmail, verified: false },
|
||||
@@ -1733,7 +1733,7 @@ if (Meteor.isServer) (() => {
|
||||
});
|
||||
|
||||
const newEmail = `${ Random.id() }@turing.com`;
|
||||
await Accounts.addEmail(userId, newEmail);
|
||||
await Accounts.addEmailAsync(userId, newEmail);
|
||||
const u1 = await Accounts._findUserByQuery({ id: userId })
|
||||
test.equal(u1.emails, [
|
||||
{ address: newEmail, verified: false },
|
||||
@@ -1749,10 +1749,10 @@ if (Meteor.isServer) (() => {
|
||||
});
|
||||
|
||||
const newEmail = `${ Random.id() }@turing.com`;
|
||||
await Accounts.addEmail(userId, newEmail);
|
||||
await Accounts.addEmailAsync(userId, newEmail);
|
||||
|
||||
const thirdEmail = origEmail.toUpperCase();
|
||||
await Accounts.addEmail(userId, thirdEmail, true);
|
||||
await Accounts.addEmailAsync(userId, thirdEmail, true);
|
||||
const u1 = await Accounts._findUserByQuery({ id: userId })
|
||||
test.equal(u1.emails, [
|
||||
{ address: thirdEmail, verified: true },
|
||||
@@ -1775,7 +1775,7 @@ if (Meteor.isServer) (() => {
|
||||
|
||||
const dupEmail = user1Email.toUpperCase();
|
||||
await test.throwsAsync(
|
||||
async () => await Accounts.addEmail(userId2, dupEmail),
|
||||
async () => await Accounts.addEmailAsync(userId2, dupEmail),
|
||||
/Email already exists/
|
||||
);
|
||||
|
||||
@@ -1797,10 +1797,10 @@ if (Meteor.isServer) (() => {
|
||||
});
|
||||
|
||||
const newEmail = `${ Random.id() }@turing.com`;
|
||||
await Accounts.addEmail(userId, newEmail);
|
||||
await Accounts.addEmailAsync(userId, newEmail);
|
||||
|
||||
const thirdEmail = `${ Random.id() }@turing.com`;
|
||||
await Accounts.addEmail(userId, thirdEmail, true);
|
||||
await Accounts.addEmailAsync(userId, thirdEmail, true);
|
||||
const u1 = await Accounts._findUserByQuery({ id: userId })
|
||||
test.equal(u1.emails, [
|
||||
{ address: origEmail, verified: false },
|
||||
|
||||
@@ -815,7 +815,7 @@ insensitive duplicates before updates.
|
||||
|
||||
<ApiBox name="Accounts.setUsername" />
|
||||
|
||||
<ApiBox name="Accounts.addEmail" />
|
||||
<ApiBox name="Accounts.addEmailAsync" />
|
||||
|
||||
By default, an email address is added with `{ verified: false }`. Use
|
||||
[`Accounts.sendVerificationEmail`](#Accounts-sendVerificationEmail) to send an
|
||||
|
||||
@@ -71,5 +71,29 @@ async function someFunction() {
|
||||
|
||||
```
|
||||
|
||||
## Accounts.addEmail
|
||||
|
||||
It is no longer available, you should use `Accounts.addEmailAsync`.
|
||||
|
||||
```javascript
|
||||
import { Accounts } from "meteor/accounts-base";
|
||||
|
||||
// Before
|
||||
|
||||
Accounts.addEmail(
|
||||
"userId",
|
||||
"newEmail",
|
||||
false, // this param is optional
|
||||
);
|
||||
// After
|
||||
|
||||
await Accounts.addEmailAsync(
|
||||
"userId",
|
||||
"newEmail",
|
||||
false, // this param is optional
|
||||
);
|
||||
|
||||
```
|
||||
|
||||
|
||||
For a full list of changes check the [changelog](https://v3-docs.meteor.com/history.html#changelog) for Meteor v3
|
||||
|
||||
Reference in New Issue
Block a user