Въведение
Phasis е чист PHP JavaScript енджин. Той лексикализира, парсва и изпълнява ECMAScript в хост процеса на PHP — без exec('node …'), без FFI и без собствено бинарно разширение. Изисква три стандартни разширения на PHP: ext-mbstring, ext-bcmath и ext-curl (транспортът по подразбиране на fetch()). ext-intl и ext-openssl са незадължителни. Вижте Първи стъпки за компилации, които не включват bcmath.
- Възможност за вграждане — добавете среда за изпълнение на JS във всяко приложение на PHP, рамка или инструмент на CLI чрез класа
Phasis\Engine. - Съответствие със спецификацията — преминава официалния набор от тестове test262 на 100 %, във всички категории и без пропуснати тестове.
- Уеб API — пълен пакет за уеб платформата (URL, TextEncoder/Decoder, atob/btoa, structuredClone, performance, DOMException), пълен пакет Fetch (fetch, Request, Response, Headers, Body, AbortController/Signal, Blob, File, FormData, EventTarget, пълна поддръжка на WHATWG Streams, navigator), плюс
crypto+SubtleCrypto,WebSocket,XMLHttpRequestи реален цикъл на събитията. 100 % от импортираните тестове на уеб платформата преминават. - Модерен синтаксис — стрелкови функции, класове, async/await, Promises, генератори, Symbol, BigInt, Proxy, Reflect, Temporal, Intl, TypedArrays, пълна поддръжка на модули.
- Взаимодействие между PHP и JS — подаване на скаларни стойности и масиви на JS чрез PHP (масивите се копират), обвързване на затварянията на PHP като функции на JS и извикване на функции на PHP от JS. Обектите на PHP все още не могат да се споделят с JS; вижте Споделени обекти.
Защо съществува Phasis
Приложенията на PHP, които трябва да изпълняват предоставен от потребителя JavaScript — енджини за шаблони, заместители за SSR във фронтенда, правила за валидиране на данни, изолирани среди за съдържание, безграфични тестови изпълнители — обикновено стартират Node.js като външен процес или пропускат тази функционалност. И двата подхода добавят оперативна сложност: втора среда за изпълнение, граница за сериализация, мрежа от канали за подпроцеси и трудна за защита конфигурация при споделен хостинг.
Phasis запълва тази празнина. Кодът ви на PHP може да лексикализира, парсва и изпълнява JavaScript, като използва само PHP 8.2+ с mbstring, bcmath и curl. Енджинът се разпространява като пакет за Composer и предлага малък интерфейс на API.
Какво прави
- Реализира пълната стандартна библиотека на ECMAScript:
Array,String,Object,Math,JSON,Date,RegExp,Map,Set,Promise,Proxy,Reflect,Symbol,BigInt,TypedArray,Temporal,Intl, генератори, асинхронни итератори и модули. - Включва API-тата на Web Platform, за които библиотеките JS от реални проекти проверяват предварително:
URL,URLSearchParams,TextEncoder/TextDecoder,atob/btoa,structuredClone,performance,DOMException. Вижте Web APIs за пълния набор. - Включва
fetchс пълното семейство Fetch —Request,Response,Headers, четци на тялото,AbortController/AbortSignal,Blob,File,FormData,EventTarget/Eventи пълния WHATWG Streams (ReadableStream,WritableStream,TransformStream, BYOB, стратегии за опашки). Реалният HTTP работи веднага чрезext-curlна PHP. - Включва
crypto+ пълнияSubtleCrypto(семейство SHA, HMAC, AES-GCM/CBC/CTR, RSA-OAEP/PSS/PKCS1, ECDSA, ECDH, HKDF, PBKDF2),WebSocket(RFC 6455 + сменяем транспорт) иXMLHttpRequest(изградено върху същия транспорт за fetch). - Включва истински цикъл на събитията:
setTimeout,setInterval,clearTimeout,clearInterval,queueMicrotask, както и Stage-3AsyncContextза предаване на стойности през асинхронни граници. - Поддържа модерен синтаксис — деструктуриране, spread/rest, изчисляеми свойства, незадължително свързване, сливане при nullish стойности, шаблонни литерали, маркирани шаблони, класове (с частни полета, статични блокове и декоратори), top-level await.
- Преобразува стойности през границата PHP↔JS. Скаларните стойности и масивите се копират навътре, извикваемите стойности PHP стават функции JS, а резултатите от JS се връщат като скаларни стойности и масиви PHP. Вижте Преобразуване на стойности за точните правила.
- Работи под контрола на хоста. Хостът управлява транспорта
fetchи кукичките за правила, цикълът на събитията работи с виртуално време, а фиксираният лимит на дълбочината на стека спира безконтролната рекурсия. Има лимит за итерациите на цикъла, но той все още не се прилага за цикли, изпълнявани от байткод VM; няма лимити за дължина на низове, изход или реално време. Вижте API: setLimit. - Проверява се спрямо Node.js (V8). CI изпълнява тестовете за единици и oracle при всяко качване към
mainи при всяка заявка за изтегляне, а тестовете Web Platform Tests и пакетите от реалния свят — при промяна в кода на машината; пълната матрица test262 се изпълнява ръчно и моментната ѝ снимка се комитва вCOMPAT.md. Вижте Съвместимост.
Какво не е
Phasis не е JIT компилатор. Това е интерпретатор, който обхожда дървото, с виртуална машина за байткод, използвана при подходящи случаи. При натоварвания, ограничени от диспечирането, очаквайте време за изпълнение около 100× това на V8. Компромисът е нулев брой зависимости, чист PHP и изпълнение под контрола на хоста — идеално за вграждане на JavaScript в приложения на PHP, където коректността и изолацията са по-важни от максималната пропускателна способност.
Откъде да започнете
- Първи стъпки — инсталирайте и изпълнете първия си скрипт.
- CLI —
bin/phasisза изпълнение на файлове, оценяване на изходен код и извеждане на AST. - API — вградете
Phasis\Engineв приложението си на PHP. - Взаимодействие — подавайте стойности и извикваеми обекти на PHP към JavaScript.
- Съвместимост — покритие с test262 и поддържани функции.
- Парсер — парсвайте JavaScript в типизиран AST или ESTree, без да го изпълнявате.
- Форматиращ инструмент — форматирайте JavaScript, JSON и CSS с оформление, съвместимо с prettier.
- Разширени теми — архитектура, виртуална машина за байткод, бенчмаркове и модел за тестване с оракул.