Git
Вопросы для работы
- как решать конфликт merge \ rebase
Knowledge
- https://ru.hexlet.io/courses/intro_to_git/lessons/intro/theory_unit
- Pull request'ы на GitHub или Как мне внести изменения в чужой проект / Хабр
- Книга про гит https://git-scm.com/book/ru/v2
git - распределенная система, может быть центральный репозиторий.
Коммит - это снимок файлов проекта, который сохранен в системе контроля версий. Набор изменений в файлах и папках, которые сохранены в репозитории под определенным именем
Ветка - хронологическая последовательность коммитов. Ветка в Git — это простой перемещаемый указатель на один из коммитов. Ветка в Git — это простой файл, содержащий 40 символов контрольной суммы SHA-1 коммита, на который она указывает
В Git HEAD - это указатель на текущую локальную ветку.
Файлы в проекте могут находиться в закоммиченном, изменном, готовом к комиту состоянии, также - в отслеживаемом и нет состоянии.
Подготовка к коммиту: с помощью git add мы добавляем файлы в индекс, в коммит идут только добавленные в индекс файлы.
Индекс в Git - специальная область, в которой хранятся изменения файлов, готовые к коммиту.
В коммит попадают те изменения, которые были проиндексированы с помощью git add. если после этого в файле были изменения, которые непроиндексированы, то в коммит попадут только проиндексированные изменения. В выводе git status это то, что будет отображаться зеленым цветом. То, что отображается красным - не проиндексировано и в коммит не попадет.
Команды в консоли
git init - создание репозитория в папке. Создастся папка .git - в ней хранится вся информация о репозитории
git add . - проиндексировать все новые файлы в папке. Можно указать имя файла - тогда только он будет добавлен в индекс
git commit -m 'name commit' - создаем снимок состояния - коммит
git commit -am 'name commit' - добавляет сразу и в индекс, и в коммит
git commit -v - в комментарий будет помещена дельта/diff изменений
git status - посмотреть статус файлов, которые ожидают коммита
git status -s - посмотреть статус файлов в более компактном виде
M- модифицированные файлы, которые ожидают коммита??- неотселживаемые файлыA- файлы, добавленные в отслеживаемые
git show - покажет инфу о последнем коммите
git diff - разница между тем, что изменено, но не проиндексировано
git diff --staged или git diff --cached - после обновления индекса перед коммитом можно так посмотреть, какие изменения были в файлах
Откатиться назад
git reset HEAD <file name> - перевести файл в неиндексируемое состояние
git checkout -- <file name> - откатиться к последнему коммиту
git restore <file name> - --\\-
git commit --amend - если вы сделали коммит и поняли, что забыли проиндексировать изменения в файле, который хотели добавить в коммит
Удалить
git rm - удалить файл из индекса и из рабочего каталога
git rm -f удалить файл из индекса если уже проиндексирован
git rm --cached README - удалить из индекса, оставив в рабочей директории. перестать отслеживать изменения в файле
Перемещение
git mv
История
git log - список коммитов в хронологическом порядке
git log -2 - вывести последние 2 коммита
git log -2 -p - по умолчинию выводится только метаинформация, чтобы вывести полную инфу, нужно добавить ключ -p.
git log -2 --stat - вывод статистики по количеству измененных файлов, а также сколько строк было добавлено или удалено
git log --pretty=oneline - вывод коммитов в одну строку. Также можно задать свой собственный формат - подробнее в документации.
git log --pretty=format:"%h %s" --graph - вывод в виде графа
Поиск за определенный период
git log --since=2.week - за какой промежуток времени ищем от настоящего момента
git log --until=1.week - задает дату, от которой надо искать до настоящего времени
поиск по параметрам
git log -SGit -p - найдет все коммиты, в которых добавлялось или удалялось слово Git
git blame file - кто автор строки в файле и в каком коммите она последний раз менялась
Хеш-сумма
У коммита есть хеш - уникальный идентификатор, автор, дата и время и комментарий, написанный автором. На основе алгоритма sha-1. Хеш вычисляется на основе файла или структуры каталога.
Может быть в длинном виде и сокращенном (7-8 первых символов от длинного формата)
Игнорирование
.gitignore
Файл помещается в корень проекта. В нем описываются шаблоны и файлы, которые им удовлетворяют, игнорируются гитом.
-
*.log
- Исключаем все файлы из папки
tmpкроме файлаtest.log. Если указать для исключения папку целиком, то отдельный файл исключить потом нельзяtmp/*.log!tmp/test.log
Например, все файлы с расширением .log и все файлы в папке tmp будут игнорироваться
www.gitignore.io - тут можно автоматически сформировать гитигнор файл
Не рекомендуется хранить
- логи
- пользовательскте файлы
- файлы сред разработки
- внешние библиотеки
- файлы локальной конфигурации (можно создавать пустой файл с раширением .dist, чтобы другой чел мог скачать, убрать расширение, заполнить локальными данными, например для подключения к БД, и пользоваться)
- Файлы ОС
- слишком большие файлы
Отслеживание пустой папки
Git ориентируется на файлы, папки попадают под отслеживание, если только в них находятся файлы, пустые папки — игнорируются.
Чтобы гит отслеживал пустые папки, нужно добавить в корень нужной для отслеживания папки пустой файл .keep
Ветки
HEAD - это указатель на текущую локальную ветку.
Ветка в Git — это простой файл, содержащий 40 символов контрольной суммы SHA-1 коммита, на который она указывает
подробнее занятие 6 про гит у ГБ, вот методичка к этому уроку
git branch - выводит список веток
git branch newbranch - создает новую ветку newbranch, но не переключает указатель HEAD на нее
git checkout newbranch - переключаемся на новую ветку: переключает указатель HEAD на нее
git branch -m newbranch newname - переименование ветки
git branch -D newname - удаление ветки
«fast-forward» - Git просто переместил указатель ветки вперёд, потому что коммит C4, на который указывает слитая ветка hotfix, был прямым потомком коммита C2, на котором вы находились до этого. Другими словами, если коммит сливается с тем, до которого можно добраться, двигаясь по истории вперёд, Git упрощает слияние, просто перенося указатель ветки вперёд, потому что в этом случае нет никаких разнонаправленных изменений, которые нужно было бы свести воедино. Это называется «fast-forward».
Чтобы влить другую ветку в текущую, нужно переключиться на текущую и выполнить git merge <другая ветка>. Таким образом можно влить ветку main в ту, над которой я работаю, если в main произошли изменения, которые мне нужны
Коммит слияния
Вместо того, чтобы просто передвинуть указатель ветки вперёд, Git создаёт новый результирующий снимок трёхстороннего слияния, а затем автоматически делает коммит. Этот особый коммит называют коммитом слияния, так как у него более одного предка.
upstream branch
Получение локальной ветки из удалённой ветки автоматически создаёт то, что называется «веткой слежения» (а ветка, за которой следит локальная называется «upstream branch»). Ветки слежения — это локальные ветки, которые напрямую связаны с удалённой веткой. Если, находясь на ветке слежения, выполнить git pull, то Git уже будет знать с какого сервера получать данные и какую ветку использовать для слияния.
Удаленный GIT репозиторий
https://smartiqa.ru/courses/git/lesson-6 прям очень хорошая статья
урок 7
Для управления подключением удаленных репозиториев в Git предусмотрена целая группа команд – git remote.
git remote -v - посмотреть путь удаленного репозитория, который связан с локальным
Поменять этот путь можно, сперва удалив связку,
git remote remove origin, а затем добавив
git remote add origin path - устанавливает в настройках локального репа путь к удаленному
remote- указывает, что сейчас будем производить работу с настройкой удаленного репаadd- добавляем новую запись в эти настройкиorigin- название удаленного репа по умолчаниюpath- путь к удаленному репу
git push -u origin master
-u- устанавливает связь между локальным и удаленным репом, чтобы в дальнейшем можно было вызывать толькоgit pushи некоторые другие команды без дополнительных параметров- origin - имя удаленного репозитория, которое задали в команде remote add,
master- имя ветки
Если мы внесли локально изменения и локальный реп не обновлен, то при вызове git pull новые изменения локально не затрутся
git pull - автоматически получить изменения из удалённой ветки и слить их со своей текущей, если настроено отслеживание. Выполнение git pull, как правило, извлекает (fetch) данные с сервера, с которого вы изначально клонировали, и автоматически пытается слить (merge) их с кодом, над которым вы в данный момент работаете.
git fetch - полностью синхронит репозиторий с локальной машиной, но не сливает их. Для этого нужно выполнить merge
Удаленные ветки
git branch -r - посмотреть список веток
git branch -m currant_branch_name new_branch_name - переименовать ветку локально. в удаленном репозитории при этом она не переименуется
merge request
В первом модуле скиллбокса второй части рассказывают про создание копии ветки, про создание merge request etc.
Конфиликты версий
простой
Когда изменения произошли в разных файлах
Сперва выполняем git pull, чтобы засинкать изменения
Сложный
При попытке сложного конфиликта надо выполнить git pull и в редакторе отредачить нужным образом код. потом выполнить git add и git commit
git message
git commit -m "puppet_ref: bump" -m $'\n'""$'\n'"Change request #4513 from l2-support/C2OPS-15006 by Evgeniy Nikulin"$'\n'""$'\n'"* logrotate: keep haproxy logs 7 days instead of 52 by Sergey Zakharii"$'\n'""$'\n'"Change request #4510 from iemmanuylov/redos by Ivan Emmanuylov"$'\n'"* files: add RedOS for c2-CA.crt by Ivan Emmanuylov"
Теги tags
Как и большинство других систем контроля версий, Git имеет возможность помечать определённые моменты в истории как важные. Как правило, эта функциональность используется для отметки моментов выпуска версий (v1.0, и т. п.).
Легковесный тег — это что-то очень похожее на ветку, которая не изменяется — просто указатель на определённый коммит. А вот аннотированные теги хранятся в базе данных Git как полноценные объекты. Они имеют контрольную сумму, содержат имя автора, его e-mail и дату создания, имеют комментарий и могут быть подписаны и проверены с помощью GNU Privacy Guard (GPG). Обычно рекомендуется создавать аннотированные теги, чтобы иметь всю перечисленную информацию; но если вы хотите сделать временную метку или по какой-то причине не хотите сохранять остальную информацию, то для этого годятся и легковесные.
git tag
git tag -l "v1.8.5*" - поиск тега по шаблону
git tag -a v1.4 -m "my version 1.4" - добавить аннотированный тег
Синкать с репозиторием нужно в явном виде git push origin main v0.1