Ruby 在复制文件时显示进度

发布于 2024-07-15 11:50:22 字数 216 浏览 9 评论 0原文

我希望能够在使用 Ruby 复制文件时显示文件复制操作的进度(当前使用 FileUtils.cp)我尝试将 verbose 选项设置为 true 但这似乎只是向我展示了发出的复制命令。

我现在正在从命令行运行这个脚本,所以理想情况下我希望能够呈现像 SCP 在复制文件时所做的那样,但只要我能看到进度,我就不会太在意演示。

I'd like to be able to show the progress of a file copy operation when copying files using Ruby (currently using FileUtils.cp) I've tried setting the verbose option to true but that just seems to show me the copy command issued.

I'm running this script from command line at the moment so ideally I'd like to be able to present something like SCP does when it copies files, but I'm not too fussed about the presentation as long as I can see the progress.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

俯瞰星空 2024-07-22 11:50:22

由于我没有足够的代表来编辑答案,所以这是我基于 pisswillis 答案的版本,我找到了 进度条 gem 我也在我的示例中使用。 我已经对此进行了测试,到目前为止一切正常,但需要进行一些清理:

require 'rubygems'
require 'progressbar'

in_name     = "src_file.txt"
out_name    = "dest_file.txt"

in_file     = File.new(in_name, "r")
out_file    = File.new(out_name, "w")

in_size     = File.size(in_name)
# Edit: float division.
batch_bytes = ( in_size / 100.0 ).ceil
total       = 0
p_bar       = ProgressBar.new('Copying', 100)

buffer      = in_file.sysread(batch_bytes)
while total < in_size do
 out_file.syswrite(buffer)
 p_bar.inc
 total += batch_bytes
 if (in_size - total) < batch_bytes
   batch_bytes = (in_size - total)
 end
 buffer = in_file.sysread(batch_bytes)
end
p_bar.finish

As I don't have enough rep to edit answers yet here is my version based on pisswillis answer, I found a progress bar gem which I'm also using in my example. I have tested this and it has worked OK so far, but it could do with some cleaning up:

require 'rubygems'
require 'progressbar'

in_name     = "src_file.txt"
out_name    = "dest_file.txt"

in_file     = File.new(in_name, "r")
out_file    = File.new(out_name, "w")

in_size     = File.size(in_name)
# Edit: float division.
batch_bytes = ( in_size / 100.0 ).ceil
total       = 0
p_bar       = ProgressBar.new('Copying', 100)

buffer      = in_file.sysread(batch_bytes)
while total < in_size do
 out_file.syswrite(buffer)
 p_bar.inc
 total += batch_bytes
 if (in_size - total) < batch_bytes
   batch_bytes = (in_size - total)
 end
 buffer = in_file.sysread(batch_bytes)
end
p_bar.finish
逆夏时光 2024-07-22 11:50:22

使用 IO.syswrite、IO.sysread 自行开发。

首先,决定进度条的长度(以字符为单位)..然后这个伪代码应该做到这一点(未经测试):

infile = File.new("source", "r")
outfile = File.new("target", "w")

no_of_bytes = infile.length / PROGRESS_BAR_LENGTH

buffer = infile.sysread(no_of_bytes)
while buffer do
 outfile = syswrite(buffer)
 update_progress_bar()
 buffer = infile.sysread(no_of_bytes)
end

其中 update_progress_bar() 是使进度条增加一个字符的方法。
上述内容未经测试,可能会让红宝石纯粹主义者感到不适。 特别是 EOFException 可能会扰乱循环。 如果 no_of_bytes 不是整数,您还需要某种方法来确保所有字节都被写入。

Roll your own using IO.syswrite, IO.sysread.

First, decide length of progress bar (in chars).. then this pseudo code should do it (NOT TESTED):

infile = File.new("source", "r")
outfile = File.new("target", "w")

no_of_bytes = infile.length / PROGRESS_BAR_LENGTH

buffer = infile.sysread(no_of_bytes)
while buffer do
 outfile = syswrite(buffer)
 update_progress_bar()
 buffer = infile.sysread(no_of_bytes)
end

where update_progress_bar() is your method to increment the progress bar by one char.
The above is not tested and will probably make ruby purists ill. In particular an EOFException might mess up the loop. Also you will need some way of making sure that all the bytes are written if no_of_bytes is not an integer.

白云悠悠 2024-07-22 11:50:22

或者你可以破解它以使用 scp,如果这是你喜欢的进度条:

def copy(source, dest)
  `scp #{source} localhost:#{dest}`
end

你必须确保源名称和目标名称对于系统调用正确转义。 localhost: 标签使 scp 复制文件,就像在计算机之间一样,因此它将显示一个进度条。

Or you could just hack it to use scp, if that's the progress bar you like:

def copy(source, dest)
  `scp #{source} localhost:#{dest}`
end

You'll have to make sure the source and dest names are properly escaped for a system call. The localhost: tag makes scp copy the files as it does between computers, so it will show a progress bar.

洒一地阳光 2024-07-22 11:50:22

在 Windows 下,不要忘记为二进制文件添加“b”,因此“w”和“r”应该是二进制文件的“wb”和“rb”。

in_file     = File.new(in_name, "rb")
out_file    = File.new(out_name, "wb")

Under Windows don't forget to add the 'b' for binary files, so 'w' and 'r' should be 'wb' and 'rb' for binary files.

in_file     = File.new(in_name, "rb")
out_file    = File.new(out_name, "wb")
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文