Настоящий JavaScript
الذهاب إلى القناة على Telegram
Тот самый канал по JavaScript. Личный блог автора - @just_genych По вопросам рекламы или разработки: @g_abashkin
إظهار المزيد6 287
المشتركون
-624 ساعات
+217 أيام
+5930 أيام
جاري تحميل البيانات...
القنوات المماثلة
سحابة العلامات
الإشارات الواردة والصادرة
---
---
---
---
---
---
جذب المشتركين
يونيو '26
يونيو '26
+103
في 0 قنوات
مايو '26
+384
في 0 قنوات
Get PRO
أبريل '26
+83
في 0 قنوات
Get PRO
مارس '26
+71
في 0 قنوات
Get PRO
فبراير '26
+23
في 0 قنوات
Get PRO
يناير '26
+18
في 0 قنوات
Get PRO
ديسمبر '25
+13
في 0 قنوات
Get PRO
نوفمبر '25
+24
في 0 قنوات
Get PRO
أكتوبر '25
+22
في 0 قنوات
Get PRO
سبتمبر '25
+21
في 0 قنوات
Get PRO
أغسطس '25
+20
في 0 قنوات
Get PRO
يوليو '25
+38
في 0 قنوات
Get PRO
يونيو '25
+52
في 0 قنوات
Get PRO
مايو '25
+121
في 0 قنوات
Get PRO
أبريل '25
+88
في 0 قنوات
Get PRO
مارس '25
+363
في 20 قنوات
Get PRO
فبراير '25
+30
في 0 قنوات
Get PRO
يناير '25
+38
في 0 قنوات
Get PRO
ديسمبر '24
+41
في 0 قنوات
Get PRO
نوفمبر '24
+64
في 2 قنوات
Get PRO
أكتوبر '24
+70
في 1 قنوات
Get PRO
سبتمبر '24
+84
في 2 قنوات
Get PRO
أغسطس '24
+70
في 0 قنوات
Get PRO
يوليو '24
+115
في 0 قنوات
Get PRO
يونيو '24
+89
في 4 قنوات
Get PRO
مايو '24
+101
في 0 قنوات
Get PRO
أبريل '24
+121
في 0 قنوات
Get PRO
مارس '24
+132
في 0 قنوات
Get PRO
فبراير '24
+101
في 0 قنوات
Get PRO
يناير '24
+86
في 0 قنوات
Get PRO
ديسمبر '23
+90
في 0 قنوات
Get PRO
نوفمبر '23
+16
في 0 قنوات
Get PRO
أكتوبر '23
+15
في 0 قنوات
Get PRO
سبتمبر '23
+16
في 0 قنوات
Get PRO
أغسطس '23
+24
في 0 قنوات
Get PRO
يوليو '23
+35
في 0 قنوات
Get PRO
يونيو '23
+20
في 0 قنوات
Get PRO
مايو '23
+15
في 0 قنوات
Get PRO
أبريل '23
+264
في 0 قنوات
Get PRO
مارس '23
+17
في 0 قنوات
Get PRO
فبراير '23
+207
في 0 قنوات
Get PRO
يناير '23
+40
في 0 قنوات
Get PRO
ديسمبر '22
+478
في 0 قنوات
Get PRO
نوفمبر '22
+1 627
في 0 قنوات
Get PRO
أكتوبر '22
+45
في 0 قنوات
Get PRO
سبتمبر '22
+451
في 0 قنوات
Get PRO
أغسطس '22
+459
في 0 قنوات
Get PRO
يوليو '22
+1 991
في 0 قنوات
Get PRO
يونيو '22
+1 567
في 0 قنوات
Get PRO
مايو '22
+1 769
في 0 قنوات
Get PRO
أبريل '22
+97
في 0 قنوات
Get PRO
مارس '22
+2 701
في 0 قنوات
| التاريخ | نمو المشتركين | الإشارات | القنوات | |
| 18 يونيو | 0 | |||
| 17 يونيو | 0 | |||
| 16 يونيو | +1 | |||
| 15 يونيو | +1 | |||
| 14 يونيو | +2 | |||
| 13 يونيو | +2 | |||
| 12 يونيو | +11 | |||
| 11 يونيو | +39 | |||
| 10 يونيو | +24 | |||
| 09 يونيو | +17 | |||
| 08 يونيو | 0 | |||
| 07 يونيو | 0 | |||
| 06 يونيو | 0 | |||
| 05 يونيو | +2 | |||
| 04 يونيو | 0 | |||
| 03 يونيو | 0 | |||
| 02 يونيو | +2 | |||
| 01 يونيو | +2 |
منشورات القناة
Iterator Helpers в JavaScript: ленивые пайплайны без промежуточных массивов и ловушка одноразовых итераторов
Iterator Helpers добавляют к итераторам
map, filter, take, reduce, toArray и другие методы в стиле массивов. Это полезно в API clients, Node.js-сервисах, SSR и build tooling, но частая ошибка - воспринимать iterator pipeline как переиспользуемую коллекцию.
Ленивость вместо временных массивов
const emails = users
.values()
.filter(user => user.active)
.map(user => user.email)
.take(10)
.toArray();
Здесь не создаются массивы после filter и map. Элементы проходят цепочку по одному: user -> filter -> map -> take.
Это выигрывает, когда данных много, нужен только префикс результата или источник потенциально бесконечный:
function* numbers() {
let i = 0;
while (true) yield i++;
}
const result = numbers()
.filter(n => n % 2 === 0)
.map(n => n * n)
.take(5)
.toArray();
Подводный камень: итератор одноразовый
const iterator = [1, 2, 3]
.values()
.map(x => x * 2);
iterator.toArray(); // [2, 4, 6]
iterator.toArray(); // []
Это не баг, а модель курсора. Если часть данных уже прочитана через next(), пайплайн продолжит с текущей позиции.
Практический совет
Не передавайте iterator pipeline как “коллекцию” между модулями:
const activeUsers = users
.values()
.filter(user => user.active);
sendEmails(activeUsers);
renderUsers(activeUsers); // может быть пусто
Если результат нужен несколько раз, материализуйте его:
const activeUsers = users
.values()
.filter(user => user.active)
.toArray();
Или отдавайте фабрику нового итератора:
const activeUsers = () =>
users.values().filter(user => user.active);
Терминальные операции запускают проход
map, filter, take ленивые. toArray, reduce, forEach, some, every, find реально потребляют итератор.
Вывод:
Iterator Helpers хороши для читаемых и экономных пайплайнов, но надежная архитектура требует явно решать, где итератор одноразовый, а где нужна материализованная коллекция.| 2 | Explicit Resource Management в JS/TS: using, await using и безопасный cleanup в async-коде без try/finally в каждом месте
В JS/TS появляется детерминированное освобождение ресурсов: не когда GC соберет объект, а при выходе из scope. В production это важно для Node.js-сервисов, SSR, SDK, API clients и shared libraries, где часто забывают вызвать close, release, rollback или unsubscribe.
Идея
Ресурс реализует протокол, а язык вызывает cleanup сам:
* using - синхронный [Symbol.dispose]()
* await using - асинхронный [Symbol.asyncDispose]()
await using дожидается cleanup, поэтому подходит для DB connection, Redis lock, stream, socket, transaction.
Production-паттерн: транзакция
class Tx {
committed = false;
async commit() {
await db.commit();
this.committed = true;
}
async [Symbol.asyncDispose]() {
if (!this.committed) await db.rollback();
}
}
async function createOrder(input: OrderInput) {
await using tx = await db.beginTransaction();
const order = await tx.orders.create(input);
await tx.audit.log("order_created", order.id);
await tx.commit();
return order;
}
Если audit.log выбросит ошибку, транзакция будет откатана без ручного try/finally в каждом use case.
Важные детали
* dispose вызывается в обратном порядке объявления
* cleanup выполняется при return и throw
* ошибки из основного кода и dispose не теряются, используется SuppressedError
* это не замена GC: GC про память, using - про внешние ресурсы
Практический совет
Для библиотечного API проектируйте не контракт "не забудь вызвать .close()", а явный протокол [Symbol.dispose] / [Symbol.asyncDispose]. В TypeScript синтаксис поддерживается с TS 5.2.
Предупреждение: если cleanup возвращает Promise, обычный using не подходит - используйте await using.
Вывод:
using и await using делают жизненный цикл ресурсов явным, снижают риск утечек и улучшают надежность async-кода без разрастания try/finally. | 180 |
| 3 | 🔍Тестовое собеседование с руководителем Frontend-разработки в этот четверг
18 июня(в четверг!) в 19:00 по мск приходи онлайн на открытое собеседование, чтобы посмотреть на настоящее интервью на Middle Frontend-разработчика.
Как это будет:
📂 Виталий Черков, руководитель группы Frontend разработки с опытом 8+ лет, будет задавать реальные вопросы и задачи разработчику-добровольцу
📂 Виталий будет комментировать каждый ответ респондента, чтобы дать понять, чего от вас ожидает собеседующий на интервью
📂 В конце можно будет задать любой вопрос Виталию
Это бесплатно. Эфир проходит в рамках менторской программы от ШОРТКАТ для Frontend-разработчиков, которые хотят повысить свой грейд, ЗП и прокачать скиллы.
Переходи в нашего бота, чтобы получить ссылку на эфир → @shortcut_front_bot
Реклама.
О рекламодателе. | 227 |
| 4 | Web Locks API в браузере: cross-tab mutex для refresh token, миграций и защиты от гонок
Когда одна сессия открыта в нескольких вкладках, frontend, SPA, SSR-клиенты и SDK начинают делить auth state, storage и кэш. Частая ошибка - защищать refresh token только in-memory single-flight: между вкладками он не работает.
Refresh token как критическая секция
Если 5 вкладок одновременно получили 401, они могут отправить несколько refresh-запросов одним token, получить invalid_grant и перетереть свежие токены старыми. Web Locks API дает mutex на один origin:
type Tokens = {
accessToken: string;
refreshToken: string;
};
const LOCK = 'auth:refresh-token';
async function ensureAccessToken(): Promise<string> {
return navigator.locks.request(LOCK, async () => {
const latest: Tokens = await loadTokens();
if (!isExpiring(latest)) {
return latest.accessToken;
}
const next = await refreshTokens(latest.refreshToken);
await saveTokens(next);
return next.accessToken;
});
}
Важный паттерн
После входа в lock нужно перечитать storage. Пока вкладка ждала, другая уже могла обновить токены. Практический совет: внутри критической секции всегда делайте double-check precondition, а не запускайте refresh сразу после ожидания.
Где еще полезно
Web Locks хорошо ложится на миграции IndexedDB/localStorage, одноразовую инициализацию кэша, защиту записи в общий browser storage и координацию фоновых задач между вкладками.
Ограничения
Lock работает только в пределах origin. Это не distributed lock и не замена серверной идемпотентности. Критическая секция должна быть короткой; для сетевого refresh ставьте timeout. Если navigator.locks нет, нужен fallback через BroadcastChannel, storage lease или серверную защиту.
Вывод:
Web Locks API полезен там, где несколько вкладок делят runtime-состояние: он снижает риск гонок, но не отменяет серверные гарантии. | 258 |
| 5 | День сурка frontend-разработчика
Зарплата стоит, скучные задачи день за днем, календарь забит созвонами, которые не влияют вообще ни на что.
Откликаешься на вакансии, а в ответ тишина либо какие-то мутные конторы. На собесах вместо нормальной оценки навыков цирк с алгоритмами на скорость, как будто ты на олимпиаде, а не работу ищешь.
И самое неприятное, пока ты варишься в этом болоте, кто-то спокойно проходит собесы и уходит в Яндекс, VK или на хорошую Валютную удаленку без лишней драмы.
Есть классные проекты и сильные команды, где разработчиков действительно ценят, дают расти, поддерживают развитие и платят достойно и ты можешь туда попасть!
👋 Меня зовут Тихон, привет! Я — действующий Frontend-разработчик и ментор. Я за руку довожу до оффера на хорошую позицию в Big Tech и сопровождаю на испытательном сроке.
Также из учеников я собираю комьюнити, где уже более 220 frontend-разработчиков🫂
А в своем канале:
👉Объясняю, как проходить HR-фильтр и превращать отклики в реальные приглашения
👉Помогаю найти мотивацию, борюсь убеждениями, которые мешают развиваться
👉На примерах объясняю, как проходить собеседования, включая техничку
👉Разбираю резюме и делюсь лайфхаками, например как аккуратно “пинговать” рекрутеров
А еще регулярно публикую полезные материалы:
▪️Задачи, на которых валяться кандидаты
▪️База по микрофронтам
▪️Подборка из 100+ каналов с вакансиями для разработчиков
▪️100 вопросов, которые точно помогут тебе на собеседовании
▪️Чек лист проверки своего резюме
А еще у меня множество успешных кейсов и отзывов, найти их можно в канале.
Реклама, erid: 2W5zFJeWaNd ИП Галактионов Тихон Витальевич, ИНН 771618975809 | 236 |
| 6 | Promise.withResolvers() в production: ручное завершение промисов без deferred-антипаттернов и утечек
Promise.withResolvers() полезен на границе event-based API и async/await: WebSocket, Worker, IPC, SDK, API clients, Node.js-сервисы. Частая ошибка - считать его безопасной заменой любому deferred и хранить resolve/reject где попало.
Что это даёт
const { promise, resolve, reject } =
Promise.withResolvers<T>();
Это тот же внешний resolve/reject, но без let, definite assignment и самодельного executor-шаблона. API стал чище, но lifecycle всё ещё ваша ответственность.
Где применять
* ожидание одного события;
* bridge callback/event API в Promise;
* request/response поверх WebSocket, Worker или IPC;
* внутренняя очередь producer/consumer.
Не стоит передавать resolve через слои, класть его в глобальное состояние или создавать promise без timeout/cancel path.
Production-паттерн
type Message = { id: string; payload: unknown };
type Waiter = {
resolve: (m: Message) => void;
reject: (e: Error) => void;
timeout: ReturnType<typeof setTimeout>;
};
const pending = new Map<string, Waiter>();
function waitForMessage(id: string, ms = 5000) {
const { promise, resolve, reject } =
Promise.withResolvers<Message>();
const timeout = setTimeout(() => {
pending.delete(id);
reject(new Error(Message timeout: ${id}));
}, ms);
pending.set(id, { resolve, reject, timeout });
return promise.finally(() => {
clearTimeout(timeout);
pending.delete(id);
});
}
Что важно
У promise есть owner - waitForMessage(). Есть timeout, очистка через finally(), а resolve/reject не утекают наружу. Иначе Map будет удерживать замыкания, таймеры и payload.
Практический совет: если у вызывающего кода есть свой lifecycle, добавьте AbortSignal и снимайте listener в finally().
Вывод:
Promise.withResolvers() стоит использовать только там, где явно определены owner, timeout/cancel path и очистка ресурсов. | 225 |
| 7 | Dual package hazard в ESM/CJS: conditional exports без двух копий singleton-состояния в одном Node.js-процессе
Это важно для SDK, API clients, SSR, Node.js-сервисов и shared libraries. Частая ошибка - считать, что одинаковый TS-код в .mjs и .cjs даст общий runtime.
Где ломается
const cjs = require('@acme/sdk')
const esm = await import('@acme/sdk')
Если require попал в dist/index.cjs, а import - в dist/index.mjs, Node загрузит два разных модуля.
Итог:
* два singleton-инстанса
* две registry/cache/map
* разные подключения
* сломанный instanceof
* расходящееся состояние
Рабочая схема
Один runtime source of truth, второй формат - только фасад. Например, состояние живет в core.cjs, а ESM лишь импортирует его:
// package.json
"exports": {
".": {
"types": "./dist/index.d.ts",
"import": "./dist/index.mjs",
"require": "./dist/core.cjs"
}
}
// core.cjs
const registry = new Registry()
module.exports = { Registry, registry }
// index.mjs
import api from './core.cjs'
export const Registry = api.Registry
export const registry = api.registry
export default api
Теперь require и import смотрят на один singleton:
cjs.registry === esm.registry // true
cjs.Registry === esm.Registry // true
Типичная ошибка
Не делайте две независимые реализации:
"import": "./dist/index.mjs",
"require": "./dist/index.cjs"
Если оба файла содержат состояние, hazard почти гарантирован. Conditional exports только маршрутизируют загрузку, но не объединяют объекты в памяти.
Практический чеклист
* закрывайте deep imports вроде @acme/sdk/dist/index.mjs
* для каждого subpath, например @acme/sdk/cache, повторяйте ту же схему
* для чистых функций риск ниже, для DI, логгеров, метрик, БД-клиентов и кэшей - критичен
Вывод:
Dual ESM/CJS-пакету нужен один общий runtime-модуль и фасадные entrypoint, а не две сгенерированные копии реализации. | 259 |
| 8 | Совет на ближайшие годы — изучайте ВАЙБ-КОДИНГ
ИИ уже пишет код, чинит баги, генерирует тесты, документацию и помогает запускать продукты быстрее, чем это делали классические команды разработки. И это уже не "будущее когда-нибудь", а реальность, которая меняет рынок уже сегодня
И те, кто научится вайбкодить сейчас, будут увереннее конкурировать на рынке и зарабатывать больше тех, кто по-прежнему делает всё вручную.
Стартовать с нуля поможет канал Вайб-кодинг. Там ребята круглосуточно мониторят более 320 российских и зарубежных источников и публикуют только главное: релизы, инструменты, гайды, курсы и практические кейсы.
Подписывайтесь, нас уже 45 тысяч: @vibecoding_tg | 294 |
| 9 | AsyncLocalStorage в Node.js: request-scoped контекст для логов, трассировки и транзакций без prop drilling
В production это нужно в Node.js-сервисах, SSR, API integration и backend-for-frontend слоях, где requestId, traceId, tenant или транзакция должны проходить через async-код. Частая ошибка - протаскивать ctx через десятки методов или, наоборот, прятать в нём бизнес-состояние.
Как это выглядит
AsyncLocalStorage использует async_hooks и привязывает store к async execution flow: promise, timeout, I/O callback и большинству стандартных API Node.js.
type Ctx = { requestId: string; traceId?: string; tx?: unknown };
const als = new AsyncLocalStorage<Ctx>();
app.use((req, _res, next) => {
als.run({
requestId: req.headers['x-request-id']?.toString() ?? randomUUID(),
traceId: req.headers.traceparent?.toString(),
}, next);
});
const getCtx = () => als.getStore();
function logInfo(msg: string, meta = {}) {
const c = getCtx();
logger.info({
requestId: c?.requestId,
traceId: c?.traceId,
...meta,
}, msg);
}
Теперь сервисный код не знает про HTTP middleware и req, но логи автоматически получают correlation metadata.
Транзакции без протаскивания tx
Для DB слоя можно делать withTransaction(), который запускает als.run({ ...ctx, tx }, fn), а getDbExecutor() возвращает ctx.tx ?? db. Trade-off хороший: меньше шума в API сервисов, но граница ответственности остаётся инфраструктурной, а не бизнесовой.
Где границы
* не заменяйте аргументы функции: бизнес-данные передавайте явно;
* не кладите в store req, res, большие payload или ORM graph;
* context не пересекает process boundary: worker threads, очереди, cron jobs и другие сервисы требуют явной передачи ids;
* нестандартные callback-based библиотеки могут разорвать async chain.
Практическое правило: используйте AsyncLocalStorage для логов, tracing, tenant/user metadata, аудита и текущей транзакции, а не для скрытого глобального состояния.
Вывод:
AsyncLocalStorage полезен, когда request-scoped инфраструктурный контекст улучшает observability и DX, но не размывает явные границы бизнес-логики. | 311 |
| 10 | АЙТИШНИКИ БЕСПЛАТНОЕ ОБУЧЕНИЕ сборник курсов, инструментов и книг
Проект «TERMINAL» стал крупнейшей библиотекой бесплатного образования. В одном канале собраны курсы, книги, полезные инструменты и практические тренажёры для всех разработчиков
🎓 Практические курсы и задания
🪽 Книги и статьи известных авторов
😮💨 Полезные инструменты и ресурсы
🌟 IT-новости и инсайды
Обучение по всем направлениям: SQL, Python, Frontend, PHP, C++, Golang, GIT, Linux, QA, Java, Vibe-coding, Infosec и др.
Ценишь знания, подпишись: Terminal_tg | 281 |
| 11 | AbortSignal.any() и AbortSignal.timeout(): единая отмена fetch, таймеров и async-операций в production
Promise.race([fetch(), timeout]) часто маскирует проблему: ждать перестали, но работа могла не остановиться. В SPA, SSR, Node.js-сервисах, SDK и API clients это приводит к висящим запросам, таймерам и retry/backoff ниже по стеку.
Собирайте отмену вокруг AbortSignal
AbortSignal.timeout(ms) сам отменится по таймауту.
AbortSignal.any([...signals]) отменится, когда отменится любой входной signal.
Так в один контракт попадают:
* caller отменил операцию
* истек timeout
* клиент закрыл соединение
* сервис уходит в graceful shutdown
const shutdown = new AbortController();
async function loadUser(id: string, opts: { signal?: AbortSignal } = {}) {
const signal = AbortSignal.any([
AbortSignal.timeout(1500),
shutdown.signal,
...(opts.signal ? [opts.signal] : []),
]);
signal.throwIfAborted();
const res = await fetch(`https://api.example.com/users/${id}`, { signal });
await sleep(100, signal); // backoff тоже отменяем
const data = await res.json();
signal.throwIfAborted();
return data;
}
Типичная ошибка
Не останавливайтесь на fetch. Один и тот же signal стоит передавать в retry, polling, очереди, sleep/timer helpers и свои async-функции. Иначе верхний слой "отменился", а нижний продолжает держать ресурсы.
Практические нюансы
* AbortSignal одноразовый: если aborted === true, нужен новый controller или timeout
* AbortSignal.any() - это fan-in, а не fan-out: он не отменяет исходные контроллеры
* смотрите на reason: timeout часто дает TimeoutError, abort - AbortError или ваш reason
* при обертках над setTimeout, stream, listener или socket чистите ресурсы при abort
Вывод:
Отмена должна быть частью контракта async-функции, а не локальным Promise.race на краю системы. | 395 |
| 12 | Нейросети, IT и AI — в одной папке
💬 С коллегами собрали новые каналы про:
💠 промпты для нейросетей и готовые решения
💠 AI-фотосессии, генерация изображений и контента
💠 новости искусственного интеллекта без лишнего шума
💠 применение AI в работе, бизнесе и повседневной жизни
💠 Python, JavaScript, Data Science и системный анализ
💠 вакансии и возможности для специалистов в IT
Посмотреть и подписаться тут 👉 https://t.me/addlist/c_rbhnzprbAwMmFi
💌 Добавить свой канал в папку | 284 |
| 13 | Страшная тайна российского айти
✖️ xCode Journal | 476 |
| 14 | Хватит гадать — DeepSeek за тебя уже всё решил 🐳
* Сейчас все только про Claude, но я перешёл на DeepSeek и не жалею. Бесплатно, контекст 1 млн токенов — закинул целую книгу, помнит всё. Код пишет отлично, а рассуждения (Reasoning) выдают логику, как у архитектора.
Решил протестировать агентский режим на задаче, которую вечно откладывал — собрать чистое инфополе с нуля. Чтобы не перебирать паблики вручную, зашёл через функцию похожих каналов в Telegram.
Скормил DeepSeek ссылки на качественных авторов по IT и AI, которых читаю сам, и попросил проанализировать сотни рекомендаций. Агент изучил контент на каналах и оставил только тех, кто делится практическим опытом по: AI-воркфлоу, автоматизации, вайб-кодингу, промт-инжинирингу, RAG-syst. нейрогенерации и др.
DeepSeek собрал полезную подборку экспертов в одну папку. Делюсь списком — внутри только полезный контент про IT & AI.
🔗Забирай в один клик: 👉 https://t.me/addlist/FYyQj91I8jJiMzg0 | 376 |
| 15 | Variadic tuple types — сложные сигнатуры без боли
До variadic tuple types
многие сложные сигнатуры в TypeScript
выглядели как наказание.
Особенно:
👉 curry
👉 compose
👉 middleware
👉 typed event emitter
👉 любые функции с «прокинь аргументы дальше»
Приходилось писать overload на overload
и дублировать типы вручную.
Как было раньше
Обычно появлялись:
👉 overload на overload
👉 ручные tuple-типы
👉 тонны дублирования
Типы быстро превращались
в нечитаемую простыню.
Что изменили variadic tuples
С их появлением стало намного проще
работать с остаточными аргументами на уровне типов.
Например:
type Fn<T extends unknown[]> =
(...args: [...T]) => void
Или собирать сигнатуры:
type Append<Args extends unknown[], Arg> =
[...Args, Arg]
Типы наконец научились нормально работать
с «переменным количеством аргументов».
Почему это важно
На практике это одна из тех TS-фич,
которые реально упростили жизнь библиотекам.
Без variadic tuples:
👉 Redux middleware typings
👉 router APIs
👉 compose/curry utilities
были бы ещё страшнее.
Где начинается тёмная магия
Проблемы начинаются,
когда variadic tuples комбинируют с:
👉 infer
👉 recursive types
👉 conditional types
Типовая система очень быстро
превращается в тёмный лес.
IDE начинает тормозить,
ошибки становятся нечитаемыми,
а compile time — расти.
Главная мысль
Variadic tuple types —
это действительно мощная фича.
Главное —
вовремя остановиться
и не превратить типы в отдельный язык программирования. | 479 |
| 16 | Стажировки и вакансии для JavaScript разработчиков
- Вакансии которых нет на джоб-агрегаторах
- Только прямые контакты HR в Telegram
@jobs_js_fronted для фронтов
@jobs_js_back для бека
Пока другие листают джоб-сайты — ты уже пишешь HR в Telegram. | 320 |
| 17 | Стажировки и вакансии для JavaScript разработчиков
- Вакансии которых нет на джоб-агрегаторах
- Только прямые контакты HR в Telegram
@jobs_js_fronted для фронтов
@jobs_js_back для бека
Пока другие листают джоб-сайты — ты уже пишешь HR в Telegram. | 235 |
| 18 | Привет, друзья! Собрали с коллегами новую папку с каналами
Здесь AI-новости, нейросети, полезные инструменты, примеры внедрения ИИ в крупный бизнес, разработка, JS, Node.js, frontend, QA, Data Science, кибербезопасность и IT-вакансии.
Посмотреть и подписаться можно тут 👉 https://t.me/addlist/XttiKDt6lhUwMzEy
💌 записаться в папку | 275 |
| 19 | На Stepik запустили мощный курс по «Troubleshooting Docker и Kubernetes: поиск и устранение проблем»
В программе только важные аспекты:
— troubleshooting Docker и образов
— диагностика сетевых проблем
— настройка readiness/liveness probes
— отладка pod’ов, деплоев и ingress
— анализ логов контейнеров и кластера
— разбор ошибок CrashLoopBackOff, OOMKilled, ImagePullBackOff и других
Собеседования на DevOps/SRE сейчас всё чаще строятся вокруг реальных инцидентов. Данный курс фокусируется именно на таких сценариях и помогает в подготовке к практическим вопросам
48 часов доступен со скидкой 25%
↗️ Пройти курс на Stepik | 339 |
| 20 | ⁉️ Устал искать интересные каналы с новостями про искусственный интеллект?
📁 СОХРАНИ СЕБЕ ЧТОБЫ НЕ ПОТЕРЯТЬ
В этой папке собраны каналы про ИИ, которые помогают быстрее разобраться в сфере, находить идеи и экономить время на поиске информации.
😏 ЗАБИРАЙ ПАПКУ ТУТ
⏰ Папка действует 72 часа.
🤩 Организаторы: Green.Papka | 826 |
متاح الآن! بحث تيليغرام 2025 — أهم رؤى العام 
