Записать файл в каталог etc в mac os x

Я пытаюсь записать файл в папку /etc в Mac OS X.

[[textView string] writeToFile:@"/etc/info.txt" atomically:YES encoding:NSUnicodeStringEncoding error:&error];

Выдает ошибку, что у меня нет прав на запись туда (естественно), но я не понимаю, как получить разрешение на запись в системные папки.

Также может кто-нибудь привести простой пример?

Пожалуйста помоги. Спасибо.


person MeIr    schedule 29.07.2011    source источник


Ответы (5)


Утверждение «вы никогда не должны писать в папку /etc/» недействительно.

Конечно, есть много веских причин для записи в системные папки - если вы пишете корпоративное программное обеспечение, которое настраивает вещи для пользователей, чтобы пользователям не нужно было делать это вручную. Это требуется многими корпорациями даже для утверждения компьютеров Mac в качестве рабочих компьютеров. Обычно это делается с помощью сценариев оболочки или языков высокого уровня (таких как Python или Ruby), но для удобства использования конечным пользователем было бы необходимо, чтобы приложения пользовательского интерфейса также могли читать и записывать изменения в системные папки (например, в папку, принадлежащую конфигурации). система управления).

Я профессионально пишу программное обеспечение, которое должно постоянно записывать в системные папки, изменять содержимое файлов конфигурации и т. д. в папках, требующих привилегий суперпользователя. У меня не было 100% успеха в этом, так как MacOSX была сделана слишком недружественной для этого (корпоративное программное обеспечение для внутреннего корпоративного использования) случая использования, и подход, который я использую, кажется, иногда не работает. В итоге я открыл диалоговое окно запроса пароля администратора с помощью объекта Apple Script. Это отстой, но сработало для моего основного варианта использования:

 NSString *shellCommand = [[NSString alloc] initWithFormat:@"do shell script \"/bin/bash /usr/bin/nameoftheshellscriptgoeshere.sh\" with administrator privileges"];

 NSAppleScript *script;

 script = [[NSAppleScript alloc] initWithSource:shellCommand];

 NSDictionary* errDict = NULL;

 [script executeAndReturnError:&errDict];

Если ваш установщик поместил сценарий оболочки nameoftheshellscriptgoeshere.sh (или любое другое имя, которое вы ему дали) в /usr/bin, вы можете творить чудеса в сценарии оболочки.

Этот подход работает только в том случае, если администрирование можно выполнить с помощью сценария оболочки. Существует обходной путь, но на самом деле он не очень красивый: необходимость записи файлов конфигурации в системный каталог с приложением Objective-C, использование которого вызывает очень утомительный цикл: вы создаете измененный файл конфигурации в папке, доступной для записи Cocoa. приложение, а затем это приложение выполняет Apple Script, который выполняет однострочный сценарий оболочки, который копирует этот временный файл конфигурации в правильное место в системной папке, требуя привилегий root. Это очень неоптимально и неуклюже и вводит зависимость от указанного сценария оболочки - другими словами, приложение пользовательского интерфейса будет работать со сбоями, если сценарий оболочки не установлен в системе. И множество ненужных отдельных частей, которые нужно поддерживать только по одной-единственной причине: повышение привилегий приложения Cocoa сложно или невозможно, а корпоративное программное обеспечение, по-видимому, не было точкой проектирования при разработке OSX.

person karoliina    schedule 20.08.2012

Для записи в /etc/ потребуется доступ на уровне root. Вам нужно будет запросить у пользователя его пароль, а затем запустить соответствующий вспомогательный инструмент и т. д., чтобы написать за вас.

См. документацию по Задачи службы авторизации. .

В общем, вам не следует никогда и ни по какой причине не писать в /etc/. Это каталог, принадлежащий системе и контролируемый ею. Конечно, учитывая Unix-основу ОС, есть вещи, которые можно сделать, сделав это, но только в крайнем случае.

person bbum    schedule 29.07.2011
comment
Можно ли получить простой пример кода для авторизованного редактирования файла? - person MeIr; 31.07.2011
comment
Не совсем - в документах есть ссылки на пример кода, IIRC. Или выполните поиск по содержащемуся в нем API. Это трудно. И, тем не менее, почему вы пишете в /etc/? - person bbum; 31.07.2011
comment
Мне нужно время от времени обновлять там пару файлов. - person MeIr; 31.07.2011
comment
Какие файлы? Почему? Запись в /etc явно запрещена. - person bbum; 31.07.2011
comment
Суть в том, что мне нужно иметь возможность записывать файлы и устанавливать разрешения для файлов в /etc/. Я могу написать все это в сценарии bash, но я хочу сделать небольшое приложение для рутины. Я знаю все проблемы, связанные с записью в /etc, и это не концерт этой темы. Я просто хочу знать, как авторизовать мой код для записи в /etc/. - person MeIr; 31.07.2011
comment
Проголосовали против, автор спрашивает, как что-то сделать, а не о том, хорошо ли это делать. - person alex; 05.08.2011
comment
И я рассказал им, как именно это сделать. Прочтите окончательные документы и используйте приведенные в них примеры. - person bbum; 05.08.2011
comment
Мне бы очень хотелось увидеть какой-нибудь простой пример/решение проблемы. - person MeIr; 06.08.2011

Для всех, кто сталкивается с этим во время поиска ответов в Google:

Если вы просто используете команду «sudo nano directory/file.name», она откроет текстовый редактор nano, а затем вы сможете записывать файлы в каталог /etc/ (или в любой другой каталог), поэтому я сделал следующее:

'судо нано /etc/krb5.conf'

который открыл текстовый редактор nano и одновременно создал файл «krb5.conf» в каталоге etc, тогда все, что мне нужно было сделать, это ввести код и записать файл. Прошло около 30 с.

person someguy    schedule 06.02.2015

Хорошо, изучив довольно много, я считаю, что нашел более/менее простой метод. Сначала проверьте ссылку: Cocoa — Получение корневого доступа для NSFileManager

Они предлагают использовать уже созданный класс «BLAuthentication», который позаботится о большом количестве кодов аутентификации для вас. Погуглите, чтобы скачать, добавить в проект и использовать в своем коде. Вот пример того, насколько это просто:

id blTmp = [BLAuthentication sharedInstance];

NSString *myCommand = [[NSString alloc] initWithString:@"/bin/cp"];

NSArray *para = [[NSArray alloc] initWithObjects:fileName, @"/etc/", nil];

[blTmp authenticate:myCommand];

if([blTmp isAuthenticated:myCommand] == true) {
    NSLog(@"Authenticated");
    [blTmp executeCommandSynced:myCommand withArgs:para];

} else { NSLog(@"Not Authenticated"); }

[fileName release];
[myCommand release];
[para release];

Естественно, приведенный выше подход не совсем отвечает на мой собственный вопрос, поскольку в приведенном выше примере вы не пишете напрямую в «/etc». Вместо этого сначала я должен записать файл в «/tmp» (или другой каталог по вашему выбору), а затем с помощью команды «cp» в Unix скопировать его в «/etc» (используя «BLAuthentication» для аутентификации).

Это самое простое, что мне удалось найти.

*Примечание. Этот метод может не работать в Lion (Mac os 10.7), поскольку «BLAuthentication» использует устаревшую функцию «AuthorizationExecuteWithPrivileges». Также я бы посоветовал посмотреть WWDC 2011, где рассказывают о безопасности и правильных способах выполнения задачи. Однако, если вам нужно создать прототип и/или поэкспериментировать, «BLAuthentication» поможет.

person MeIr    schedule 12.08.2011
comment
Обновление: я тестирую свое приложение на Mac OS 10.7, и AuthorizationExecuteWithPrivileges работает. - person MeIr; 30.09.2011

Как создать каталог /logs, в который можно писать:

  1. Отключить SIP (режим восстановления, csrutil disable)
  2. Откройте режим восстановления, нажимая command + R, пока не увидите логотип Apple.
  3. Начать сначала
  4. Откройте терминал
  5. echo 'logs' | sudo tee -a /etc/synthetic.conf
  6. Перезагрузить
  7. Или вы можете вручную создать файл /etc/synthetic.conf.
  8. synthetic.conf
    • #create an empty directory named "logs" at / which may be mounted over
    • logs
  9. Затем перезагрузите систему
  10. Make sure **/etc/synthetic.conf** has the following permissions:
    • root: read, write
    • колесо: читать
    • все: читать
person MADHUR GUPTA    schedule 23.12.2020