tra-loi-cau-hoi-phat-trien-web.com

Hiển thị tổng tiến độ trong rsync: có thể không?

Tôi đã tìm kiếm tùy chọn này rồi, nhưng chỉ tìm thấy giải pháp liên quan đến vá tùy chỉnh . Thực tế là nó không hiển thị trong - trợ giúp và không có thêm thông tin nào có thể cho thấy câu trả lời là 'không', nhưng tôi muốn thấy điều này được xác nhận.

Có thể hiển thị tổng tiến trình truyền tệp với rsync?

260
Aron Rotteveel

Hiện tại đã có một cách chính thức để thực hiện việc này trong rsync (phiên bản giao thức 3.1.0 phiên bản 31, Đã thử nghiệm với Ubuntu Trusty 14.04).

#> ./rsync -a --info=progress2 /usr .
    305,002,533  80%   65.69MB/s    0:00:01  xfr#1653, ir-chk=1593/3594)

Tôi đã thử với thư mục /usr Vì tôi muốn tính năng này để chuyển đổi toàn bộ hệ thống tệp và /usr Dường như là một mẫu đại diện tốt.

--info=progress2 Cho tỷ lệ phần trăm chung đẹp, ngay cả khi đó chỉ là một phần giá trị. Trên thực tế, thư mục /usr Của tôi có hơn 6 hợp đồng biểu diễn:

#> du -sh /usr
6,6G    /usr/

rsync mất rất nhiều thời gian để quét tất cả. Vì vậy, gần như toàn bộ thời gian mà tôi thấy đã hoàn thành khoảng 90%, nhưng dù sao cũng thật thoải mái khi thấy rằng một cái gì đó đang được sao chép :)

Người giới thiệu:

409
Avio

Bạn có thể với 'pv' (apt-get install pv với Debian và ubfox). Tôi khuyên bạn nên theo dõi số lượng tệp được truyền, vì lượng dữ liệu được truyền không tương quan với kích thước của tệp nhưng trên đồng bằng giữa nguồn và đích. Và đếm các tệp sẽ đếm cùng một tiến trình cho một đồng bằng lớn và một tệp khác có đồng bằng nhỏ. Điều đó có nghĩa là trong mọi trường hợp, ước tính ETA có thể còn xa. ETA dựa trên kích thước chỉ hoạt động nếu đích của bạn trống, trong trường hợp này là delta == kích thước nguồn.

Ý tưởng chung là phát ra một dòng trên mỗi tệp 'được chuyển' từ rsync và đếm các dòng đó bằng 'pv':

[.__.] rsync -ai/nguồn từ xa:/mệnh | pv -les [số lượng tệp]>/dev/null [.__.]

Tôi có xu hướng sao lưu toàn bộ hệ thống tệp (vì một số lý do), trong trường hợp này bạn có thể sử dụng df rẻ hơn nhiều để lấy số lượng tệp (thay vì du hoặc find wich sẽ đi qua hệ thống phân cấp nguồn của bạn một lần khác sau khi rsync thực hiện). Tùy chọn -x xuất hiện để đảm bảo rsync vẫn ở trên cùng một hệ thống tệp nguồn (và không tuân theo các giá trị gắn kết bên trong khác):

[.__.] rsync -aix/nguồn từ xa:/mệnh | pv -les $ (df -i/source | Perl -ane 'in $ F [2] nếu $ F [5] = ~ m: ^ /:')>/dev/null [.__.]

Nếu bạn muốn đếm tập tin trong/nguồn theo cách chung, hãy sử dụng find /source|wc -l (cảnh báo lại: có thể chậm và nặng về I/O).

48
zerodeux

Phần sau áp dụng cho phiên bản rsync 3.0.0 trở lên. Các tùy chọn được mô tả dưới đây được giới thiệu trong bản phát hành đó vào ngày 1 tháng 3 năm 2008.

Cùng với - thông tin = tiến trình2 bạn cũng có thể sử dụng - no-inc-recursive tùy chọn (hoặc ngắn hơn - no-ir bí danh) để vô hiệu hóa đệ quy gia tăng.

Điều này sẽ xây dựng toàn bộ danh sách tệp lúc đầu, thay vì tăng dần khám phá thêm các tệp khi quá trình chuyển tiếp diễn ra. Vì nó sẽ biết tất cả các tập tin trước khi bắt đầu, nó sẽ đưa ra một báo cáo tốt hơn về tiến trình tổng thể. Điều này áp dụng cho số lượng tệp - nó không báo cáo bất kỳ tiến trình nào dựa trên kích thước tệp.

Điều này liên quan đến một sự đánh đổi. Xây dựng toàn bộ danh sách tập tin trước thời hạn sẽ tốn nhiều bộ nhớ hơn và nó có thể trì hoãn đáng kể việc bắt đầu chuyển giao thực tế. Như bạn mong đợi, càng có nhiều tệp, độ trễ sẽ càng dài và càng cần nhiều bộ nhớ.

Sau đây là từ hướng dẫn rsync (nguồn - http://rsync.samba.org/ftp/rsync/rsync.html ):

- r, --recursive

Điều này nói với rsync để sao chép các thư mục đệ quy. Xem thêm --dirs (-d). Bắt đầu với rsync 3.0.0, thuật toán đệ quy được sử dụng bây giờ là quét tăng dần sử dụng ít bộ nhớ hơn trước và bắt đầu chuyển sau khi quét một vài thư mục đầu tiên đã hoàn tất. Quét tăng dần này chỉ ảnh hưởng đến thuật toán đệ quy của chúng tôi và không thay đổi chuyển không đệ quy. Nó cũng chỉ có thể khi cả hai đầu của quá trình chuyển ít nhất là phiên bản 3.0.0.

Một số tùy chọn yêu cầu rsync để biết danh sách tệp đầy đủ, vì vậy các tùy chọn này vô hiệu hóa chế độ đệ quy gia tăng. Chúng bao gồm: --delete-before, --delete-after, --Prune-blank-dirs và --delay-update. Do đó, chế độ xóa mặc định khi bạn chỉ định --delete hiện là --delete-during khi cả hai đầu của kết nối ít nhất là 3.0.0 (sử dụng --del hoặc --delete-during để yêu cầu chế độ xóa được cải thiện này một cách rõ ràng). Xem thêm tùy chọn --delete-delay là lựa chọn tốt hơn so với sử dụng --delete-after.

Có thể vô hiệu hóa đệ quy tăng dần bằng cách sử dụng tùy chọn - no-inc-recursive hoặc ngắn hơn - no-i-r bí danh.

Xem thêm https://rsync.samba.org để biết sự khác biệt về phiên bản cụ thể (cuộn xuống và kiểm tra các liên kết Tin tức phát hành).

40
Nate

danakim là chính xác. Không có cách tầm thường để thêm chỉ số tiến độ tổng.

Lý do cho điều này là khi rsync xem danh sách các tệp để đồng bộ hóa, nó không biết trước những tệp nào sẽ cần thay đổi. Nếu bạn đang thực hiện chuyển giao delta, bản thân đồng bằng phải được tính toán trước để đưa ra một bức tranh tổng thể về công việc cần phải hoàn thành.

Nói cách khác, cách dễ nhất để tính toán có bao nhiêu công việc phải làm là thực sự làm nó.

37
David Mackintosh

Đối với chuyển khoản dài, tôi hài lòng với việc chạy du -s cả từ hai phía. Cũng watch -n1 du -s, nếu tôi cảm thấy thực sự lo lắng.

watch thực thi một lệnh (du -s here) định kỳ (cứ sau 1 giây tại đây) và hiển thị toàn màn hình đầu ra.

29
funollet

Về cơ bản là không. Bạn chỉ có thể hiển thị tiến trình trên mỗi tệp với cờ --proceed, nhưng đó là về nó.

Tôi đoán bạn có thể viết một trình bao bọc xung quanh nó hoặc sử dụng bất kỳ bản vá nào bạn đã tìm thấy nhưng bạn phải tự hỏi liệu nó có thực sự xứng đáng không, bạn có thực sự cần một tiến trình tổng thể cho rsync không?

13
danakim

Tôi đã sử dụng câu trả lời từ zerodeux và viết kịch bản bash nhỏ của riêng mình:

#!/bin/bash

RSYNC="ionice -c3 rsync"
# don't use --progress
RSYNC_ARGS="-vrltD --delete --stats --human-readable"
SOURCES="/dir1 /dir2 /file3"
TARGET="storage::storage"

echo "Executing dry-run to see how many files must be transferred..."
TODO=$(${RSYNC} --dry-run ${RSYNC_ARGS} ${SOURCES} ${TARGET}|grep "^Number of files transferred"|awk '{print $5}')

${RSYNC} ${RSYNC_ARGS} ${SOURCES} ${TARGET} | pv -l -e -p -s "$TODO"
8
FloHallo

Tôi cũng đã tìm kiếm cách hiển thị toàn bộ tiến trình với rsync và tôi đã tìm thấy một câu trả lời hữu ích từ bài đăng này: https://stackoverflow.com/questions/7157973/monitoring-rsync-proTHER

Về cơ bản, bạn có thể sử dụng - info = Progress2 trong phiên bản dev của rsync 3.1.0 . Đây là những gì doc đã nói:

Ngoài ra còn có tùy chọn --info = Progress2 cung cấp số liệu thống kê dựa trên toàn bộ chuyển, thay vì các tệp riêng lẻ. Sử dụng cờ này mà không xuất tên tệp (ví dụ: tránh -v hoặc chỉ định --info = name0 nếu bạn muốn xem cách chuyển đang thực hiện mà không cuộn màn hình với nhiều tên. (Bạn không cần chỉ định - tùy chọn tiến trình để sử dụng --info = Progress2.)

7
Zhenyi Zhang

Nếu bạn don lồng có rsync mới nhất (ví dụ: OS X có 2.6.9) và có thể sử dụng --info=progress2, ở đây, một cách khác để tự cứu mình khỏi các trang cuộn văn bản đang tiến hành:

rsync -aPh <source> <destination> | xargs -L1 printf "\33[2K\rTransferring: %s"

Điều đó sẽ in ra, trên một dòng, tên của tệp mới nhất được chuyển:

Transferring: the-latest.file

6
Aral Balkan

Tôi đã sử dụng câu trả lời từ zerodeux và viết kịch bản BASH nhỏ của riêng mình:

#!/bin/bash

RSYNC="ionice -c3 rsync"
# don't use --progress
RSYNC_ARGS="-vrltD --delete --stats --human-readable"
SOURCES="/dir1 /dir2 /file3"
TARGET="storage::storage"

#echo "Executing dry-run to see how many files must be transferred..."
TODO=$(find ${SOURCES} | wc -l)

${RSYNC} ${RSYNC_ARGS} ${SOURCES} ${TARGET} | pv -l -e -p -s "$TODO"

Tôi đã thay đổi TODO chạy khô thành

TODO=$(find ${SOURCES} | wc -l)

Nó tìm thấy số lượng tập tin rất nhanh!

6
user151779

Tôi muốn bình luận nhưng không đủ danh tiếng. Đáp lại nhận xét của naught101 đối với câu trả lời đã chọn, tùy chọn --prowards cho biết có bao nhiêu tệp đã được chuyển ra khỏi tổng số tiền cần chuyển. Tôi đã không nhận ra điều này cho đến khi nhìn vào bài đăng này và xem xét đầu ra cẩn thận hơn.

Chỉ số 'để kiểm tra' cho thấy có bao nhiêu tệp bị bỏ sót trong tổng số. Điều này được sử dụng nhiều nhất khi rsync đến một đích mới để bạn biết tất cả các tệp sẽ được sao chép hoàn toàn.

Từ trang người đàn ông:

When [each] file transfer  finishes,  rsync  replaces  the
progress line with a summary line that looks like this:

    1238099 100%  146.38kB/s    0:00:08  (xfer#5, to-check=169/396)

In this example, the file was  1238099  bytes  long  in
total,  the average rate of transfer for the whole file
was 146.38 kilobytes per second over the 8 seconds that
it took to complete, it was the 5th transfer of a regu-
lar file during the current rsync  session,  and  there
are 169 more files for the receiver to check (to see if
they are up-to-date or not) remaining out  of  the  396
total files in the file-list.
4
Michael S

Sử dụng

lsof -ad3-999 -c rsync

Để xem những gì tệp rsync hiện đang mở (sẽ hiển thị kích thước tệp) các bản sao rsync vào một tệp ẩn cục bộ

4
Cloom Magoo

Lưu ý cảnh báo ở đây rằng thậm chí --info = Progress2 không hoàn toàn đáng tin cậy vì đây là tỷ lệ phần trăm dựa trên số lượng tệp rsync 'biết' tại thời điểm tiến trình đang được hiển thị. Đây không nhất thiết là tổng số tệp cần được đồng bộ hóa (ví dụ: nếu nó phát hiện ra một số lượng lớn tệp lớn trong một thư mục được lồng sâu). Một cách để đảm bảo rằng --info = Progress2 không 'nhảy lùi' trong chỉ báo tiến trình sẽ buộc rsync quét tất cả các thư mục trước khi bắt đầu đồng bộ hóa (thay vì hành vi mặc định của nó là thực hiện quét đệ quy tăng dần), bằng cách cung cấp tùy chọn --no-inc-đệ quy. Tuy nhiên, lưu ý rằng tùy chọn này cũng sẽ tăng thời gian sử dụng bộ nhớ rsync và thời gian chạy.

3
lonetwin

Tôi sử dụng tập lệnh trích xuất thông tin từ/Proc // io cho quy trình rsync (hoặc bất kỳ quy trình nào khác cho vấn đề đó) và biết tổng số tiền cần chuyển sẽ tính toán tiến trình.

#!/bin/bash

usage()
{
   echo "usage: $0 PID BASEMSIZE [DELAY[s|m|h]]"
}

if [ $# -lt 2 ]; then
   usage
   exit 1
Elif [ $# -eq 3 ]; then
   DELAY=$3
else
   DELAY=5s
fi

PID=$1
PBASE=`echo "scale=2; $2/1024"|bc`

R_PID=$PID
W_PID=$PID

R_SPEED_MAX=0
W_SPEED_MAX=0
R_SPEED_CUM=0
W_SPEED_CUM=0
R_SPEED_AVG=0
W_SPEED_AVG=0

ETA=0
ETA_H=0
ETA_M=0
ETA_S=0

while [ ! -r /proc/$PID/io ];
do
   clear
   echo "Waiting for process with PID=$PID to appear!"
   sleep 1
done

B_READ_PREV=`cat /proc/$R_PID/io|awk '$1 ~ /^read_bytes/ {print $2}'`
B_WRITE_PREV=`cat /proc/$W_PID/io|awk '$1 ~ /^write_bytes/ {print $2}'`
T1=`date +%s.%N`

count=0
while true
do
   [ ! -r /proc/$PID/io ] && break
   clear
   B_READ=`cat /proc/$R_PID/io|awk '$1 ~ /^read_bytes/ {print $2}'`
   B_WRITE=`cat /proc/$W_PID/io|awk '$1 ~ /^write_bytes/ {print $2}'`
   BL_READ=`echo "scale=2; ($B_READ-$B_READ_PREV)/1048576"|bc`
   BL_WRITE=`echo "scale=2; ($B_WRITE-$B_WRITE_PREV)/1048576"|bc`
   GB_DONE=`echo "scale=2; $B_WRITE/1073741824"|bc`
   PDONE=`echo "scale=2; $GB_DONE*100/$PBASE"|bc`
   T2=`date +%s.%N`
   TLOOP=`echo "scale=2; ($T2-$T1)/1"|bc`
   R_SPEED=`echo "scale=2; $BL_READ/$TLOOP"|bc`
   W_SPEED=`echo "scale=2; $BL_WRITE/$TLOOP"|bc`

   if [ $count -ge 1 ]; then
      R_SPEED_CUM=`echo "scale=2; $R_SPEED_CUM+$R_SPEED"|bc`
      R_SPEED_AVG=`echo "scale=2; $R_SPEED_CUM/$count"|bc`
      W_SPEED_CUM=`echo "scale=2; $W_SPEED_CUM+$W_SPEED"|bc`
      W_SPEED_AVG=`echo "scale=2; $W_SPEED_CUM/$count"|bc`
      [ `echo "scale=2; $W_SPEED > $W_SPEED_MAX"|bc` -eq 1 ] && W_SPEED_MAX=$W_SPEED
      [ `echo "scale=2; $R_SPEED > $R_SPEED_MAX"|bc` -eq 1 ] && R_SPEED_MAX=$R_SPEED
   fi

   if [ `echo "scale=2; $W_SPEED_AVG > 0"|bc` -eq 1 ]; then
      ETA=`echo "scale=2; (($PBASE-$GB_DONE)*1024)/$W_SPEED_AVG"|bc`
      ETA_H=`echo "scale=0; $ETA/3600"|bc`
      ETA_M=`echo "scale=0; ($ETA%3600)/60"|bc`
      ETA_S=`echo "scale=0; ($ETA%3600)%60"|bc`
   fi

   echo "Monitoring PID: $PID"
   echo
   echo "Read:       $BL_READ MiB in $TLOOP s"
   echo "Write:      $BL_WRITE MiB in $TLOOP s"
   echo
   echo "Read Rate:  $R_SPEED MiB/s ( Avg: $R_SPEED_AVG, Max: $R_SPEED_MAX )"
   echo "Write Rate: $W_SPEED MiB/s ( Avg: $W_SPEED_AVG, Max: $W_SPEED_MAX )"
   echo
   echo "Done: $GB_DONE GiB / $PBASE GiB ($PDONE %)"
   [ `echo "scale=2; $ETA > 0"|bc` -eq 1 ] && printf "ETA: %02d:%02d:%05.2f (%.2fs)\n" $ETA_H $ETA_M $ETA_S $ETA
   echo "Elapsed: `ps -p $PID -o etime=`"

   T1=`date +%s.%N`
   sleep $DELAY
   B_READ_PREV=$B_READ
   B_WRITE_PREV=$B_WRITE
   ((count++))
done
echo "----- Finished -------------------------------------------------------------------"
2
nito

Nếu phiên bản rsync của bạn không chấp nhận --info=progress2 tùy chọn, bạn có thể sử dụng tqdm :

Để cài đặt:

pip install tqdm

Để sử dụng:

[.__.] $ rsync -av/nguồn/mệnh | tqdm --unit_scale | wc -l [.__.] 10.0Mit [00:02, 3.58Mit/s] [.__.]
2
ostrokach

Có lẽ bạn có thể kết hợp pv với rsync. Đặc biệt là tham số --size Có thể hữu ích. Nhìn vào các tài liệu, một cái gì đó như pv --size $(du -sb . | awk '{print $1}') | rsync -av . Host:/your/path sẽ hoạt động.

Tại đây bạn sẽ tìm thấy các tài liệu và phần mềm.

Tôi đã không tự mình thử điều này.

1
Christian

Có thể hơi muộn ở đây nhưng người tìm câu trả lời trong tương lai có thể có lợi.

Điều này cũng làm tôi khó chịu vì vậy tôi nghĩ tôi sẽ chán nản và viết kịch bản đầu tiên của mình. Gói tiện ích phải được cài đặt (Sudo apt-get install zenity), nhưng tôi chắc chắn rằng nó có thể sẽ ở đó. Ngoài ra, tôi sử dụng wmctrl (điều khiển trình quản lý cửa sổ) để thay đổi tiêu đề của hộp thoại tiến trình khi hoàn thành, nó có thể dễ dàng cài đặt nhưng sẽ không tạo ra sự khác biệt nếu bạn không. Tôi chỉ muốn xem khi nó được thực hiện trong bảng điều khiển của tôi.

Kịch bản về cơ bản yêu cầu một thư mục nguồn và đích, tính toán tỷ lệ phần trăm của đích trên kích thước nguồn bằng du và hiển thị một thanh tiến trình.

Lưu ý: Điều này chỉ hoạt động để đồng bộ hóa thư mục/tập tin hoàn chỉnh (tôi thường sử dụng nó để tạo bản sao lưu của bộ đệm apt), vì vậy không có tùy chọn --exclude =/file/in/Source-thư mục. Cũng sẽ không hoạt động nếu có tệp/thư mục trong thư mục Đích không có trong thư mục nguồn. Tôi không chắc liệu nó có hoạt động cho các nguồn/đích từ xa không vì tôi chưa bao giờ có nhu cầu về nó hoặc các tài nguyên để kiểm tra nó.

Tái bút Kịch bản này có thể được viết rất tệ hoặc rất kém hiệu quả, (kịch bản còn nguyên vẹn ở đây), nhưng ít nhất nó phục vụ mục đích của nó và tất nhiên bạn được hoan nghênh chỉnh sửa và cải thiện nó cho phù hợp với nhu cầu của bạn. PSS. Ngoài ra, không thể có nút hủy để giết rsync nên tôi mới gỡ bỏ nó.

    #!/bin/bash
set -e;

WELC="Running RsyncP as $USER";

function echo_progress()
{
    while (($TRANSFER_SIZE > 1000));    
    do  
        DEST_SIZE=$(du -s $DEST_FOLDER | cut -d / -f 1); 
        ((TRANSFER_SIZE=$SOURCE_SIZE-DEST_SIZE)); 
        PROGRESS_PERC=$((DEST_SIZE*100/SOURCE_SIZE));
        echo $PROGRESS_PERC;
        sleep 0.1s;
    done;
    echo 100;
    zenity --info --width=250 --title=RsyncP --text="File syncing complete!";
}

function get_input()
{
    dirs=$(zenity --forms --width=500 --title="RsyncP" --text="Enter source And destination directories" --add-entry="Source: " --add-entry="Destination: " --separator=" ");

    SOURCE_FOLDER=$(echo $dirs | cut -d' ' -f 1);
    DEST_FOLDER=$(echo $dirs | cut -d' ' -f 2);

    OPTIONS=-$(zenity --list --title="RsyncP Options" --text="Select rsync options" --separator='' --height=470 --width=470 --checklist --column "activate" --column "Option" --column "Description" FALSE v "Verbose (Terminal only)" FALSE q "Quiet, supress non-error messages (Terminal only)" FALSE P "Progress (Terminal only)" FALSE a "Archive (lrpog)" TRUE r "Recurse into directories" FALSE p "Preserve permissions" FALSE o "Preserve owner" FALSE g "Preserve group" FALSE l "Copy symlinks as symlinks");

    zenity --question --no-wrap --title="RsyncP" --width=500 --text="rsync  $OPTIONS $SOURCE_FOLDER $DEST_FOLDER\nDo you want to continue?";

    SOURCE_SIZE=$(du -s $SOURCE_FOLDER | cut -d / -f 1); 
    DEST_SIZE=$(du -s $DEST_FOLDER | cut -d / -f 1); 
    PROGRESS_PERC=$((DEST_SIZE*100/SOURCE_SIZE)); 
    TRANSFER_SIZE=1001;
}

if [ "$(id -u)" != "0" ]; then
    zenity --question --title=RsyncP --text="$WELC, Continue?";
    get_input;
    rsync  $OPTIONS $SOURCE_FOLDER $DEST_FOLDER & 
    echo_progress | zenity --progress --title=RsyncP --no-cancel --auto-close --text="Copying from \n$SOURCE_FOLDER to \n$DEST_FOLDER" ;

else            
    zenity --question --title=RsyncP --text="$WELC, Continue?";
    get_input; 
    Sudo rsync  $OPTIONS $SOURCE_FOLDER $DEST_FOLDER & 
    echo_progress | zenity --progress --title=RsyncP --no-cancel --auto-close --text="Copying from \n$SOURCE_FOLDER to \n$DEST_FOLDER" ;
fi
1
neill_L