Jak ustawić określone uprawnienia do plików podczas przekierowywania danych wyjściowych?


12

To prawdopodobnie duplikat, ale wszystkie moje wyszukiwania pokazują pytania dotyczące błędów odmowy uprawnień.

Uruchamiam polecenie w powłoce bash. Chcę przekierować dane wyjściowe, aby dołączyć je do pliku, który prawdopodobnie nie istnieje przy pierwszym uruchomieniu. Chcę ustawić tryb uprawnień do określonych plików, jeśli przekierowanie danych wyjściowych musi utworzyć ten plik. Czy można to zrobić za pomocą jednego polecenia?

Na przykład mogę spróbować

foo >> /tmp/foo.log 0644

gdzie 0644są uprawnienia, z którymi chcę foo.logskończyć. Większość poleceń, z którymi eksperymentowałem w bash, kończy się interpretacją 0644jako dodatkowy argument foo.

Mam wrażenie, że zajmie to drugie polecenie chmoduprawnień przed lub po napisaniu do niego.

Używam GNU bash 4.2.25 i Ubuntu 12.04, jeśli to robi różnicę - preferowane są ogólne odpowiedzi.

Odpowiedzi:


5

O ile mi wiadomo, nie można tego zrobić podczas instalacji, prosty skrypt może być najlepszym rozwiązaniem.

if [ -e /tmp/foo.log ]; then
    foo >> /tmp/foo.log
else
    foo >> /tmp/foo.log
    chmod 0644 /tmp/foo.log
fi

Dzięki Slowki, to też było moje przeczucie. Zostawię to otwarte przez kilka dni, w nadziei na przyciągnięcie guru, który nas oświeci.
Patrick M

3
Problem z tym podejściem polega na tym, że tworzy krótkie okno czasowe, gdy uprawnienia do pliku są nieprawidłowe. Nie użyłbym tego, jeśli celem jest ochrona wrażliwych danych.
proski

1
Ta odpowiedź działa, o ile to możliwe, ale @proski ma rację: umaskodpowiedzi są lepsze i jedną z nich należy zaakceptować.
Scott

15

Wiem, że to stare pytanie, ale chciałem dodać moje dwa centy.

Miałem ten sam pomysł i wpadłem na rozwiązanie podobne do BowlesCR . Problem z jego rozwiązaniem polegał na tym, że moje polecenie ( foo) nie działało, jeśli zmieniłem umask przed jego uruchomieniem, więc oto moje podejście do problemu:

foo | ( umask 0033; cat >> /tmp/foo.log; )

Tutaj umaskwpływa tylko na przekierowanie do foo.logpodpowłoki. Wszystko inne pozostaje nienaruszone.

Trochę zawiłe, ale działa.


Bardzo ładne i skuteczne :) Po prostu nie można go używać z przekierowaniem stderr na szczycie standardowego redir.
Orsiris de Jong,

5

Bez prawdziwego skryptu możesz trochę połączyć:

touch /tmp/foo.log; chmod 0644 /tmp/foo.log; foo >> /tmp/foo.log

Skutecznie podobny do odpowiedzi Slowki , ale skondensowany w jedno-liniowy.

Jedyne, o czym myślę, to majstrowanie przy umasku. Najlepiej to zrobić w podpowłoce, aby nie zanieczyszczać bieżącego środowiska:

(umask 0033 && foo >> /tmp/foo.log)

Dwa problemy z tym jednak.

  1. Umask nie może podnieść uprawnień powyżej poziomu określonego w creat()syscall (0666 wydaje się być tym, czego używa Bash).
  2. Nie zmieni to uprawnień do istniejącego pliku (ponieważ umaskdotyczy tylko tworzenia plików ).

Nadal jestem na tyle nowy, by * nix, że umask wciąż jest dla mnie odrobiną magii. Dzięki za podpowiedź, z pewnością ją przeczytam.
Patrick M

Hmm… Nadal pozwala nieuprzywilejowanemu procesowi otwierać plik, a później czytać jego zawartość.
Feuermurmel

(1) Gratulujemy znalezienia interesującego, użytecznego zastosowania cat. (Chociaż nie jest to zgodne ze standardowym wzorcem bezużytecznych zastosowań  cat.) (2) Zakładam, że chciałeś powiedzieć, że domyślnie bash ma domyślnie tryb  0666 podczas tworzenia plików, więc zredagowałem twoją odpowiedź, aby tak powiedzieć. (Zobacz to ,  to   ... (ciąg dalszy)
Scott

( Ciąg dalszy )… i  to .) Pytanie to wspomina w szczególności o trybie 0644. Zatem umaskwartość 22, 23 lub 32 również działałaby w tym kontekście (nie trzeba używać początkowych zer); kiedy tryby i  umaskwartości są określone liczbowo, zawsze są interpretowane jako ósemkowe).  22 jest częściej stosowany konwencjonalnie.
Scott,

@Feuermurmel: Co z tego? Pytanie wyraźnie wymaga trybu 644. Musimy założyć, że PO wie, że 644 oznacza świat do odczytu i ma na celu upublicznienie jego informacji.
Scott,

1

Gdy przekierowanie ustawia nieprawidłowe uprawnienia, np .:

$ rm capture.*
$ perl -e 'print STDERR "$$ STDERR\n"; print STDOUT "$$ STDOUT\n"' \
                            >> capture.STDOUT 2>> capture.STDERR
$ perl -e 'print STDERR "$$ STDERR\n"; print STDOUT "$$ STDOUT\n"' \
                            >> capture.STDOUT 2>> capture.STDERR
$ ls -l capture.*
-rw-rw-rw- 1 jcookinf jcookinf 22 Jun 12 10:38 capture.STDERR
-rw-rw-rw- 1 jcookinf jcookinf 22 Jun 12 10:38 capture.STDOUT
$ cat capture.*
215 STDERR
216 STDERR
215 STDOUT
216 STDOUT

Wierzę, że możesz użyć czegoś, co dał xynomorf, i rozwiązać problem stderr z Orsiris de Jong z niewielką modyfikacją, aby użyć substytucji procesu bash .

$ rm capture.*
$ perl -e 'print STDERR "$$ STDERR text\n"; print STDOUT "$$ STDOUT text\n"' \
            > >(umask 0033; cat >> capture.STDOUT) 2> >(umask 0033; cat >> capture.STDERR)
$ perl -e 'print STDERR "$$ STDERR text\n"; print STDOUT "$$ STDOUT text\n"' \
            > >(umask 0033; cat >> capture.STDOUT) 2> >(umask 0033; cat >> capture.STDERR)
$ ls -l capture.*
-rw-r--r-- 1 jcookinf jcookinf 32 Jun 12 10:43 capture.STDERR
-rw-r--r-- 1 jcookinf jcookinf 32 Jun 12 10:43 capture.STDOUT
$ cat capture.*
233 STDERR text
238 STDERR text
233 STDOUT text
238 STDOUT text

Oczywiście, użyj, umask 0077aby uzyskać tryb 600 i zabronić innym użytkownikom oglądania zawartości.


0

Jeśli chcesz przekierować do skryptu, w przeciwieństwie umaskdo podstawiania procesów install, możesz także ustawić bit wykonania:

install -m 755 <(echo commands go here) newscript

<()umieszcza dane wyjściowe w pliku tymczasowym, patrz Zastąpienie procesu

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.