diff --git a/docs/history.md b/docs/history.md index 34d1da533e..1664baa212 100644 --- a/docs/history.md +++ b/docs/history.md @@ -7,6 +7,14 @@ * `email`: - `Email.send` is no longer available. Use `Email.sendAsync` instead. +* `accounts-2fa`: + - Some methods are now async. See below: + - `Accounts._is2faEnabledForUser` + - `(Meteor Method) - generate2faActivationQrCode` + - `(Meteor Method) - enableUser2fa` + - `(Meteor Method) - disableUser2fa` + - `(Meteor Method) - has2faEnabled` + * `accounts-password`: - `Accounts.sendResetPasswordEmail` is now async - `Accounts.sendEnrollmentEmail` is now async @@ -18,6 +26,14 @@ * `boilerplate-generator`: - `toHTML` is no longer available (it was already deprecated). Use `toHTMLStream` instead. +* `oauth`: + - `_endOfPopupResponseTemplate` and `_endOfRedirectResponseTemplate` are no longer a property but now a function that returns a promise of the same value as before + - the following methods are now async: + - `OAuth._renderOauthResults` + - `OAuth._endOfLoginResponse` + - `OAuth.renderEndOfLoginResponse` + - `OAuth._storePendingCredential` + - `OAuth._retrievePendingCredential` #### Internal API changes diff --git a/packages/accounts-2fa/2fa-server.js b/packages/accounts-2fa/2fa-server.js index 111a655999..45f701a2ee 100644 --- a/packages/accounts-2fa/2fa-server.js +++ b/packages/accounts-2fa/2fa-server.js @@ -13,8 +13,8 @@ Accounts._check2faEnabled = user => { ); }; -Accounts._is2faEnabledForUser = () => { - const user = Meteor.user(); +Accounts._is2faEnabledForUser = async () => { + const user = await Meteor.user(); if (!user) { throw new Meteor.Error('no-logged-user', 'No user logged in.'); } @@ -34,9 +34,9 @@ Accounts._isTokenValid = (secret, code) => { }; Meteor.methods({ - generate2faActivationQrCode(appName) { + async generate2faActivationQrCode(appName) { check(appName, String); - const user = Meteor.user(); + const user = await Meteor.user(); if (!user) { throw new Meteor.Error( @@ -59,7 +59,7 @@ Meteor.methods({ }); const svg = new QRCode(uri).svg(); - Meteor.users.update( + await Meteor.users.update( { _id: user._id }, { $set: { @@ -72,9 +72,9 @@ Meteor.methods({ return { svg, secret, uri }; }, - enableUser2fa(code) { + async enableUser2fa(code) { check(code, String); - const user = Meteor.user(); + const user = await Meteor.user(); if (!user) { throw new Meteor.Error(400, 'No user logged in.'); @@ -94,7 +94,7 @@ Meteor.methods({ Accounts._handleError('Invalid 2FA code', true, 'invalid-2fa-code'); } - Meteor.users.update( + await Meteor.users.update( { _id: user._id }, { $set: { @@ -106,14 +106,14 @@ Meteor.methods({ } ); }, - disableUser2fa() { + async disableUser2fa() { const userId = Meteor.userId(); if (!userId) { throw new Meteor.Error(400, 'No user logged in.'); } - Meteor.users.update( + await Meteor.users.update( { _id: userId }, { $unset: { @@ -122,8 +122,8 @@ Meteor.methods({ } ); }, - has2faEnabled() { - return Accounts._is2faEnabledForUser(); + async has2faEnabled() { + return await Accounts._is2faEnabledForUser(); }, }); diff --git a/packages/accounts-2fa/server_tests.js b/packages/accounts-2fa/server_tests.js index 8a95fc5602..2b627ff595 100644 --- a/packages/accounts-2fa/server_tests.js +++ b/packages/accounts-2fa/server_tests.js @@ -1,15 +1,16 @@ import { Accounts } from 'meteor/accounts-base'; import { Random } from 'meteor/random'; -const findUserById = id => Meteor.users.findOne(id); +const findUserById = + async id => await Meteor.users.findOne(id); -Tinytest.add('account - 2fa - has2faEnabled - server', test => { +Tinytest.addAsync('account - 2fa - has2faEnabled - server', async test => { // Create users - const userWithout2FA = Accounts.insertUserDoc( + const userWithout2FA = await Accounts.insertUserDoc( {}, { emails: [{ address: `${Random.id()}@meteorapp.com`, verified: true }] } ); - const userWith2FA = Accounts.insertUserDoc( + const userWith2FA = await Accounts.insertUserDoc( {}, { emails: [{ address: `${Random.id()}@meteorapp.com`, verified: true }], @@ -19,10 +20,10 @@ Tinytest.add('account - 2fa - has2faEnabled - server', test => { } ); - test.equal(Accounts._check2faEnabled(findUserById(userWithout2FA)), false); - test.equal(Accounts._check2faEnabled(findUserById(userWith2FA)), true); + test.equal(Accounts._check2faEnabled(await findUserById(userWithout2FA)), false); + test.equal(Accounts._check2faEnabled(await findUserById(userWith2FA)), true); // cleanup - Accounts.users.remove(userWithout2FA); - Accounts.users.remove(userWith2FA); + await Accounts.users.remove(userWithout2FA); + await Accounts.users.remove(userWith2FA); }); diff --git a/packages/minifier-js/minifier-tests.js b/packages/minifier-js/minifier-tests.js index ec8cdc288e..dbca03c5d1 100644 --- a/packages/minifier-js/minifier-tests.js +++ b/packages/minifier-js/minifier-tests.js @@ -1,23 +1,22 @@ -Tinytest.add('minifier-js - verify how terser handles an empty string', (test) => { - let result = meteorJsMinify(''); +Tinytest.addAsync('minifier-js - verify how terser handles an empty string', async (test) => { + let result = await meteorJsMinify(''); test.equal(result.code, ''); test.equal(result.minifier, 'terser'); }); -Tinytest.add('minifier-js - verify terser is able to minify valid javascript', (test) => { - let result = meteorJsMinify('function add(first,second){return first + second; }\n'); +Tinytest.addAsync('minifier-js - verify terser is able to minify valid javascript', async (test) => { + let result = await meteorJsMinify('function add(first,second){return first + second; }\n'); test.equal(result.code, 'function add(n,d){return n+d}'); test.equal(result.minifier, 'terser'); }); -Tinytest.add('minifier-js - verify error handling is done as expected', (test) => { - test.throws( () => meteorJsMinify('let name = {;\n'), undefined ); +Tinytest.addAsync('minifier-js - verify error handling is done as expected', async (test) => { + await test.throwsAsync( async () => await meteorJsMinify('let name = {;\n'), undefined ); }); -Tinytest.add('minifier-js - verify tersers error object has the fields we use for reporting errors to users', (test) => { - let result; +Tinytest.addAsync('minifier-js - verify tersers error object has the fields we use for reporting errors to users', async (test) => { try { - result = meteorJsMinify('let name = {;\n'); + await meteorJsMinify('let name = {;\n'); } catch (err) { test.isNotUndefined(err.name); diff --git a/packages/minifier-js/minifier.js b/packages/minifier-js/minifier.js index e1053a7e15..c0fe999508 100644 --- a/packages/minifier-js/minifier.js +++ b/packages/minifier-js/minifier.js @@ -1,18 +1,11 @@ let terser; -const terserMinify = async (source, options, callback) => { +const terserMinify = async (source, options) => { terser = terser || Npm.require("terser"); - try { - const result = await terser.minify(source, options); - callback(null, result); - return result; - } catch (e) { - callback(e); - return e; - } + return await terser.minify(source, options); }; -export const meteorJsMinify = function (source) { +export const meteorJsMinify = async function (source) { const result = {}; const NODE_ENV = process.env.NODE_ENV || "development"; @@ -33,13 +26,7 @@ export const meteorJsMinify = function (source) { safari10: true, // set this option to true to work around the Safari 10/11 await bug }; - const terserJsMinify = Meteor.wrapAsync(terserMinify); - let terserResult; - try { - terserResult = terserJsMinify(source, options); - } catch (e) { - throw e; - } + const terserResult = await terserMinify(source, options); // this is kept to maintain backwards compatability result.code = terserResult.code; diff --git a/packages/oauth/oauth_server.js b/packages/oauth/oauth_server.js index 1b591a455b..7c705d07fd 100644 --- a/packages/oauth/oauth_server.js +++ b/packages/oauth/oauth_server.js @@ -251,7 +251,7 @@ const isSafe = value => { }; // Internal: used by the oauth1 and oauth2 packages -OAuth._renderOauthResults = (res, query, credentialSecret) => { +OAuth._renderOauthResults = async (res, query, credentialSecret) => { // For tests, we support the `only_credential_secret_for_test` // parameter, which just returns the credential secret without any // surrounding HTML. (The test needs to be able to easily grab the @@ -282,18 +282,23 @@ OAuth._renderOauthResults = (res, query, credentialSecret) => { } } - OAuth._endOfLoginResponse(res, details); + await OAuth._endOfLoginResponse(res, details); } }; +const getAsset = (name) => { + return new Promise((resolve, reject) => Assets.getText( + `${name}.html`, + (err, data) => err ? reject(err) : resolve(data))) +} // This "template" (not a real Spacebars template, just an HTML file // with some ##PLACEHOLDER##s) communicates the credential secret back // to the main window and then closes the popup. -OAuth._endOfPopupResponseTemplate = Assets.getText( - "end_of_popup_response.html"); +OAuth._endOfPopupResponseTemplate = + async () => await getAsset('end_of_popup_response') -OAuth._endOfRedirectResponseTemplate = Assets.getText( - "end_of_redirect_response.html"); +OAuth._endOfRedirectResponseTemplate = + async () => await getAsset('end_of_redirect_response') // Renders the end of login response template into some HTML and JavaScript // that closes the popup or redirects at the end of the OAuth flow. @@ -306,7 +311,7 @@ OAuth._endOfRedirectResponseTemplate = Assets.getText( // - redirectUrl // - isCordova (boolean) // -const renderEndOfLoginResponse = options => { +const renderEndOfLoginResponse = async options => { // It would be nice to use Blaze here, but it's a little tricky // because our mustaches would be inside a