Skip to content

Commit 7d08b65

Browse files
committed
Fix #2160 - Add m/py:progress events
1 parent b818305 commit 7d08b65

15 files changed

+69
-15
lines changed

docs/index.js

+1-1
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

docs/index.js.map

+1-1
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

esm/interpreter/_python.js

+19
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,31 @@
11
import * as JSON from '@ungap/structured-clone/json';
22
import IDBMapSync from '@webreflection/idb-map/sync';
3+
import { fetchFiles, fetchJSModules, fetchPaths } from './_utils.js';
34
import { dedent } from '../utils.js';
45
import { io } from './_io.js';
56

67
export const loader = new WeakMap();
78

89
// REQUIRES INTEGRATION TEST
910
/* c8 ignore start */
11+
export const loadProgress = async (self, progress, interpreter, config, baseURL) => {
12+
if (config.files) {
13+
progress('Loading files');
14+
await fetchFiles(self, interpreter, config.files, baseURL);
15+
progress('Loaded files');
16+
}
17+
if (config.fetch) {
18+
progress('Loading fetch');
19+
await fetchPaths(self, interpreter, config.fetch, baseURL);
20+
progress('Loaded fetch');
21+
}
22+
if (config.js_modules) {
23+
progress('Loading JS modules');
24+
await fetchJSModules(config.js_modules, baseURL);
25+
progress('Loaded JS modules');
26+
}
27+
};
28+
1029
export const registerJSModule = (interpreter, name, value) => {
1130
if (name === 'polyscript') {
1231
value.lazy_py_modules = async (...packages) => {

esm/interpreter/_utils.js

+4
Original file line numberDiff line numberDiff line change
@@ -167,4 +167,8 @@ export const fetchJSModules = ({ main, worker }, baseURL) => {
167167
}
168168
return all(promises);
169169
};
170+
171+
export const createProgress = prefix => detail => {
172+
dispatchEvent(new CustomEvent(`${prefix}:progress`, { detail }));
173+
};
170174
/* c8 ignore stop */

esm/interpreter/micropython.js

+12-7
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import fetch from '@webreflection/fetch';
22

3-
import { fetchFiles, fetchJSModules, fetchPaths, writeFile } from './_utils.js';
4-
import { getFormat, loader, registerJSModule, run, runAsync, runEvent } from './_python.js';
3+
import { createProgress, writeFile } from './_utils.js';
4+
import { getFormat, loader, loadProgress, registerJSModule, run, runAsync, runEvent } from './_python.js';
55
import { stdio, buffered } from './_io.js';
66
import { absoluteURL } from '../utils.js';
77
import mip from '../python/mip.js';
@@ -21,6 +21,8 @@ const mkdir = (FS, path) => {
2121
}
2222
};
2323

24+
const progress = createProgress('mpy');
25+
2426
export default {
2527
type,
2628
module: (version = '1.24.0-preview-114') =>
@@ -31,16 +33,19 @@ export default {
3133
stdout: buffered(console.log),
3234
});
3335
url = url.replace(/\.m?js$/, '.wasm');
36+
progress('Loading MicroPython');
3437
const interpreter = await get(loadMicroPython({ linebuffer: false, stderr, stdout, url }));
3538
const py_imports = importPackages.bind(this, interpreter, baseURL);
3639
loader.set(interpreter, py_imports);
37-
if (config.files) await fetchFiles(this, interpreter, config.files, baseURL);
38-
if (config.fetch) await fetchPaths(this, interpreter, config.fetch, baseURL);
39-
if (config.js_modules) await fetchJSModules(config.js_modules, baseURL);
40-
40+
await loadProgress(this, progress, interpreter, config, baseURL);
4141
// Install Micropython Package
4242
this.writeFile(interpreter, './mip.py', mip);
43-
if (config.packages) await py_imports(config.packages);
43+
if (config.packages) {
44+
progress('Loading packages');
45+
await py_imports(config.packages);
46+
progress('Loaded packages');
47+
}
48+
progress('Loaded MicroPython');
4449
return interpreter;
4550
},
4651
registerJSModule,

esm/interpreter/pyodide.js

+19-5
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { create } from 'gc-hook';
22

3-
import { RUNNING_IN_WORKER, fetchFiles, fetchJSModules, fetchPaths, writeFile } from './_utils.js';
4-
import { getFormat, loader, registerJSModule, run, runAsync, runEvent } from './_python.js';
3+
import { RUNNING_IN_WORKER, createProgress, writeFile } from './_utils.js';
4+
import { getFormat, loader, loadProgress, registerJSModule, run, runAsync, runEvent } from './_python.js';
55
import { stdio } from './_io.js';
66
import { isArray } from '../utils.js';
77

@@ -73,6 +73,8 @@ const applyOverride = () => {
7373
}
7474
});
7575
};
76+
77+
const progress = createProgress('py');
7678
/* c8 ignore stop */
7779

7880
// REQUIRES INTEGRATION TEST
@@ -85,17 +87,17 @@ export default {
8587
// apply override ASAP then load foreign code
8688
if (!RUNNING_IN_WORKER && config.experimental_create_proxy === 'auto')
8789
applyOverride();
90+
progress('Loading Pyodide');
8891
const { stderr, stdout, get } = stdio();
8992
const indexURL = url.slice(0, url.lastIndexOf('/'));
9093
const interpreter = await get(
9194
loadPyodide({ stderr, stdout, indexURL }),
9295
);
9396
const py_imports = importPackages.bind(interpreter);
9497
loader.set(interpreter, py_imports);
95-
if (config.files) await fetchFiles(this, interpreter, config.files, baseURL);
96-
if (config.fetch) await fetchPaths(this, interpreter, config.fetch, baseURL);
97-
if (config.js_modules) await fetchJSModules(config.js_modules, baseURL);
98+
await loadProgress(this, progress, interpreter, config, baseURL);
9899
if (config.packages) await py_imports(config.packages);
100+
progress('Loaded Pyodide');
99101
return interpreter;
100102
},
101103
registerJSModule,
@@ -129,9 +131,21 @@ function transform(value) {
129131

130132
// exposed utility to import packages via polyscript.lazy_py_modules
131133
async function importPackages(packages) {
134+
// temporary patch/fix console.log which is used
135+
// not only by Pyodide but by micropip too and there's
136+
// no way to intercept those calls otherwise
137+
const { log } = console;
138+
const _log = (detail, ...rest) => {
139+
log(detail, ...rest);
140+
console.log = log;
141+
progress(detail);
142+
console.log = _log;
143+
};
144+
console.log = _log;
132145
await this.loadPackage('micropip');
133146
const micropip = this.pyimport('micropip');
134147
await micropip.install(packages, { keep_going: true });
148+
console.log = log;
135149
micropip.destroy();
136150
}
137151
/* c8 ignore stop */

esm/worker/_template.js

+5
Original file line numberDiff line numberDiff line change
@@ -211,4 +211,9 @@ add('message', ({ data: { options, config: baseURL, configURL, code, hooks } })
211211
add('error');
212212
add('message');
213213
add('messageerror');
214+
if (syncMainAndWorker) {
215+
addEventListener('py:progress', ({ type, detail }) => {
216+
window.dispatchEvent(new window.CustomEvent(type, { detail }));
217+
});
218+
}
214219
});

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,6 @@
8686
"to-json-callback": "^0.1.1"
8787
},
8888
"worker": {
89-
"blob": "sha256-n5bp7XbiMOC5xSM8r1BjWIl0efV5DHH41AoMDzRWNdg="
89+
"blob": "sha256-RmKg3DGPQyD4Ez4YcM6qJi5Pi+a6Jpk53iO3ATXuQXw="
9090
}
9191
}

test/index.html

+1
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
<meta name="viewport" content="width=device-width,initial-scale=1.0" />
66
<title>python</title>
77
<link rel="stylesheet" href="style.css" />
8+
<script>addEventListener('py:progress', ({ detail }) => console.log({ detail }));</script>
89
<script type="module" src="../dist/index.js"></script>
910
</head>
1011
<body>

test/index.js

+1
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@ globalThis.indexedDB = { open: () => ({}) };
3636
globalThis.document = document;
3737
globalThis.Element = window.Element;
3838
globalThis.CustomEvent = CustomEvent;
39+
globalThis.dispatchEvent = Object;
3940
globalThis.MutationObserver = window.MutationObserver;
4041
globalThis.Worker = class {};
4142
globalThis.XPathResult = {};

test/matplot.html

+1
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
<meta name="viewport" content="width=device-width,initial-scale=1.0" />
66
<title>python</title>
77
<link rel="stylesheet" href="style.css" />
8+
<script>addEventListener('py:progress', ({ detail }) => console.log({ detail }));</script>
89
<script defer src="./counter.js"></script>
910
<script type="module" src="../dist/index.js"></script>
1011
</head>

test/matplot.json.html

+1
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
<meta name="viewport" content="width=device-width,initial-scale=1.0" />
66
<title>python</title>
77
<link rel="stylesheet" href="style.css" />
8+
<script>addEventListener('py:progress', ({ detail }) => console.log({ detail }));</script>
89
<script defer src="./counter.js"></script>
910
<script type="module" src="../dist/index.js"></script>
1011
</head>

test/matplot.worker.html

+1
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
<meta name="viewport" content="width=device-width,initial-scale=1.0" />
66
<title>python</title>
77
<link rel="stylesheet" href="style.css" />
8+
<script>addEventListener('py:progress', ({ detail }) => console.log({ detail }));</script>
89
<script defer src="./counter.js"></script>
910
<script type="module" src="../dist/index.js"></script>
1011
</head>

test/micropython.html

+1
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
<meta name="viewport" content="width=device-width,initial-scale=1.0" />
66
<title>python</title>
77
<link rel="stylesheet" href="style.css" />
8+
<script>addEventListener('mpy:progress', ({ detail }) => console.log({ detail }));</script>
89
<script defer src="./counter.js"></script>
910
<script type="module" src="../dist/index.js"></script>
1011
</head>

test/micropython/random.html

+1
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
<head>
44
<meta charset="UTF-8">
55
<meta name="viewport" content="width=device-width, initial-scale=1.0">
6+
<script>addEventListener('mpy:progress', ({ detail }) => console.log({ detail }));</script>
67
<script type="module" src="../../dist/index.js"></script>
78
<script type="micropython">
89
import random, js

0 commit comments

Comments
 (0)