Mailspring/internal_packages/onboarding/lib/onboarding-helpers.es6
2016-06-12 21:13:46 -04:00

170 lines
5.2 KiB
JavaScript

/* eslint global-require: 0 */
import crypto from 'crypto';
import {EdgehillAPI, NylasAPI, AccountStore, RegExpUtils, IdentityStore} from 'nylas-exports';
import url from 'url';
function base64url(inBuffer) {
let buffer;
if (typeof inBuffer === "string") {
buffer = new Buffer(inBuffer);
} else if (inBuffer instanceof Buffer) {
buffer = inBuffer;
} else {
throw new Error(`${inBuffer} must be a string or Buffer`)
}
return buffer.toString('base64')
.replace(/\+/g, '-') // Convert '+' to '-'
.replace(/\//g, '_'); // Convert '/' to '_'
}
export function pollForGmailAccount(sessionKey, callback) {
EdgehillAPI.makeRequest({
path: `/oauth/google/token?key=${sessionKey}`,
method: "GET",
error: callback,
success: (json) => {
if (json && json.data) {
callback(null, JSON.parse(json.data));
} else {
callback(null, null);
}
},
});
}
export function buildGmailSessionKey() {
return base64url(crypto.randomBytes(40));
}
export function buildGmailAuthURL(sessionKey) {
// Use a different app for production and development.
const env = NylasEnv.config.get('env') || 'production';
let googleClientId = '372024217839-cdsnrrqfr4d6b4gmlqepd7v0n0l0ip9q.apps.googleusercontent.com';
if (env !== 'production') {
googleClientId = '529928329786-e5foulo1g9kiej2h9st9sb0f4dt96s6v.apps.googleusercontent.com';
}
const encryptionKey = base64url(crypto.randomBytes(24));
const encryptionIv = base64url(crypto.randomBytes(16));
return url.format({
protocol: 'https',
host: 'accounts.google.com/o/oauth2/auth',
query: {
response_type: 'code',
state: `${sessionKey},${encryptionKey},${encryptionIv},`,
client_id: googleClientId,
redirect_uri: `${EdgehillAPI.APIRoot}/oauth/google/callback`,
access_type: 'offline',
scope: `https://www.googleapis.com/auth/userinfo.email \
https://www.googleapis.com/auth/userinfo.profile \
https://mail.google.com/ \
https://www.google.com/m8/feeds \
https://www.googleapis.com/auth/calendar`,
prompt: 'consent',
},
});
}
export function buildWelcomeURL(welcomeRoot, {source}) {
const identity = IdentityStore.identity();
if (!identity || !identity.id) { NylasEnv.reportError(new Error("buildWelcomeURL: Can't find Nylas ID")) }
const query = {
f: base64url(identity.firstname),
l: base64url(identity.lastname),
n: base64url(identity.id),
utm_medium: "N1",
}
if (source) { query.utm_source = source }
return url.format({
pathname: `${welcomeRoot}/welcome`,
query: query,
})
}
export function runAuthRequest(accountInfo) {
const {username, type, email, name} = accountInfo;
const data = {
provider: type,
email: email,
name: name,
settings: Object.assign({}, accountInfo),
};
// handle special case for exchange/outlook/hotmail username field
data.settings.username = username || email;
if (data.settings.imap_port) {
data.settings.imap_port = data.settings.imap_port / 1;
}
if (data.settings.smtp_port) {
data.settings.smtp_port = data.settings.smtp_port / 1;
}
// if there's an account with this email, get the ID for it to notify the backend of re-auth
const account = AccountStore.accountForEmail(accountInfo.email);
const reauthParam = account ? `&reauth=${account.id}` : "";
// Send the form data directly to Nylas to get code
// If this succeeds, send the received code to N1 server to register the account
// Otherwise process the error message from the server and highlight UI as needed
return NylasAPI.makeRequest({
path: `/auth?client_id=${NylasAPI.AppID}&n1_id=${IdentityStore.identityId()}${reauthParam}`,
method: 'POST',
body: data,
returnsModel: false,
timeout: 150000,
auth: {
user: '',
pass: '',
sendImmediately: true,
},
})
.then((json) => {
json.email = data.email;
return EdgehillAPI.makeRequest({
path: "/connect/nylas",
method: "POST",
timeout: 60000,
body: json,
})
})
}
export function isValidHost(value) {
return RegExpUtils.domainRegex().test(value) || RegExpUtils.ipAddressRegex().test(value);
}
export function accountInfoWithIMAPAutocompletions(existingAccountInfo) {
const CommonProviderSettings = require('./common-provider-settings.json');
const email = existingAccountInfo.email;
const domain = email.split('@').pop().toLowerCase();
const template = CommonProviderSettings[domain] || {};
const usernameWithFormat = (format) => {
if (format === 'email') {
return email
}
if (format === 'email-without-domain') {
return email.split('@').shift();
}
return undefined;
}
// always pre-fill SMTP / IMAP username, password and port.
const defaults = {
imap_host: template.imap_host,
imap_port: template.imap_port || 993,
imap_username: usernameWithFormat(template.imap_user_format),
imap_password: existingAccountInfo.password,
smtp_host: template.smtp_host,
smtp_port: template.smtp_port || 587,
smtp_username: usernameWithFormat(template.smtp_user_format),
smtp_password: existingAccountInfo.password,
ssl_required: (template.ssl === '1'),
}
return Object.assign({}, existingAccountInfo, defaults);
}