Add `Module['fetchSettings']` for controlling fetch settings. NFC (#16361)
This is the first example of an opt-in by default incoming module API,
so it doesn't effect code size unless users opt into it explicitly.
Fixes: #15569
Sam Clegg authored 2 years ago
GitHub committed 2 years ago
143 | 143 |
'nullability',
|
144 | 144 |
}
|
145 | 145 |
|
|
146 |
# These symbol names are allowed in INCOMING_MODULE_JS_API but are not part of the
|
|
147 |
# default set.
|
|
148 |
EXTRA_INCOMING_JS_API = [
|
|
149 |
'fetchSettings'
|
|
150 |
]
|
146 | 151 |
|
147 | 152 |
VALID_ENVIRONMENTS = ('web', 'webview', 'worker', 'node', 'shell')
|
148 | 153 |
SIMD_INTEL_FEATURE_TOWER = ['-msse', '-msse2', '-msse3', '-mssse3', '-msse4.1', '-msse4.2', '-mavx']
|
|
339 | 344 |
settings object.
|
340 | 345 |
"""
|
341 | 346 |
|
342 | |
# Stash a copy of all available incoming APIs before we possibly override it
|
343 | |
settings.ALL_INCOMING_MODULE_JS_API = settings.INCOMING_MODULE_JS_API
|
|
347 |
# Stash a copy of all available incoming APIs before the user can potentially override it
|
|
348 |
settings.ALL_INCOMING_MODULE_JS_API = settings.INCOMING_MODULE_JS_API + EXTRA_INCOMING_JS_API
|
344 | 349 |
|
345 | 350 |
def standardize_setting_change(key, value):
|
346 | 351 |
# boolean NO_X settings are aliases for X
|
162 | 162 |
|
163 | 163 |
When compiled with ``PROXY_TO_WORKER = 1`` (see `settings.js <https://github.com/emscripten-core/emscripten/blob/main/src/settings.js>`_), this callback (which should be implemented on both the client and worker's ``Module`` object) allows sending custom messages and data between the web worker and the main thread (using the ``postCustomMessage`` function defined in `proxyClient.js <https://github.com/emscripten-core/emscripten/blob/main/src/proxyClient.js>`_ and `proxyWorker.js <https://github.com/emscripten-core/emscripten/blob/main/src/proxyWorker.js>`_).
|
164 | 164 |
|
|
165 |
.. js:function:: Module.fetchSettings
|
|
166 |
|
|
167 |
Override the default settings object used when fetching the Wasm module from
|
|
168 |
the network. This attribute is expected to be a string and it defaults to ``{
|
|
169 |
credentials: 'same-origin' }``.
|
974 | 974 |
return ret;
|
975 | 975 |
}
|
976 | 976 |
|
|
977 |
function makeModuleReceiveExpr(name, defaultValue) {
|
|
978 |
checkReceiving(name);
|
|
979 |
if (expectToReceiveOnModule(name)) {
|
|
980 |
return `Module['${name}'] || ${defaultValue}`;
|
|
981 |
} else {
|
|
982 |
return `${defaultValue}`;
|
|
983 |
}
|
|
984 |
}
|
|
985 |
|
977 | 986 |
function makeModuleReceiveWithVar(localName, moduleName, defaultValue, noAssert) {
|
978 | 987 |
if (!moduleName) moduleName = localName;
|
979 | 988 |
checkReceiving(moduleName);
|
835 | 835 |
&& !isFileURI(wasmBinaryFile)
|
836 | 836 |
#endif
|
837 | 837 |
) {
|
838 | |
return fetch(wasmBinaryFile, { credentials: 'same-origin' }).then(function(response) {
|
|
838 |
return fetch(wasmBinaryFile, {{{ makeModuleReceiveExpr('fetchSettings', "{ credentials: 'same-origin' }") }}}).then(function(response) {
|
839 | 839 |
if (!response['ok']) {
|
840 | 840 |
throw "failed to load wasm binary file at '" + wasmBinaryFile + "'";
|
841 | 841 |
}
|
|
1180 | 1180 |
!isFileURI(wasmBinaryFile) &&
|
1181 | 1181 |
#endif
|
1182 | 1182 |
typeof fetch == 'function') {
|
1183 | |
return fetch(wasmBinaryFile, { credentials: 'same-origin' }).then(function (response) {
|
|
1183 |
return fetch(wasmBinaryFile, {{{ makeModuleReceiveExpr('fetchSettings', "{ credentials: 'same-origin' }") }}}).then(function(response) {
|
1184 | 1184 |
// Suppress closure warning here since the upstream definition for
|
1185 | 1185 |
// instantiateStreaming only allows Promise<Repsponse> rather than
|
1186 | 1186 |
// an actual Response.
|
852 | 852 |
// optimize.
|
853 | 853 |
//
|
854 | 854 |
// Setting this list to [], or at least a short and concise set of names you
|
855 | |
// actually use, can be very useful for reducing code size. By default the
|
856 | |
// list contains all the possible APIs.
|
|
855 |
// actually use, can be very useful for reducing code size. By default, the
|
|
856 |
// list contains a set of commonly used symbols.
|
857 | 857 |
//
|
858 | 858 |
// FIXME: should this just be 0 if we want everything?
|
859 | 859 |
// [link]
|
109 | 109 |
|
110 | 110 |
function getSourceMapPromise() {
|
111 | 111 |
if ((ENVIRONMENT_IS_WEB || ENVIRONMENT_IS_WORKER) && typeof fetch == 'function') {
|
112 | |
return fetch(wasmSourceMapFile, { credentials: 'same-origin' }).then(function(response) {
|
|
112 |
return fetch(wasmSourceMapFile, {{{ makeModuleReceiveExpr('fetchSettings', "{ credentials: 'same-origin' }") }}}).then(function(response) {
|
113 | 113 |
return response['json']();
|
114 | 114 |
}).catch(function () {
|
115 | 115 |
return getSourceMap();
|
11717 | 11717 |
self.do_runf(test_file('other/test_legacy_runtime.c'), 'hello from js')
|
11718 | 11718 |
self.set_setting('STRICT')
|
11719 | 11719 |
self.do_runf(test_file('other/test_legacy_runtime.c'), 'ReferenceError: allocate is not defined', assert_returncode=NON_ZERO)
|
|
11720 |
|
|
11721 |
def test_fetch_settings(self):
|
|
11722 |
create_file('pre.js', '''
|
|
11723 |
Module = {
|
|
11724 |
fetchSettings: { cache: 'no-store' }
|
|
11725 |
}''')
|
|
11726 |
self.emcc_args += ['--pre-js=pre.js']
|
|
11727 |
self.do_runf(test_file('hello_world.c'), '`Module.fetchSettings` was supplied but `fetchSettings` not included in INCOMING_MODULE_JS_API', assert_returncode=NON_ZERO)
|
|
11728 |
|
|
11729 |
# Try again with INCOMING_MODULE_JS_API set
|
|
11730 |
self.set_setting('INCOMING_MODULE_JS_API', 'fetchSettings')
|
|
11731 |
self.do_runf(test_file('hello_world.c'), 'hello, world')
|
|
11732 |
src = read_file('hello_world.js')
|
|
11733 |
self.assertContained("fetch(wasmBinaryFile, Module['fetchSettings'] || ", src)
|