Sed với chỉnh sửa tại chỗ thay đổi quyền sở hữu nhóm của tập tin


8

Tôi có phptập lệnh shell ( ) liên lạc với tệp đích theo cách này:

  • kiểm tra xem tập tin và thư mục được ghi với php's is_writable()(Tôi không nghĩ rằng đây là vấn đề)
  • không chỉnh sửa tập tin tại chỗ bằng sedlệnh:

grep -q "$search" "$passwd_file" && { sed -i "s|$search|$replace|" "$passwd_file"; printf "Password changed!\n"; } || printf "Password not changed!\n"

Kết quả là tôi nhận được (mọi thứ khác chính xác nhưng) tệp đã myuser:www-datađược myuser:myuser.

sedthay đổi quyền sở hữu nhóm tệp như nó có vẻ không, và làm cách nào để tránh nó, nếu có thể?


Câu trả lời:


16

Có một chút vấn đề với sedchế độ chỉnh sửa tại chỗ -i. sedtạo một tệp tạm thời trong cùng thư mục được gọi sedy08qMA, trong đó y08qMAlà một chuỗi được tạo ngẫu nhiên. Tập tin đó chứa đầy nội dung sửa đổi của tập tin gốc. Sau thao tác, sedxóa tệp gốc và đổi tên tệp tạm thời với tên tệp gốc. Vì vậy, nó không phải là một chỉnh sửa tại chỗ thực sự . Nó tạo ra một tệp mới với sự cho phép của người dùng gọi và số inode mới. Hành vi đó chủ yếu là không xấu, nhưng ví dụ, các liên kết cứng bị hỏng.

Tuy nhiên, nếu bạn muốn chỉnh sửa tại chỗ thực sự , bạn nên sử dụng ed. Nó đọc các lệnh từ stdin và chỉnh sửa tệp trực tiếp mà không cần tệp tạm thời (nó được thực hiện trên edbộ nhớ của bộ nhớ). Một thực tế phổ biến là sử dụng printfđể tạo danh sách lệnh:

printf "%s\n" '1,$s/search/replace/g' wq | ed -s file

Các printflệnh sản xuất đầu ra như sau:

1,$s/search/replace/g
wq

Hai dòng đó là edcác lệnh. Người đầu tiên tìm kiếm chuỗi searchvà thay thế nó bằng replace. Cái thứ hai ghi ( w) các thay đổi vào tệp và thoát ( q). -sngăn chặn đầu ra chẩn đoán.


8

Các -itham số của sedcông trình bằng cách tạo ra một tập tin tạm thời trong quá trình hoạt động, sau đó ghi đè lên tập tin thực tế với các tập tin tạm thời cuối cùng. Đó rất có thể là nguyên nhân gây ra sự cố, vì khi tạo quyền sở hữu tệp tạm thời mặc định làmyuser:myuser

Bạn có thể đặt setgidbit trên thư mục mẹ (chỉ khi thư mục mẹ được sở hữu bởi nhóm www-data), để các tệp được tạo trong thư mục này kế thừa cùng một nhóm.
Để làm việc đó:

chmod g+s parent-dir-of-your-file  

Tôi nghĩ rằng đây là một cách sử dụng rất điển hình của setgidbit.


@cuonglm Tôi vừa thực hiện một bước trên sed -i, tìm thấy dòng sau trong dấu vết, có nghĩa là nó đã tạo tệp tạm thời trong thư mục hiện tại? open("./sedKyG9Ei", O_RDWR|O_CREAT|O_EXCL, 0600) = 4
Dave.d

@DavidDai: Vâng, trí nhớ sai của tôi.
cuonglm

2

Việc sử dụng edthay vì sedcó vẻ khá thừa đối với điều này, do bạn phải đưa vào một đầu vào bổ sung. Bản phân phối tôi đang làm việc ngay bây giờ (CentOS 5.10) có -ctùy chọn sedsử dụng 'sao chép' tệp tạm thời thay vì chỉ đổi tên nó khi được sử dụng với -itùy chọn. Tôi đã thử nghiệm nó và nó hoạt động hoàn hảo, bảo vệ chủ sở hữu và nhóm ban đầu khi thực hiện chỉnh sửa nội tuyến. Nó KHÔNG bảo toàn thời gian sửa đổi.

ví dụ, sed -ci -e '3,5d' file.txt

  • -c sử dụng bản sao thay vì đổi tên (nghĩa là bảo toàn quyền sở hữu / nhóm)
  • -i chỉnh sửa nội tuyến
  • -e kịch bản / biểu thức sẽ được thực thi

Không chắc chắn mức độ phổ biến của tùy chọn này đối với sedcác phân phối khác. Solaris 10 không có nó, nhưng Solaris không có nhiều thứ tôi muốn.


Âm thanh khá tiện dụng. Không phải trong Ubuntu 14.04, FWIW. :-(
John Rix
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.