Как работаешь с кодом с костылями?
Комментарии (1)
Ответ сгенерирован нейросетью и может содержать ошибки
Работа с техническим долгом
Кажда разработчик рано или поздно сталкивается с кодом, содержащим "костыли" (workarounds, хаки, временные решения). Правильное управление таким кодом критично для поддержки проекта и команды. Мой подход систематический и ориентирован на долгосрочную стабильность.
Шаг 1: Оценка и документирование
Перво-наперво нужно понять, что перед тобой:
// ❌ Костыль без комментария
if (userAgent.includes('Safari')) {
element.style.width = '99%'; // Магическое число
}
// ✅ Документированный костыль
// HACK: Safari 15 имеет баг с width: 100% в flex контексте
// Issue: https://bugs.webkit.org/show_bug.cgi?id=123456
// TODO: Удалить когда Safari >= 16 будет минимальной версией
if (userAgent.includes('Safari')) {
element.style.width = '99%';
}
Документирование важно, потому что:
- Помогает будущим разработчикам (или тебе через полгода) понять, почему это было необходимо
- Указывает версии браузеров или библиотек, где был баг
- Показывает ссылку на issue или PR для отслеживания
Шаг 2: Создание Issue и отслеживание
Для каждого костыля создаю Issue с меткой "technical-debt":
Заголовок: [TECH DEBT] Удалить костыль для Safari flex width
Описание:
- Текущее решение: 99% ширина вместо 100%
- Причина: баг в Safari 15
- Можно удалить: когда будет поддержка только Safari 16+
- Файл: /src/components/Modal.tsx:45
- Обсуждение: https://bugs.webkit.org/...
Это позволяет:
- Отслеживать все костыли в одном месте
- Периодически проверять, можно ли их удалить
- Планировать рефакторинг в спринтах
Шаг 3: Минимизация влияния
Если нужно работать с существующим костылем, стараюсь ограничить его влияние:
// ❌ Плохо: костыль загрязняет весь компонент
function Modal() {
if (browser.isSafari) {
// специальная логика
}
if (browser.isIE) {
// еще специальная логика
}
// основной код
}
// ✅ Хорошо: костыль изолирован в отдельном хуке
function useWorkaroundSafariWidth() {
const ref = useRef(null);
useEffect(() => {
if (ref.current && isSafariBelow16()) {
ref.current.style.width = '99%';
}
}, []);
return ref;
}
function Modal() {
const safariRef = useWorkaroundSafariWidth();
return <div ref={safariRef}>...</div>;
}
Шаг 4: Прогрессивное улучшение
Если костыль сложный, разбиваю рефакторинг на части:
// Фаза 1: Изолирование
// Выношу костыль в отдельный файл/модуль
// Фаза 2: Тестирование
// Добавляю тесты для текущего поведения
// Убеждаюсь, что костыль работает как ожидается
// Фаза 3: Подготовка замены
// Пишу новый код, который работает без костыля
// Запускаю оба варианта параллельно
// Фаза 4: Миграция
// Постепенно переходим на новый код
// Удаляем старый костыль
Шаг 5: Коммуникация в команде
Обсуждаю костыли на code review и ретроспективах:
В PR comment:
"Я вижу здесь костыль для IE11 (строка 42). Он документирован
и отслеживается в issue #1234. Планируем удалить в спринте N,
когда поддержка IE11 будет прекращена."
Это помогает:
- Предотвратить дублирование костылей
- Объединить усилия команды
- Планировать удаление
Пример реальной ситуации
// Костыль: Firefox не поддерживает CSS mask-image с SVG
function getBackgroundImage(svgUrl: string) {
const isFirefox = navigator.userAgent.includes('Firefox');
if (isFirefox) {
// WORKAROUND: Firefox баг #1234567
// CSS mask-image не работает с внешними SVG
// Используем встроенный SVG вместо ссылки
return `url('data:image/svg+xml;utf8,<svg>...</svg>')`;
}
return `url('${svgUrl}')`;
}
Когда Firefox выпустит фикс:
// Обновляем функцию
function getBackgroundImage(svgUrl: string) {
// Костыль удален - Firefox теперь поддерживает CSS mask-image
return `url('${svgUrl}')`;
}
Вредные практики, которых избегаю
// ❌ Не делаю так:
// 1. Оставляю костыли без документации
// 2. Не отслеживаю их
// 3. Дублирую один костыль в разных местах
// 4. Забываю про них навсегда
// 5. Добавляю все новые костыли вместо рефакторинга
Системный подход
- Каждый костыль должен быть задокументирован - комментарий с причиной
- Каждый костыль должен быть отслежен - issue или TODO
- Костыли должны быть минимизированы - не должны загрязнять основной код
- Регулярно проверяю - можно ли удалить, когда поддержка изменилась
- Планирую рефакторинг - включаю в спринты удаление техдолга
Итог
Костыли иногда необходимы для решения срочных проблем. Но их нужно рассматривать как временные решения, а не постоянные. Правильная документация, изоляция, отслеживание и планомерное удаление - ключ к поддерживаемому коду. Это показывает профессионализм и заботу о качестве проекта.