Сквозной проект: настройка Mac как у профи + куда расти

Рейтинг: 74.1% · 11 голосов
Подробный курс по macOS для разработчиков и админов: архитектура и Apple Silicon, терминал и zsh, Homebrew и пакеты, launchd и автоматизация, APFS и Time Machine, безопасность (SIP, Gatekeeper, TCC, FileVault), сеть, логи и диагностика, MDM и DDM, контейнеры и виртуализация, восстановление. По официальной документации Apple, актуально на 2026 (macOS 26 Tahoe).
Ответить
Аватара пользователя
Artem_MacAdmin
Сообщения: 47
Зарегистрирован: 11 май 2026, 05:31

Сквозной проект: настройка Mac как у профи + куда расти

Сообщение Artem_MacAdmin »

Оглавление курса (47)
  1. Что такое macOS: Unix под капотом и место в 2026
  2. Архитектура macOS: XNU, тома и Signed System Volume
  3. Apple Silicon: ARM, Rosetta 2 и отличия от Intel
  4. Установка, обновление и восстановление macOS
  5. Finder, рабочий стол и продуктивность
  6. Системные настройки и их управление из CLI (defaults)
  7. Пользователи и группы: учётные записи и управление
  8. Терминал и zsh: командная строка macOS
  9. CLI на macOS: BSD-команды и отличия от Linux
  10. Настройка zsh: .zshrc, prompt, плагины
  11. Файловая система и права: POSIX, ACL, атрибуты, флаги
  12. Homebrew: пакетный менеджер для macOS
  13. Homebrew глубже: tap, Brewfile, services, обслуживание
  14. Другие пакеты: MacPorts, mas, Nix и App Store
  15. Установка приложений: .app, .dmg, .pkg и Gatekeeper
  16. Управление приложениями и их данные
  17. launchd и launchctl: система запуска macOS
  18. Свои службы и периодические задачи на launchd
  19. Автоматизация: Shortcuts, AppleScript и osascript
  20. Конфигурация как код: defaults, plist и профили
  21. APFS: снапшоты, клоны, контейнеры и шифрование
  22. Управление дисками: diskutil, образы и форматирование
  23. Time Machine и резервное копирование
  24. Внешние диски, форматы и сетевые тома
  25. Модель безопасности macOS: SIP и целостность системы
  26. Gatekeeper, нотаризация и защита от вредоносов
  27. Приватность и TCC: разрешения на доступ
  28. FileVault: полнодисковое шифрование
  29. Связка ключей и управление секретами
  30. Сетевой экран и защита сети
  31. Сеть в macOS: настройка и инструменты
  32. Диагностика сети на Mac
  33. Общий доступ: SSH, экран, файлы, удалённое управление
  34. Процессы и ресурсы: мониторинг производительности
  35. Логи macOS: unified logging и диагностика
  36. Производительность и энергия: powermetrics, диагностика
  37. Энергия, сон и обслуживание системы
  38. Профили конфигурации и основы MDM
  39. Управление парком Mac: MDM, DDM и zero-touch (2026)
  40. Среда разработчика на Mac: Xcode CLT, git, версии
  41. Контейнеры на Mac: Docker Desktop, OrbStack, Apple container
  42. Виртуализация: Virtualization.framework, UTM, Linux и Windows
  43. Режимы загрузки и восстановление (Apple Silicon)
  44. Сброс, NVRAM, Safe Mode и сброс настроек
  45. Траблшутинг macOS: дерево решений по симптомам
  46. Место на диске и обслуживание системы
  47. Сквозной проект: настройка Mac как у профи + куда расти (вы здесь)
Боль, которую закрываем

Достал из коробки новый Mac на Apple Silicon. Дальше два часа кликов: поставить браузер, накатить терминал, прикрутить шрифт, вспомнить как включался FileVault, скопировать ssh-ключи с флешки, по памяти проставить десяток defaults write, чтобы Finder показывал скрытые файлы и не плодил .DS_Store на сетевых шарах. Через год переезд на новую машину - и весь этот ритуал заново, но половину команд ты уже забыл.

Профи так не делает. У него настройка mac - это репозиторий. Один прогон скрипта превращает чистую систему в полностью рабочую среду: софт, конфиги, ключи, безопасность. Это финальный урок, и мы собираем всё, что прошли в курсе, в один воспроизводимый bootstrap. Идея простая: машина должна быть одноразовой. Сломалась, потерялась, выдали новую - не жалко, потому что состояние живёт в git, а не в голове.

В этом уроке мы построим скелет такого проекта: dotfiles в git, Homebrew плюс Brewfile (весь софт одной командой), скрипт системных настроек через defaults, zsh с человеческим prompt, ключи SSH и GPG, среда разработки (CLT и mise), базовая безопасность (FileVault, файрвол, проверка TCC). И, главное, идемпотентный скрипт-обёртка - почти как Ansible, только для одного Mac. В конце - карта роста до ACSP и вход в комьюнити Mac-админов.

Изображение

Архитектура bootstrap: что есть что

Разложим проект на слои. Каждый слой - отдельный кусок, который можно прогнать в отрыве от других.
  • dotfiles - твои .zshrc, .gitconfig, .ssh/config, конфиги редактора. Лежат в git-репозитории, в систему попадают через симлинки.
  • Brewfile - декларативный список всего софта: формулы (CLI), каски (.app), Mac App Store приложения через mas, шрифты.
  • defaults-скрипт - системные и приложенческие настройки через команду defaults write.
  • secrets - SSH/GPG-ключи. В репозиторий не коммитятся, восстанавливаются отдельно (1Password, зашифрованный бэкап, аппаратный ключ).
  • bootstrap.sh - дирижёр, который вызывает всё перечисленное в правильном порядке и делает это идемпотентно.
Ключевое слово - идемпотентность. Скрипт можно запускать сколько угодно раз, и результат один и тот же: если симлинк уже стоит - не дублируем, если пакет стоит - brew его пропускает, если defaults уже выставлен - перезапись тем же значением безвредна. Это и отличает bootstrap от одноразовой простыни команд. Запустил на новой машине - получил полную настройку. Запустил через полгода на рабочей - подтянулись изменения, ничего не сломалось.

Почему именно симлинки, а не копирование? Потому что правишь .zshrc прямо в репозитории (он у тебя под версионным контролем), а в домашней папке лежит ссылка на него. Поправил - сразу видно в git diff, закоммитил, на других машинах подтянул git pull. Копия бы разъехалась с источником на первой же правке.

Слой 1. Dotfiles в git

Создаём репозиторий и кладём туда конфиги. Структура обычно такая:

Код: Выделить всё

~/dotfiles/
  Brewfile
  zsh/.zshrc
  git/.gitconfig
  ssh/config
  macos/defaults.sh
  bootstrap.sh
Сам линковщик - десяток строк на zsh. Главное тут - флаги ln. На BSD (а macOS это BSD, не GNU/Linux) поведение ln отличается от линуксового, и есть грабли с -f при работе с директориями. Безопасный вариант для файлов:

Код: Выделить всё

#!/bin/zsh
set -euo pipefail
DOTFILES="$HOME/dotfiles"

link() {
  local src="$1" dst="$2"
  if [[ -L "$dst" ]]; then
    rm "$dst"                 # снимаем старый симлинк
  elif [[ -e "$dst" ]]; then
    mv "$dst" "$dst.bak"      # реальный файл - в бэкап, не теряем
  fi
  ln -s "$src" "$dst"
  print "linked: $dst -> $src"
}

link "$DOTFILES/zsh/.zshrc"      "$HOME/.zshrc"
link "$DOTFILES/git/.gitconfig"  "$HOME/.gitconfig"
Разберём логику. Если по целевому пути уже симлинк (-L) - удаляем и ставим заново, это и даёт идемпотентность. Если там реальный файл (-e, но не -L) - не затираем молча, а уносим в .bak. Команда set -euo pipefail - страховка: -e валит скрипт на первой ошибке, -u ловит опечатки в именах переменных, pipefail не даёт ошибке в середине пайпа потеряться. Без этого bootstrap может тихо отработать наполовину, и ты узнаешь об этом в самый неудобный момент.

Слой 2. Homebrew и brew bundle - весь софт одной командой

На Apple Silicon Homebrew живёт в /opt/homebrew (на старых Intel был /usr/local). Это важно для PATH и для скриптов, которые ищут brew. Сначала ставим сам менеджер и активируем его в текущей сессии:

Код: Выделить всё

/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
eval "$(/opt/homebrew/bin/brew shellenv)"
Дальше - сердце автоматизации софта, brew bundle. Это встроенная в Homebrew подкоманда (раньше тап, теперь часть ядра), которая читает декларативный Brewfile и приводит систему к описанному состоянию. Снять текущий снимок установленного добра можно так:

Код: Выделить всё

brew bundle dump --file=~/dotfiles/Brewfile --force
Флаг --force перезапишет существующий файл, --file задаёт путь. Получишь что-то вроде:

Код: Выделить всё

tap "homebrew/bundle"
brew "git"
brew "mise"
brew "ripgrep"
cask "iterm2"
cask "visual-studio-code"
cask "font-jetbrains-mono-nerd-font"
mas "Xcode", id: 497799835
Тут brew - это CLI-формула, cask - графическое .app, mas - приложение из Mac App Store (нужна отдельная утилита mas и логин в App Store). Теперь на любой новой машине весь этот список ставится одной командой:

Код: Выделить всё

brew bundle install --file=~/dotfiles/Brewfile
И вот тут идемпотентность работает из коробки: brew bundle ставит только то, чего нет, остальное пропускает. Прогнал второй раз - почти мгновенно, потому что ставить нечего. Проверить, всё ли на месте, не устанавливая, можно так:

Код: Выделить всё

brew bundle check --file=~/dotfiles/Brewfile
Вывод в стиле The Brewfile's dependencies are satisfied или список того, чего не хватает. А если хочешь, чтобы машина строго соответствовала файлу и лишний софт удалялся - есть cleanup (осторожно, он сносит то, чего нет в Brewfile):

Код: Выделить всё

brew bundle cleanup --force --file=~/dotfiles/Brewfile
Это превращает Brewfile в источник истины: что в файле - то и в системе, ни больше ни меньше. Для mac для разработчика это золото: добавил строчку, закоммитил, на всех машинах прогнал bundle - софт синхронизирован.

Слой 3. Системные настройки через defaults write

Графические тумблеры в Системных настройках (System Settings, не старые Preferences) под капотом пишут в plist-домены. Команда defaults даёт прямой доступ к ним - значит, настройку можно заскриптовать. Несколько рабочих примеров с разбором:

Код: Выделить всё

# показывать расширения файлов всегда
defaults write NSGlobalDomain AppleShowAllExtensions -bool true

# не плодить .DS_Store на сетевых и USB-томах
defaults write com.apple.desktopservices DSDontWriteNetworkStores -bool true
defaults write com.apple.desktopservices DSDontWriteUSBStores -bool true

# Finder: строка пути и полный путь в заголовке
defaults write com.apple.finder ShowPathbar -bool true
defaults write com.apple.finder _FXShowPosixPathInTitle -bool true

# скриншоты в ~/Screenshots, формат png
mkdir -p "$HOME/Screenshots"
defaults write com.apple.screencapture location -string "$HOME/Screenshots"
defaults write com.apple.screencapture type -string "png"
Что тут важно понимать. Первый аргумент - домен (NSGlobalDomain - глобальный, или bundle id приложения вроде com.apple.finder). Дальше ключ, тип (-bool, -string, -int, -float) и значение. Тип указывать обязательно - если запишешь true как строку вместо булева, приложение настройку не поймёт. Прочитать текущее значение - defaults read com.apple.finder ShowPathbar, узнать тип - defaults read-type.

Грабли номер один: многие демоны кешируют настройки и не перечитывают plist на лету. После пачки defaults write надо пнуть процессы, иначе будешь думать, что команда не сработала:

Код: Выделить всё

killall Finder
killall Dock
killall SystemUIServer
Грабли номер два: на свежих macOS часть доменов под защитой TCC и SIP, и запись в них требует прав или вообще игнорируется из скрипта. Не всё, что работало в 2018-м, пишется так же в 2026-м на macOS 26 Tahoe. Поэтому правило: каждую строку defaults проверяй на своей версии руками, а не копируй гайды десятилетней давности пачкой.

Слой 4. Среда разработки: CLT, mise, zsh и prompt

Базовый компилятор и git тянет за собой Command Line Tools. Их можно поставить отдельно от полного Xcode:

Код: Выделить всё

xcode-select --install
Дальше - менеджер версий рантаймов. Раньше у каждого языка был свой (nvm, rbenv, pyenv), теперь де-факто стандарт - mise (бывший rtx, идейный наследник asdf, но быстрее и без шимов). Один инструмент ставит и переключает node, python, ruby, go - по версии из mise.toml в каждом проекте. Активируется в zsh строкой в .zshrc:

Код: Выделить всё

# в ~/.zshrc
eval "$(mise activate zsh)"
И дальше прямо в проекте:

Код: Выделить всё

mise use node@22
mise use python@3.13
mise install
Команда mise use пишет версию в локальный mise.toml и ставит её, mise install подтягивает всё описанное. Зашёл в каталог проекта - mise молча подменил версии под него, вышел - вернул глобальные. Список доступных версий - mise ls-remote node.

Prompt. zsh - дефолтная оболочка macOS с Catalina, так что bash-овые гайды не всегда подходят. Минимальный вменяемый prompt с веткой git без тяжёлых фреймворков:

Код: Выделить всё

# в ~/.zshrc
autoload -Uz vcs_info
precmd() { vcs_info }
zstyle ':vcs_info:git:*' formats ' (%b)'
setopt PROMPT_SUBST
PROMPT='%F{cyan}%~%f%F{yellow}${vcs_info_msg_0_}%f %# '
Это родной механизм zsh: vcs_info собирает имя ветки перед каждым приглашением, PROMPT_SUBST разрешает подстановку. Хочешь красивее и из коробки - ставь starship одной строкой в Brewfile, тоже кроссплатформенно и быстро.

Слой 5. Ключи SSH/GPG и базовая безопасность

Ключи в git коммитить нельзя - это слой secrets, он восстанавливается отдельно. Генерация современного ssh-ключа:

Код: Выделить всё

ssh-keygen -t ed25519 -C "you@example.com"
ed25519 короче и безопаснее старого RSA. На Mac приватный ключ удобно держать в Keychain, чтобы не вводить пароль каждый раз. В ~/.ssh/config:

Код: Выделить всё

Host *
  AddKeysToAgent yes
  UseKeychain yes
  IdentityFile ~/.ssh/id_ed25519
UseKeychain - это macOS-специфика, на Linux такого нет. Добавить ключ в агент с сохранением пароля в Связке ключей:

Код: Выделить всё

ssh-add --apple-use-keychain ~/.ssh/id_ed25519
Теперь безопасность - четыре проверки, которые на рабочей машине обязаны быть зелёными.

FileVault. Шифрование диска. Статус:

Код: Выделить всё

fdesetup status
Ответ FileVault is On. - то, что нужно. Включать FileVault из скрипта через fdesetup enable с передачей логина и пароля в современных macOS не делай: этот режим помечен deprecated и требует, чтобы вызывающее приложение имело Full Disk Access в Системных настройках -> Конфиденциальность и безопасность. В реальном парке FileVault включают через MDM с эскроу ключа восстановления, а на личной машине - руками тумблером, это надёжнее.

Файрвол приложений (фильтр входящих по приложениям, application firewall):

Код: Выделить всё

/usr/libexec/ApplicationFirewall/socketfilterfw --getglobalstate
Покажет Firewall is enabled. или disabled. Включение требует sudo. На современных macOS файрвол тоже всё чаще удобнее тумблером в Системных настройках -> Сеть -> Файрвол - часть флагов socketfilterfw менялась между версиями, так что состояние читай командой, а решение принимай осознанно.

SIP (System Integrity Protection) - защита системных томов. Должна быть включена:

Код: Выделить всё

csrutil status
Ждём System Integrity Protection status: enabled. Если disabled - кто-то ходил в Recovery и отключал, на рабочей машине это красный флаг.

TCC (Transparency, Consent, and Control) - подсистема приватности, та самая, что спрашивает доступ к камере, микрофону, диску, экрану. Сбросить разрешения конкретной службы (например, если приложение залипло в неправильном состоянии):

Код: Выделить всё

tccutil reset Camera com.example.app
tccutil reset All com.example.app
База TCC напрямую не редактируется - она под SIP, и это by design. Управляешь через системный диалог или, в парке, через MDM-профиль PPPC. Это важный момент гигиены: bootstrap не должен пытаться силой пробить TCC, он должен оставить чистое состояние, а доступы пользователь выдаёт осознанно при первом запуске приложений.

Слой 6. Дирижёр bootstrap.sh - Ansible для одного Mac

Собираем всё в один идемпотентный вход. Логика - последовательность шагов, каждый безопасен при повторе:

Код: Выделить всё

#!/bin/zsh
set -euo pipefail

# 1. Homebrew
if ! command -v brew >/dev/null 2>&1; then
  /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
fi
eval "$(/opt/homebrew/bin/brew shellenv)"

# 2. софт из Brewfile
brew bundle install --file="$HOME/dotfiles/Brewfile"

# 3. симлинки конфигов
"$HOME/dotfiles/link.sh"

# 4. системные настройки
"$HOME/dotfiles/macos/defaults.sh"

# 5. проверка безопасности (только репорт, без насилия)
print "== security =="
fdesetup status
csrutil status
Это и есть подход как у Ansible: декларативное желаемое состояние плюс шаги, безопасные при повторном прогоне. command -v brew проверяет, стоит ли уже Homebrew, и не ставит второй раз. brew bundle сам идемпотентен. link.sh не дублирует симлинки. defaults.sh перезаписывает теми же значениями. Финал - не молчаливое включение защиты, а отчёт: видишь статус и решаешь сам. Один скрипт - вся настройка mac воспроизводима.

Чек-лист готовности рабочей машины
  • FileVault On (fdesetup status)
  • SIP enabled (csrutil status)
  • Файрвол приложений включён (socketfilterfw --getglobalstate)
  • Автообновления macOS включены
  • Brewfile в git, brew bundle check проходит
  • dotfiles в git, симлинки на месте
  • ssh-ключ ed25519, в Связке ключей, добавлен на GitHub/GitLab
  • CLT стоят (xcode-select -p отвечает)
  • Резервная копия (Time Machine или иной бэкап) настроена
  • Ключ восстановления FileVault сохранён в надёжном месте (не на том же диске)
Типичные грабли
  • Секреты в git. Закоммитил .ssh с приватным ключом в публичный репо - всё, ключ скомпрометирован, перевыпускай. Держи secrets отдельным слоем, в .gitignore - .ssh, .gnupg, .env.
  • defaults без killall. Команда отработала, а изменений не видно - демон не перечитал plist. Пни Finder/Dock/SystemUIServer.
  • Неверный тип в defaults write. Записал -string "true" вместо -bool true - настройка молча игнорируется.
  • Жёсткий fdesetup enable из скрипта. Deprecated и требует Full Disk Access. На парке - MDM, на личной - тумблер.
  • ln -sf на каталог. BSD-ln при -f на существующий каталог создаст симлинк внутри него, а не заменит - получишь вложенность. Снимай старый симлинк явно через rm.
  • Путь /usr/local вместо /opt/homebrew. Перенёс скрипт с Intel на Apple Silicon и забыл - brew не находится. Используй brew shellenv, не хардкодь путь.
Мини-лаба: собери свой bootstrap
  • Создай git-репозиторий ~/dotfiles, добавь в .gitignore секреты.
  • Сними снимок текущего софта: brew bundle dump --file=~/dotfiles/Brewfile --force. Открой файл, удали лишнее, оставь только нужное.
  • Положи .zshrc в ~/dotfiles/zsh/, напиши link.sh по примеру выше, прогони. Проверь, что в $HOME появился симлинк (ls -la ~/.zshrc).
  • Напиши macos/defaults.sh с тремя настройками, запусти, не забудь killall Finder. Убедись глазами, что изменилось.
  • Сгенерируй ed25519-ключ, пропиши UseKeychain в ~/.ssh/config, добавь ключ через ssh-add --apple-use-keychain.
  • Прогони весь bootstrap.sh дважды подряд. Второй прогон не должен ничего ломать и должен отработать быстро - это и есть проверка идемпотентности.
  • Закоммить и запушь. Теперь твоя машина воспроизводима.
Карта роста: куда двигаться дальше

Курс закончен, но Mac-администрирование - это глубокий колодец. Куда расти:
  • Сертификация ACSP (Apple Certified Support Professional). Подтверждает умение развернуть, настроить и продиагностировать macOS и сервисы Apple для пользователей. По состоянию на 2025 экзамен опирается на актуальные macOS/iOS/iPadOS, целевая аудитория - специалисты поддержки, техкоординаторы, продвинутые пользователи. Готовишься по гайду Apple, сдаёшь экзамен, получаешь цифровой бейдж. Хороший внешний маркер, что ты не просто кликер.
  • Управление парком. Один Mac ты теперь настраиваешь скриптом. Сотню - через MDM. Учи Jamf Pro (стандарт индустрии) или открытые стеки, осваивай DDM (Declarative Device Management) - в 2026 это магистральное направление MDM, устройство само поддерживает заданное состояние без постоянного опроса сервером. Профили конфигурации, PPPC для TCC, эскроу ключей FileVault - всё это масштаб парка.
  • Скриптинг и автоматизация. zsh и bash ты уже трогал. Дальше - выпуск пакетов (pkgbuild, productbuild), подпись и нотаризация, упаковка софта для тихой раскатки, launchd для фоновых служб вместо cron.
  • Сообщество MacAdmins. Главная точка входа - MacAdmins Slack (тысячи инженеров, каналы по Jamf, munki, packaging, security). Плюс осенние конференции (MacAdmins Conference в Penn State, MacSysAdmin, локальные митапы). Там живёт практика, которой нет в документации, и там быстрее всего догоняешь изменения каждой новой macOS.
Итог курса

Мы прошли путь от файловой системы APFS и устройства томов, через терминал, launchd, права POSIX/ACL/xattr, сеть, Homebrew, безопасность (FileVault, SIP, Gatekeeper, TCC) - и сошлись здесь, в одном bootstrap-проекте, где всё это работает вместе. Главная мысль курса: Mac - это не набор кнопок, а Unix-система с прозрачной механикой, которой можно управлять кодом. Машина одноразовая, состояние в git, настройка - команда, а не ритуал. Дальше - ACSP, парк, комьюнити. Открывай терминал и собирай свой dotfiles-репозиторий прямо сейчас, пока тёплая память от курса не остыла.
👍4 ❤️1 🔥1 😄 🤔2
Аватара пользователя
elasticmain
Сообщения: 1
Зарегистрирован: 31 май 2026, 00:21

Re: Сквозной проект: настройка Mac как у профи + куда расти

Сообщение elasticmain »

Прогнал bootstrap дважды как в лабе, второй раз brew bundle отработал за секунду - вот теперь понял что значит идемпотентность на практике, спасибо. Раньше реально каждую новую машину руками два часа ковырял.
👍1 ❤️1 🔥1 😄 🤔
Аватара пользователя
pandas42
Сообщения: 1
Зарегистрирован: 13 май 2026, 08:25

Re: Сквозной проект: настройка Mac как у профи + куда расти

Сообщение pandas42 »

А fdesetup enable из скрипта реально не стоит? У меня на парке через Jamf эскроу ключа настроен, а на личной думал заскриптовать. Понял, оставлю тумблером, тем более про Full Disk Access не знал - спасибо что предупредили.
👍1 ❤️1 🔥1 😄 🤔
Ответить
← Предыдущая глава
Место на диске и обслуживание системы

Все главы курса «macOS для профи: администрирование, терминал и Homebrew»

Поделиться темой: ✈ Telegram VK
Похожие запросы: Восстановление macOS

Вернуться в «macOS для профи: администрирование, терминал и Homebrew»

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и 1 гость