-
Notifications
You must be signed in to change notification settings - Fork 54
/
referrer-window.html
113 lines (104 loc) · 3.98 KB
/
referrer-window.html
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
<!DOCTYPE html>
<html>
<head>
<title>Worklet: Referrer</title>
<script src="/common/get-host-info.sub.js"></script>
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>
<script src="worklet-test-utils.js"></script>
</head>
<body>
<script>
function createScriptURLForTopLevel(scriptOrigin) {
if (scriptOrigin === 'same')
return new URL('referrer-checker.py', location.href);
if (scriptOrigin === 'remote') {
return new URL(get_host_info().HTTPS_REMOTE_ORIGIN +
'/worklets/resources/referrer-checker.py');
}
assert_unreached('scriptOrigin should be \'same\' or \'remote\'');
}
function createScriptURLForDecendant(scriptOrigins) {
if (scriptOrigins.topLevel === 'same' &&
scriptOrigins.descendant === 'same') {
return new URL('import-referrer-checker-worklet-script.sub.js',
location.href);
}
if (scriptOrigins.topLevel === 'same' &&
scriptOrigins.descendant === 'remote') {
return new URL(
'import-remote-origin-referrer-checker-worklet-script.sub.js',
location.href);
}
if (scriptOrigins.topLevel === 'remote' &&
scriptOrigins.descendant === 'same') {
url = new URL(
get_host_info().HTTPS_REMOTE_ORIGIN +
'/worklets/resources/' +
'import-same-origin-referrer-checker-worklet-script-from-remote-origin.sub.js');
return url;
}
if (scriptOrigins.topLevel === 'remote' &&
scriptOrigins.descendant === 'remote') {
return new URL(
get_host_info().HTTPS_REMOTE_ORIGIN +
'/worklets/resources/import-referrer-checker-worklet-script.sub.js');
}
assert_unreached('scriptOrigins have an invalid origin combination.');
}
function isDestinationCrossOrigin(fetchType, scriptOrigins) {
if (fetchType === 'top-level')
return scriptOrigins.topLevel === 'remote';
// Compute a descendant's cross-origin-ness relative to the top-level script.
if (fetchType === 'descendant')
return scriptOrigins.descendant !== scriptOrigins.topLevel;
assert_unreached('fetchType has an invalid value.');
}
function createExpectedReferrer(
importerURL, fetchType, referrerPolicy, scriptOrigins) {
if (referrerPolicy === 'no-referrer')
return "";
if (referrerPolicy === 'same-origin') {
if (isDestinationCrossOrigin(fetchType, scriptOrigins))
return "";
// Delete query params to make it easier to match with an actual referrer in
// the referrer-checker.py.
const expectedReferrer = new URL(importerURL);
for (var key of expectedReferrer.searchParams.keys())
expectedReferrer.searchParams.delete(key);
return expectedReferrer;
}
if (referrerPolicy === 'origin')
return (new URL(importerURL)).origin + '/';
assert_unreached('referrerPolicy has an invalid value.');
}
window.onmessage = e => {
const workletType = e.data.workletType;
const fetchType = e.data.fetchType;
const referrerPolicy = e.data.referrerPolicy;
const scriptOrigins = e.data.scriptOrigins;
let scriptURL;
let expectedReferrer;
if (fetchType === 'top-level') {
scriptURL = createScriptURLForTopLevel(scriptOrigins.topLevel);
expectedReferrer = createExpectedReferrer(
location.href, fetchType, referrerPolicy, scriptOrigins);
} else if (fetchType === 'descendant') {
scriptURL = createScriptURLForDecendant(scriptOrigins);
expectedReferrer = createExpectedReferrer(
scriptURL, fetchType, referrerPolicy, scriptOrigins);
} else {
assert_unreached('fetchType should be \'top-level\' or \'descendant\'');
}
const params = new URLSearchParams;
params.append('requestor_origin', document.location.origin);
params.append('referrer_policy', referrerPolicy);
params.append('expected_referrer', expectedReferrer);
get_worklet(workletType).addModule(scriptURL + '?' + params)
.then(() => window.opener.postMessage('RESOLVED', '*'))
.catch(e => window.opener.postMessage(e.message, '*'));
};
window.opener.postMessage('LOADED', '*');
</script>
</body>
</html>