- Андрей Куманяев/
- Git: руководства и команды/
- Как закоммитить все изменения в Git: git commit -a и git add -A/
Как закоммитить все изменения в Git: git commit -a и git add -A
В Git нет одной «правильной» команды для коммита всех изменений — есть несколько способов, каждый с нюансами. Ключевое различие: git commit -a не добавляет новые файлы (untracked), а git add -A добавляет всё включая новые.
Способ 1: git commit -a (только отслеживаемые файлы) #
# Закоммитить все изменения в уже отслеживаемых файлах
git commit -a -m "Update all tracked files"
# Сокращённо
git commit -am "Update all tracked files"
Важное ограничение: -a не добавляет новые файлы (untracked). Только изменения и удаления в уже отслеживаемых файлах.
# Создали новый файл
touch new-feature.js
# git commit -a не добавит его:
git commit -am "Add new feature"
# new-feature.js НЕ попадёт в коммит
# Нужно сначала явно добавить
git add new-feature.js
git commit -am "Add new feature"
Способ 2: git add -A && git commit #
# Добавить всё (включая новые файлы) и закоммитить
git add -A
git commit -m "Add all changes"
# Что делает -A:
# ✓ Изменённые файлы
# ✓ Удалённые файлы
# ✓ Новые (untracked) файлы
# ✓ Переименованные файлы
git add -A эквивалентен git add --all — добавляет абсолютно все изменения.
Способ 3: git add . && git commit #
# Добавить из текущей папки и ниже
git add .
git commit -m "Add changes in current directory"
В современных версиях Git (2.x) git add . ведёт себя аналогично git add -A — добавляет всё, включая удалённые файлы. В старых версиях Git git add . не добавляло удалённые файлы.
Сравнение способов #
Команда Изменённые Удалённые Новые файлы
git commit -a ✓ ✓ ✗
git add -A ✓ ✓ ✓
git add . ✓ ✓ ✓ (Git 2.x)
Проверка перед коммитом #
Перед коммитом всех изменений — посмотреть что именно попадёт:
# Посмотреть что будет добавлено через -a
git diff # все неindexированные изменения
# Посмотреть что попадёт в коммит (если уже git add)
git status
git diff --staged
# "Сухой прогон" — показывает файлы без реального add
git add --dry-run -A
Сохранение части изменений (интерактивное добавление) #
Если нужно закоммитить не все, а только часть изменений:
# Интерактивный выбор
git add -p
# Git будет спрашивать по каждому блоку изменений:
# Stage this hunk? [y,n,q,a,d,/,e,?]
# y - добавить
# n - пропустить
# q - выйти
# a - добавить весь файл
# d - пропустить весь файл
Алиасы для быстрого коммита #
# Создать алиас для быстрого коммита всего
git config --global alias.ca 'commit -am'
# Использование
git ca "Quick update"
# Алиас для add и commit
git config --global alias.aac '!git add -A && git commit -m'
# Использование
git aac "Add all and commit"
Правильный рабочий процесс #
Хотя git commit -am удобно, осознанный процесс надёжнее:
# 1. Посмотреть что изменилось
git status
git diff
# 2. Добавить файлы осознанно
git add src/feature.js
git add tests/feature.test.js
# (не трогаем debug.log и временные файлы)
# 3. Проверить что попадёт в коммит
git status
git diff --staged
# 4. Создать коммит
git commit -m "feat: add user authentication"
Автоматический git add -A или git commit -a может случайно включить в коммит лишние файлы (временные, конфиденциальные, отладочные). Убедитесь, что .gitignore настроен корректно.
Часто задаваемые вопросы #
Почему git commit -a не добавляет новые файлы? Это сознательное решение Git. Новые файлы требуют явного добавления (git add), чтобы случайно не закоммитить нежелательное. После первого git add файл становится «отслеживаемым» и будет подхватываться -a.
В чём разница между git add . и git add -A? В Git 2.x они эквивалентны. В старых версиях (1.x) git add . не добавляло удалённые файлы — для них нужен был git add -u. В современном Git используйте любой из вариантов.
Как проверить что git commit -am не добавит лишнего? Запустите git status перед коммитом. Посмотрите раздел “Changes not staged” — это то, что -a добавит. Раздел “Untracked files” — это то, что -a НЕ добавит.
Можно ли сделать git add -A безопасным? Да, через хорошо настроенный .gitignore. Если все нежелательные файлы в .gitignore — git add -A не захватит их.
Интерактивное добавление файлов (git add -p) #
Самый безопасный способ добавить именно то что нужно:
# Интерактивный режим выбора изменений
git add -p
# или
git add --patch
# Git будет показывать по одному блоку (hunk) и спрашивать:
# Stage this hunk? [y,n,q,a,d,/,e,?]
# y - добавить блок
# n - пропустить
# q - выйти из режима
# a - добавить все блоки в этом файле
# d - пропустить все блоки в этом файле
# / - поиск блока
# e - редактировать блок вручную
# ? - помощь
Это идеальный способ для разработчика который хочет полностью контролировать что попадёт в коммит:
# Пример рабочего процесса
git add -p
# Выбрать только релевантные изменения
git status # проверить что добавилось
git diff --staged # посмотреть финальное содержимое
git commit -m "feat: specific feature"
Различие между git add -u, git add . и git add -A #
Полная таблица поведения:
# git add -u (--update)
# ✓ Изменённые файлы
# ✓ Удалённые файлы
# ✗ Новые файлы
git add -u
# git add . (текущая директория и ниже)
# ✓ Изменённые файлы
# ✓ Удалённые файлы
# ✓ Новые файлы (Git 2.x+)
# ✗ Файлы выше текущей директории
git add .
# git add -A (все изменения, везде)
# ✓ Изменённые файлы
# ✓ Удалённые файлы
# ✓ Новые файлы
# ✓ Везде в репозитории
git add -A
# Практический пример структуры:
# project/
# src/feature.js (изменён)
# src/new.js (новый)
# config.old.js (удалён)
# other/data.json (изменён)
cd project/src
git add -u # добавит feature.js, добавит информацию об удалении config.old.js
git add . # добавит feature.js, new.js, добавит информацию об удалении config.old.js (из текущей директории)
git add -A # добавит ВСЁ из всего репозитория
Staging по типам файлов или директориям #
Когда нужна полная контроль:
# Добавить только JavaScript файлы
git add '*.js'
# Добавить файлы из конкретной папки
git add src/
git add tests/
# Добавить несколько конкретных файлов
git add file1.js file2.js file3.js
# Добавить по маске
git add 'feature/**/*.test.js' # все тесты в feature директории
# Исключить файлы
git add src/ '!src/temp.js' # добавить всё из src кроме temp.js
Проверка перед коммитом: полный рабочий процесс #
Профессиональный процесс с максимальной безопасностью:
# 1. Посмотреть общее состояние
git status
# 2. Посмотреть все нестейджированные изменения
git diff
# 3. Посмотреть удалённые файлы
git ls-files -d
# 4. Интерактивное добавление (самое безопасное)
git add -p
# Выбрать нужные блоки, пропустить лишнее
# 5. Проверить что готово коммититься
git status
# Должны увидеть раздел "Changes to be committed"
# 6. Посмотреть точное содержимое коммита
git diff --staged
# 7. Создать коммит только если всё верно
git commit -m "feat: clear description of changes"
# 8. Проверить результат
git log -1 --stat
Это кажется долго, но даёт 100% уверенность что коммит содержит только нужные изменения.
Алиасы для безопасного коммита #
Создать удобные команды:
# Алиас для проверки перед коммитом
git config --global alias.check '!git status && echo "\n--- Staged Changes ---" && git diff --staged'
# Использование
git check
# Проверит и покажет что будет закоммичено
# Алиас для безопасного staging
git config --global alias.safe '!echo "Running checks..." && git diff && echo "\nUse git add -p for interactive staging"'
# Алиас для просмотра того что добавится с -A
git config --global alias.preview '!git add -An .'
Восстановление случайно добавленных файлов #
Если случайно добавили что-то через git add -A:
# Посмотреть что в staging area
git diff --staged
# Убрать конкретный файл из staging (но оставить в рабочей директории)
git restore --staged filename.log
# Убрать всё из staging
git reset
# Убрать всё из staging и восстановить из последнего коммита
git reset --hard
# Отменить весь коммит если уже закоммитили
git reset --soft HEAD~1
# Теперь можно пересоздать коммит правильно
Common mistakes когда коммитят всё сразу #
Ошибка 1: node_modules попали в коммит
# Проблема: забыли про .gitignore
git add -A
git commit -m "update"
# Теперь в репо огромная папка node_modules
# Решение:
git rm -r --cached node_modules
echo "node_modules/" >> .gitignore
git add .gitignore
git commit -m "Remove node_modules"
Ошибка 2: локальные конфиги попали в коммит
# Проблема: добавили .env или .local файлы
git add -A # он добавил всё включая .env
# Решение: немедленно
git rm --cached .env
echo ".env" >> .gitignore
git add .gitignore
git commit --amend --no-edit
git push --force origin main
# Срочно: смените все пароли в .env!
Ошибка 3: дебаг-вывод остался в коде
// src/api.js
console.log(apiKey) // Забыли удалить перед commit
process.env.SECRET
# Только через code review можно ловить такое
# Лучше: настроить eslint правило
"no-console": "warn"
Часто задаваемые вопросы #
Почему git commit -a не добавляет новые файлы? Это сознательное решение Git. Новые файлы требуют явного добавления (git add), чтобы случайно не закоммитить нежелательное. После первого git add файл становится «отслеживаемым» и будет подхватываться -a.
В чём разница между git add . и git add -A? В Git 2.x они эквивалентны. В старых версиях (1.x) git add . не добавляло удалённые файлы — для них нужен был git add -u. В современном Git используйте любой из вариантов.
Как проверить что git commit -am не добавит лишнего? Запустите git status перед коммитом. Посмотрите раздел “Changes not staged” — это то, что -a добавит. Раздел “Untracked files” — это то, что -a НЕ добавит.
Можно ли сделать git add -A безопасным? Да, через хорошо настроенный .gitignore. Если все нежелательные файлы в .gitignore — git add -A не захватит их.
Как отменить git add перед коммитом? git restore --staged filename убирает из staging. Или git reset убирает всё из staging.
Чем git add -p лучше git add -A? git add -p показывает каждое изменение и просит подтверждение. Это гораздо безопаснее для избежания случайных добавлений.
Что если файл в .gitignore но хочу его добавить? git add -f filename — принудительно добавить даже игнорируемый файл.
Заключение #
Для коммита всех изменений в отслеживаемых файлах — git commit -am "message". Для добавления новых файлов вместе со всеми изменениями — git add -A && git commit -m "message". Для максимальной безопасности используйте git add -p для интерактивного выбора. Перед любым массовым добавлением — запускайте git status для проверки. Помните что .gitignore предотвращает случайное добавление нежелательных файлов.