Câu hỏi Làm thế nào để đệ quy chmod tất cả các thư mục ngoại trừ các tập tin?


Làm thế nào để chmod 755 tất cả các thư mục nhưng không có tập tin (đệ quy)?

Inversely, làm thế nào để chmod chỉ tập tin (đệ quy) nhưng không có thư mục?


518
2018-01-06 01:56


gốc


Liên quan: Thay đổi tất cả các quyền đối với tệp và thư mục của một thư mục thành 644/755tại SO - kenorb


Các câu trả lời:


Đưa ra đệ quy thư mục quyền đọc và thực thi:

find /path/to/base/dir -type d -exec chmod 755 {} +

Đưa ra đệ quy các tập tin đọc đặc quyền:

find /path/to/base/dir -type f -exec chmod 644 {} +

Hoặc, nếu có nhiều đối tượng để xử lý:

chmod 755 $(find /path/to/base/dir -type d)
chmod 644 $(find /path/to/base/dir -type f)

Hoặc, để giảm chmod sinh sản:

find /path/to/base/dir -type d -print0 | xargs -0 chmod 755 
find /path/to/base/dir -type f -print0 | xargs -0 chmod 644

722
2018-01-06 01:58



Hai ví dụ đầu tiên không thành công đối với các thư mục có quá nhiều tệp: -bash: /bin/chmod: Argument list too long. Lệnh cuối cùng hoạt động với nhiều tệp, nhưng khi sử dụng sudo người ta phải cẩn thận để đặt nó trước xargs thay vì chmod: find /path/to/base/dir -type d -print0 | sudo xargs -0 chmod 755 - Agargara
Cũng cần lưu ý, các lệnh này là bao gồm của thư mục cơ sở. Trong ví dụ trên, dir cũng sẽ được đặt thành 755. - CenterOrbit
chmod ... $(find /path/to/base/dir -type ...) không cho tên tập tin có dấu cách trong tên. - Dan Dascalescu
Tôi nghĩ rằng phiên bản chính xác nhất (nhưng không phải nhanh nhất) đối với không gian và ký hiệu trong tên tệp và số lượng tệp là find /path/to/base/dir -type d -exec chmod 755 {} \; (find /path/to/base/dir -type f -exec chmod 644 {} \;). - Peter K


Một lý do phổ biến cho loại điều này là để thiết lập thư mục để 755 nhưng các tập tin để 644. Trong trường hợp này có một cách nhanh hơn một chút so với nik của find thí dụ:

chmod -R u+rwX,go+rX,go-w /path

Ý nghĩa:

  • -R = đệ quy;
  • u+rwX = Người dùng có thể đọc, viết và thực thi;
  • go+rX = nhóm và những người khác có thể đọc và thực thi;
  • go-w = nhóm và những người khác không thể viết

Điều quan trọng cần lưu ý ở đây là chữ hoa X hoạt động khác với chữ thường x. Trong hướng dẫn sử dụng, chúng ta có thể đọc:

Các bit thực thi / tìm kiếm nếu tệp là một thư mục hoặc bất kỳ bit thực thi / tìm kiếm nào được đặt trong chế độ gốc (chưa sửa đổi).

Nói cách khác, chmod u + X trên một tập tin sẽ không thiết lập bit thực thi; và g + X sẽ chỉ đặt nếu nó đã được đặt cho người dùng.


261
2018-01-06 03:22



-R = đệ quy; u + rwX = Người dùng có thể đọc, viết và thực thi; go + rX = nhóm và những người khác có thể đọc và thực thi; go-w = nhóm và những người khác không thể viết - släcker
Mẫu này sẽ không khắc phục được tình huống khi ai đó đã thực hiện chmod -R 777 kể từ khi +X tùy chọn sẽ không đặt lại các bit thực thi hiện có trên các tệp. Sử dụng -x sẽ thiết lập lại các thư mục, và ngăn chặn giảm dần vào chúng. - Andrew Vit
@ ring0: Tôi không có ý định trả lời câu hỏi theo nghĩa đen như đã đặt ra - nik đã làm điều đó một cách hoàn hảo. Tôi chỉ ra một giải pháp rẻ hơn cho trường hợp phổ biến nhất. Và có, bạn có được quyền khác nhau cho các tập tin và thư mục với X, như đã giải thích trong phần bình luận. - bobince
go+rX,go-w -> go=rX phải không? - Pierre de LESPINAY
Bạn cũng có thể dùng chmod u-x,u+X kết hợp, vv, để loại bỏ các bit thực thi cho các tệp, nhưng thêm chúng cho các thư mục. - w0rp


Nếu bạn muốn đảm bảo các tệp được đặt thành 644 và có các tệp trong đường dẫn có cờ thực thi, trước tiên bạn sẽ phải xóa cờ thực thi. + X không xóa cờ thực thi khỏi các tệp đã có nó.

Thí dụ:

chmod -R ugo-x,u+rwX,go+rX,go-w path

Cập nhật: điều này dường như thất bại vì thay đổi đầu tiên (ugo-x) làm cho thư mục không thể thực hiện được, vì vậy tất cả các tệp bên dưới nó không bị thay đổi.


12
2018-01-22 16:14



Điều này phù hợp với tôi và tôi không hiểu tại sao điều đó lại không xảy ra. (Chắc chắn, nếu bạn đã làm chmod -R ugo-x path, Điều đó có thể là vấn đề. Nhưng lệnh hoàn thành sẽ làm chmod u+rwX trên mỗi thư mục trước khi nó cố gắng thâm nhập vào nó.) Tuy nhiên, tôi tin rằng chmod R u=rw,go=r,a+X path là đủ - và ngắn hơn. - Scott
Tôi thấy điều này làm việc đúng cách; không có vấn đề gì khi nhập thư mục - Someone Somewhere


Tôi quyết định viết một kịch bản nhỏ cho bản thân mình.

Kịch bản chmod đệ quy cho thư mục và / hoặc tệp - Gist

Về cơ bản nó có chmod đệ quy nhưng cũng cung cấp một chút linh hoạt cho các tùy chọn dòng lệnh (bộ thư mục và / hoặc quyền truy cập tập tin, hoặc loại trừ cả hai nó sẽ tự động đặt lại mọi thứ thành 755-644). Nó cũng kiểm tra một vài tình huống lỗi.

Tôi cũng đã viết về nó trên blog của tôi.


4
2017-09-18 14:00





Đưa ra đệ quy thư mục quyền đọc và thực thi:

find /path/to/base/dir -type d -exec chmod 755 {} \;

Đưa ra đệ quy các tập tin đọc đặc quyền:

find /path/to/base/dir -type f -exec chmod 644 {} \;

Tốt hơn là không bao giờ để tôi nâng cấp câu trả lời của nik về mặt chính xác. Giải pháp của tôi chậm hơn, nhưng nó hoạt động với bất kỳ số lượng tệp nào, với bất kỳ ký hiệu nào trong tên tệp và bạn có thể chạy nó với sudo bình thường (nhưng hãy cẩn thận rằng nó có thể phát hiện các tệp khác nhau với sudo).


3
2018-02-21 11:58





Hãy thử tập lệnh python này; nó không yêu cầu sinh sản của các quá trình và chỉ có hai syscalls cho mỗi tập tin. Ngoài việc thực hiện trong C, nó có lẽ sẽ là cách nhanh nhất để làm nó (tôi cần nó để sửa chữa một hệ thống tập tin của 15 triệu tập tin mà tất cả được thiết lập để 777)

#!/usr/bin/python3
import os
for par, dirs, files in os.walk('.'):
    for d in dirs:
        os.chmod(par + '/' + d, 0o755)
    for f in files:
        os.chmod(par + '/' + f, 0o644)

Trong trường hợp của tôi, một thử / bắt được yêu cầu xung quanh chmod cuối cùng, kể từ khi chmodding một số tập tin đặc biệt không thành công.


0
2018-03-26 04:37





Bạn cũng có thể dùng tree:

tree -faid /your_directory | xargs -L1 -I{} sudo chmod +x {}

-1
2018-02-16 09:34





Bạn có thể sử dụng tập lệnh bash sau đây làm ví dụ. Hãy chắc chắn cung cấp cho nó quyền thực thi (755). Chỉ cần sử dụng ./autochmod.sh cho thư mục hiện tại hoặc ./autochmod.sh <dir> để chỉ định một thư mục khác.

#!/bin/bash

if [ -e $1 ]; then
    if [ -d $1 ];then
        dir=$1
    else
        echo "No such directory: $1"
        exit
    fi
else
    dir="./"
fi

for f in $(ls -l $dir | awk '{print $8}'); do
    if [ -d $f ];then
        chmod 755 $f
    else
        chmod 644 $f
    fi
done

-2
2018-01-29 11:56



Wow! Rất nhiều vấn đề! (1) Nếu $1 không phải là rỗng, nhưng không phải là tên của một thư mục (ví dụ: là lỗi đánh máy), sau đó dir được đặt thành . không có tin nhắn. (2) $1 nên là "$1" và $dir nên là "$dir". (3) Bạn không cần phải nói "./"; "." là tốt (và, nói đúng, bạn không cần báo giá ở đây). (4) Đây không phải là một giải pháp đệ quy. (5) Trên hệ thống của tôi, ls -l … | awk '{ print $8 }' nhận thời gian sửa đổi của tệp. Bạn cần { print $9 } để có được từ đầu tiên của tên tệp. Và thậm chí sau đó, (6) điều này không xử lý tên tập tin với không gian màu trắng. … - Scott
… Và, cuối cùng nhưng không kém phần quan trọng (∞) nếu tập lệnh này nằm trong thư mục hiện tại, nó sẽ chmod  chinh no đến 644, do đó làm cho bản thân nó không thể thực thi được! - Scott