Все про JavaScript | Wannabe School
304 subscribers
35 photos
6 videos
35 links
Website: http://wannabe.school

Правила каналу: https://t.me/wannabe_community/1/45
Download Telegram
ofetch як головний HTTP клієнт

Всі ми багато разів використовували axios як головну бібліотеку для надсилання запитів. Його перша версія вийшла 9 років тому. Не дивлячись на його оновлення та зручний API, він застарів, бо під капотом використовується XHR.

Заміною XHR є вбудований в браузери fetch який має простий та зручний API, і стабільну підтримку починаючи з 2016 року.

Обидва HTTP клієнти спрощують надсилання запитів, але використовувати їх без додаткових налаштувань дуже незручно. Нам 100% будуть потрібні додаткові інтерсептори, аборт контроллери тощо.

npm світ не стоїть на місці і вже зараз ми можемо використовувати альтернативну бібліотеку ofetch. Вона побудована на основі fetch з додаванням звичних нам API.

ofetch був створений немало відомим ком'юніті unjs, які створили також nitro, consola, unplugin тощо.

Nuxt 3 вже використовує цей HTTP клієнт як основний. Тому рекомендуємо його і вам.

@wannabe_javascript
👍10🔥2👏1🤔1
Додаємо справжню реактивніть в React за допомогою signals

Фреймворк Preact у вересні минулого року анонсував signals, які мають більш чистий та зручний спосіб роботи зі станом. Майже так само як ref у Vue.

Сам React не вводив підтримку сигналів, але Preact створили бібліотеку під назвою @preact/signals-react за допомогою якої у нас з'являється можливість використовувати сигнали і прилеглі методи всередині реакту.

Можна виділити три головні переваги перед звичайними useState та useMemo:

1. Зміна стану через value.
Більше не треба деструктурувати масив з useState, ми можемо напряму змінювати та брати потрібне значення через .value.

2. useMemo useComputed не потребує залежностей.
Бібліотека сигналів аналізує все, що знаходиться всередині колбеку і автоматично апдейтить значення.

3. Немає зайвих перерендерів.
При використанні змінної сигнала або комп'ютед, ми можемо виводити значення, не додавая .value. Сигнал автоматично дістає значення і рендерить його в JSX. При цьому сам компонент не робить повний ререндер, як при використанні useState, а змінюється тільки значення з сигналу та його комп'ютедів.

На скріншоті використовуються хуки, але можна й інакше.

@wannabe_javascript
👍5🔥3👏1🤔1
new Map замість switch ... case

Map вже давно не новий синтаксис, але його до сих пір мало хто використовує в повній мірі. А WeakMap взагалі й досі залишається загадкою для багатьох розробників.

Найпростіший приклад використання new Map - це альтернатива конструкції switch ... case, яка не подобається багатьом девам через свою громіздкість.

У нас є одна змінна з різними розширеннями, в залежності від яких ми хочемо отримати contentType.

const extension = '.html';
let contentType;
switch (extension) {
case '.css':
contentType = 'text/css';
break;
default:
contentType = 'text/html';
}

Попередній код - це обробка тільки двох кейсів прикладу, який знаходиться на скріншоті, але при цьому займає стільки ж місця.

Окрім економії місця new Map може дати вам кращу типизацію в TypeScript. Використовуючи generic types, ви з легкістю можете описати, що саме є ключем та значенням.

type Extension = '.css' | '.js' | '.json';
new Map<Extension, string>([]);

Тому при написанні умов з однією змінною подумайте, чи можете ви замінити if ... else або switch ... case на new Map.

@wannabe_javascript
👍7🔥1
Якого CSS селектору не існує?
Anonymous Quiz
10%
is
0%
not
3%
has
33%
where
13%
&
40%
Всі існують
Vite (віт) – бандлер замінивший Webpack.

В сучасному JavaScript існує безліч бандлерів, але Vite заполонив майже весь простір. Він зароджувався як заміна vue-cli, але переріс до самостійної бібліотеки. І зараз разом з Vite можна використовувати купу фреймворків та створювати свої власні бібліотеки.

Чому Vite став такий популярний? Швидкість та простота. Vite з коробки може працювати з TypeScript, підіймати dev сервер і слідкувати за файлами.

Просто спробуйте ці команди, перед цим створивши файл index.html

npm i vite
npx vite

Важливим моментом є екосистема. Vite має безліч плагінів, які допоможуть налаштувати ваш проєкт більш точніше. Та не треба забувати про фреймворк для тестування Vitest, який також став неймовірно популярним через свою швидкість та багатофункціональність.

На даний момент головний конкурент для Vite - це Turbopack від компанії Vercel. Turbopack анонсувався з фразою "10x Faster than Vite", що не є повною правдою, але незважаючи на це, Vite ще довгий час буде головним бандлером, бо Turbopack тільки стає на ноги і використовувати його без Next.js ми не бачимо сенсу.

@wannabe_javascript
👍4🔥1
This media is not supported in your browser
VIEW IN TELEGRAM
GitHub Gists або як швидко комусь надіслати шматок коду?

Йшов 2023 рік. Розробники все ще не знали про сервіс під назвою GitHub Gists, який з'явився 15! років тому.

Часто трапляється, коли треба шкидко переслати код іншій людині. Зазвичай ви просто копіюєте його та кидаєте в месенджер, наприклад, той же Телеграм, де код виглядає максимально погано.

GitHub Gists дозволяє створити сторінку з фрагментами коду за лічені секунди і далі переслати її кому завгодно. При цьому створений гіст може бути як публічним, так і приватним.

Якщо вам потрібно переслати більше одного фрагмента коду (наприклад, CSS та JSX темплейти), Gists дозволяє водночас додавати декілька фрагментів до одного гіста.

Заходимо на Github Gists, логінемось (якщо раніше цього не зробили), вставляємо код і натискаємо на кнопку. Копіюємо URL адресу і надсилаємо потрібній людині, все.

Ви витратили на 2 секунди більше на створення такої сторінки, проте інша людина зекономила декілька хвилин на читанні та розумінні вашого коду.

@wannabe_javascript
🔥8👍2👏2
Писати full-stack додатки в одному фреймворці?

Зазвичай для фронтенду ви обираєте React, Vue, Angular або щось подібне. Для бекенду може бути Nest.js, Express, Koa, Fastify та інше.

А чому не робити фронт та бек на одному фреймворці? 🤔

Nuxt та Next вже давно мають можливість створювати власні API. Але й досі мало хто використовує їх серверну частину як справжній бекенд, обираючи інші фреймворки.

Чому так?

Не дивлячись на багато можливостей бекенду всередині Nuxt та Next, їх все ще може бути недостаньо для великих проєктів. До того ж деякі компанії бояться робити продукт на одному фреймворці, бо впаде він - впаде все.

Особисто для нас є ще один мінус - відсутність бібліотек для бекенду. Якщо взяти той же Nest.js, він дає з коробки все, що треба для бекенду: логи, корси, валідації тощо. Nuxt та Next же мають недостатньо функцій.

В яких випадках ми би рекомендували використовувати один фреймворк?

🧑‍💻Ви маленька компанія або фрілансер
Ви витратите набагато менше часу на написання цілого додатку, використовуючи лише один фреймворк.

💵 Фінансові обмеження
Обираючи тільки Nuxt чи Next, ви можете відмовитись від другого розробника, серверу та девопсу, до того ж створений додаток можна з легкістю самостійно задеплоїти на Vercel чи Netlify.

⚙️ Наявність бібліотеки
Якщо ви знайдете бібліотеку, яка вирішить всі проблеми з архітектурою, логами, плагінами тощо.

За таким підходом майбутнє, треба лише трішки почекати 🤫

@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
👍5🔥3👏1
This media is not supported in your browser
VIEW IN TELEGRAM
AI всюди, навіть в комітах?

Багато хто з вас вже користується плагіном під назвою GitHub Copilot, який в рази пришвидшує розробку за допомогою підказок ШІ при написанні коду. А також його молодшим братом GitHub Copilot Chat - аналогом ChatGPT, тільки для програмістів.

Можливо, комусь приглянувся Cursor - редактор з вбудованим AI на основі VS Code. Або ви віддаєте перевагу Tabnine, який додає той самий функціонал, що і Copilot, тільки по своєму.

AI всюди і далі його буде ставати тільки більше.

А зараз ми би хотіли розповісти про, здавалося би, дрібничку, яка насправді дуже спрощує найнеприємнішу частину при написанні коду - вигадування назв для комітів 😨

GitLens нещодавно додав генерацію комітів в експериментальному режимі.

Плюси тут очевидні: GitLens сканує змінені файли і генерує для них ім'я коміту 🤯

Також відзначили декілька мінусів:

якщо ви використовуєте Conventional Commits неймінг, то він не буде враховуватися при генерації;

бувають рідкі випадки, коли він не розуміє, що саме було змінено в файлах, і генерує звичайну назву на кшталт Refactor code.

Так, ця фіча досі експериментальна, проте вона вже доволі добре працює, і ми можемо сміливо рекомендувати її використовувати.

❗️Майте на увазі, що генератор використовує ChatGPT, тому ваші дані можуть потрапити в базу OpenAI.

На відео приклад її працездатності.

@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥4👍1👏1😱1
Яка база даних не є SQL базою?
Anonymous Quiz
10%
Oracle Database
35%
MariaDB
35%
IndexedDB
21%
IBM Db2
БЕМ - ворог, який став союзником.

БЕМ (Блок Елемент Модифікатор) - це методологія написання імен CSS класів, яка розповсюдилася на увесь світ. Наразі її використовують найбільші компанії світу.

Чому ворог? БЕМ був придуманий в компанії яндекс, офіс якої знаходиться в тій самій сусідній країні.

Чому
тоді ми розповідаємо про дану методологію? 🤯 Бо вона вже давно вийшла за рамки компанії яндекс і почала розвиватися самостійно.

❗️Ми наполегливо рекомендуємо використовувати дану методологію іменування класів у власних проєктах.


Як все ж таки іменувати? Розберемо приклад багатофункціональної кнопки та уявимо, що вона зелена .

<button class="button">✓</button>


Виглядає не складно, а тепер почнемо додавати функціонал: наприклад, кнопка матиме лоадер всередині себе.

<button class="button">

<div class="button__loader" />
</button>


До лоадеру додався клас button__loader з двома підкреслюваннями, і тим самим ми вказали, що loader є елементом button і не може бути використаним ніде, окрім самого button.

Уявимо, після цього ми вирішили, що кнопка може не бути зеленою, а тільки мати зелений border. І що тепер, копіювати? 😢 Ні, копіювання - це зло. Краще зробити наступним чином:

<button class="button button--outline">

<div class="button__loader" />
</button>


Ми додали клас button--outline, який є модифікатором. Таким чином у нас з'явилася структура:

• button - сам блок
• button--outline - модифікатор, який змінює тільки незначні стилі
• button__loader - елемент

В SCSS це можна описати так:

.button {
background: green;

&--outline {
background: none;
border: 1px solid green;
}

&__loader {
// якісь інші стилі
}
}


@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
👍12🔥4👏1
CSR, SSR, SSG. Який тип рендерингу обрати? 🤔

Сучасний фронтенд має безліч технологій для прискорення завантаження сторінок, але більшість з них має низьку ефективність. Розглянемо кардинально інший світ завантаження додатків.

📐

CSR, або Client Side Rendering, – це класичний метод рендерингу у більшості сучасних SPA-фреймворків, таких як React або Vue. Він працює дуже просто:

• браузер завантажує ваш скомпільований JS-код
• код інтерпретується браузером
• ваш JS вставляє HTML-елементи та CSS-стилі

Звучить зрозуміло і не вимагає використання сервера, але чому не всі використовують цей метод?


• поки браузер завантажує JS, юзер бачить лише білий екран
• страждає SEO
• при пересиланні у Telegram або інші соцмережі неможливо додати картинку та опис до сторінки
• все навантаження лягає на браузер

📐

Тому на допомогу прийшов SSR, або Server Side Rendering. Як він вирішує ці проблеми?

• перший рендер відбувається на сервері
• після рендеру сторінка передається браузеру
• відбувається гідрація (розповімо про це пізніше)
• користувач отримує сайт з мінімальним очікуванням

Але і у SSR є недоліки


• потрібен сервер для рендерингу
не такий простий у розумінні
• проєкт збільшується в розмірі

📐

А що як використовувати CSR та SSR одночасно? Тут на допомогу приходить SSG (Static Site Generation).

• сервер відсутній, але користувач одразу отримує готовий сайт
SEO та швидкість завантаження будуть на висоті

SSG також має свої недоліки


• будь-яке оновлення сайту потребує повної перезбірки
• проєкт не є динамічним, всі сторінки будуються заздалегідь, тому динамічні шляхи створити неможливо

Тож що і коли обрати?


💪 CSR – для динамічних сайтів, де не важлива SEO-оптимізація. Наприклад, адмін-панелі та проєкти, до яких пошукові системи не мають доступу.

💪 SSR – для проєктів, де важливі SEO-оптимізація та швидкість завантаження. Це можуть бути, наприклад, інтернет-магазини, де корисно отримувати контент швидше, ніж за допомогою CSR.

💪 SSG – ідеально підходить для документацій, блогів, лендінгів, оскільки вся інформація відома заздалегідь.

@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
👍7🔥3🤯1
Який зі сторів в React не перезаписує весь стейт при змінах?
Anonymous Quiz
23%
Redux
32%
Zustand
18%
MobX
12%
Context API
15%
Recoil
👍2🔥2👏1😭1
Expo - найпростіший спосіб створювати мобільні додатки📱

JavaScript - це неймовірно велика екосистема, на базі якої можна створювати безліч речей, в тому числі й мобільні додатки.

Найпопулярніший спосіб створення додатків - це react-native. Але він може здатися складним для початківців, бо потребує доволі багато налаштувань 😰

І це ідеальний випадок звернути увагу на Expo. Він є оболочкою до react-native та пропонує великий набір сервісів - від ліхтарика до пуш-повідомлень.

Створення мобільного додатку починається зі звичних React та JavaScript.

npx create-expo-app my-app


Майте на увазі, що дана команда встановлює мінімальний набір, навіть без TypeScript.

Тому для TS існує темплейт, який можна встановити за допомогою наступної команди:

npx create-expo-app -t expo-template-blank-typescript


Expo дає можливість одночасно писати додаток під iOS, Android та веб, використовуючи одну кодову базу.

Також Expo є сервісом, який допомагає робити білди та деплоїти проєкти в стори, такі як Google Play та App Store 💪

Тому для старту вашої мобільної розробки ми рекомендуємо придивитися саме до Expo 🔥

@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
2👍2🔥1👏1
Гідрація - як оживають сторінки після рендеру на сервері?

У пості про методи рендерингу ми згадували гідрацію в контексті SSR. Тож, що це таке? 🤔

Гідрація в SSR - це процес, в якому HTML, що був згенерований на сервері, оживає на клієнті завдяки JavaScript. Це дозволяє вашому додатку й надалі бути реактивним у браузері, не дивлячись на те, що браузер отримав тільки HTML.

Чому на клієнт потрапляє HTML, який не є реактивним?

У процесі рендерингу ваших компонентів на сервері неможливо передати всі обробники, змінні, функції та подібне на клієнт. Це теж саме, що намагатися передати JS код в GET запиті.

Але оскільки сучасні мета фреймворки, наприклад, Nuxt або Next, мають доступ як до сервера, так і до клієнта, вони можуть проаналізувати, що відрендерив сервер і оживити його тими самими компонентами, які рендерилися на сервері 😵‍💫.

Дуже спрощена версія гідрації:

// серверна частина
import { renderToString } from 'framework';

return renderToString(<MyApp />);


// клієнтська частина
import { hydrate } from 'framework';

hydrate(<MyApp />, document.getElementById('root'));


Якщо якимось чином компоненти на сервері та клієнті будуть відрізнятися, то ми отримаємо помилку гідрації, що відрендерений HTML не співпадає .

Іноді бувають випадки, коли HTML дійсно повинен відрізнятися. Для цього можна використовувати рендеринг компонентів тільки на якійсь з одних сторін.

Рекомендуємо ознайомитися з поняттям ClientOnly в Nuxt та з Server Components в Next.js, щоб більше зрозуміти, де та що саме вам може знадобитися.

@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
👍3🔥3👏1
Новий рік - новий Vue.

Ось і закінчився 2023 рік, а разом з ним - підтримка Vue 2.

24 грудня вийшла версія 2.7.16 Swan Song та 31 грудня Vue 2 офіційно перейшов в статус EOL (End of Life).

Тому всі, хто не встиг перейти на Vue 3, саме час почати міграцію 😉

Vue 2.0 вийшов 7 років тому і з тих пір подарував нам багато нових можливостей для створення додатків. А тепер давайте подивимося, що нам подарувала нова версія Vue:

Vite - один із найпопулярніших бандлерів для JavaScript. Має 4 мільйони скачувань на тиждень.

Vitest - зручний тул для тестування, який прийшов на заміну Jest. Має майже 1.5 мільйони скачувань на тиждень.

unjs - екосистема JavaScript, яка налічує понад 50 пакетів та має загалом майже 250 мільйонів скачувань на тиждень.

nitro - SSR фреймворк, на якому працює Nuxt.

Та ще купа корисного: UnoCSS, Vike, Volar, VitePress, unplugin тощо.

Vue, як один із головних фреймворків сучасного JavaScript, дає нам, розробникам, неймовірно велику екосистему, яка інтегрується з багатьма іншими фреймворками та бібліотеками.

Тому добра конкуренція з React, Angular, Svelte та іншими тільки вдосконалює наш з вами код.

Vue 2. F. 🫡

@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥7👍1👏1😢1
Слідкування за об'єктами та їх значеннями?

Ви коли-небудь задумувалися, як можна реагувати на якісь зміни в об'єктах? Наприклад, всередині форми на кожен інпут дані одразу зберігати в базі.

Звичайно, в першу чергу ви подумаєте про useEffect в React чи watch у Vue, але уявимо, що будь-який фреймворк для нас недоступний.

Який нативний спосіб в JavaScript існує для реагування на зміни?

Поганий варіант 👎

Повісити на кожен <input> новий addEventListener('input', () => {}) та всередині надсилати запит.

Проблема 🤔

Якщо ми повісимо debounce на кожен такий addEventListener, то на якомусь моменті деякі дані можуть загубитися, бо немає єдиного стейту даних.

Насправді проблем може бути багато, але debounce найкращий приклад.

Рішення 💡

Створити об'єкт та огорнути його в new Proxy, а кожен <input> просто буде зберігати дані в цьому об'єкті.

const obj = {};
const proxy = new Proxy(obj, {
set(obj, prop, newVal) {
// Записуємо дані
obj[prop] = newVal;

// Тут можемо надіслати запит на бекенд

// Кажемо, що все добре
return true;
},
});


input.addEventListener('input', ({ target }) => {
proxy.firstName = target.value;
});


console.log(obj);
// => { firstName: 'Valerii' }


Деякі фреймворки, як Vue 3, використовують Proxy, як головний спосіб реагування на зміни юзера.

Тому якщо якимось чином ви опинитеся без реактивного фреймворка, ви зможете написати банальну реактивність самі.

@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥5👍3👏2💯1
TypeScript для фізичних девайсів 📟

Екосистема JavaScript виходить за межі інтернету. Спочатку придумали TypeScript, який перевернув розробку на JS, а тепер ще й з'явився DeviceScript 😱

DeviceScript був створений компанією Microsoft на основі TypeScript. Назва говорить сама за себе: тепер ми можемо створювати нові додатки не тільки у браузерах, на серверах, десктопах чи мобільних, а ще й на фізичних пристроях.

Чи каже вам про щось назва Raspberry Pi? Якщо так, тоді ви вже розумієте, до чого йде діло. 😉 Raspberry Pi - це фізична плата, до якої можна під'єднувати різні речі, такі як:

- лампочки
- датчики температури
- датчики вітру
- вібромоторчики
- тощо


Список девайсів, як і драйверів, неймовірно великий. Тому ми наполегливо рекомендуємо ознайомитися із DeviceScript.

А якщо у вас немає часу або вам взагалі не цікава розробка на фізичних девайсах, тоді можете подивитися принаймні приклад зі створенням показу температури на дісплей 🤫

Ви тільки уявіть, знаючи лише один JavaScript, ми можемо стільки всього створювати, хіба це не чудово? 🤩

@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥4🤯3👍1👏1🤔1😱1
Як розширити вже існуючий глобальний інтерфейс в TypeScript?

1️⃣ Якщо в TypeScript ви спробуєте записати будь-яку змінну в глобальний об'єкт, то отримаєте помилку:

window.newVariable = 'Hello';
// Property 'newVariable' does not exist


2️⃣ Або нам треба розширити вже існуючий глобальний інтерфейс:

Array.prototype.filterMap = function (callback) {
return this
.map(callback)
.filter((value) => value);
};
// Property 'filterMap' does not exist


3️⃣ Чи якимось чином TS інтерфейс бібліотеки не має опису змінної:

import { userInfo } from 'lib';

userInfo.fullName
// Property 'fullName' does not exist


Для всіх цих кейсів існують способи розширення TypeScript інтерфейсів❗️

1️⃣ В першому прикладі нам допоможе розширення інтерфейсу Window, в нього ми можемо записувати будь-що:

declare global {
interface Window {
testVariable: string;
}
}


2️⃣ Другий приклад розширює існуючий клас Array, бо нам захотілося створити свій метод роботи з масивами:

declare global {
interface Array<T> {
filterMap(
callback: (
value: T,
index: number,
array: T[]
) => unknown): unknown[];
}
}


3️⃣ А якщо нам треба розширити інтерфейс бібліотеки, то код стає більш цікавішим, оскільки нам треба знайти оригінальний інтерфейс, імпортувати його ➡️ і тільки після цього ми зможемо розширяти. Без імпорту така схема працювати не буде:

import { UserInfo } from 'lib';

declare module 'lib' {
interface UserInfo {
fullName: string;
}
}


Глобальні розширення зазвичай створюють в файлах global.d.ts або declarations.d.ts 😉

@wannabe_javascript
Please open Telegram to view this post
VIEW IN TELEGRAM
👍3🔥2👏1🤔1