portaldacalheta.pt
  • Основен
  • Инженерно Управление
  • Мобилен Дизайн
  • Разпределени Екипи
  • Пъргав
Back-End

Кодиране на треска в кабината: Урок за Node.js отзад



Заключването на COVID-19 задържа много от нас у дома, може би с надеждата, че обикновената треска в кабината е най-лошият вид треска, която ще изпитаме. Много от нас консумират повече видео съдържание от всякога. Въпреки че упражненията са особено важни в момента, понякога има носталгия по лукса на доброто, старомодно дистанционно управление, когато лаптопът е извън обсега.

Ето къде се появява този проект: Възможността да трансформирате всеки смартфон - дори стар, който иначе е безполезен поради липса на актуализации - в удобно дистанционно за следващия Netflix / YouTube / Amazon Prime Video / и т.н. binge-watch. Това е и Node.js back-end tutorial: шанс да научите основите на back-end JavaScript, използвайки Express рамката и механизма за шаблони Pug (бивш Jade).



Ако това звучи обезсърчително, пълното Node.js проектът ще бъде представен в края; читателите трябва да научат само толкова, колкото се интересуват от тях, и ще има доста по-нежни обяснения на някои основи по пътя, които по-опитните читатели могат да пропуснат.



Защо не просто ...?

Читателите може да се чудят: „Защо да се занимавам с кодиране на заден край на Node.js?“ (Освен възможността за обучение, разбира се.) „Няма ли вече приложение за това?“



Разбира се - много от тях. Но има две основни причини това да не е желателно:

  1. За тези, които се опитват да преназначат по-стар телефон, това може просто вече не е опция , какъвто е случаят с устройството с Windows Phone 8.1, което исках да използвам. (Магазинът за приложения беше официално затворен в края на 2019 г.)
  2. Доверието (или липсата му). Подобно на толкова много приложения, които могат да бъдат намерени на която и да е мобилна платформа, те често идват с изискването потребителите да предоставят много повече разрешения, отколкото е необходимо на приложението за това, което предвижда да направи. Но дори ако този аспект е подходящо ограничен, естеството на приложението за дистанционно управление означава, че потребителите все още трябва да се доверят, че разработчиците на приложения не злоупотребяват с привилегиите си на работния плот на решението, като включват шпионски софтуер или друг злонамерен софтуер.

Тези проблеми съществуват отдавна и дори са мотивация за подобен проект от 2014 г., намерен в GitHub. nvm улеснява инсталирането на по-стари версии на Node.js и дори ако няколко зависимости се нуждаят от надстройка, Node.js имаше страхотна репутация, че е съвместим назад.



За съжаление, bitrot спечели. Упоритият подход и фоновата съвместимост на Node.js не са подходящи за безкрайни оттегляния и невъзможни цикли на зависимост сред старите версии на Grunt, Bower и десетки други компоненти. Часове по-късно не беше ясно, че ще бъде много по-лесно да започнем от нулата - собственият съвет на този автор срещу преоткриване на колелото независимо от това.

Нови Gizmos от старо: Пренасочване на телефони като дистанционни управления, използващи Node.js Back End

Първо, обърнете внимание, че този проект Node.js в момента е специфичен за Linux - разработен и тестван по-специално за Linux Mint 19 и Linux Mint 19.3, но със сигурност може да се добави поддръжка за други платформи. То може вече работят на Mac.



Ако приемем модерна версия на Node.js е инсталиран и е отворен команден ред в нова директория, която ще служи като корен на проекта, готови сме да започнем с Express:

npx express-generator --view=pug

Забележка: Тук, npx е удобен инструмент, който се доставя с npm, мениджъра на пакети Node.js, който се доставя с Node.js. Използваме го, за да стартираме скелетния генератор на приложението на Express. Към момента на писане, генераторът прави проект Express / Node.js, който по подразбиране все още дърпа шаблонния механизъм, наречен Jade, въпреки че Jade проект се преименува на „Pug“ от версия 2.0 нататък. За да бъдем актуални и да използваме Pug веднага - плюс, избягвайте предупрежденията за оттегляне - ние се придържаме към --view=pug, опция в командния ред за express-generator скрипт, който се изпълнява от npx.



След като приключим, трябва да инсталираме някои пакети от новопопълнения списък със зависимости на нашия проект Node.js в package.json Традиционният начин да направите това е да стартирате npm i (i за „инсталиране“). Но някои все още предпочитат скоростта на Прежда , така че ако сте инсталирали това, просто стартирайте yarn без параметри.

В този случай трябва да е безопасно да игнорирате (надявам се скоро да бъде поправен) предупреждение за оттегляне от една от подзависимостите на Pug, стига достъпът да се запазва до необходимата база в локалната мрежа.



Бързо yarn start или npm start, последвано от навигиране до localhost:3000 в браузър, показва, че нашият основен експресен Node.js back end работи. Можем да го убием с Ctrl+C.

Node.js Back-end Tutorial, Стъпка 2: Как да изпращате натискания на клавиши на хост машината

С дистанционно част от половината вече направено, нека насочим вниманието си към контрол част. Имаме нужда от нещо, което може програмно да управлява машината, на която ще стартираме нашия Node.js, като се преструваме, че натиска клавиши на клавиатурата.



За това ще инсталираме xdotool използвайки неговите официални инструкции . Бърз тест на примерната им команда в терминал:

xdotool search 'Mozilla Firefox' windowactivate --sync key --clearmodifiers ctrl+l

... трябва да направи точно това, което пише, ако приемем, че Mozilla Firefox е отворен по това време. Това е добре! Лесно е да накараме нашия проект Node.js да извика инструменти за команден ред като xdotool, както скоро ще видим.

Node.js Back-end Tutorial, Стъпка 3: Дизайн на характеристиките

Това може да не е вярно за всички, но лично аз намирам, че много съвременни физически дистанционни управления имат около пет пъти повече бутони, отколкото някога ще използвам. Така че за този проект разглеждаме оформление на цял екран с решетка три на три от хубави, големи, лесни за насочване бутони. От личните предпочитания зависи какви могат да бъдат тези девет бутона.

Оказва се, че клавишните комбинации дори за най-простите функции не са еднакви Нетфликс , Youtube , и Amazon Prime Video . Тези услуги също не работят с общи медийни клавиши, както е вероятно приложението на родния музикален плейър. Също така някои функции може да не са налични при всички услуги.

Така че това, което ще трябва да направим, е да дефинираме различно оформление на дистанционното управление за всяка услуга и да осигурим начин за превключване между тях.

Определяне на оформленията за дистанционно управление и съпоставянето им с клавишни комбинации

Нека вземем бърз прототип, работещ с шепа предварителни настройки. Ще ги поставим в common/preset_commands.js - „често срещани“, защото ще включим тези данни от повече от един файл:

module.exports = { // We could use ️ but some older phones (e.g., Android 5.1.1) won't show it, hence ️ instead 'Netflix': { commands: { '-': 'Escape', '+': 'f', '': 'Up', '⇤': 'XF86Back', '️': 'Return', '': 'Down', '': 'Left', '': 'Right', '': 'm', }, }, 'YouTube': { commands: { '⇤': 'shift+p', '⇥': 'shift+n', '': 'Up', 'CC': 'c', '️': 'k', '': 'Down', '': 'j', '': 'l', '': 'm', }, }, 'Amazon Prime Video': { window_name_override: 'Prime Video', commands: { '⇤': 'Escape', '+': 'f', '': 'Up', 'CC': 'c', '️': 'space', '': 'Down', '': 'Left', '': 'Right', '': 'm', }, }, 'Generic / Music Player': { window_name_override: '', commands: { '⇤': 'XF86AudioPrev', '⇥': 'XF86AudioNext', '': 'XF86AudioRaiseVolume', '': 'r', '️': 'XF86AudioPlay', '': 'XF86AudioLowerVolume', '': 'Left', '': 'Right', '': 'XF86AudioMute', }, }, };

Стойностите на ключовия код могат да бъдат намерен с помощта на xev . (За мен тези „аудио без звук“ и „аудио възпроизвеждане“ не бяха открити по този метод, така че аз също се консултирах списък с медийни ключове .)

Читателите могат да забележат разликата в случая между space и Return - независимо от причината за това, тази подробност трябва да бъде уважена за xdotool да работи коректно. Във връзка с това имаме няколко дефиниции, написани изрично - напр. shift+p въпреки че P също ще работи - само за да бъдат ясни намеренията ни.

Node.js Back-end Tutorial, Стъпка 4: Крайна точка на „API“ на нашия API (извинете играта на думи)

Ще ни трябва крайна точка до POST до, което от своя страна ще симулира натискания на клавиши, използвайки xdotool. Тъй като ще имаме различни групи ключове, които можем да изпратим (по един за всяка услуга), ще извикаме крайната точка за конкретен group Ще преназначим генерираното users крайна точка чрез преименуване routes/users.js до routes/group.js и извършване на съответните промени в app.js:

// ... var indexRouter = require('./routes/index'); var groupRouter = require('./routes/group'); // ... app.use('/', indexRouter); app.use('/group', groupRouter); // ...

The ключ функционалността използва xdotool чрез извикване на системна обвивка в routes/group.js. Ще кодираме твърдо YouTube като избрано меню за момента, само за целите на тестването.

const express = require('express'); const router = express.Router(); const debug = require('debug')('app'); const cp = require('child_process'); const preset_commands = require('../common/preset_commands'); /* POST keystroke to simulate */ router.post('/', function(req, res, next) { const keystroke_name = req.body.keystroke_name; const keystroke_code = preset_commands['YouTube'].commands[keystroke_name]; const final_command = `xdotool search 'YouTube' windowactivate --sync key --clearmodifiers ${keystroke_code}`; debug(`Executing ${final_command}`); cp.exec(final_command, (err, stdout, stderr) => { debug(`Executed ${keystroke_name}`); return res.redirect(req.originalUrl); }); }); module.exports = router;

Тук хващаме искания ключ „name“ от POST тяло на заявката (req.body) под параметъра, наречен keystroke_name. Това ще бъде нещо като ️. След това използваме това, за да търсим съответния код от preset_commands['YouTube'] s commands обект.

Последната команда е на повече от един ред, така че s в края на всеки ред обединява всички парчета в една команда:

  • search 'YouTube' извлича първия прозорец с „YouTube“ в заглавието.
  • windowactivate --sync активира извлечения прозорец и изчаква, докато е готов да получи натискане на клавиш.
  • key --clearmodifiers ${keystroke_code} изпраща натискане на клавиш, като се увери, че временно изчиства модификаторните клавиши като Caps Lock, които могат да попречат на това, което изпращаме

На този етап кодът приема, че го подаваме на валиден вход - нещо, за което ще бъдем по-внимателни по-късно.

За улеснение, кодът също така ще приеме, че има само един отворен прозорец на приложението със заглавие „YouTube“ - ако има повече от едно съвпадение, няма гаранция, че ще изпратим натискания на клавиши до предвидения прозорец. Ако това е проблем, може да помогне заглавията на прозорците да могат да се променят просто чрез превключване на разделите на браузъра във всички прозорци, освен този, за да се управлява от разстояние.

С това готово можем да стартираме нашия сървър отново, но този път с разрешено отстраняване на грешки, за да можем да видим изхода на нашите debug обаждания. За да направите това, просто стартирайте DEBUG=old-fashioned-remote:* yarn start или DEBUG=old-fashioned-remote:* npm start. След като стартира, пуснете видеоклип в YouTube, отворете друг прозорец на терминала и опитайте cURL повикване:

curl --data 'keystroke_name=️' http://localhost:3000/group

Това изпраща POST заявка с исканото име на натискане на клавиш в тялото към нашата локална машина на порт 3000, портът, който нашият заден край слуша. Изпълнението на тази команда трябва да изведе бележки за Executing и Executed в npm прозореца и по-важното е да изведете браузъра и да поставите видеото му на пауза. Повторното изпълнение на тази команда трябва да даде същия изход и да го постави на пауза.

Node.js Back-end Tutorial, Стъпка 5: Множество оформления за дистанционно управление

Задният ни край не е съвсем свършен. Ще ни е необходим и за да можем:

  1. Съставете списък с оформления на дистанционно управление от preset_commands.
  2. Съставете списък с „имена“ на натискане на клавиш, след като сме избрали конкретно оформление на дистанционното управление. (Можехме също така да изберем да използваме common/preset_commands.js директно на предния край, тъй като това вече е JavaScript и е филтрирано там. Това е едно от потенциалните предимства на Node.js back end, просто не го използваме тук .)

И двете тези функции са мястото, където нашият урок на Node.js се пресича с предния край, базиран на Pug, който ще изградим.

Използване на Pug Templating за представяне на списък с дистанционни управления

Задната част на уравнението означава модифициране routes/index.js да изглежда така:

const express = require('express'); const router = express.Router(); const preset_commands = require('../common/preset_commands'); /* GET home page. */ router.get('/', function(req, res, next) { const group_names = Object.keys(preset_commands); res.render('index', { title: 'Which Remote?', group_names, portrait_css: `.group_bar { height: calc(100%/${Math.min(4, group_names.length)}); line-height: calc(100vh/${Math.min(4, group_names.length)}); }`, landscape_css: `.group_bar { height: calc(100%/${Math.min(2, group_names.length)}); line-height: calc(100vh/${Math.min(2, group_names.length)}); }`, }); }); module.exports = router;

Тук хващаме имената на оформлението на дистанционното управление (group_names), като извикваме Object.keys на нашия preset_commands файл. След това ги изпращаме и някои други данни, които ще са ни необходими, на механизма за шаблони на Pug, който автоматично се извиква чрез res.render()

Внимавайте да не объркате значението на keys тук с ключа удари изпращаме: Object.keys ни дава масив (подреден списък), съдържащ всички ключове от двойки ключ-стойност които съставляват обект в JavaScript:

const my_object = { 'a key': 'its corresponding value', 'another key': 'its separate corresponding value', };

Ако погледнем common/preset_commands.js, ще видим горния модел и нашия ключове (в обектния смисъл) са имената на нашите групи: 'Netflix', 'YouTube' и др. Съответните им стойности не са прости низове като my_object има по-горе - те самите са цели обекти със собствени ключове, т.е. commands и евентуално window_name_override.

Персонализираният CSS, който се предава тук, е, разбира се, малко хак. Причината, поради която изобщо се нуждаем, вместо да използваме модерно решение, базирано на flexbox, е по-добра съвместимост с прекрасния свят на мобилните браузъри в техните още по-прекрасни по-стари въплъщения. В този случай основното нещо, което трябва да се отбележи, е, че в хоризонтален режим ние държим бутоните големи, като показваме не повече от две опции на екран; в портретен режим, четири.

Но къде всъщност това се превръща в HTML за изпращане в браузъра? Ето къде views/index.pug влиза, което ще искаме да изглежда така:

extends layout block header_injection style(media='(orientation: portrait)') #{portrait_css} style(media='(orientation: landscape)') #{landscape_css} block content each group_name in group_names span(class='group_bar') a(href='/group/?group_name=' + group_name) #{group_name}

Първият ред е важен: extends layout означава, че Pug ще взема този файл в контекста на views/layout.pug, което е нещо като родителски шаблон, който ще използваме отново тук, а също и в друг изглед. Ще трябва да добавим няколко реда след link ред, така че крайният файл да изглежда така:

doctype html html head title= title link(rel='stylesheet', href='/stylesheets/style.css') block header_injection meta(name='viewport', content='user-scalable=no') body block content

Тук няма да навлизаме в основите на HTML, но за непознати с тях читатели този код на Pug отразява HTML кода със стандартни тарифи, който се намира почти навсякъде. The шаблониране аспектът му започва с title= title, което задава HTML заглавието на каквато и да е стойност, съответстваща на title ключ на обекта, който предаваме Pug през res.render.

Можем да видим различен аспект на шаблонирането на два реда по-късно с block ние назоваваме header_injection. Блокове като тези са заместители, които могат да бъдат заменени от шаблони, които разширяват текущия. (Без връзка, линията meta е просто бързо решение за мобилните браузъри, така че когато потребителите докосват контрола на силата на звука няколко пъти подред, телефонът се въздържа от увеличаване или намаляване.)

Обратно към нашите block s: Ето защо views/index.pug определя свои собствени block и със същите имена, намерени в views/layout.pug. В случая на header_injection, това ни позволява да използваме CSS, специфичен за портретни или пейзажни ориентации, в които ще бъде телефонът.

content е мястото, където поставяме основната видима част от уеб страницата, която в този случай:

  1. Цикли през group_names масив го предаваме,
  2. създава елемент за всеки с CSS клас group_bar приложени към него, и
  3. създава връзка във всеки въз основа на group_name.

Класът CSS group_bar можем да дефинираме във файла, изтеглен чрез views/layout.pug, а именно public/stylesheets/style.css:

html, body, form { padding: 0; margin: 0; height: 100%; font: 14px 'Lucida Grande', Helvetica, Arial, sans-serif; } .group_bar, .group_bar a, .remote_button { box-sizing: border-box; border: 1px solid white; color: greenyellow; background-color: black; } .group_bar { width: 100%; font-size: 6vh; text-align: center; display: inline-block; } .group_bar a { text-decoration: none; display: block; }

В този момент, ако npm start все още работи, ще отиде на http://localhost:3000/ в настолен браузър трябва да се показват два много големи бутона за Netflix и YouTube, а останалите са достъпни чрез превъртане надолу.

Тест на селектора за оформление на дистанционното управление с помощта на настолен браузър, показващ два много големи бутона за Netflix и YouTube.

Но ако щракнем върху тях в този момент, те няма да работят, защото все още не сме дефинирали маршрута, към който се свързват (GET оттенъкът на /group.)

Показване на избраното оформление на дистанционното управление

За целта ще добавим това към routes/group.js малко преди финала module.exports линия:

router.get('/', function(req, res, next) { const group_name = req.query.group_name || ''; const group = preset_commands[group_name]; return res.render('group', { keystroke_names: Object.keys(group.commands), group_name, title: `${group_name.match(/([A-Z])/g).join('')}-Remote` }); });

Това ще получи името на групата, изпратено до крайната точка (например, като поставите ?group_name=Netflix в края на /group/), и използвайте това, за да получите стойността на commands от съответната група. Тази стойност (group.commands) е обект и ключовете на този обект са имената (keystroke_names), които ще покажем в оформлението на дистанционното ни управление.

Забележка: Неопитните разработчици няма да се нуждаят от подробности за това как работи, но стойността за title използва малко от регулярни изрази за да превърнем имената на нашите групи / оформления в съкращения - например дистанционното ни управление в YouTube ще има заглавието на браузъра YT-Remote По този начин, ако отстраняваме грешки на нашата хост машина, преди да изпробваме нещата по телефона, няма да имаме xdotool хващаме самия прозорец на браузъра за дистанционно управление, вместо този, който се опитваме да контролираме. Междувременно на нашите телефони заглавието ще бъде хубаво и кратко, ако искаме да маркираме дистанционното управление.

Както при предишната ни среща с res.render, и тази изпраща данните си, за да се смеси с шаблона views/group.pug Ще създадем този файл и ще го запълним с това:

extends layout block header_injection script(type='text/javascript', src='/javascript/group-client.js') block content form(action='/group?group_name=' + group_name, method='post') each keystroke_name in keystroke_names input(type='submit', name='keystroke_name', value=keystroke_name, class='remote_button')

Както при views/index.pug, ние заместваме двата блога от views/layout.pug. Този път не залагаме CSS в заглавката, а някои JavaScript от страна на клиента, до които ще стигнем скоро. (И да, в момент на разсъдливост преименувах неправилно плурализираните javascripts ...)

Основното content ето HTML форма, направена от куп различни бутони за изпращане, по един за всеки keystroke_name. Всеки бутон изпраща формуляра (като прави заявка POST), използвайки името на натискането на клавиш, което показва като стойността, която изпраща с формуляра.

Ще ни е необходим и малко повече CSS в основния ни файл със стилове:

.remote_button { float: left; width: calc(100%/3); height: calc(100%/3); font-size: 12vh; }

По-рано, когато настроихме крайната точка, завършихме обработката на заявката с:

return res.redirect(req.originalUrl);

Това на практика означава, че когато браузърът изпрати формуляра, задната част на Node.js реагира, като казва на браузъра да се върне към страницата, от която е изпратен формулярът, т.е. основното оформление на дистанционното управление. Би било по-елегантно, без да превключвате страници; ние обаче искаме максимална съвместимост със странния и прекрасен свят на отпадналите мобилни браузъри. По този начин, дори без изобщо да работи JavaScript от предния край, нашият фонов проект Node.js Трябва все още функционира.

Тире на Front-end JavaScript

Недостатъкът на използването на формуляр за подаване на натискания на клавиши е, че браузърът трябва да изчака и след това да изпълни допълнително двупосочно пътуване: Страницата и нейните зависимости трябва да бъдат поискани от нашия Node.js back end и доставени. След това те трябва да бъдат изобразени отново от браузъра.

Читателите може да се чудят какъв ефект може да има това. В края на краищата страницата е малка, зависимостите й са изключително минимални и окончателният ни проект Node.js ще работи по локална wifi връзка. Трябва да е настройка с ниска латентност, нали?

Както се оказва - поне при тестване на по-стари смартфони с Windows Phone 8.1 и Android 4.4.2 - ефектът за съжаление е доста забележим в често срещания случай на бързо докосване за увеличаване или намаляване на силата на звука на възпроизвеждането с няколко стъпала. Ето къде JavaScript може да помогне, без да отнема от елегантния ни резервен вариант на ръчни POST чрез HTML формуляри.

На този етап, нашият окончателен клиентски JavaScript (който трябва да бъде въведен public/javascript/group-client.js) трябва да е съвместим със стари, вече не поддържани мобилни браузъри. Но ние не се нуждаем от много от него:

(function () { function form_submit(event) { var request = new XMLHttpRequest(); request.open('POST', window.location.pathname + window.location.search, true); request.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded'); request.send('keystroke_name=' + encodeURIComponent(event.target.value)); event.preventDefault(); } window.addEventListener('DOMContentLoaded', function() { var inputs = document.querySelectorAll('input'); for (var i = 0; i

Тук, form_submit функцията просто изпраща данните чрез асинхронно повикване, а последният ред предотвратява нормалното поведение на изпращане на браузърите, при което се зарежда нова страница въз основа на отговора на сървъра. Втората половина на този фрагмент просто изчаква, докато страницата се зареди, и след това закача всеки бутон за изпращане, за да използва form_submit Цялото нещо е увито IIFE .

Финални щрихи

Има редица промени към горните фрагменти във финалната версия на нашия урок на кода на Node.js, най-вече за целите на по-доброто обработване на грешки:

  • Задният край на Node.js сега проверява имената на групите и натисканията на клавиши, изпратени до него, за да се увери, че съществуват. Този код е във функция, която се използва повторно и за GET и POST функции на routes/group.js.
  • Използваме Pug error шаблон, ако не го направят.
  • Предната част на JavaScript и CSS сега правят бутоните временно очертани в сиво, докато чакат отговор от сървъра, зелено веднага щом сигналът премине докрай xdotool и обратно без проблеми и червено, ако нещо не работи както се очаква.
  • Задният край на Node.js ще отпечата проследяване на стека, ако умре, което ще бъде по-малко вероятно предвид горното.

Читателите са добре дошли да разгледат (и / или клонират) цялостния проект Node.js на GitHub .

Node.js Back-end Tutorial, Стъпка 5: Тест от реалния свят

Време е да го изпробвате на действителен телефон, свързан към същата wifi мрежа като хоста, който работи npm start и филм или музикален плейър. Въпросът е само да насочите уеб браузъра на смартфона към локалния IP адрес на хоста (с :3000 суфикс към него), което може би е най-лесно да се намери, като стартирате hostname -I | awk '{print }' в терминал на хоста.

Един от проблемите, които потребителите на Windows Phone 8.1 могат да забележат, е опитът да се придвижат до нещо като 192.168.2.5:3000 ще даде изскачащо съобщение за грешка:

Екранна снимка на съобщение за грешка в Windows Phone със заглавие

За щастие няма нужда да се обезсърчавате: Просто добавете префикс с http:// или добавяне на последващ / получава го, за да извлече адреса без допълнителни оплаквания.

Екранът за избор на оформление на дистанционното управление.

Избирането на опция там трябва да ни отведе до работещо дистанционно управление.

The

За допълнително удобство потребителите може да поискат да коригират DHCP настройките на своя рутер, за да присвояват винаги един и същ IP адрес на хоста, и да маркират екрана за избор на оформление и / или всякакви любими оформления.

Искания за изтегляне Добре дошли

Вероятно не всеки ще хареса този проект точно такъв, какъвто е. Ето няколко идеи за подобрения за тези, които искат да се задълбочат по-нататък в кода:

emacs срещу notepad++
  • Трябва да е лесно да променяте оформленията или да добавяте нови за други услуги, като Disney Plus.
  • Може би някои биха предпочели оформлението в „лек режим“ и опцията за превключване между тях.
  • Резервирането от Netflix, тъй като е необратимо, наистина може да използва „сигурен ли си?“ някакво потвърждение.
  • Проектът със сигурност ще се възползва Windows поддържа.
  • xdotool В документацията се споменава OSX - работи ли този (или би могъл ли) проект на съвременен Mac?
  • За разширено излежаване, начин за търсене и разглеждане на филми, вместо да се налага да избирате един филм на Netflix / Amazon Prime Video или да създавате плейлист в YouTube на компютъра.
  • Автоматизиран тестов пакет, в случай че някоя от предложените промени наруши първоначалната функционалност.

Надявам се да ви е харесал този урок на Node.js отзад и подобрен медиен опит като резултат. Приятно стрийминг - и кодиране!

Свързани: Изграждане на Node.js / TypeScript REST API, Част 1: Express.js

Разбиране на основите

Node.js за задния край ли е?

Да. Node.js е програма от командния ред, която изпълнява JavaScript код и обикновено се използва на уеб хост за обслужване на уеб страници, свързване с бази данни и т.н.

Достатъчен ли е Node.js за заден край?

Абсолютно. Правилно проектиран, задната част на Node.js може да се мащабира както и всяка технология. Въпреки това често се интегрира с други важни компоненти, като достъп до слоя от база данни на приложението.

Какво е Express.js?

Express е модул за Node.js, който намалява количеството на шаблонния код, необходим за писане на обща функционалност на уеб сървъра. Има собствена зряла под-екосистема. Повечето уеб сървъри на Node.js използват Express.

Какво е Pug / Jade?

Pug (по-рано Jade) е шаблонна машина, която се интегрира с Express. Всъщност от години това е механизмът на шаблоните по подразбиране, който генераторът на проекти Express включва в нови проекти.

Какво е xdotool?

Програмата за команден ред xdotool симулира натискания на клавиши на компютъра, на който работи. Този проект позволява на телефона да извършва подобни действия на компютър чрез уеб страница, превръщайки го в дистанционно управление.

Как да създадете персонализирани шрифтове: 7 стъпки и 3 казуса

Инструменти И Уроци

Как да създадете персонализирани шрифтове: 7 стъпки и 3 казуса
ARM сървъри: Архитектура на мобилния процесор за центрове за данни?

ARM сървъри: Архитектура на мобилния процесор за центрове за данни?

Back-End

Популярни Публикации
Плащане напред: Разбиране на изкупувания с ливъридж
Плащане напред: Разбиране на изкупувания с ливъридж
Индустриален анализ и Porter’s Five Force: По-задълбочен поглед върху силата на купувача
Индустриален анализ и Porter’s Five Force: По-задълбочен поглед върху силата на купувача
Разширена реалност vs. Виртуална реалност vs. Смесена реалност: Уводно ръководство
Разширена реалност vs. Виртуална реалност vs. Смесена реалност: Уводно ръководство
Ще отвори ли Spotify не-IPO пътя за технологичните компании?
Ще отвори ли Spotify не-IPO пътя за технологичните компании?
Прогнозиране на харесвания: Вътре в алгоритмите на прост механизъм за препоръки
Прогнозиране на харесвания: Вътре в алгоритмите на прост механизъм за препоръки
 
Ефективни стартови платки: какви са те и как да ги изградим
Ефективни стартови платки: какви са те и как да ги изградим
Ръководител на клиентския опит
Ръководител на клиентския опит
Игла в купа сено: чудесен урок за мащабен текстов алгоритъм за търсене
Игла в купа сено: чудесен урок за мащабен текстов алгоритъм за търсене
Структурата на данните Trie: Пренебрегван скъпоценен камък
Структурата на данните Trie: Пренебрегван скъпоценен камък
Краят на уеб формите
Краят на уеб формите
Популярни Публикации
  • производителност на scala срещу java 8
  • сила на купувача петте сили на портиера
  • как да направите жетон
  • отваряне на xml файлове в word
  • кога да използвате рубин върху релси
  • какви са инструментите на командния ред
Категории
  • Инженерно Управление
  • Мобилен Дизайн
  • Разпределени Екипи
  • Пъргав
  • © 2022 | Всички Права Запазени

    portaldacalheta.pt