Source Maps: отладка prod кода
Source maps — файлы-маппинги, связывающие минифицированный/транспилированный код продакшна с исходным кодом, позволяя отлаживать в браузере с оригинальными именами переменных и номерами строк.
Зачем нужно
Продакшн-бандл — это минифицированный код вида a.b(c,d) в одну строку. При ошибке стек-трейс показывает бессмысленные строки и символы. Source maps позволяют браузеру (и Sentry) показывать оригинальный TypeScript-код с нормальными именами функций и точными строками.
Где используется
- Отладка ошибок в DevTools при развёрнутом приложении
- Sentry/Bugsnag — человекочитаемые stack traces в продакшне
- TypeScript — маппинг
.js→.ts - Vite, webpack, esbuild — генерируют source maps как опция сборки
Как работают source maps
dist/app.js:1:847 → src/components/Button.tsx:42:10
Source map (.js.map) — JSON-файл содержит:
{
"version": 3,
"sources": ["src/app.ts"],
"names": ["createUser", "validateEmail"],
"mappings": "AAAA,SAASA..." // VLQ-кодированные позиции
}
Связь с файлом
// В конце минифицированного файла:
//# sourceMappingURL=app.js.map
// Или через заголовок HTTP-ответа:
SourceMap: /static/app.js.map
Настройка в сборщиках
Vite
// vite.config.ts
export default {
build: {
sourcemap: true, // генерировать .js.map рядом с файлом
// sourcemap: 'inline', // встроить base64 в .js (увеличивает размер)
// sourcemap: 'hidden', // генерировать, но не добавлять ссылку в .js
},
};
webpack
// webpack.config.js
module.exports = {
mode: 'production',
devtool: 'source-map', // отдельный .js.map
// devtool: 'hidden-source-map', // .js.map без ссылки (для Sentry)
// devtool: 'eval-source-map', // быстро, только для разработки
};
TypeScript (tsconfig.json)
{
"compilerOptions": {
"sourceMap": true, // генерировать .js.map
"inlineSourceMap": false, // не встраивать в .js
"inlineSources": true, // включить исходный .ts в .map
"sourceRoot": "/src" // базовый путь к источникам
}
}
Использование в DevTools
1. Открыть DevTools (F12) → Sources
2. Если source maps подключены — в Sources видны оригинальные .ts/.tsx файлы
3. Брейкпоинты ставятся в исходном коде
4. Stack trace в Console показывает оригинальные строки
Source maps и Sentry
// При загрузке source maps в Sentry через CLI
npx @sentry/cli sourcemaps upload \
--org my-org \
--project my-project \
--auth-token $SENTRY_TOKEN \
dist/
// Или через Vite плагин
import { sentryVitePlugin } from '@sentry/vite-plugin';
export default {
plugins: [sentryVitePlugin({ authToken: process.env.SENTRY_TOKEN })],
build: { sourcemap: true },
};
Безопасность source maps
Открытые source maps → любой пользователь видит исходный код
Решения:
1. 'hidden' mode — .map файл генерируется, но не доступен публично
2. Загрузка в Sentry с удалением .map с сервера
3. Ограничение доступа к *.map через nginx
# nginx — запрет публичного доступа к source maps
location ~* \.js\.map$ {
return 404;
}
Частые ошибки
- Source maps в продакшне публично доступны — раскрывают исходный код
devtool: 'eval'в продакшне — не работает в браузерах с CSP- Не загружают source maps в Sentry — stack traces в ошибках нечитаемы
- Нет
inlineSources: trueв TypeScript — Sentry не может показать код строки