Як використовувати нову експериментальну функцію Profiler в React

Ось і вийшов React 16.4.0! І в такі моменти ви розумієте, наскільки ви JavaScript — гік, якщо слідкуйте за мінорними оновленнями свого улюбленого фреймворка. Відмінно!

Якщо ви читали нотатки про випуск версії 16.4, опубліковані командою React, повинно бути порахували це оновлення досить нудним. Pointer Events виглядають заманливо, але якщо чесно, до цього мало що про них чув.

Крім того, є багфикс для як-би нового методу getDerivedStateFromProps (тепер він буде викликатися при кожному рендері). Я ще недостатньо цим користувався, тому для мене це оновлення було дуже важливим.

Потім я побачив похований під заголовками анонс про те, що вони додали новий експериментальний компонент unstable_Profiler. Бачачи, що моє життя зараз досить нестійка(unstable_), я вирішив прочитати RFC і спробувати його.

TLDR;

Люди з команди React намагаються зробити рендеринг асинхронним. Це може ускладнити визначення часу відтворення компонентів при монтуванні/оновлення. Тому, вони вовтузяться з цим новим блискучим компонентом Profiler

Так що ви можете використовувати сьогодні?

Отже, якщо ви профі у відстеженні продуктивності своїх реактив-додатків, це, безперечно, стане ще одним хорошим інструментом у вашому арсеналі. Якщо це не про вас, можете далі не читати і повернутися до створення кльові додатків.

Використання <Profiler/>

Попередження: можливо вам не слід використовувати це у production (ну справді, це ж unstable_). Пізніше вони допилят можливість профілювати і production код.

В принципі, Profiler, це компонент, який можна вийняти з пакета React за замовчуванням. Оскільки у нього обережне ім’я з підкресленням, на яке багато линтеры лаються, ви можете обійти це наступним чином:

import React, { unstable_Profiler as Profiler } from 'react';
...
const Profiler = React.unstable_Profiler;

Тепер, коли у вас є Profiler, давайте попрофилируем компоненти! Ви можете обернути будь-яку частину вашого JSX дерева в Profiler щоб подивитися що з нею відбувається. Profiler приймає функцію onRender, в якій фіксуються відомості про час відтворення. Ось простий приклад лічильника:

import React, { unstable_Profiler as Profiler } from 'react';
class ComponentWithProfiling extends React.Component {
 state = {
 count: 0
};
 logProfile = (id, phase, actualTime, baseTime, startTime, commitTime) => {
 console.log(`${id}'s ${phase} phase:`);
 console.log(`Actual time: ${actualTime}`);
 console.log(`time Base: ${baseTime}`);
 console.log(`Start time: ${startTime}`);
 console.log(`Commit time: ${commitTime}`);
};
 go = direction => () => this.setState(({ count }) => ({
 count: direction === "up" ? count + 1 : count - 1
}));
render() {
 return (
 <Profiler id="app" onRender={this.logProfile}>
 <button onClick={this.go("up")}>️</button>
 <div>The count is {this.state.count}</div>
 <button onClick={this.go("down")}></button>
</Profiler>
);
}
}

Врахуйте, що ви повинні дати id кожного фрагменту, який профилируете Як бачите нижче, onRender приймає купу цікавих метрик:

Читайте також  Машинний зір: установка, налаштування і використання Google Cloud Vision на PHP


7jroojkv30.codesandbox.io

По-перше, ви можете бачити яка була фаза візуалізації (або mount або update), що можна використовувати для ідентифікації частин коду, які несподівано оновлюються (так само, як відмінний пакет why-did-you-update, який я використовував багато разів і настійно рекомендую).

Далі, отримуємо actualTime і baseTime. Вони пов’язані з фактичним часом, який React витрачає на обчислення візуалізації; тобто з’ясування, що змінилося. Зверніть увагу, що фактичний час (actual time) початкового підключення (mount) довше, часу оновлення (update). Це тому, що при першому підключенні технічно все «нове». У той час як при оновленні розрахунки повинні бути простіше, оскільки, я сподіваюся, компоненти в дереві оновлюються тільки в тому випадку, якщо вони справді змінилися (тобто коли змінилися значення prop/states).

У великих/реальних додатках ці дані дозволять зрозуміти де shouldComponentUpdate використовується некоректно або взагалі не використовується, місця, де пропсы з ссылочными типами часто змінюються, або передаються нові пропсы або просто місця де ви не очікували, що оновлення займуть так багато часу.

Останні дані, які ми отримуємо в onRender — це startTime і commitTime. Це, по суті, таймштампы з моменту первісного запуску. startTime — це час з якого вибраний компонент почав виконувати розрахунки для відтворення, тоді як commitTime — час коли React фактично зафіксував ці зміни при відображенні.

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

Висновок

Особисто для мене, цей інструмент поки не буде дуже корисний. Але це одна з тих речей, про які добре знати, тому що, якщо я коли-небудь зіткнуся з цими вузькими місцями в продуктивності, це буде непоганим засобом щоб їх виміряти.

Читайте також  Записки IoT-провайдера. LoRaWAN і RS-485

Важливо спочатку виміряти свої проблеми з продуктивністю, таким чином, коли ви робите “покращення”, ви зможете сказати, чи дійсно це покращує ситуацію або тільки погіршує. Я виявив, що оптимізація продуктивності — це одна з тих речей, на яку можна витратити багато часу. Тому перш ніж щось оптимізувати., переконайтеся, що це реально необхідно.

Я з нетерпінням чекаю, що команда React зробить з Profiler в майбутньому.

На даний момент (актуальна версія 16.6.0) Profiler не працює при server-side рендерінгу. Feature request вже є.

Степан Лютий

Обожнюю технології в сучасному світі. Хоча частенько і замислююся над тим, як далеко вони нас заведуть. Не те, щоб я прям і знаюся на ядрах, пікселях, коллайдерах і інших парсеках. Просто приходжу в захват від того, що може в творчому пориві вигадати людський розум.

You may also like...

Залишити відповідь

Ваша e-mail адреса не оприлюднюватиметься. Обов’язкові поля позначені *