import { StyleSheet } from 'react-native'; import WebView from 'react-native-webview'; import { handleWebViewMessage, pyodideRef } from './extractActivity'; const CDN = 'https://cdn.jsdelivr.net/pyodide/v0.26.4/full/'; // v0.18.1: last version whose JS wrapper avoids ??, ?., and other syntax // unavailable on Chrome <80 (e.g. Karoo WebView 61). Used in the compat path. const CDN_COMPAT = 'https://cdn.jsdelivr.net/pyodide/v0.18.1/full/'; // Python snippets embedded as JSON strings to avoid any JS/TS escaping issues. const PY_INSTALL_PACKAGES = [ 'import micropip', 'await micropip.install(["fitdecode", "gpxpy"])', ].join('\n'); // emfs:// is Pyodide's Emscripten-FS URL scheme — the only reliable way to // install a wheel from bytes without an http/https URL (blob: URLs are not // recognised by micropip and cause an InvalidRequirement parse error). // _wheel_path is set as a Pyodide global before this runs. const PY_INSTALL_WHEEL = [ 'import micropip', 'await micropip.install("emfs://" + _wheel_path, deps=False)', ].join('\n'); const PY_EXTRACT = [ 'import json, shutil', 'from pathlib import Path', 'from bincio.extract.parsers.factory import parse_file', 'from bincio.extract.metrics import compute', 'from bincio.extract.writer import make_activity_id, write_activity', '', 'outdir = Path("/tmp/bincio_out")', 'if outdir.exists(): shutil.rmtree(outdir)', 'outdir.mkdir()', '', 'activity = parse_file(Path("/tmp/" + _filename))', 'metrics = compute(activity)', 'write_activity(activity, metrics, outdir, privacy="public", rdp_epsilon=0.0001)', 'act_id = make_activity_id(activity)', '', 'detail_path = outdir / "activities" / (act_id + ".json")', 'ts_path = outdir / "activities" / (act_id + ".timeseries.json")', 'geojson_path = outdir / "activities" / (act_id + ".geojson")', '', '# write_activity in the installed wheel silently skips timeseries — write it directly.', 'if not ts_path.exists():', ' from bincio.extract.timeseries import build_timeseries as _bts', ' _ts = _bts(activity.points, activity.started_at, "public")', ' if _ts.get("t"):', ' ts_path.write_text(json.dumps(_ts))', '', 'json.dumps({', ' "id": act_id,', ' "detail": json.loads(detail_path.read_text()),', ' "timeseries": json.loads(ts_path.read_text()) if ts_path.exists() else None,', ' "geojson": json.loads(geojson_path.read_text()) if geojson_path.exists() else None,', '})', ].join('\n'); // JSON.stringify gives us safely-quoted JS string literals for embedding in HTML. const PYODIDE_HTML = `
`; export function PyodideWebView() { return ( ); } const styles = StyleSheet.create({ // Off-screen but still rendered — display:none / opacity:0 can suppress JS on some platforms. hidden: { position: 'absolute', top: -2000, left: 0, width: 1, height: 1, }, });