Терминал: список всех каталогов, для которых у пользователя или группы есть разрешение на запись

Handbrake и DVD :: RIP оба позволят вам делать очереди, но это довольно утомительный процесс. Вы должны вручную ввести номер эпизода, среди других утомительных вещей. Это было не для меня.

Поэтому, когда я хотел разорвать мои DVD-диски Family Guy, я написал простой скрипт, который я мог бы использовать в будущем:

#!/bin/bash

series=$1
disk=$2
count=$3
offset=0
name="Family Guy"
scratch="~/Desktop/"
destination="/media/ned/tv/$name"

#mkdir $scratch

for c in $(seq 1 1 $count)
do
    ep=`printf "%02.f" $(( ($disk-1)*$count+$c ))`
    fn="$scratch/$name ${series}x$ep.mp4"
    echo "Ripping $name ${series}x${ep} to fn"
    /home/oli/hb/HandBrakeCLI -S 200 -Z Television -a 1 -i /dev/sr0 -o "$fn" -t $(($c + $offset))
done

#echo "moving..."
#mv $scratch/* "$destination"
echo "done."

eject
sleep 2
eject

Это действительно очень сырой, и есть много возможностей для его улучшения. Формат его вызова:

script_name <series> <disk> <number-of-episodes-per-disk>
1
задан 13 April 2017 в 15:23

3 ответа

В чате мы пришли к следующим инструкциям для пользователя и группы:

sudo find / -type d -user rinzwind -perm /u=w
sudo find / -type d -group rinzwind -perm /g=w
sudo find / -type d -perm /o=w

Или соединить все три в одном:

sudo find -type d \( \( -user rinzwind -perm /u=w \) -o \( -group rinzwind -perm /g=w \) -o -perm /o=w \)

Без / он ищет текущий каталог ,

Принимал менее 2 секунд на 67 Гб данных в моей системе;)

4
ответ дан 23 May 2018 в 12:48
  • 1
    Хм .. может, я что-то делаю неправильно? Но когда я выполняю именно это для целевого пользователя ftpgisdata, я не получаю никаких результатов. Он просто падает до следующей строки в терминале: find -type d -user ftpgisdata -perm /u=w,g=w – elrobis 16 March 2016 в 23:03
  • 2
    sudo mkdir cheese; sudo chmod o+w cheese - это каталог, который любой может писать, но не будет отображаться ни в одном из них. – Oli♦ 16 March 2016 в 23:04
  • 3
    @elrobis Измените их, чтобы они запустили find /. В настоящее время он просто ищет текущий рабочий каталог. – Oli♦ 16 March 2016 в 23:05
  • 4
    О, хорошо. .. также следует, что если я cd /, что он будет искать вперед от корня и рассматривать любого данного пользователя или группу? Он работает прямо сейчас и выглядит многообещающим - определенно занимает немного больше 2 секунд! – elrobis 16 March 2016 в 23:08
  • 5
    И вам, вероятно, понадобится запустить это с помощью sudo, чтобы избежать ошибок разрешения. – muru 16 March 2016 в 23:09

Отвечайте в процессе строительства, пожалуйста, будьте терпеливы

Тестирование для себя

Можно проверить права на запись для себя со следующим кодом:

[ -w /home/$USER ] && echo yes # using home directory as example

] Используя флаг -d для теста, мы можем проверить, является ли что-то каталогом.

Зная все это и find, мы можем сделать

find /home/ -print0 2> /dev/null | while IFS=""  read -r -d "" file ; do [ -d "$file"  ] &&  [ -w "$file" ]  && echo "$file" is writeable ; done

. Замечание: Очевидно, если вы получаете ошибки разрешения с помощью find, вы не можете прочитать этот файл, поэтому нет причин выводить эти ошибки, следовательно, перенаправление на dev null. Очевидно, что это не сработает, если мы хотим узнать разрешения для пользователей, отличных от себя, и обратите внимание - / home - только пример. Такие папки, как /var, имеют папки, разделяемые между несколькими пользователями

Тестирование для себя

Можно использовать stat для каждого файла find находит и отфильтровывает его с помощью awk

 find /var -type d -exec stat --format '%g %n'  {} \; 2> /dev/null | awk '$1=='1000'{print}' 

Здесь я фильтрую числовой идентификатор моего собственного пользователя, 1000, но это может быть идентификатор любого пользователя. Конечно, можно играть с опциями, использовать имя группы вместо числовых идентификаторов. Это что-то очень гибкое и адаптируемое к той цели, в которой вы нуждаетесь

Небольшие настройки

Итак, я заметил, что вы упоминаете, что вы вошли в систему под именем root. Вот результат моей команды, где я статирую файлы и печатаю их группу и имя файла, а затем отфильтровываю AWK с помощью соответствующего имени группы.

$ find /proc -type d -exec stat --format '%G %n'  {} \; 2> /dev/null  | awk '$1=="syslog"{print}'
syslog /proc/560
syslog /proc/560/task
syslog /proc/560/task/560
syslog /proc/560/task/560/net
syslog /proc/560/task/560/attr
syslog /proc/560/task/562
syslog /proc/560/task/562/net
syslog /proc/560/task/562/attr
syslog /proc/560/task/563
syslog /proc/560/task/563/net
syslog /proc/560/task/563/attr
syslog /proc/560/task/564
syslog /proc/560/task/564/net
syslog /proc/560/task/564/attr
syslog /proc/560/net
syslog /proc/560/attr
^C
2
ответ дан 23 May 2018 в 12:48
  • 1
    Правда, я вошел в систему как маршрут, но в основном я хочу узнать и «какие каталоги могут писать пользователю X?» & Quot; Я просто пробовал ваш подход к пользователю с id = 1001, то есть $1=='1001', но он не возвращал никаких просмотров. Мысли? – elrobis 17 March 2016 в 00:00
  • 2
    @elrobis Да, у меня есть отслеживаемые стороны - я понимаю, что вы хотели проверить права на запись в каталоге для каждого пользователя. Дело в том, что пользователь может быть частью группы, поэтому они могут писать в каталог. Например, группа каталогов foobar, но пользователь, принадлежащий к этой группе, может иметь имя пользователя scooby. Это более сложная проблема, которая кажется. , . Я буду работать над этим больше, возможно, вам нужно будет написать функции для проверки пользователя и проверки доступа к записи группы в файл – Sergiy Kolodyazhnyy 17 March 2016 в 00:09

Если у вас есть поиск GNU, вы можете использовать тест -writable (обратите внимание на орфографию, это не writeable). Это использует системный вызов access(2) вместо того, чтобы просто пытаться понять, что происходит от просмотра разрешений, поэтому он корректно работает с ACL. (Но может разбиться на NFS с сопоставлениями с идентификаторами).

Он также найдет каталоги, которые могут быть записаны пользователем благодаря тому, что он является членом вторичной группы. (например, каталог из /usr/local, доступный для записи в группе admin, или что-то вроде chown root:users /data/share && chmod 2775 /data/share, где некоторые учетные записи являются членами группы users.)

username_to_check=peter base_dir=/   # for example
sudo -u "$username_to_check" find "$base_dir" -type d -writable  2>/dev/null ## GNU find, not POSIX

быть ошибками, когда find сталкивается с каталогами, к которым пользователь не может спуститься, поэтому мы перенаправляем ошибки на /dev/null.

Это не будет содержать каталогов, которые могут быть записаны, но внутри каталогов без разрешения на выполнение, поскольку [ f11], поскольку пользователь не может перемещаться по более высоким каталогам. Однако, если процесс, который им принадлежит, запускается внутри такого каталога, они смогут писать с ним относительные пути. (или они захватывают дескриптор открытого файла в такой каталог, они могут использовать openat(2)). pwd не будет работать, если у них нет разрешения на исполнение для одного из компонентов каталога полного пути, поэтому это не обычная настройка.

Это также пропускает записываемые каталоги, которые находятся внутри исполняемого файла, но не читаемые каталоги. Чтобы обойти эти ограничения, вероятно, запустите find -type d как root и используйте find -writable в качестве пользователя для проверки результирующих путей. Это может быть более эффективным, чем цикл оболочки с использованием [ -w "$f" ].

POSIX find(1) имеет гораздо меньше опций, чем поиск GNU. Если ваш скрипт должен быть переносимым в POSIX, возможно, проще всего подключиться к чему-то другому, который проверяет разрешения, например, оболочку с [ -w "$f" ] (см. Другой ответ, который предлагает это.)

2
ответ дан 23 May 2018 в 12:48
  • 1
    Проблема с запуском find как non-root заключается в том, что вы не оцениваете все дерево. Например, создайте следующее: sudo mkdir -p cheese/deep; sudo chmod o+w cheese/deep; sudo chmod o-r cheese, кто-нибудь может записать на cheese/deep, но они не могут прочитать содержимое родительского каталога cheese, и поэтому find не может видеть cheese/deep. Ваша находка просто выйдет из строя (и подавит ошибку). Сожалею. – Oli♦ 17 March 2016 в 17:09
  • 2
    @ Oli: О, верно, я не заметил x без дела r. Благодарю. Я предполагаю, что мы могли бы построить командную строку find с циклом оболочки, который выполняет итерацию по вторичным группам пользователя, если мы не хотим просто передавать вывод root-find в другой процесс, который выполняет access(2) как пользователь. Этот второй процесс может быть find -writable. – Peter Cordes 17 March 2016 в 17:24
  • 3
    Питер благодарит за ваш вклад и полезное описание. Я запустил ваше решение и обновил сообщение, чтобы включить результат для того же пользователя, с которым я тестировал. – elrobis 17 March 2016 в 17:48
  • 4
    Также неплохой подход, но это оказалось довольно сложным, и вы почти подали заявку на отчет об ошибке, чтобы улучшить этот D: вопрос действительно, когда вы смотрите на обеспечение безопасности системы. И это слишком сложно. – Rinzwind 17 March 2016 в 18:11

Другие вопросы по тегам:

Похожие вопросы: