નેટિવ Polling API વ્યાખ્યાયિત કરતો PHP RFC મંજૂર કરવામાં આવ્યો છે અને ભાષાના માસ્ટર બ્રાન્ચમાં મર્જ કરવામાં આવ્યો છે, જે ડેવલપર્સને ફાઇલ ડિસ્ક્રિપ્ટર્સ (file descriptors) ને પોલ કરવા માટે ઝડપી, OS-સ્તરની રીત આપે છે. તાજેતરમાં ઉમેરવામાં આવેલા Fibers સાથે જોડાઈને, PHP પાસે હવે અસિંક્રોનસ (asynchronous) કોડ માટે એક ઇન-બિલ્ટ, કાર્યક્ષમ પાયો છે—એક એવી ખામી જે લાંબા સમયથી લાઇબ્રેરીઓને તેમના પોતાના કામચલાઉ ઉપાયો (work-arounds) તૈયાર કરવા માટે મજબૂર કરતી હતી.

Fibers અને event loop, અલગ કરેલા

Fibers એ લો-લેવલ કંટ્રોલ-ફ્લો પ્રિમીટિવ (primitive) છે. તેઓ કોઈ ફંક્શનને પસંદ કરેલા બિંદુએ તેનું એક્ઝિક્યુશન સ્થગિત કરવા અને પછી બરાબર ત્યાંથી ફરી શરૂ કરવા દે છે જ્યાંથી તે અટક્યું હતું. મહત્વપૂર્ણ રીતે, એક fiber ને સોકેટ્સ, ટાઈમર્સ અથવા અન્ય કોઈ I/O સોર્સ વિશે કંઈ ખબર હોતી નથી; તે ફક્ત જરૂરિયાત મુજબ અટકે છે અને ફરી શરૂ થાય છે.

Event loop એ શેડ્યુલર છે જે નક્કી કરે છે કે સ્થગિત થયેલ fiber ને ક્યારે ફરી શરૂ કરવું જોઈએ. એક સામાન્ય async stack માં, લૂપ ફાઇલ ડિસ્ક્રિપ્ટર્સના સેટ પર નજર રાખે છે, તે વાંચવા યોગ્ય (readable) અથવા લખવા યોગ્ય (writable) બને તેની રાહ જુએ છે, અને પછી યોગ્ય fiber ને જાગૃત કરે છે.

PHP પાસે અગાઉ Fibers હતા પરંતુ ઓપરેટિંગ સિસ્ટમને કયા ડિસ્ક્રિપ્ટર્સ તૈયાર છે તે પૂછવા માટે નેટિવ મિકેનિઝમનો અભાવ હતો. પરિણામે stream_select() અથવા એક્સટર્નલ એક્સ્ટેન્શન પર નિર્ભરતા રહેતી હતી, અને દરેક async લાઇબ્રેરીએ Linux ના epoll, BSD ના kqueue, Windows ના IOCP વગેરે માટે પોતાના બેક-એન્ડ્સ લખવા પડતા હતા.

નવું Polling API તે ખૂટતા ભાગને પૂરો કરે છે. તે OS ની પોલિંગ સુવિધાઓ (Linux પર epoll, BSD/macOS પર kqueue, વગેરે) ની આસપાસ એક થિન રેપર (thin wrapper) પ્રદાન કરે છે. API Fibers નું સ્થાન લેતું નથી; તે ફક્ત event loop ને જરૂરી ઝડપ અને સ્કેલેબિલિટી આપે છે.

ReactPHP, Amp અને મિત્રો માટે આ ફેરફાર શા માટે મહત્વપૂર્ણ છે

ReactPHP અને Amp v3 એ OS પોલિંગ મિકેનિઝમ્સ પર તેમના પોતાના એબ્સ્ટ્રેક્શન લેયર્સ (abstraction layers) બનાવ્યા છે. તે લેયર્સમાં મલ્ટિપલ કોડ પાથ હોય છે, જે દરેક ચોક્કસ પ્લેટફોર્મ માટે ટ્યુન કરેલા હોય છે, અને તેમને કર્નલ ફેરફારો સાથે સિંક રાખવા પડે છે. નેટિવ Polling API સાથે, લાઇબ્રેરીઓ તે મોટાભાગના પ્લમ્બિંગ (plumbing) ને છોડી શકે છે અને સિંગલ, કોર-પ્રોવાઈડેડ કોલ પર નિર્ભર રહી શકે છે.

  • Maintenance – ઓછા પ્લેટફોર્મ-સ્પેસિફિક બ્રાન્ચ્સ એટલે ઓછા બગ્સ અને સિક્યુરિટી રિવ્યુ માટે નાનું સપાટી ક્ષેત્ર (surface area).
  • Performance – નેટિવ કોલ સીધો epoll/kqueue સાથે વાત કરે છે.
  • Portability – "vanilla" PHP પર ચાલતો કોડ હવે કોઈપણ વૈકલ્પિક એક્સ્ટેન્શનની જરૂરિયાત વિના તમામ સપોર્ટેડ ઓપરેટિંગ સિસ્ટમ્સ પર સમાન બેઝલાઇન પર્ફોર્મન્સ મેળવે છે.

તેનાથી વિપરીત, Swoole એ ફૂલ-રનટાઇમ રિપ્લેસમેન્ટ તરીકે રહે છે જે પોતાનું event loop અને coroutine સિસ્ટમ સાથે આવે છે. Polling API Swoole ના ટ્રેડ-ઓફ્સ (trade-offs) ને અસર કરતું નથી; જે ડેવલપર્સને અલ્ટ્રા-લો લેટન્સી અથવા કસ્ટમ મેમરી મેનેજમેન્ટની જરૂર છે તેઓ તેને હજુ પણ એક અલગ વિકલ્પ તરીકે ગણશે.

એક ઝડપી બેન્ચમાર્ક વાર્તા કહે છે

એક મિનિમલ શેડ્યુલરે મલ્ટિપલ ફાઇબર્સને મેનેજ કરવા માટે સિંગલ Io\Poll\Context નો ઉપયોગ કરીને રો સોકેટ્સ (raw sockets) દ્વારા કેટલાક URL મેળવ્યા. બે અવલોકનો સામે આવ્યા:

  1. Speed – વધુ કન્કરન્ટ રિક્વેસ્ટ ઉમેરવાથી કુલ સમય વધતો નથી; રિક્વેસ્ટ બેચ સૌથી ધીમી સિંગલ રિક્વેસ્ટ જેટલી જ ઝડપથી પૂર્ણ થાય છે. બીજા શબ્દોમાં કહીએ તો, કન્કરન્સી ઓવરહેડ અસરકારક રીતે શૂન્ય છે.
  2. CPU coststream_select() સાથે, જેમ સ્ટ્રીમ્સની સંખ્યા વધે છે તેમ CPU વપરાશ નોંધપાત્ર રીતે વધે છે, કારણ કે ફંક્શનને દરેક કોલ પર દરેક ડિસ્ક્રિપ્ટર પર ઇટરેટ કરવું પડે છે. કર્નલની સિંગલ સિસ્ટમ કોલમાં ઘણા ડિસ્ક્રિપ્ટર્સનું મોનિટર કરવાની ક્ષમતાને કારણે, Polling API નો ખર્ચ ત્રણ સ્ટ્રીમથી લઈને ત્રીસ સ્ટ્રીમ સુધી સ્થિર રહે છે.

ડેવલપર્સ હવે શું કરવું જોઈએ

  • Amp v3 અપનાવો જો તમે ફાઇબર-નેટિવ સ્ટાઇલ પસંદ કરતા હોવ જે સીધી રીતે નવા API સાથે સુસંગત હોય. તેનું પબ્લિક ઇન્ટરફેસ પહેલેથી જ અન્ડરલાઇંગ પોલર સાથે મેપ થાય છે, તેથી તમે તમારા કોડને ફરીથી લખ્યા વિના તેનો લાભ મેળવી શકો છો.
  • ReactPHP સાથે જ રહો જો તમને લૂપના લાઇફસાયકલ પર સ્પષ્ટ નિયંત્રણ ગમતું હોય.
  • પ્રોડક્શન વર્કલોડ્સ માટે કસ્ટમ શેડ્યુલર્સ ટાળો. પ્રોડક્શન માટે તમારો પોતાનો શેડ્યુલર ન લખો.