You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
|`GpuCompute` / `GpuArray` / `GpuBridge`| f32 대규모 선형대수를 WebGPU 컴퓨트로 오프로드: 잔류 핸들(업로드 1회, GPU 위에서 `matmul` / `map` / `binary` / `transpose` / `reduce` 체이닝, 다운로드 1회, 공유메모리 타일드 커널). 전체 파이프라인이 GPU에 남는다: `matmul -> relu -> sum`(loss), `x.transpose() @ dy`, 잔차 `(A@B) + C`. `Runtime.enableGpu()`가 파이썬에 배선(`pyprocGpu.matmul`이 numpy 배열을). 실 GPU에서 WASM numpy 대비 ~127배 실측. f32 한정(WGSL은 f64 없음), 창 있는 브라우저 + GPU 필요 |
225
-
| `BrowserControl` | MV3 확장 offscreen에서 파이썬이 브라우저를 조작: `Runtime.enableBrowserControl()` -> `install()` -> `pyprocBrowser.tab(url, mode)`. Playwright급 표면: 항법(`navigate` / `reload` / `back` / `forward`), 입력(`click` / `doubleClick` / `rightClick` / `hover` / `type` / `fill` / `press` / `select`), 조회·추출(`text` / `attr` / `value` / `exists` / `count` / `texts` / `boundingBox` / `title` / `url` / `content`), 대기(`waitFor` / `waitForFunction`), 캡처·에뮬레이션(`screenshot` / `pdf` / `setViewport` / `setUserAgent` / `setHeaders` / `emulateMedia` 다크모드 / `setTimezone` / `setOffline` / `setGeolocation` / `setLocale`), 다운로드(`enableDownloads` / `waitForDownload`로 무엇이 다운로드되는지 관측), 콘솔(`enableConsole` / `consoleLogs` / `waitForConsole`로 페이지 로그·미처리 에러 캡처), 접근성(`accessibilityTree`로 페이지를 role/name 시맨틱으로 회수 = 에이전트 의미 네비게이션), 쿠키(`cookies` / `setCookie` / `clearCookies` / `deleteCookie`), 파일(`upload`), 다이얼로그(`setDialogHandler`가 alert/confirm/prompt 자동 응답), 네트워크(`route`로 CDP Fetch 요청 차단·목킹·변조·붙잡기, 붙잡은 요청은 `pendingRequests` + `continueRequest` / `fulfillRequest` / `abortRequest`로 요청마다 Python이 결정, `waitForResponse` / `requests` / `responseBody`로 응답 관측·바디 캡처), 프레임(`frames` / `frame`으로 iframe 내부 드릴다운: same-origin은 isolated world, cross-origin OOPIF는 그 타깃에 attach). 포인터 op는 대상을 자동 스크롤한다. 두 mode: `script`(chrome.scripting, 스텔스, `navigator.webdriver` 미점화)와 `debugger`(chrome.debugger CDP, 신뢰 입력 `isTrusted=true`, 캡처·에뮬·다이얼로그·네트워크 전 표면). 한 탭에 대한 영속 세션 핸들. 탭이 외부 종료되면 이후 op가 `SessionLost` 예외. 프로세스 OS 융합: `routeBrowserWorker`(offscreen 릴레이) + `installBrowserWorker`(워커 측)로 Pyodide 워커 N개가 각자 독립 인터프리터(N GIL)로 자기 세션을 몬다 = Playwright가 못 하는 차별점. 서비스워커 절반은 별도 subpath `pyproc/browser-control-host`. Chromium 확장 전용 |
226
225
|`bootSession` / `Session` / `openMachine`| 세션 부활 + 이동 가능한 `.pymachine` 이미지: 결정적 리플레이 + 사용자 델타, OPFS 영속(`save` / `load`) 또는 한 파일 내보내기(`exportImage` / `openMachine`) |
Copy file name to clipboardExpand all lines: README.md
-1Lines changed: 0 additions & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -222,7 +222,6 @@ Capabilities are opt-in - turn on only what you need, and consume the capability
222
222
|`MachineJournal`| Write-ahead log: the machine checkpoints itself while idle, so a crashed tab still boots back into its last commit |
223
223
|`MachineJail`| Permission jail: `permissions{net, clipboard, home, workers}` enforced in two tiers, a cooperative Python chokepoint plus the browser's own wall (a `connect-src` CSP on the jail context blocks disallowed hosts even if the jailed code tries `import js`) |
224
224
|`GpuCompute` / `GpuArray` / `GpuBridge`| Offload large f32 linear algebra to WebGPU compute: a residency handle (upload once, chain `matmul` / `map` / `binary` / `transpose` / `reduce` on the GPU, download once) with a shared-memory tiled kernel. Full pipelines stay GPU-resident: `matmul -> relu -> sum` (loss) and `x.transpose() @ dy` / residual `(A@B) + C`. `Runtime.enableGpu()` wires it into Python (`pyprocGpu.matmul` on numpy arrays). Measured ~127x vs WASM numpy on a real GPU; f32 only (WGSL has no f64), needs a windowed browser with a GPU |
225
-
| `BrowserControl` | Drive the browser from Python inside an MV3 extension offscreen document: `Runtime.enableBrowserControl()` -> `install()` -> `pyprocBrowser.tab(url, mode)`. Playwright-class surface: navigation (`navigate` / `reload` / `back` / `forward`), input (`click` / `doubleClick` / `rightClick` / `hover` / `type` / `fill` / `press` / `select`), query/extract (`text` / `attr` / `value` / `exists` / `count` / `texts` / `boundingBox` / `title` / `url` / `content`), waiting (`waitFor` / `waitForFunction`), capture/emulation (`screenshot` / `pdf` / `setViewport` / `setUserAgent` / `setHeaders` / `emulateMedia` dark mode / `setTimezone` / `setOffline` / `setGeolocation` / `setLocale`), downloads (`enableDownloads` / `waitForDownload` observe what is being downloaded), console (`enableConsole` / `consoleLogs` / `waitForConsole` capture page logs and uncaught errors), accessibility (`accessibilityTree` reads the page as role/name semantics for agent navigation), cookies (`cookies` / `setCookie` / `clearCookies` / `deleteCookie`), files (`upload`), dialogs (`setDialogHandler` auto-answers alert/confirm/prompt), network (`route` blocks / mocks / modifies / holds requests via CDP Fetch; held requests are decided per-request from Python via `pendingRequests` + `continueRequest` / `fulfillRequest` / `abortRequest`; `waitForResponse` / `requests` / `responseBody` observe responses and capture bodies), frames (`frames` / `frame` drill into an iframe: same-origin via an isolated world, cross-origin OOPIF by attaching to its target). Pointer ops auto-scroll the target into view. Two modes: `script` (chrome.scripting, stealth, no `navigator.webdriver`) and `debugger` (chrome.debugger CDP, trusted input `isTrusted=true`, full capture/emulation/dialog/network). Persistent session handle over one tab; a tab closed externally raises `SessionLost`. Process-OS fusion: `routeBrowserWorker` (offscreen relay) + `installBrowserWorker` (worker side) let N Pyodide workers each drive their own session with an independent interpreter (N GILs), the differentiator Playwright cannot match. The service worker half is a separate subpath `pyproc/browser-control-host`. Chromium extension only |
226
225
|`bootSession` / `Session` / `openMachine`| Session revival and portable `.pymachine` images: deterministic replay plus user delta, persisted to OPFS (`save` / `load`) or exported as one file (`exportImage` / `openMachine`) |
|`PyProc`| Process OS kernel: snapshot-fork spawn, `map` / `mapArray` parallelism, lifecycle (`kill` / `signal` / respawn), `fork(2)` (clone a live process, its variables and arrays travel), and flow IPC (`pipe` / `lock` / `semaphore` / `shm`: SAB ring-buffer pipes with real blocking read and backpressure) |
**가상 오리진 경계 (정직한 벽)**: SW 합성 응답이라 진짜 오리진과 다르다. (1) `Set-Cookie`는 스트립된다(쿠키 세션 불가 = 토큰 방식 사용). (2) WebSocket 업그레이드는 가로채지 않는다(ASGI dispatch는 HTTP 요청/응답 단위). (3) 스트리밍/SSE는 축적 후 일괄 응답이다(청크 스트림 아님). (4) 엔드포인트는 `async def` 강제(동기 dispatch 없음). 부활(저널/세션/openMachine) 후에는 파일 핸들·DB 커넥션 같은 프로세스 자원이 되살아나지 않는다: 리플레이+델타는 파이썬 힙 상태를 복원하지 그 밖의 OS 자원을 복원하지 않으므로, 소비자는 부팅 훅(`boot.py` 또는 `Init`)에서 그런 자원을 재개설한다.
58
58
59
-
subpath export: `pyproc/runtime`, `pyproc/reactive`, `pyproc/syscall-bridge`, `pyproc/process-os`, `pyproc/worker`, `pyproc/browser-control-host`. **src 내부 경로 deep import 금지** (내부 파일 배치는 릴리즈 간 바뀔 수 있다. 실제로 v0.0.3에서 레이어 폴더로 재배치됐고 subpath 이름은 불변이었다).
60
-
61
-
### 브라우저 컨트롤 확장 (BrowserControl)
62
-
63
-
`BrowserControl`은 MV3 확장 안에서만 성립한다(offscreen document = 런타임 호스트, service worker = 권한 소유). 코어의 "단일 import + 버전 핀"과 달리, 확장은 파일이 확장 패키지 안에 물리적으로 있어야 하고 manifest 키의 상당수가 제품 결정이 아니라 pyproc 런타임 요구다. 조립 레퍼런스(실 src를 import하는 최소 픽스처): `tests/browser/runExtension.mjs` + `tests/browser/extensionFixture/`.
64
-
65
-
**두 절반(같은 핀 강제)**:
66
-
- offscreen: `boot()` + `Runtime.enableBrowserControl()` + `install()` (능력, index import). JSPI 필요 = `rt.runAsync` 경로.
67
-
- service worker: `openBrowserControlHost()` (subpath `pyproc/browser-control-host`).
68
-
- 두 절반은 `browserControlProtocol`의 버전된 메시지로 통신하고(현재 `PROTOCOL_VERSION=2`), `install()`이 핸드셰이크로 버전 불일치를 loud fail한다. **두 절반은 반드시 같은 pyproc 핀**이어야 한다(다른 핀 = 프로토콜 드리프트 = 런타임 파손).
69
-
70
-
**프로세스 OS 융합(워커 N = 세션 N, 독립 GIL N)**: `install()`은 offscreen 메인 인터프리터를 배선한다. N개 워커가 각자 파이썬으로 브라우저를 몰려면(진짜 병렬), dedicated Worker엔 `chrome.*`이 없으므로(제약 A) offscreen이 라우터가 된다. 워커 측은 `installBrowserWorker(py)`(그 워커 파이썬의 `_pyprocBrowserSend`를 offscreen postMessage로 배선 + `pyprocBrowser` 모듈 실행), offscreen 측은 스폰한 워커마다 `routeBrowserWorker(worker)`(워커 op를 SW 호스트로 릴레이). 워커는 offscreen(COI)에서 스폰돼 crossOriginIsolated를 상속해야 SAB/JSPI(run_sync)가 산다. 파이썬 연산은 워커별 GIL로 물리 병렬, 브라우저-op은 SW 단일 CDP 큐로 직렬(정직한 천장: N배 연산 병렬 + 1배 op 레이트). 실측: 실 src 픽스처가 Pyodide 워커를 이 경로로 몰아 검증.
71
-
72
-
**조작 표면(`pyprocBrowser.tab(url, mode)` -> `BrowserTab`)**: 항법(navigate/reload/back/forward), 입력(click/doubleClick/rightClick/hover/type/fill/press/select, 좌표 입력은 자동 스크롤 내장 + scrollIntoView/upload), 조회·추출(evaluate/text/html/attr/value/exists/count/texts/boundingBox/title/url/content), 대기(waitFor/waitForFunction), 캡처·에뮬레이션(screenshot/pdf/setViewport/setUserAgent/setHeaders/emulateMedia 다크모드·setTimezone·setOffline·setGeolocation 좌표 스푸핑·setLocale 언어 스푸핑), 다운로드 관측(enableDownloads/waitForDownload = 무엇이 다운로드되는지 파일명·URL 회수, 저장 경로 지정은 browser-level이라 미지원), 콘솔·에러 캡처(enableConsole/consoleLogs/waitForConsole = 페이지 console.* + 미처리 예외 관측), 접근성 트리(accessibilityTree = role/name 시맨틱으로 페이지 회수), 쿠키(cookies/setCookie/clearCookies/deleteCookie), 다이얼로그(setDialogHandler/lastDialog = alert/confirm/prompt 세션 정책 자동 응답), 네트워크(route/unroute = CDP Fetch 차단·정적 응답·요청 변조·붙잡기, 붙잡은 요청의 콜백형 결정 pendingRequests/continueRequest/fulfillRequest/abortRequest, waitForResponse/requests/responseBody = 응답 관측·바디 캡처), 프레임(frames/frame = iframe 내부 드릴다운. same-origin은 isolated world, cross-origin OOPIF는 chrome.debugger.getTargets에서 이 페이지 iframe src로 스코프해 targetId로 직접 attach = 둘 다 지원). 조작 계열은 핸들을 돌려 체이닝되고, 조회 계열은 JSON-값을 돌려준다(structured clone 경계라 PyProxy 아님). mode="debugger"는 CDP 신뢰 입력(isTrusted=true) + 캡처·에뮬·다이얼로그·네트워크 전 표면, mode="script"는 chrome.scripting 합성 입력(isTrusted=false)이고 CDP 전용 표면은 미지원 예외다. CDP 전용 표면은 추가 권한이 아니라 `debugger`가 여는 CDP Page/Network/Emulation/Fetch/DOM 도메인으로 대행한다. 전 표면은 attempts 게이트(1-16) + 실 src 픽스처로 브라우저 실측 통과(정본 타입: `index.d.ts`의 `BrowserTab`).
|`permissions: contentSettings`| setGeolocation 권한 부여. CDP Browser.grantPermissions가 browser-level이라 막혀 chrome.contentSettings.location로 우회. 지오로케이션 안 쓰면 생략 가능 |
84
-
|`minimum_chrome_version: 116`| offscreen API 하한 |
85
-
86
-
제품 결정(소비자 몫): `name`/`description`/`host_permissions` 범위/웹스토어 메타. offscreen이 자기 확장 자산을 로드하는 경로엔 `web_accessible_resources`가 불필요하다(same-origin 확장 문서, 픽스처 실측 확인).
87
-
88
-
**vendoring(SHA-핀 단일 import로는 부족)**: 확장은 번들러 없이 상대 경로로 로드되므로, pyproc `src` 트리를 구조 보존해 확장에 vendoring한다(offscreen이 `boot()`로 워커를 스폰하면 `worker.js`가 같은 폴더 계약을 확장 안으로 끌고 온다). vendor Pyodide 코어도 확장에 번들(`npm run fetch:engine`). 번들 소비자(Vite)는 subpath export로, 언번들 확장은 구조 보존 vendoring으로 도달한다.
89
-
90
-
**offscreen 격리 vs iframe 역전(Phase 2)**: 프로세스 OS는 COI(COEP require-corp)를 요구하는데 cross-origin iframe 역전(고정 화면)은 credentialless를 강제해 쿠키/sandbox가 막힌다(실측 3중 확증). 그래서 런타임(COI offscreen)과 iframe 셸(non-COI 문서)은 **다른 문서로 분리**한다. iframe 셸 UI는 제품 몫이고 pyproc은 헤더 제거 프리미티브만 기여한다.
59
+
subpath export: `pyproc/runtime`, `pyproc/reactive`, `pyproc/syscall-bridge`, `pyproc/process-os`, `pyproc/worker`. **src 내부 경로 deep import 금지** (내부 파일 배치는 릴리즈 간 바뀔 수 있다. 실제로 v0.0.3에서 레이어 폴더로 재배치됐고 subpath 이름은 불변이었다).
91
60
92
61
- 타입은 동봉된 `index.d.ts`가 계약이다.
93
62
- 엔진 내부(`HEAPU8`, `Runtime.raw` 등)를 직접 만지지 않는다. `raw`는 탈출구이고 계약 밖이다.
0 commit comments