• úvod
  • témata
  • události
  • tržiště
  • diskuze
  • nástěnka
  • přihlásit
    registrace
    ztracené heslo?
    ANGEL333node.js - Evented I/O for V8 JavaScript

    Věříte, že nějaký webapp framwork postavený na node.js (Express?) bude v budoucnosti rozšířený podobně jako jsou nyní např. Django, CakePHP, Rails, Zend, atd..?

    55 hlasy od 55 respondentů

      Relativně nové server-side javascriptové API. Hlavní předností je, že je event-driven a neblokující. Již nyní obsahuje implementaci protokolů HTTP, TCP, DNS, rozhraní pro práci s procesy, soubory, atd..

      Instalace je velmi jednoduchá, jediná závislost je Python, potom node.js nainstalujete jako standardní program.

      Odkazy:


    • Oficiální web: http://nodejs.org

    • Přednáška od Ryana Dahla (autor node.js)

    • Git repozitář: http://github.com/ry/node
    • rozbalit záhlaví
      B3DA
      B3DA --- ---
      KOC256: pokud to chces poslat vse najednou, vytvor si pole tech stringu, a udelej neco jako
      const promises = arr.map(u => updatePage(u))
      Promise.allSettled(promises)
        .then(results => {
          // foreach results = r => r.status === 'fullfiled' ? r.value : r.reason ...
        }).catch(...)
      

      muzes pouzit i Promise.all(), ale pokud ti spadne jeden request, rejectne se i zbytek..
      KOC256
      KOC256 --- ---
      YORK:
      No je to v podstatě moje druhá appka, takže ani moc nevím co a jak refaktorizovat. Jsou to nějaké kusy kódů z tutoriálů a googlení.

      no musel jsem ty foreache přepsat na for, protože jinak při prostém přidání async přes ty dvě functions, to stejně padalo zase na nějakou chybu s tím volaním stránky. Předpokládám, že nějaká vlastnost těch async...

      Nyní tedy takto:
      // NE Object.keys(result.GP.c).forEach(async function(k) {
      for (var k in Object.keys(result.GP.c)) {

      Aha, tak ted zjistuji, ze to tu mam dve hodiny rozepsane... :D
      A dosel jsem k tomu samemu jako B3DA.

      Jen je pravda, ze mi to vsechno jede seriove, takze jak tu zaznelo poooomaaaaaluuuu.

      Jak to teda napsat, aby ten cyklus probihal asynchronne? Asi staci naznacit konstrukcne... :o)
      YORK
      YORK --- ---
      AREX: Awaity v cyklu udělat jdou, akorát pak přijdeš o výhodu asynchronního kódu. Počká to nejdří na první, pak na druhej, pak na třetí, atd. Promise.all() se od toho liší v tom, že může všechno probíhat současně a čekáš na to, až doběhnou všechny.

      (Rozumnej linter samozřejmě await v cyklu označí jako chybu, protože to prakticky nikdy nechceš udělat. Ale technicky to jde.)
      B3DA
      B3DA --- ---
      v tomhle pripade mozna spis
      Promise.allSettled()

      nebo treba neco jako
      
      for (const key of Object.keys(result.GP.c)) {
        const foo = await updatePage(result.GP.c[k].code[kk])
      }
      
      AREX
      AREX --- ---
      YORK: Dělat callback do `forEach` jako async nebude nikdy fungovat, protože na to nebude nic čekat. Obecně smyčky a async je bolavé téma. Takový ošklivý hack je `await Promise.all(result.GP.c.map(async ...)`

      Ale ta dvakrát vnořená smyčka v tom udělá ještě větší bordel :) Takový jiný trick je v podstatě chainovat jeden Promise a ten pak počkat.

      KOC256: Asi bych ti doporučil nejprve v rámci těch smyček se sestavit flat array, to můžeš v pohodě udělat synchronně a pak použít ten trik co jsem psal výše s Promise.all.
      YORK
      YORK --- ---
      KOC256: Aha, v tom případě není problém v tom, že bys přes await volal funkci, která není async, ale že používáš await ve funkci, která není async. Řekl bych, že jak máš

      "Object.keys(result.GP.c).forEach(function(k) {"

      tak to 'funcion(k)' musí bejt async.


      Osobně bych ten kód refactoroval, všechny inline funkce bych pojmenoval a vyhodil ven, aby bylo dobře vidět, že každou async funkci voláš přes await a že každá funkce, ve který používáš await, je async.
      KOC256
      KOC256 --- ---
      YORK:
      kdyz spodni kod hodim do toho vrchniho pod radek console.log('Loading XML done.');
      tak to zacne hajlovat, ze se mu nelibi Await postupne u:
      await page.goto('https://www.neco.com/' + result.GP.c[k].code[kk], {waitUntil: 'networkidle2'});
      if (await page.$('#CB_dMessage') != null) {
      } else if (await page.$('#CB_aMessage') != null) {

      Kdyz je dam pryc tak to zhuci, protoze samozrejme ty page.$... necekaji na nacteni stranky a tedy tam nic nenajdou...
      KOC256
      KOC256 --- ---
      YORK:
      No to jsem samozrejme zkousel, ale proste porad se tomu neco nelibilo...

      Da se prvni blok zaobalit do nejakeho stavu, kde bude vracet jen promenou "result", kterou si prave v tom spodnim kodu nejak nactu?

      Jinak pokud to chapu, tak musim bud vrchni kod dostat doprostred toho spodniho, nebo ten spodni do prostred toho vrchniho. COz mi pak prijde cele to strasne zneprehlednujici... :(
      YORK
      YORK --- ---
      KOC256: Zkuz smazat 'await' z řádku, kde ti to píše syntax error.
      KOC256
      KOC256 --- ---
      KOC256:
      jo to spojení je o tom, že to co vrchní kód "vrací" jako "result", spodní kód jako "result" očekává... :-)
      KOC256
      KOC256 --- ---
      Já jsem pořád ztracený v té asynchronitě...

      Mám dva funkční kusy kodů a nejsem schopen je spojit...
      Jedná se o vyplnění místa kde níže je napsáno "// X řádků kódu"

      Kód 1 - má za úkol stáhnout XML z webu a naparsovat ho do JSON.
      
      	http.get('http://www.nejaky-web.net/xml/file.xml', function(res) {
      		var response_data = '';
      		res.setEncoding('utf8');
      		res.on('data', function(chunk) {
      			response_data += chunk;
      		});
      		res.on('end', function() {
      			parser.parseString(response_data, function(err, result) {
      				if (err) {
      					console.log('Got error: ' + err.message);
      				} else {
      					console.log('Loading XML done.');
      				}
      			});
      		});
      		res.on('error', function(err) {
      			console.log('Got error: ' + err.message);
      		});
      	});
      


      Pak mám druhý kód, který vychází co mám v těch prvních 300 řádcích a taky mi funguje...:
      
      	puppeteer.launch({
      		headless: true
      		, userDataDir: '/var/www/node/data/'
      		, ignoreHTTPSErrors: true
      		, args: [
      			  '--no-sandbox'
      			, '--disable-setuid-sandbox'
      			, '--enable-file-cookies'
      		]})
      	.then(async browser => {
      		const page = await browser.newPage();
      
      		// set timeout
      		await page.setDefaultNavigationTimeout(10000);
      
      		Object.keys(result.GP.c).forEach(function(k) {
      			res.write('<b>' + result.GP.c[k].p[0].$.title + '</b><br/>');
      			Object.keys(result.GP.c[k].code).forEach(function(kk) {
      				res.write(result.GP.c[k].code[kk]);
      				try {
      					await page.goto('https://www.neco.com/' + result.GP.c[k].code[kk], {waitUntil: 'networkidle2'});
      
      					if (await page.$('#CBody_dMessage') != null) {
      						res.write(' => <span style="color:orange;font-weight:bold;">D</span><br/>');
      					} else if (await page.$('#CB_aMessage') != null) {
      						res.write(' => <span style="color:red;font-weight:bold;">A</span><br/>');
      					} else {
      						res.write(' => <span style="color:green;font-weight:bold;">OK</span><br/>');
      					}
      				} catch (error) {
      					console.log('ERROR');
      					res.write('<br/><br/>ERROR<br/>');
      					res.end();
      				}
      			});
      		});
      		res.end();
      		
      		await page.close();
      		await browser.close();
      	});
      


      Zkousel jsem dane kusy kodu do sebe ruzne napasovavat ale jak z prava, tak z leva se vzdy dostanu do stavu, kde mi to hlasi:

      SyntaxError: await is only valid in async function


      Dokázal by mi někdo jednoduše vysvětlit jak tyto kusy kódu spojit? Nechce se mi dělat prasárnu, kde jedním voláním provedu download a uložení a druhým načtení tohoto souboru a provedení druhého kusu kódu. TO přece musí jít. Dokonce jsem první kus kódu se snažil přepsat do puppeteeru či třeba R2, ale prostě vždycky to na něčem zhavarovalo.

      Díky...
      THEODORT
      THEODORT --- ---
      KOC256: ano, trivialni router kterej smeruje na dane casti kodu.
      KOC256
      KOC256 --- ---
      Mám jednoúčelovou aplikaci, která má následující kostru...
      
      var express = require('express');
      var app     = express();
      const puppeteer = require('puppeteer');
      require('events').EventEmitter.prototype._maxListeners = 100;
      
      let settings = require('./settings.json');
      
      app.get('/', function(req, res) {
      // 300 řádků kódu
      })
      
      var server = app.listen('80')
      exports = module.exports = server;
      


      A potřebuji přidat ještě druhou jednoúčelnou apliaci...
      Předpokládám, že primitivní řešení je udělat něco jako:
      
      var express = require('express');
      var app     = express();
      const puppeteer = require('puppeteer');
      require('events').EventEmitter.prototype._maxListeners = 100;
      
      let settings = require('./settings.json');
      
      app.get('/', function(req, res) {
      // 300 řádků kódu
      })
      
      app.get('/druha-aplikace/', function(req, res) {
      // X řádků kódu
      })
      
      var server = app.listen('80')
      exports = module.exports = server;
      


      Volání pak:
      http://domena.tld/
      a
      http://domena.tld/druha-aplikace/

      A dotaz je, jaká je praxe, jak toto dělat správně, ale pořád jednoduše? Mít tam nějaké funkce, které budou v requirovaných souborech? /plně se nechci pouštět do nějakých frameworků a řešit tam routery a další aplikační vrstvy...
      FEDY
      FEDY --- ---
      JUNIOR: proste to pripis do toho objektu - {msg:'Email has been sent', layout: false} pokud to chapu spravne tedy ...
      JUNIOR
      JUNIOR --- ---
      Ahoj,
      poprvé řeším něco na backendu a tak nějak se rozkoukávám.

      Prosím, dělám si v node.js emailový formulář a v jednom řádku mám:

      app.get('/', (req, res) => {
      res.render('contact', {layout: false});
      });


      a dále mám:
      res.render('contact', {msg:'Email has been sent'})

      a potřebuji tam dostat {layout: false}


      Jak to mám prosím zapsat aby to fungovalo a neházelo mi to errory?

      Díky
      ELPASO
      ELPASO --- ---
      FEDY: Jsem absolutni rookie. Takze me nenapadlo debug node prehodit na celej msg. Sice tam neni nazev source nodu ale je tam ID zigbee senzoru ze ktereho tecou data.

      Diky. Stacilo nakopnout :)
      FEDY
      FEDY --- ---
      ELPASO: ja na to uz dlouho nesahal, ale nemuzes si udelat console.log celeho msg objektu ? pokud tam neco takoveho nejni, tak by nemel byt problem si to na tom zdrojovem zarizeni do objektu pridat, ne ?
      ELPASO
      ELPASO --- ---
      nazdar,

      pouzivate tu nekdo NodeRed? Potreboval bych vedet jestli lze z nejake promene vycitat nazev NODE ze ktereho prichazi msg.payload? na zaklade nazvu zdroje modifikuju odchozi zpravu a chtel bych to automatizovat abych nemusel manualne definovat promenou v kazde funkci pripojene na zdrojovej NODE.

      thx
      TREE
      TREE --- ---
      Poucny a zaroven docela desivy video o tom jak se dnes pasuje zavadnej kod do npm package, jak je to relativne snadny a jak se proti tomu da tezko branit.. Doporucuju!
      Analysis of an exploited npm package – Jarrod Overson
      https://www.youtube.com/watch?v=cvtt8TexqbU
      ROMANICAK
      ROMANICAK --- ---
      Ahoj, pomohl by mi prosim nekdo, kdo tohle uz treba nekdy resil?

      angularjs - How to properly embed MJPEG video in Angular app - Chrome, Edge, other browsers - Stack Overflow
      https://stackoverflow.com/...ly-embed-mjpeg-video-in-angular-app-chrome-edge-other-browsers/52695879
      ROMANICAK
      ROMANICAK --- ---
      ROMANICAK:

      Nikdo tu neni, kdo by vedel jak udelat co potrebuju?

      Co se mi k tomu podarilo najit, nevim jak moc je to relevantni:

      73395 - MJPEG image can't stop loading - chromium - Monorail
      73395 - MJPEG image can't stop loading - chromium - Monorail
      https://bugs.chromium.org/p/chromium/issues/detail?id=73395
      https://gist.github.com/legege/5301477
      GitHub - videogular/videogular: The HTML5 video player for AngularJS
      GitHub - videogular/videogular: The HTML5 video player for AngularJS
      https://github.com/videogular/videogular
      Kliknutím sem můžete změnit nastavení reklam