rsync, xóa các tập tin ở phía nhận đã bị xóa ở phía gửi. (Nhưng đừng xóa mọi thứ)


9

Tôi muốn sử dụng rsync để ...

  • xóa các tập tin ở phía bên nhận cũng bị xóa ở phía gửi
  • không xóa các tệp khác trong thư mục rsynced ở phía nhận

Ví dụ: giả sử tôi có một thư mục local-src:

TRƯỚC: local-src địa phương chứa ...

a.txt
b.txt
c.txt

thư mục từ xa của tôi mà tôi muốn đồng bộ hóa với nội dung của local-srcđược gọi remote-src.

TRƯỚC: remote-src từ xa chứa ...

a.txt
b.txt
c.txt
d.txt
README.md

Hãy nói rằng tôi xóa một số tệp trong local-src:

SAU KHI XÓA ĐỊA PHƯƠNG: local-src chứa tại địa phương ...

c.txt

Làm cách nào tôi có thể sử dụng rsync theo cách để đảm bảo rằng các tệp bị xóa tại nguồn cũng bị xóa tại đích, nhưng không xóa các tệp khác tại đích. Ví dụ: tôi muốn có những điều sau đây tại điểm đến:

SAU KHI XÓA ĐỊA PHƯƠNG: remote-src chứa từ xa ...

c.txt
d.txt
README.md

Đó là, a.txtb.txtcũng bị xóa từ xa, nhưng d.txtREADME.txtđược để lại một mình.

Có cách nào để đạt được điều này với rsync không?

EDIT: Phán quyết dường như là điều này có thể là không thể với rsync. Tôi đã được hỏi tại sao tôi cần điều này, vì vậy để minh họa trường hợp sử dụng của tôi:

Hãy nói rằng tôi có một máy chủ web. Trên máy chủ web đó, tôi đã có một loạt các thư mục, giả sử rằng tôi có một thư mục Avà một public_htmlthư mục mà trang web của tôi được phục vụ từ đó. Hãy nói rằng tôi có một số quy trình tự động tạo ra các tệp trong thư mục A. Tôi muốn rsync (hoặc đồng bộ sử dụng một số công cụ khác) các tập tin được tạo hoặc cập nhật trong Avào public_htmlthư mục, mà không xóa các tập tin tùy ý khác mà có thể trong vòng public_html. Tôi chắc chắn không muốn rsync vô tình xóa trang web của mình.

Nếu rsync không phải là công cụ cho công việc này, liệu có ai khác biết làm thế nào tôi có thể làm điều này không?


2
Sau khi đọc lại câu hỏi của bạn, tôi không nghĩ rằng điều này là có thể rsyncvì không có cách nào để biết tập tin nào đã có trong thư mục từ xa. Bạn có thể cần phải tìm ra một công cụ khác.
Spack

rsync sẽ không cho phép bạn làm điều này, nhưng nếu bạn quét toàn bộ thư mục mỗi khi bạn xóa các tệp, bạn có thể giữ chúng đồng bộ, không phải là một giải pháp chỉ là một đề xuất.
Aadi Droid

1
Tôi đoán bạn đã nghĩ về điều này, nhưng bạn không thể đặt các tệp này vào thư mục con (hoặc một nơi nào khác) và tham chiếu chúng từ public_html? Bằng cách đó, bạn có một thư mục được đồng bộ hóa dễ dàng và rõ ràng, mà không ảnh hưởng đến các tệp trong các phần khác của hệ thống tệp của máy chủ web.
MattJenko

Câu trả lời:


2

Những gì bạn muốn làm là hợp lý, nhưng sử dụng rsyncđể tự làm thì không. Vì vậy, câu trả lời là không .

Lý do rất đơn giản: rsynckhông có lịch sử về những gì có trong mỗi thư mục và không có cách nào để biết những gì cần phải xóa và những gì không. Không phải không có hỗ trợ bổ sung.

Bạn nên tự hỏi tại sao bạn thích làm điều này với rsyncvà làm cho nó rõ ràng hơn. Có những chương trình khác sử dụng librsync1.somà thông minh hơn.


Với các ràng buộc thoải mái mà bạn không cần rsyncmỗi se, bạn có thể xem qua sao lưu dự phòng :

mkdir a
touch a/xx
touch a/yy
rdiff-backup a b
ls b 

Điều này cho thấy xxyyđang ở b.

touch b/zz
rm a/xx
rdiff-backup a b

Điều này cho thấy xxzzđang ở b. rdiff-backupcũng giữ một thư mục rdiff-backup-datatrong b, do đó bạn có thể rollback bất kỳ thay đổi, bạn nên tẩy này một cách thường xuyên bằng cách sử dụng rdiff-backuplệnh. (Ví dụ là với các tệp cục bộ để hiển thị thêm dữ liệu trong mục tiêu sẽ không bị xóa, nhưng sao lưu dự phòng cũng hoạt động trên mạng).


Một cách khác là thiết lập một số hệ thống kiểm soát sửa đổi phân tán (mercurial, bazaar, git). Với mercurial, ví dụ bạn có thể có một tập lệnh (tôi sử dụng Makefile cho điều đó), nó đẩy tất cả các thay đổi đến máy chủ và sau đó cập nhật các tệp đã kiểm tra ở đó, bỏ qua mọi tệp bổ sung có trên máy chủ từ xa (nhưng có không được đặt dưới sự kiểm soát sửa đổi).

Trên máy chủ, bạn sẽ làm:

hg init
hg add file_list_excluding_that_should_not_should_be_deleted_if_not_on_client
hg commit -m "initial setup"

Trên máy khách:

hg clone ssh://username@server/dir_to_repository

Bây giờ nếu bạn xóa một tệp trên máy khách và làm:

hg commit -m "removed file"
ssh username@server "cd dir_to_repository; hg update --clean"

Tệp đã xóa của bạn bị xóa trên máy chủ, nhưng mọi dữ liệu khác (không được thêm vào kho lưu trữ) sẽ không bị xóa.


Tôi có thể chấp nhận rằng rsync sẽ không làm điều này. Nhưng tôi không đồng ý rằng điều này là không thể với rsync - nếu rsync biết về phía gửi tệp nào đã bị xóa, tại sao nó không thể gửi thông tin đó cho phía nhận trong diff? Sau khi so sánh độ mới, tôi không hiểu tại sao bên nhận không thể xóa các tệp được chỉ định xóa trong diff, mà không xóa mọi thứ khác trong thư mục. Xóa mọi tệp khác (không xóa được tại nguồn) trong thư mục có vẻ không hợp lý với tôi.
Heather Miller

Trong mọi trường hợp, lý do tôi cần điều này là như sau. Tôi có một thư mục, hãy gọi nó A, trong đó một số quy trình được tự động hóa và các tệp được tạo tự động ở đó. Tôi đã có một máy chủ web và tôi muốn các tệp trong đó Ađược gắn vào public_htmlthư mục của máy chủ web, tất nhiên mà không xóa mọi thứ khác trong public_htmlthư mục của máy chủ web. Nếu bất cứ ai có bất kỳ ý tưởng nào để đạt được điều này với một công cụ khác, nó sẽ được chào đón nhiều hơn. Tôi sẽ cập nhật câu hỏi của tôi để phản ánh điều này.
Heather Miller

Để làm rõ nhận xét đầu tiên của tôi ở trên- Tôi nên nói "Tôi không đồng ý rằng một cái gì đó như thế này là không thể với một công cụ như rsync". Theo trực giác, có vẻ như điều này không thể quá khó để đạt được (trừ khi tôi thiếu một cái gì đó).
Heather Miller

Hừm, được rồi Tôi nghĩ rằng tôi đã thấy ngay bây giờ - làm thế nào rsync có thể biết khi nào một cái gì đó bị xóa trong local-srcthư mục mà không có quá trình xem thư mục đó để thay đổi. Có lẽ điều này sẽ khó khăn.
Heather Miller

@HeatherMiller Giống như tôi đã viết, yêu cầu của bạn là hợp lý, nhưng rsynckhông phải là công cụ. Hãy nhận ra rằng synctrong rsyncxuất phát từ việc đồng bộ hóa và đó không phải là chính xác những gì bạn muốn làm. Trong sự phát triển của rsynctrọng tâm là hiệu quả (giảm thiểu) việc truyền dữ liệu. Các công cụ khác như rdiff-backup(và có thể cvsup) đã sử dụng các kỹ thuật của nó cho việc đó nhưng dựa trên các tính năng bổ sung.
Anthon

1

Tôi không nghĩ rằng điều này là có thể mà không loại trừ rõ ràng các tệp ở phía bên nhận như là một phần của lệnh rsync. Xem phần trang dành cho người đàn ông để biết rsync: "QUY TẮC TRỰC TIẾP VÀ XÓA".

Nếu không có tùy chọn xóa, các quy tắc trên mỗi thư mục chỉ có liên quan ở phía gửi, vì vậy bạn có thể thoải mái loại trừ các tệp hợp nhất mà không ảnh hưởng đến việc chuyển. Để làm cho điều này trở nên dễ dàng, công cụ sửa đổi 'e' sẽ thêm loại trừ này cho bạn, như đã thấy trong hai lệnh tương đương sau:

          rsync -av --filter=': .excl' --exclude=.excl host:src/dir /dest
          rsync -av --filter=':e .excl' host:src/dir /dest

Tuy nhiên, nếu bạn muốn xóa ở bên nhận VÀ bạn muốn loại trừ một số tệp khỏi bị xóa, bạn cần chắc chắn rằng bên nhận biết phải loại trừ những tệp nào. Cách dễ nhất là bao gồm các tệp hợp nhất mỗi thư mục trong quá trình chuyển và sử dụng --delete-after, bởi vì điều này đảm bảo rằng bên nhận nhận được tất cả các quy tắc loại trừ giống như bên gửi trước khi nó cố gắng xóa bất cứ điều gì:

          rsync -avF --delete-after host:src/dir /dest

Tuy nhiên, nếu các tệp hợp nhất không phải là một phần của chuyển khoản, bạn sẽ cần chỉ định một số quy tắc loại trừ toàn cầu (nghĩa là được chỉ định trên dòng lệnh) hoặc bạn sẽ cần duy trì các tệp hợp nhất theo thư mục của riêng mình trên bên nhận. Một ví dụ đầu tiên là điều này (giả sử rằng các tệp .rules từ xa tự loại trừ):

   rsync -av --filter=’: .rules’ --filter=’. /my/extra.rules’
      --delete host:src/dir /dest

Trong ví dụ trên, tệp Extra.rules có thể ảnh hưởng đến cả hai phía của quá trình chuyển, nhưng (về phía gửi), các quy tắc phụ thuộc vào các quy tắc được hợp nhất từ ​​các tệp .rules vì ​​chúng được chỉ định sau quy tắc hợp nhất mỗi thư mục.

Trong một ví dụ cuối cùng, phía từ xa loại trừ các tệp bộ lọc .rsync khỏi quá trình truyền, nhưng chúng tôi muốn sử dụng các tệp bộ lọc .rsync của riêng mình để kiểm soát những gì bị xóa ở phía nhận. Để làm điều này, chúng tôi phải loại trừ cụ thể các tệp hợp nhất mỗi thư mục (để chúng không bị xóa) và sau đó đặt quy tắc vào các tệp cục bộ để kiểm soát những gì khác không nên xóa. Giống như một trong các lệnh sau:

       rsync -av --filter=':e /.rsync-filter' --delete \
           host:src/dir /dest
       rsync -avFF --delete host:src/dir /dest

0

Nếu tôi hiểu chính xác, đó --excludecó thể là những gì bạn đang tìm kiếm:

$ ls src dst
dst:
a.txt  b.txt  c.txt  d.txt  README.md

src:
c.txt
$ rsync --update --delete --recursive --exclude="d.txt" --exclude="README.md" src/ dst
$ ls src dst
dst:
c.txt  d.txt  README.md

src:
c.txt

Ồ không. Tôi không muốn phải liệt kê thủ công tất cả các tệp mà tôi muốn loại trừ. Tôi chỉ muốn rsync để xóa các tệp mà tôi đã xóa tại nguồn - Tôi không cần phải biết tại nguồn những tệp nào có thể tồn tại trong cùng thư mục tại đích.
Heather Miller

0

Tôi có một câu trả lời cho điều đó. Tôi nghĩ rằng nó hoạt động. Và nó làm việc cho tôi. Trước tiên, bạn phải có rsynccác tập tin từ xa đến tập tin cục bộ. Sau đó, phía địa phương chứa tất cả các tập tin.

sudo rsync -r -a -v --delete /root@xx.xx.xx.xx:/remote_dir/ /local_dir/

bây giờ ở phía địa phương

a.txt
b.txt
c.txt
d.txt
README.md

Sau đó, bạn có thể xóa các tập tin hoặc làm bất cứ điều gì bạn muốn. (Ở phía địa phương). Trong câu hỏi của bạn, bạn xóa những tập tin này.

xóa các tập tin

a.txt
b.txt

Sau đó, bạn có thể rsynctệp cục bộ sang phía từ xa. Sau đó cả hai bên có cùng một tệp.

sudo rsync -r -a -v --delete /local_dir/ root@xx.xx.xx.xx:/remote_dir/

nó cho

c.txt
d.txt
README.md

các tệp ở phía từ xa và phía cục bộ. (Bằng cách sử dụng --delete, nó sẽ xóa các tệp khác ở phía từ xa không khớp với phía cục bộ ).

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.