kan het in zwang zijn, maar is er een praktische reden om Node aan te nemen.js? Lee Boynton laat zien hoe het kan worden gebruikt om een real-time nieuwsfeed toe te voegen aan uw PHP site.

Dit artikel laat u zien hoe u Node kunt gebruiken om real-time functies toe te voegen aan uw PHP-gebaseerde website. Eerste, we zullen kijken Een beetje meer op wat maakt Node een goede pasvorm voor real-time apps, voordat we gaan om te laten zien hoe je een real-time nieuwsfeed te bouwen en op te nemen in uw PHP website.

Thread-based vs Event-based

traditioneel wordt PHP geserveerd met Apache en de mod_php module. Als je het ’top’ commando uitvoert op je Unix-gebaseerde webserver zul je waarschijnlijk een groot aantal Apache processen zien die webclients bedienen. In deze setup, elke client verzoek start meestal een nieuw Apache proces totdat alle beschikbare RAM is opgebruikt. Onlangs is nginx en php-fpm naar voren gekomen als de meest efficiënte methode om PHP-websites te bedienen, maar zelfs in deze setup wordt elke client bediend door een ander PHP-proces. Het belangrijkste punt hier is dat, van begin tot eind, een client request is het gebruik van een PHP proces voor de gehele duur. Als het lang duurt om elk verzoek te verwerken, kunnen de bronnen van de server zeer snel worden opgebruikt.

In knooppunt dient een enkel Knooppuntproces gewoonlijk elke client in een gebeurtenislus. Voor langdurige, dure processen zoals toegang tot het bestandssysteem, een database of een externe API, wordt aanbevolen om asynchrone methode aanroepen te gebruiken in plaats van die te blokkeren. Dit wordt bereikt door het gebruik van callbacks die worden geactiveerd wanneer een actie zoals het openen van het bestandssysteem is voltooid. Dit betekent dat een enkel knooppunt proces nieuwe aanvragen kan blijven verwerken terwijl de dure operatie op de achtergrond wordt uitgevoerd. Wanneer de dure bewerking is voltooid, gaat het terug naar de gebeurtenisluswachtrij om verder te worden verwerkt door Node.

in essentie kan Node worden gezien als een vergelijkbare omgeving voor het bouwen van toepassingen zoals Python ‘ s Twisted of EventMachine in Ruby. Node heeft ook een ingebouwde productie-ready HTTP-server, zodat het geen aparte server nodig heeft om het uit te voeren, zoals Apache of Nginx, waardoor de lean resource-vereisten verder worden verbeterd (met uitzondering van geheugenlekken).

var http = require('http');http.createServer(function (req, res) { res.writeHead(200, {'Content-Type': 'text/plain'}); res.end('Hello Worldn');}).listen(1337, '127.0.0.1');console.log('Server running at http://127.0.0.1:1337/');

Het code voorbeeld hierboven laat zien hoe je een verplichte” hello world ” webserver kunt schrijven in slechts een paar regels code. De eerste regel toont het gebruik van het modulesysteem dat bekend staat als CommonJS welke Node gebruikt om afzonderlijke modules op te nemen. De require-functie is ingebouwd en importeert in dit geval de HTTP-module van het knooppunt voor gebruik in de toepassing. De tweede regel maakt een nieuw webserverobject aan. Merk op dat de eerste parameter voor de createServer methode een anonieme functie is. De meeste methoden in Node accepteren een callback functie als parameter, en dit is de sleutel tot het bouwen van event-driven applicaties.

de volgende regel van uitvoering is regel 5, die methode chaining gebruikt om de listen methode aan te roepen op de return waarde van de createServer methode (de waarde geretourneerd is de HTTP module instantie). De listen methode zorgt ervoor dat de server HTTP aanvragen begint te accepteren op poort 1337 op localhost. De laatste regel schrijft een bericht naar de console om te zeggen dat de server is gestart. Alleen wanneer een verzoek aan de server wordt gedaan wordt de anonieme functie aangeroepen, die de HTTP-statuscode instelt op 200 OK en de Content-Type header. Het’ Hello World ‘ bericht is eindelijk geschreven naar de HTTP response body op lijn 4.

waarom zou ik Node moeten gebruiken.js dan?

node ‘ s event-driven model is vooral geschikt voor real-time toepassingen zoals games, nieuwsfeeds en chat toepassingen. Daarnaast kunt u ook dezelfde taal gebruiken op de frontend en backend. JavaScript wordt alleen maar populairder als meer rijke client-side applicaties worden gebouwd en webbrowsers sneller bij het uitvoeren van JavaScript. Moeten schakelen tussen talen kan frustrerend zijn.

WordPress Spezial

Entwickler Magazin Spezial Vol. 10: WordPressEntwickler Magazin Spezial Vol. 10: WordPress
Alles rund um WordPress im Entwickler Spezial Vol. 10-ab 18.11.2016 im Handel.
WordPress ist längst weit mehr als ein simples Blogsystem. In diesem Sonderheft beschäftigen sich zahlreiche Spezialisten mit allen wichtigen Fragen rund um das verbreitetste CMS im Web; und dabei geht es nicht nur um klassische Themen, sondern auch um Affiliate Marketing, E-Commerce u.v.m.

ten Tweede, het heeft een goede ondersteuning voor WebSockets. Hoewel het mogelijk is om WebSockets in PHP te ondersteunen, maakt de asynchrone aard van Node en de ingebouwde HTTP-server het een betere pasvorm. WebSockets zijn een manier om een blijvende verbinding met de browser te onderhouden om gegevens snel naar de client te pushen. In vergelijking met eerdere oplossingen zoals long polling of comet, WebSockets hebben veel lagere latency, omdat er geen overhead van het instantiëren van een HTTP-verbinding elke keer dat sommige gegevens moeten worden verzonden. Het nadeel van WebSockets is dat het een HTML5-functie is, en als zodanig niet zo goed wordt ondersteund in browsers als gewone oude Ajax is. Het is echter mogelijk om gracieus terug te vallen op alternatieve technieken zoals lange polling in browsers die geen WebSockets ondersteunen.

op de internationale PHP Conferentie van dit jaar kunt u meer te weten komen over het integreren van knooppunten.js met PHP!

De internationale PHP conferentie is ‘ s werelds eerste PHP conferentie en is al meer dan een decennium een mijlpaal voor top-notch pragmatische expertise in PHP en webtechnologieën . Op het IPC ontmoeten internationaal gerenommeerde experts uit de PHP industrie PHP gebruikers en ontwikkelaars van grote en kleine bedrijven. Bekijk onze Early Bird prijzen voor geweldige kortingen!

Hier zijn enkele highlight-sessies van IPC:

  • het maken van uw hoek.js applicatie toegankelijk
    Dirk Ginader (Google)
  • TypeScript – JavaScript-ontwikkeling productiever en robuuster maken
    Rainer Stropek (software architects gmbh)
  • How to get ready for PHP 7
    Sebastian Bergmann (thePHP.cc)

bedenk wel dat Node een onvolwassen platform is in vergelijking met PHP. Oorspronkelijk gemaakt in 2009, het is nog in de kinderschoenen en heeft Versie 1.0 nog niet bereikt – als dat voor u belangrijk is. Het kan zijn dat API ‘ s die je gebruikt change in de toekomst, of niet in staat om een framework dat dezelfde feature set als uw favoriete PHP framework heeft te vinden. Inderdaad, in mijn ervaring de derde partij bibliotheken en frameworks beschikbaar hebben de neiging om te bestaan uit veel kleinere bundels van functionaliteit die je nodig hebt om samen te werken.

Er is ook een groter risico op geheugenlekken waardoor uw toepassing tot stilstand komt. Knooppunten processen meestal continu draaien, terwijl PHP processen de neiging om periodiek worden respawned om het effect van geheugenlekken te ontkennen.

het integrerende deel

De news feed zal worden geïntegreerd met een basis PHP website die gebruikers logins en sessies afhandelt, met behulp van een gemeenschappelijke setup van php-fpm en nginx. We zullen JavaScript gebruiken om te communiceren met een Node-applicatie op de server en dynamisch de nieuwsfeed bij te werken zonder de pagina opnieuw te laden. Eerst even een korte opmerking over sessies.

als u dit nog niet doet, moet u een gecentraliseerde opslagruimte gebruiken voor uw sessies (figuur 1). Memcached kan eenvoudig worden gebruikt voor deze taak met behulp van de ingebouwde sessie save handler in de PECL memcached extensie. Als u de mogelijkheid wilt om de server te herstarten die uw sessies opslaat zonder gegevens te verliezen, dan is Redis een goede gok. Hoe dan ook, een gecentraliseerde sessie opslag stelt u in staat om te laden balans van uw applicatie over meerdere webservers. Het stelt u ook in staat om sessiegegevens te delen met applicaties die zijn gebouwd met andere programmeertalen.

figuur 1: gedeelde sessiearchitectuur.

Er is echter een klein probleem met het ontleden van sessiegegevens. Hieronder ziet u het standaard serialisatieformaat van een PHP-sessie:

not|a:2:{i:0;s:4:"easy";i:1;a:1:{s:2:"to";s:5:"parse";}}

Het kan lijken alsof u stringmanipulatie kunt gebruiken om het te ontleden, maar er kunnen edge-gevallen zijn die lastig op te lossen zijn. Het zou leuk zijn als de sessie in het geliefde JSON-formaat zou worden geserialiseerd:

{"this":{"is": "easier", "to": "parse"}}

veel beter. Het is vrij eenvoudig om je eigen session serialiser te schrijven die alles wat je opslaat in $_SESSION zal converteren naar JSON formaat, zie mijn versie.

U kunt ook msgpack overwegen dat kan worden geconfigureerd om sessies te serialiseren, zoals in de onderstaande code, die ook laat zien hoe memcached te gebruiken als de session save handler.


Er is een bibliotheek van derden beschikbaar voor Node die msgpack kan serialiseren en deserialiseren, beschikbaar in npm (Node Package Manager, bevat een groot aantal modules die kunnen worden gebruikt in uw toepassing met slechts een eenvoudige NPM installatie ). We zullen nu kijken naar het bouwen van de news feed met behulp van Node en het opnemen van dit in een PHP-applicatie.

PHP App

de PHP applicatie behandelt eenvoudig gebruikers logins en sessies. Sessies worden opgeslagen in memcached, maar kunnen vrij gemakkelijk worden opgeslagen in redis. De code hieronder toont fragmenten van de eenvoudige één pagina applicatie (voor de volledige bron ga naar github.com/lboynton/phphants-march-php).

// // <!]>

de eerste regel van het script bevat het Composer autoloader bestand, wat betekent dat alle afhankelijkheden automatisch automatisch geladen worden, waardoor er geen aparte include of require regels nodig zijn (Noot van de redactie: voor meer informatie over Composer, zie Jefersson Nathan De O. Chaves ‘ artikel). In dit geval is de session save handler het enige stukje externe code dat vereist is. Het is echter heel eenvoudig om pakketten van derden die beschikbaar zijn op packagist of elders op een later tijdstip op te nemen met behulp van Composer die ook automatisch zal worden toegevoegd aan autoloading. Regels 3 en 4 zetten een verbinding op met memcached, terwijl de sessie save handler wordt geïnitialiseerd en geregistreerd met PHP in regels 5-14. Gebruikers worden ingelogd door simpelweg de gebruikersnaam als een GET parameter op te geven, hoewel dit in een echt systeem moet worden vervangen door een meer functioneel authenticatiesysteem.

aan de JavaScript-kant gebruiken we enkele bibliotheken van derden : jQuery, underscore.js en de Socket.IO client, dat is het browsergedeelte van de Knooppuntmodule die we zullen gebruiken om gegevens naar de browser te pushen. De io.connect methode call creëert een verbinding met de Node applicatie, die een van een aantal transporten zoals websockets of Ajax kan gebruiken, afhankelijk van browser ondersteuning. Socket.on methode stelt een event handler die een nieuwsbericht op de pagina wanneer een ‘nieuws’ gebeurtenis wordt geactiveerd door de server kant zal maken.

opmerking: De toepassing gebruikt Composer voor het installeren van de session save handler en Bower, een pakketbeheerder voor het installeren van assets aan de clientzijde. Voer ‘NPM-g install bower’uit om Bower te installeren. Dan om de activa te installeren, doe ‘bower install’. U kunt ook de scripttags en stylesheets bijwerken met lokale versies.

de toepassing wordt geserveerd met nginx. Hier is het Nginx configuratie bestand:

upstream node { server localhost:3000;}server { listen 8080; server_name php-node-demo.localhost; root /home/lee/public_html/php-node-demo; index index.php; location / { try_files $uri $uri/ /index.php?$args; } location ~ .php$ { include fastcgi_params; fastcgi_index index.php; fastcgi_pass unix:/var/run/php5-fpm.sock; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; } location ~ /socket.io { proxy_pass http://node; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; }}

regels 1-3 definiëren een upstream server die de Node app draait. Elk verzoek eindigt op .php zal worden verzonden naar php-fpm (regels 15-20), terwijl alle verzoeken met /socket.io in de URL zal worden doorgegeven aan de Node app (lijnen 22-27). Regels 25 en 26 vertellen nginx om protocol switching te ondersteunen en websockets in staat om te worden proxied aan knooppunt. Dit betekent dat de PHP app en Node app beide draaien op dezelfde poort, wat de client betreft.

knooppunt.js App

het knooppunt.js app behandelt gewoon elke klant verzoeken voor de news feed. Fragmenten ervan worden hieronder weergegeven (zie github.com/lboynton/phphants-march-node voor de volledige bron).

io.set('authorization', function(handshake, callback) { var cookies = cookie.parse(handshake.headers.cookie); mcClient.get('sessions/' + cookies.PHPSESSID, function(error, result) { if (error) { callback(error, false); } else if (result) { handshake.session = JSON.parse(result); callback(null, true); } else { callback('Could not find session ID ' + cookies.PHPSESSID + ' in memcached', false); } });});io.sockets.on('connection', function(socket) { var session = socket.handshake.session; sockets = socket;);function getNews() { redis.blpop('news', 0, function(err, data) {news = JSON.parse(data);if (typeof news.to !== 'undefined') { if (typeof sockets !== 'undefined') {sockets.emit('news', news.content); }} else { io.sockets.emit('news', news.content);}process.nextTick(getNews); });}

Socket.io is een bibliotheek die een enkele API levert voor het uitvoeren van WebSocket communicatie tussen client en server. Het ondersteunt ook sierlijke fallback wanneer WebSockets niet beschikbaar zijn in de browser, en andere handige functies in een messaging-protocol, zoals hartslagen, timeouts en ontkoppeling ondersteuning die niet out of the box wordt ondersteund met de HTML5 WebSocket API.

het eerste fragment configureert autorisatie voor aanvragen die Socket.io ontvangt. Wanneer een nieuw verzoek binnenkomt, zal het de cookies in het verzoek ontleden en proberen een memcached sleutel op te halen die overeenkomt met de waarde van de PHPSESSID-cookie (de standaardnaam voor de PHP-sessiecookie). Indien gevonden, zal het de geparseerde waarde van de memcached sleutel in data opslaan.sessie die later kan worden geopend.

het volgende fragment configureert wat er moet gebeuren wanneer Socket.io activeert de’ verbinding ‘ gebeurtenis. Deze gebeurtenis wordt geactiveerd tijdens de eerste verbinding van de client, zodra deze is geautoriseerd. De sessiegegevens die eerder uit memcached werden opgehaald, kunnen nu via de socket worden geraadpleegd.handdruk variabele. Wanneer de client verbinding maakt, wordt de socket-instantie gekoppeld aan de gebruikersnaam van de client, zodat berichten naar individuele gebruikers kunnen worden verzonden.

Het Laatste fragment bevat een functie om te controleren op nieuwe nieuwsitems in een Redis-wachtrij. Het maakt gebruik van het BLPOP commando in redis, wat betekent dat als de wachtrij leeg is, het zal blokkeren totdat sommige gegevens aan de wachtrij worden toegevoegd voordat het wordt gekraakt. Wanneer sommige gegevens kunnen worden popped uit de wachtrij, het wordt ontleed als JSON alvorens te bepalen of de inhoud moet worden verzonden naar elke aangesloten client of slechts een enkele gebruiker. De inhoud van het nieuwsbericht wordt naar de juiste socket gestuurd door de methode emit() aan te roepen op de socket die eerder was geassocieerd met de gebruiker in de connection event handler.

ten slotte, het proces van Node.nexttick () methode wordt aangeroepen met de getNews functie als argument. Dit betekent dat de getNews functie de volgende keer dat de event loop loopt zal worden aangeroepen en zal doorgaan met het controleren van de Redis wachtrij voor gegevens totdat de toepassing wordt gestopt.

om te installeren, gebruikt u npm om de vereiste afhankelijkheden te downloaden. Voer vervolgens de applicatie uit met de node-app.js.

u kunt nu een webbrowser openen en naar http://localhost:8080/?username=bob navigeren en de toepassing news feed zien. Open nu een tweede browser tab of venster met een andere gebruikersnaam, bijvoorbeeld http://localhost:8080/?username=sally.

het bijwerken van de Feed

Het bijwerken van de feed is gewoon een geval van het duwen van een nieuw nieuwsitem in de wachtrij. Maak verbinding met de Redis CLI interface met het commando redis-cli. Dit is een interactieve shell voor redis, waarmee je commando ‘ s direct naar de server kunt sturen. Het onderstaande codevoorbeeld laat zien hoe naar de wachtrij te pushen:

rpush news '{"content": "Testy test", "to": "bob"}'

In het webbrowservenster dat u hebt geopend voor gebruiker bob zou u het nieuwsbericht van boven aan de pagina moeten zien glijden. Als alternatief kun je news naar zowel bob, sally als andere aangesloten clients pushen door de parameter “to” uit te sluiten, als volgt:

rpush news '{"content": "Everyone should see this"}'

In een echte applicatie push je data in de wachtrij vanuit PHP, bijvoorbeeld met de php-redis extensie of predis.

conclusie

Dit is slechts een eenvoudig voorbeeld om te laten zien hoe Node kan worden geà ntegreerd met uw PHP applicatie. Er zijn een paar beperkingen in de implementatie. Het zal bijvoorbeeld slechts één verbinding van elke gebruiker onthouden. Als een gebruiker meerdere tabbladen of Vensters heeft die open staan voor de nieuwsfeed, wordt slechts één pagina bijgewerkt. Dit kan worden opgelost door het opslaan van een array van sockets per gebruiker, en het bijhouden van elke verbinding en loskoppeling toe te voegen of te verwijderen van de sockets uit de array. Het is aan de lezer om een betere oplossing te implementeren. Het toonde ook tools zoals Composer en Bower die ik ten zeerste aanbevelen u overwegen te gebruiken in uw toepassingen.

Lee Boynton is een ontwikkelaar gevestigd in Hampshire, Verenigd Koninkrijk, met een bijzondere interesse in real-time toepassingen zoals instant messaging en activiteitenstreams. Hij heeft kennis van server side ontwikkeling en administratie evenals frontend ontwikkeling. Hij werkt bij het lokale bedrijf Symbios Group en is ook lid van PHP Hampshire voor wie hij helpt bij het organiseren van evenementen.

Geef een antwoord

Het e-mailadres wordt niet gepubliceerd.