-
Notifications
You must be signed in to change notification settings - Fork 8
/
Copy pathpostMessageRelay.js
115 lines (107 loc) · 3.34 KB
/
postMessageRelay.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
/* eslint-env browser, webextensions */
var postMessageRelay; // eslint-disable-line no-var, no-unused-vars
(() => {
'use strict';
const port = browser.runtime.connect({name: 'webappfind-postMessage-content-script'});
function l (...msgs) {
console.log(...msgs);
}
function sameOriginAndHasType (data) {
return origin === location.origin && // Security
data && data.webappfind && data.webappfind.type; // === type;
}
window.addEventListener('unload', () => {
port.postMessage({type: 'unload'});
});
// Listen for subsequent requests to read the file (necessary also for
// cases where the 'view' listener cannot be added immediately,
// e.g., within our SVG-edit extension which is loaded by the main page
// doing a script tag injection)
window.addEventListener('message', function ({origin, data}) {
if (!sameOriginAndHasType(data)) {
return;
}
const {type, pathID, content} = data.webappfind;
// console.log('type', type, origin, data);
switch (type) {
case 'read':
port.postMessage({type: 'read', pathID});
break;
case 'save':
if (!pathID) { // User may be attempting edit with view-only access
console.log('No path ID provided');
return;
}
// l(content.length);
l('saving... pathID:', pathID, 'length: ', content.length);
port.postMessage({type: 'save', pathID, content});
break;
default:
throw new TypeError('Unexpected type: ' + type);
}
});
async function webappfindStart (result) {
// l(JSON.stringify(result));
const {pathID, content, site, mode, binary} = result;
let {args, error} = result;
/* if (site !== location.href) { // Not matching with about:newtab, but not needed
console.log('Mismatch for ' + site + ' and ' + location.href);
return;
} */
l('made it past site check', site);
try {
args = JSON.parse(args);
} catch (err) {
error = err;
}
const message = {
webappfind: {
type: 'view',
pathID: mode === 'edit' ? pathID : null,
args,
binary,
content,
error: Boolean(error)
}
};
console.log('sending', JSON.stringify(message));
// Todo: make option to enable but indicate this is a major
// privacy leak! (at least until such time as a null
// origin is allowed)
// This should work but
// [tabs.create](https://developer.mozilla.org/en-US/Add-ons/WebExtensions/API/tabs/create)
// does not work with the `file:` protocol
if (0 && site.startsWith('file:')) {
l('file protocol');
// Todo: We could (and should) set this message to the
// relevant URL if `file:` support is added
try {
window.postMessage(message, '*'); // location.href); // Gives security error while location.origin is `null` for file:
} catch (e) {
l('file protocol err: ' + e);
}
} else {
l('pathID', pathID, 'contentlen', content.length || (content.data && content.data.length), 'location.origin', location.origin);
window.postMessage(message, location.origin);
}
}
port.onMessage.addListener(function ({type, result, pathID, error}) {
switch (type) {
case 'saveEnd':
window.postMessage({
webappfind: {
type: 'save-end',
pathID,
// result,
error: Boolean(error)
}
}, location.origin);
break;
case 'start':
webappfindStart(result);
break;
default:
throw new TypeError('Unexpected type: ' + type);
}
});
})();