1 | const Listr = require('listr')
|
2 | const got = require('got')
|
3 | const { JSDOM } = require('jsdom')
|
4 | const bresolve = require('browser-resolve')
|
5 | const Promise = require('bluebird')
|
6 | const readFile = require('mz/fs').readFile
|
7 |
|
8 | const pmPath = bresolve.sync('plug-modules', { filename: __filename })
|
9 |
|
10 |
|
11 | const stubs = {
|
12 | localStorage: {
|
13 | getItem () {},
|
14 | setItem () {},
|
15 | clear () {}
|
16 | },
|
17 | gapi: {
|
18 | client: {
|
19 | setApiKey () {},
|
20 | load () {}
|
21 | }
|
22 | },
|
23 | Intercom: {},
|
24 | amplitude: { __VERSION__: true },
|
25 | FB: { init: function () {} }
|
26 | }
|
27 |
|
28 | function waitForRequireJs (window) {
|
29 | return new Promise((resolve, reject) => {
|
30 |
|
31 | const intv = setInterval(waitForRequireJs, 20)
|
32 | function waitForRequireJs () {
|
33 | if (window.requirejs) {
|
34 | window.define('facebook', stubs.FB)
|
35 |
|
36 |
|
37 |
|
38 |
|
39 |
|
40 |
|
41 | const orig = window.require
|
42 | window.require = Object.assign((arg, ...rest) => {
|
43 | if (Array.isArray(arg) && arg[0].indexOf('http') !== 0) {
|
44 | return orig(arg, () => {
|
45 |
|
46 | resolve()
|
47 | })
|
48 | }
|
49 | return orig(arg, ...rest)
|
50 | }, orig)
|
51 | const origDefine = window.define
|
52 | window.define = Object.assign((name, dependencies, ...args) => {
|
53 | if (name === 'async') {
|
54 | return origDefine('async', {
|
55 | load: (name, parent, onload) => onload({})
|
56 | })
|
57 | }
|
58 | if (Array.isArray(dependencies)) {
|
59 | dependencies = dependencies.map((dep) => dep === 'recaptcha' ? 'module' : dep)
|
60 | }
|
61 | return origDefine(name, dependencies, ...args)
|
62 | }, origDefine)
|
63 | clearInterval(intv)
|
64 | }
|
65 | }
|
66 | })
|
67 | }
|
68 |
|
69 | const PLUG_ROOM_URL = 'https://plug.dj/plug-socket-test'
|
70 |
|
71 |
|
72 |
|
73 |
|
74 |
|
75 |
|
76 | module.exports = function createMapping (cookie, ctx) {
|
77 | const reqAsync = (req, id) => new Promise((resolve, reject) => req(id, resolve, reject))
|
78 |
|
79 | return new Listr([
|
80 | {
|
81 | title: 'Loading plug.dj',
|
82 | task: (ctx) =>
|
83 | got(PLUG_ROOM_URL, {
|
84 | headers: { cookie: cookie }
|
85 | }).then((response) => {
|
86 | ctx.source = response.body
|
87 | })
|
88 | },
|
89 | {
|
90 | title: 'Opening plug.dj',
|
91 | task: (ctx) => {
|
92 | ctx.dom = new JSDOM(ctx.source, {
|
93 | url: PLUG_ROOM_URL,
|
94 | runScripts: 'dangerously',
|
95 | resources: 'usable',
|
96 | beforeParse (window) {
|
97 | Object.assign(window, stubs)
|
98 | ctx.window = window
|
99 | }
|
100 | })
|
101 | }
|
102 | },
|
103 | {
|
104 | title: 'Injecting module mapping helper',
|
105 | task: (ctx) =>
|
106 | readFile(require.resolve('./get-mapping'), 'utf8').then((source) => {
|
107 | ctx.window.eval(source)
|
108 | })
|
109 | },
|
110 | {
|
111 | title: 'Waiting for plug.dj to finish loading',
|
112 | task: (ctx) => waitForRequireJs(ctx.window)
|
113 | },
|
114 | {
|
115 | title: 'Running plug-modules',
|
116 | task: (ctx) => Promise.resolve(readFile(pmPath, 'utf-8'))
|
117 |
|
118 | .then((plugModules) => plugModules.replace('define([', 'define("plug-modules",['))
|
119 |
|
120 | .then((src) => ctx.window.eval(src))
|
121 | .then(() => reqAsync(ctx.window.requirejs, [ 'plug-modules' ]))
|
122 | .then((pm) => ctx.window.getMapping(pm))
|
123 | .tap(() => ctx.window.close())
|
124 | .then(JSON.parse)
|
125 | .then((result) => {
|
126 | ctx.window = null
|
127 | ctx.mapping = result.mapping
|
128 | ctx.appUrl = result.appUrl
|
129 | })
|
130 | }
|
131 | ], { context: ctx })
|
132 | }
|