Skip to content

Commit d9464f2

Browse files
author
Evgeniya Bashieva
committed
fix: prettier
1 parent 8fd98fd commit d9464f2

File tree

3 files changed

+253
-188
lines changed

3 files changed

+253
-188
lines changed

lessons/lesson22/lesson.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -407,4 +407,4 @@ alert(s(3)(4)(5)()); // 12
407407
- [Debug Visualizer](https://marketplace.visualstudio.com/items?itemName=hediet.debug-visualizer)
408408
- [Visualize JavaScript code execution](http://www.pythontutor.com/javascript.html#mode=edit)
409409
- [JavaScript Visualizer (ES5)](https://ui.dev/javascript-visualizer/)
410-
- [Code to graph](https://crubier.github.io/code-to-graph/)
410+
- [Code to graph](https://crubier.github.io/code-to-graph/)

lessons/lesson23/lesson.md

Lines changed: 75 additions & 71 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
# Lesson 23
2+
23
## OTUS Javascript Basic
34

45
### Разделение логики и представления
@@ -9,33 +10,33 @@
910

1011
#### Цели занятия
1112

12-
* Разобрать, как разделение кода на составляющие помогает с переиспользованием кода и его поддержкой (на простых примерах с запросами и DOM).
13-
* Узнать подходы: принцип единственной ответственности, представление, шаблонизация, сервисный слой, MVC и увидеть, как они выражаются в коде (используя то, что уже известно: функции, async/await, fetch, DOM, события).
14-
* На практике: маленькие примеры и рефакторинг (без классов — только функции).
13+
- Разобрать, как разделение кода на составляющие помогает с переиспользованием кода и его поддержкой (на простых примерах с запросами и DOM).
14+
- Узнать подходы: принцип единственной ответственности, представление, шаблонизация, сервисный слой, MVC и увидеть, как они выражаются в коде (используя то, что уже известно: функции, async/await, fetch, DOM, события).
15+
- На практике: маленькие примеры и рефакторинг (без классов — только функции).
1516

1617
<!--v-->
1718

1819
#### **Компетенции:**
19-
* Применение метанавыков для обработки информации и принятия решений.
20-
* Умение структурировать программы.
20+
21+
- Применение метанавыков для обработки информации и принятия решений.
22+
- Умение структурировать программы.
2123

2224
<!--v-->
2325

2426
### План занятия
2527

26-
* Введение: Зачем разделять — как "сортировка" в коде
27-
* Теория: Определения и подходы.
28-
* Маленькие примеры с запросами и DOM: "до/после"
29-
* Лайвкодинг: Плохой код → шаг за шагом в MVC
30-
* Итоги
28+
- Введение: Зачем разделять — как "сортировка" в коде
29+
- Теория: Определения и подходы.
30+
- Маленькие примеры с запросами и DOM: "до/после"
31+
- Лайвкодинг: Плохой код → шаг за шагом в MVC
32+
- Итоги
3133

3234
<!--s-->
3335

3436
### Введение:
3537

3638
<!--v-->
3739

38-
3940
### Почему разделение — это легко и выгодно?
4041

4142
Вы уже знаете DOM, async/await и fetch, функции и объекты. Но в простых скриптах часто всё смешивается: fetch в обработчике клика + innerHTML там же. Результат — дубли, ошибки при изменении (сломал UI — сломал запрос).
@@ -55,16 +56,17 @@
5556
### fetch в обработчике + DOM
5657

5758
```javascript
58-
document.getElementById('btn').addEventListener('click', async () => {
59-
const response = await fetch('https://jsonplaceholder.typicode.com/users/1');
59+
document.getElementById("btn").addEventListener("click", async () => {
60+
const response = await fetch("https://jsonplaceholder.typicode.com/users/1");
6061
const data = await response.json();
61-
document.getElementById('output').innerHTML = `<div>${JSON.stringify(data)}</div>`;
62+
document.getElementById("output").innerHTML = `<div>${JSON.stringify(
63+
data
64+
)}</div>`;
6265
});
6366
```
6467

6568
Плохо: данные и отображение смешаны, нет переиспользования, любая ошибка в fetch ломает UI
6669

67-
6870
<!--s-->
6971

7072
### Представление (View)
@@ -79,31 +81,34 @@ document.getElementById('btn').addEventListener('click', async () => {
7981

8082
```javascript
8183
function renderDataAndFetch() {
82-
fetch('https://jsonplaceholder.typicode.com/users/1')
83-
.then(res => res.json())
84-
.then(data => {
85-
document.getElementById('output').innerHTML = `<pre>${JSON.stringify(data, null, 2)}</pre>`;
84+
fetch("https://jsonplaceholder.typicode.com/users/1")
85+
.then((res) => res.json())
86+
.then((data) => {
87+
document.getElementById("output").innerHTML = `<pre>${JSON.stringify(
88+
data,
89+
null,
90+
2
91+
)}</pre>`;
8692
});
8793
}
8894
renderDataAndFetch();
8995
```
9096

9197
Плохо: функция одновременно делает fetch и вставку в DOM, нарушается принцип единственной ответственности
9298

93-
9499
<!--s-->
95100

96101
### Шаблонизация
97102

98103
Определение: генерация HTML из заготовки и данных.
99104

100-
Пример:
105+
Пример:
101106

102107
<!--v-->
103108

104109
```js
105110
for (let i = 0; i < data.length; i++) {
106-
html += '<p>' + data[i] + '</p>';
111+
html += "<p>" + data[i] + "</p>";
107112
}
108113
```
109114

@@ -113,23 +118,22 @@ for (let i = 0; i < data.length; i++) {
113118

114119
Функции для запросов и расчётов.
115120

116-
Пример:
121+
Пример:
117122

118123
<!--v-->
119124

120125
### сервисный fetch встроен в обработчик
121126

122127
```javascript
123-
document.getElementById('btn').addEventListener('click', async () => {
124-
const res = await fetch('https://jsonplaceholder.typicode.com/users/1');
128+
document.getElementById("btn").addEventListener("click", async () => {
129+
const res = await fetch("https://jsonplaceholder.typicode.com/users/1");
125130
const data = await res.json();
126131
console.log(data);
127132
});
128133
```
129134

130135
Плохо: нет переиспользования, каждый обработчик дублирует fetch, тестировать сложно
131136

132-
133137
<!--s-->
134138

135139
### Теория: MVC
@@ -142,12 +146,11 @@ Controller — связывает (addEventListener → model → view).
142146

143147
Преимущества: структура и масштабируемость.
144148

145-
146149
<!--s-->
147150

148151
### Примеры: "До" и "После"
149152

150-
Используем fetch, addEventListener, innerHTML.
153+
Используем fetch, addEventListener, innerHTML.
151154

152155
Каждый пример: "плохой" (смешанный) и "хороший" (разделённый).
153156

@@ -159,11 +162,11 @@ Controller — связывает (addEventListener → model → view).
159162
<button id="btn">Показать</button>
160163
<div id="name"></div>
161164
<script>
162-
function showName() {
163-
var name = 'Алекс';
164-
document.getElementById('name').innerHTML = 'Имя: ' + name;
165-
}
166-
document.getElementById('btn').addEventListener('click', showName);
165+
function showName() {
166+
var name = "Алекс";
167+
document.getElementById("name").innerHTML = "Имя: " + name;
168+
}
169+
document.getElementById("btn").addEventListener("click", showName);
167170
</script>
168171
```
169172

@@ -174,13 +177,17 @@ document.getElementById('btn').addEventListener('click', showName);
174177
### Пример 1: "После"
175178

176179
```javascript
177-
function getName() { return 'Алекс'; }
180+
function getName() {
181+
return "Алекс";
182+
}
178183

179184
function renderName(name) {
180-
document.getElementById('name').innerHTML = `Имя: ${name}`;
185+
document.getElementById("name").innerHTML = `Имя: ${name}`;
181186
}
182187

183-
document.getElementById('btn').addEventListener('click', () => renderName(getName()));
188+
document
189+
.getElementById("btn")
190+
.addEventListener("click", () => renderName(getName()));
184191
```
185192

186193
Разделение: данные и представление отделены.
@@ -192,21 +199,20 @@ document.getElementById('btn').addEventListener('click', () => renderName(getNam
192199
### Пример 2: "До" — список имён
193200

194201
```javascript
195-
const names = ['Маша', 'Петя'];
196-
let html = '<ul>';
202+
const names = ["Маша", "Петя"];
203+
let html = "<ul>";
197204

198205
for (let i = 0; i < names.length; i++) {
199206
// Здесь потенциальная уязвимость:
200-
// если names[i] придёт из ненадёжного источника,
207+
// если names[i] придёт из ненадёжного источника,
201208
// вставка через + в innerHTML позволит выполнить HTML/JS
202-
html += '<li>' + names[i] + '</li>';
209+
html += "<li>" + names[i] + "</li>";
203210
}
204211

205-
html += '</ul>';
212+
html += "</ul>";
206213

207214
// Здесь тоже уязвимость: innerHTML вставляет HTML напрямую
208-
document.getElementById('list').innerHTML = html;
209-
215+
document.getElementById("list").innerHTML = html;
210216
```
211217

212218
Недостаток: небезопасно.
@@ -216,16 +222,16 @@ document.getElementById('list').innerHTML = html;
216222
### Пример 2: "После" — шаблон
217223

218224
```javascript
219-
const names = ['Маша', 'Петя'];
225+
const names = ["Маша", "Петя"];
220226

221227
function renderListSafe(items, containerId) {
222228
const container = document.getElementById(containerId);
223229

224230
// создаём новый ul
225-
const ul = document.createElement('ul');
231+
const ul = document.createElement("ul");
226232

227-
items.map(name => {
228-
const li = document.createElement('li');
233+
items.map((name) => {
234+
const li = document.createElement("li");
229235
li.textContent = name; // безопасно
230236
ul.appendChild(li);
231237
});
@@ -234,16 +240,13 @@ function renderListSafe(items, containerId) {
234240
container.replaceChildren(ul);
235241
}
236242

237-
renderListSafe(names, 'list');
238-
239-
243+
renderListSafe(names, "list");
240244
```
241245

242246
безопаснее
243247

244248
<!--s-->
245249

246-
247250
### Пример 3: "До" — расчёт суммы
248251

249252
```javascript
@@ -252,20 +255,21 @@ let sum = 0;
252255
for (let i = 0; i < prices.length; i++) {
253256
sum += prices[i];
254257
}
255-
document.getElementById('total').innerText = 'Сумма: ' + sum;
258+
document.getElementById("total").innerText = "Сумма: " + sum;
256259
```
257260

258261
Недостаток: логика и DOM смешаны.
259262

260263
<!--v-->
264+
261265
### Пример 3: "После" — сервис
262266

263267
```javascript
264268
function calculateSum(prices) {
265269
return prices.reduce((total, price) => total + price, 0);
266270
}
267271
function renderTotal(sum) {
268-
document.getElementById('total').innerText = `Сумма: ${sum}`;
272+
document.getElementById("total").innerText = `Сумма: ${sum}`;
269273
}
270274
renderTotal(calculateSum([100, 200]));
271275
```
@@ -280,26 +284,27 @@ renderTotal(calculateSum([100, 200]));
280284
<button id="btn">Загрузить</button>
281285
<div id="user"></div>
282286
<script>
283-
document.getElementById('btn').addEventListener('click', function() {
284-
fetch('https://jsonplaceholder.typicode.com/users/1')
285-
.then(r => r.json())
286-
.then(user => {
287-
document.getElementById('user').innerHTML = user.name;
288-
});
289-
});
287+
document.getElementById("btn").addEventListener("click", function () {
288+
fetch("https://jsonplaceholder.typicode.com/users/1")
289+
.then((r) => r.json())
290+
.then((user) => {
291+
document.getElementById("user").innerHTML = user.name;
292+
});
293+
});
290294
</script>
291295
```
292296

293297
Недостаток: асинхронный код и DOM в обработчике.
294298

295299
<!--v-->
300+
296301
### Пример 4: "После" — сервис + View
297302

298303
```javascript
299304
// Сервис: получает данные пользователя
300305
async function getUser(id) {
301306
const res = await fetch(`https://jsonplaceholder.typicode.com/users/${id}`);
302-
if (!res.ok) throw new Error('Ошибка запроса');
307+
if (!res.ok) throw new Error("Ошибка запроса");
303308
return await res.json();
304309
}
305310

@@ -319,14 +324,15 @@ async function handleClick(id, containerId) {
319324
}
320325

321326
// Пример привязки к кнопке
322-
document.getElementById('btn').addEventListener('click', () => handleClick(1, 'user'));
327+
document
328+
.getElementById("btn")
329+
.addEventListener("click", () => handleClick(1, "user"));
323330
```
324331

325332
Код становится чище и надёжнее.
326333

327334
<!--s-->
328335

329-
330336
### Практика
331337

332338
<!--s-->
@@ -335,22 +341,20 @@ document.getElementById('btn').addEventListener('click', () => handleClick(1, 'u
335341

336342
Основные выводы:
337343

338-
* SRP, View, шаблоны, сервисы и MVC разделяют fetch и DOM.
339-
* Переиспользование: общие функции для разных мест.
344+
- SRP, View, шаблоны, сервисы и MVC разделяют fetch и DOM.
345+
- Переиспользование: общие функции для разных мест.
340346

341347
<!-- v -->
342348

343-
### Домашнее задание: Смотрите на портале
344-
349+
### Домашнее задание: Смотрите на портале
345350

346351
<!--s-->
347352

348353
### Дополнительные материалы
349354

350-
* SRP и SOLID в JavaScript
351-
* MVC без фреймворков
352-
* Шаблоны в JavaScript
353-
355+
- SRP и SOLID в JavaScript
356+
- MVC без фреймворков
357+
- Шаблоны в JavaScript
354358

355359
<!--s-->
356360

0 commit comments

Comments
 (0)