SSD Nodes Learn 🎉 VPS от $5.50/мес
Руководства Matt ConnorАвтор: Matt Connor · Обновлено 2026-08-21

Почему nano выдает Permission denied при сохранении

Ошибка сохранения в nano возникает из-за прав доступа, блокировки родительской директории, режима read-only или нехватки места. Проверьте владельца файла и UID в контейнере.

Почему nano не сохраняет файл

nano не сохраняет файл по одной из четырех причин: у вас нет прав владельца на файл, родительский каталог запрещает действия, которые пытается выполнить nano, файловая система смонтирована в режиме «только чтение» или переполнена, либо вы работаете внутри контейнера от имени другого пользователя. Первые две причины связаны с правами доступа, последние две — нет. Проверяйте их именно в этом порядке: первая причина встречается чаще всего, для её подтверждения достаточно одной команды, а для исправления используется sudoedit, а не sudo nano.

Пока редактор открыт, данные не потеряны. Текст находится в оперативной памяти, поэтому вы можете оставить файл открытым, записать буфер по пути, на который у вас есть права, и переместить его на место позже. Этот способ выхода описан ближе к концу данного руководства.

Выполните эти проверки перед изменением прав доступа

Применяйте каждую команду к реальному пути, который вы редактируете. Они отвечают на разные вопросы, поэтому выполните их все, прежде чем что-либо менять. Изменение прав доступа до того, как вы выясните, какая именно проверка не проходит, обычно создает вторую проблему поверх первой.

id
ls -l /etc/nginx/nginx.conf
ls -ld /etc/nginx
namei -l /etc/nginx/nginx.conf
findmnt -no SOURCE,FSTYPE,OPTIONS -T /etc/nginx/nginx.conf
df -h /etc/nginx
df -i /etc/nginx

id выводит идентификатор пользователя и идентификаторы групп, под которыми вы работаете в данный момент. ls -l показывает владельца, группу и биты прав доступа самого файла. ls -ld показывает те же данные для каталога, в котором находится файл; это отдельный вопрос, требующий отдельного ответа. namei -l проходит по каждой части пути и выводит владельца и права доступа для каждого элемента, отвечая на оба вопроса в одном выводе. findmnt указывает файловую систему по данному пути и параметры, с которыми она была смонтирована. df -h сообщает о свободном месте, а df -i сообщает о свободных inode, которые заканчиваются независимо от места на диске. Если эти строки прав доступа вам еще не знакомы, начните с как читать строку прав доступа, которую выводит ls -l.

Причина 1: файл принадлежит root, а вы — нет

Чтение и запись — это разные права доступа, и большинство файлов в /etc доступны для чтения всем пользователям. Именно поэтому nano открывает файл, показывает содержимое и позволяет вводить текст: эти действия не затрагивают диск. Отказ происходит в момент сохранения, когда ядро сравнивает ваш идентификатор пользователя и идентификаторы групп с владельцем, группой и битами прав доступа к файлу. nano лишь передает сообщение, полученное от ядра, поэтому никакие параметры nano не изменят результат.

id и ls -l в совокупности объясняют эту ситуацию. Файл принадлежит пользователю root, вы не являетесь root, а биты прав для остальных пользователей не разрешают запись. Повторное нажатие Ctrl-O не поможет.

Почему sudoedit — правильный способ редактирования файлов, принадлежащих root

SUDO_EDITOR=nano sudoedit /etc/nginx/nginx.conf

Команда sudo создает временную копию файла, устанавливает вас его владельцем, запускает nano для этой копии от вашего имени, а после завершения работы редактора копирует результат обратно на место с привилегиями root. Редактор никогда не запускается от имени root. sudo -e — это та же команда под другим именем. Редактор выбирается из SUDO_EDITOR, затем VISUAL, затем EDITOR, поэтому export EDITOR=nano в профиле вашей оболочки делает его значением по умолчанию везде. Если в вашем файле sudoers отключен флаг env_editor, эти переменные игнорируются, и редактор выбирается из настройки editor в sudoers.

sudo nano также сохраняет файл, и в этом заключается проблема. Он предоставляет полноценному интерактивному редактору привилегии root во всей файловой системе на время сессии, поэтому одна опечатка в пути при сохранении приведет к перезаписи другого системного файла с правами root. Работа в качестве обычного пользователя, который вызывает sudo только для тех шагов, где это необходимо — это полезная привычка, и sudoedit — это то, как эта привычка выглядит в момент редактирования конфигурационного файла.

Два правила sudoedit часто удивляют пользователей. Утилита отказывается редактировать символические ссылки и файлы внутри каталогов, в которые у вас есть права на запись, если вы не являетесь root. Второе правило существует потому, что любой, кто может писать в каталог, способен подменить файл, пока редактор открыт. Оба поведения являются настройками по умолчанию в sudoers (sudoedit_follow выключено, sudoedit_checkdir включено). Если файл еще не существует, он будет создан для вас.

Причина 2: за что на самом деле отвечает родительский каталог

В рекомендациях для других редакторов говорится, что для сохранения файла требуются права на запись в каталог, так как многие редакторы сохраняют изменения, создавая новый файл и переименовывая его поверх старого. nano работает иначе. Он открывает указанный файл и записывает данные непосредственно в него, поэтому для уже существующего файла бит записи каталога не проверяется.

Каталог по-прежнему определяет другие параметры, поэтому ls -ld включен в контрольный список:

  • Для создания файла, которого еще не существует, требуются права на запись и выполнение для каталога, так как в него необходимо добавить новое имя. Ваш umask определяет права, с которыми создается новый файл.
  • Для доступа к файлу необходимо право на выполнение (также называемое правом поиска) для каждого каталога в пути. Отсутствие этого права хотя бы в одном каталоге блокирует доступ ко всему, что находится внутри, а namei -l покажет, в каком именно.
  • Сохранение с созданием резервных копий или с включенной блокировкой файлов приводит к записи второго файла рядом с оригиналом, поэтому эти функции требуют прав на запись в каталог. Резервные копии — это опция -B или set backup в файле nanorc, а блокировка — это -G или set locking. Обе функции отключены, если только вы или ваш дистрибутив не включили их принудительно.

Права на каталоги имеют такое же значение и в других частях системы. SSH-сервер отклоняет ключ, если ваш домашний каталог или каталог .ssh доступны для записи другим пользователям; это распространенная причина того, что SSH отклоняет ваш ключ при входе.

Поскольку nano записывает данные в уже существующий файл, файл сохраняет свой inode — идентификатор на диске, стоящий за именем файла. Любой процесс, удерживающий файл открытым, продолжает отслеживать его, а файл, примонтированный через bind mount в контейнер, продолжает работать. Редакторы, которые сохраняют изменения путем замены файла, разрывают такое монтирование, так как монтирование привязано к inode, а не к имени.

Причина 3: файловая система доступна только для чтения или переполнена

findmnt отчет ro в параметрах означает, что операция записи заведомо обречена на провал. Либо файловая система была смонтирована таким образом через /etc/fstab или bind-mount в режиме только для чтения, либо ядро перевело её в этот режим после ошибки диска. Второй случай — критический. sudo dmesg -T | tail -50 показывает ошибки ввода-вывода и файловой системы, которые привели к перемонтированию; исправление требует проверки файловой системы в размонтированном состоянии, что на VPS означает загрузку в rescue-консоли провайдера.

Переполненная файловая система блокирует запись по другой причине. df -h описывает обычный случай. df -i охватывает ситуацию, которую часто упускают: иноды берутся из фиксированного пула, созданного при разметке диска, и дерево из множества мелких файлов может исчерпать их все, даже если df -h показывает наличие свободных гигабайт. Когда место закончилось, а очевидных причин нет, расхождения в выводе df и du при переполнении диска объясняют проблему удаленных, но все еще открытых файлов.

Одна деталь объясняет здесь запутанный симптом. При создании файловой системы ext4 резервирует часть блоков для пользователя root, поэтому root может продолжать запись после того, как обычным пользователям отказано в доступе. sudo в таком случае кажется решением, но диск быстро заполняется до конца, и проблема возвращается в более острой форме.

Поскольку nano усекает файл перед записью нового содержимого, прерывание записи из-за нехватки места может привести к тому, что файл станет короче, чем был. Копируйте важные конфигурационные файлы перед редактированием, если файловая система почти заполнена. sudo cp -a /etc/nginx/nginx.conf /root/nginx.conf.bak сохраняет владельца, группу и права доступа при копировании.

Причина 4: вы редактируете bind mount внутри контейнера

Владение файлом определяется числовым идентификатором. Ядро хранит ID пользователя, а имя, которое вы видите, зависит от того, какой /etc/passwd выполняет поиск. Поэтому один и тот же файл может отображаться под разными именами или просто числом на хосте и внутри контейнера. Сравнивайте числовые значения, а не имена: выполните id -u внутри контейнера и ls -ln для файла.

Файл, подключенный через bind mount, сохраняет владельца, который был у него на хосте. Если файл на хосте принадлежит вашему пользователю, а процесс в контейнере запущен от имени другого пользователя, запись внутри контейнера будет запрещена, а sudo внутри контейнера не изменит владельца на хосте. Исправьте это на хосте, установив владельца с тем же ID, от имени которого работает контейнер, либо запустите контейнер от имени пользователя, который уже владеет этими файлами. Образы от linuxserver.io и аналогичных проектов предоставляют переменные PUID и PGID, которые задают пользователя, от имени которого выполняется процесс.

Стоит знать еще о двух случаях с контейнерами. Монтирование в режиме только для чтения с помощью :ro или запуск контейнера с флагом --read-only запрещает запись независимо от прав владения, а cat /proc/mounts внутри контейнера покажет соответствующий флаг. При использовании rootless Podman пространство имен пользователей (user namespace) отображает ID пользователей контейнера на диапазон ID хоста, поэтому файл, который внутри контейнера выглядит принадлежащим root, снаружи принадлежит вашей непривилегированной учетной записи.

Также возможна ситуация, когда редактирование проходит успешно, но изменения исчезают. Файл, который вы изменяете внутри контейнера по пути, не являющемуся точкой монтирования, сохраняется в записываемом слое этого контейнера, и этот слой удаляется при пересоздании контейнера. Изменяйте файл на стороне хоста в точке монтирования или при сборке образа, если изменения должны быть постоянными.

Аварийный выход: сохранение в доступный вам путь

Не пытайтесь получить привилегии изнутри редактора. Нажмите Ctrl-O, очистите путь в строке приглашения, введите путь в вашей домашней директории, например /home/you/nginx.conf.new, и нажмите Enter. Затем нажмите Ctrl-X для выхода. Теперь ваша работа сохранена на диске, принадлежит вам, а дальнейшие действия сводятся к обычному копированию файла.

sudo cp /home/you/nginx.conf.new /etc/nginx/nginx.conf
sudo nginx -t

Используйте cp вместо mv. cp выполняет запись поверх существующего файла, поэтому файл сохраняет своего владельца, группу и права доступа. mv в пределах одной файловой системы заменяет файл вашим, из-за чего конфигурация в /etc переходит в собственность вашей учетной записи, что создает новую проблему с правами доступа, которую вам придется решать.

Перед перезагрузкой чего-либо проверьте результат с помощью инструмента, отвечающего за данный файл. sudo nginx -t проверяет конфигурацию nginx, а sudo sshd -t проверяет конфигурацию SSH-сервера. Для двух файлов существуют специализированные редакторы, которые выполняют всю эту процедуру за вас: sudo visudo для /etc/sudoers и crontab -e для ваших cron-заданий. Каждый из них редактирует временную копию, проверяет синтаксис и устанавливает файл только в том случае, если он прошел проверку.

FAQ

Стоит ли использовать sudo nano или sudoedit для редактирования системного файла?

Используйте sudoedit. Эта команда копирует файл во временную копию, принадлежащую вам, запускает редактор от имени вашего пользователя и записывает результат обратно с правами root после закрытия редактора. Таким образом, сам редактор никогда не получает привилегий суперпользователя. Установите SUDO_EDITOR, VISUAL или EDITOR в значение nano, чтобы выбрать nano. sudo nano также работает, но этот способ предоставляет интерактивному редактору доступ с правами root ко всем путям в системе на время сеанса. Это означает, что одна опечатка в имени файла при сохранении может привести к повреждению системного файла.

Нужны ли права на запись в директорию для сохранения файла в nano?

Нет, если файл уже существует. nano записывает данные непосредственно в файл, поэтому ядро проверяет бит записи у самого файла и бит выполнения у всех директорий в пути. Бит записи директории важен, если файл ещё не создан, так как необходимо создать новое имя, а также при включённых резервных копиях или блокировке файлов, поскольку в этих случаях создаётся второй файл рядом с исходным.

Владелец указан верно, и диск не переполнен. Что ещё может блокировать запись?

Четыре причины. Файловая система может быть смонтирована в режиме только для чтения, что показывает findmnt -no OPTIONS -T /etc/nginx/nginx.conf. На файле может быть установлен атрибут неизменяемости (immutable), который показывает lsattr и снимает sudo chattr -i; пока этот атрибут установлен, даже root не может изменить файл. Пул инодов может быть исчерпан, несмотря на наличие свободного места, что показывает df -i. SELinux или AppArmor могут запретить запись, даже если биты разрешений позволяют её; в таком случае аудит-лог зафиксирует отказ для указанного пути.

Куда внести изменения, если файл совсем не сохраняется?

Нажмите Ctrl-O и укажите путь, на который у вас есть права — в вашей домашней директории или в любом другом месте, доступном для записи вашему пользователю. Буфер всё ещё находится в памяти, поэтому набранный текст не будет потерян. После этого скопируйте сохранённый файл на место с помощью sudo cp, что сохранит владельца и права исходного файла, а затем проверьте его с помощью встроенной команды тестирования сервиса перед его перезагрузкой.

Почему мои правки внутри Docker контейнера исчезают?

Если путь не является точкой монтирования, правки попадают в записываемый слой контейнера, который удаляется при замене контейнера. Редактируйте файл на стороне хоста через bind mount или volume, либо включите его в образ. Если путь является bind mount и в сохранении отказано, сравните id -u внутри контейнера с числовым идентификатором владельца из ls -ln: файл сохраняет владельца с хоста, и процесс внутри контейнера должен соответствовать ему.