Ruby - 如何使用 open-uri 获取文件的名称?

标签 ruby http url uri open-uri

我想通过这种方式下载一个音乐文件:

require 'open-uri'

source_url = "http://soundcloud.com/stereo-foo/cohete-amigo/download"

attachment_file = "test.wav"

open(attachment_file, "wb") do |file|  
  file.print open(source_url).read
end

在该示例中,我想将“Test.wav”更改为真实文件名(例如 JDownloader 程序)。

编辑:我不是指临时文件,我指的是像 Jdownloader 一样在网络中存储的文件:“Cohete Amigo - Stereo Foo.wav”

感谢阅读

更新:

我试过用这个来存储名字:

attachment_file = File.basename(open(source_url))

我认为这没有意义,但我不知道该怎么做,抱歉。

最佳答案

文件名存储在名为 Content-Disposition 的 header 字段中。然而解码这个字段可能有点棘手。例如,在此处查看一些讨论:

How to encode the filename parameter of Content-Disposition header in HTTP?

对于 open-uri,您可以通过 meta 访问所有 header 字段返回的 File 类的访问器:

f = open('http://soundcloud.com/stereo-foo/cohete-amigo/download')
f.meta['content-disposition']
=> "attachment;filename=\"Stereo Foo - Cohete Amigo.wav\""

所以为了解码类似的东西,你可以这样做:

cd = f.meta['content-disposition'].
filename = cd.match(/filename=(\"?)(.+)\1/)[2]
=> "Stereo Foo - Cohete Amigo.wav"

它适用于您的特定情况,如果引号 " 不存在,它也适用。但是在更复杂的内容处理情况下,例如 UTF-8 文件名,您可能会遇到一些麻烦. 虽然不确定 UTF-8 的使用频率,甚至 soundcloud 是否也使用过 UTF-8。所以也许您不必担心这一点(未经确认或测试)。

您还可以使用更高级的网络爬虫框架,例如 Mechanize ,并相信它会为您解码:

require 'mechanize'

agent = Mechanize.new
file = agent.get('http://soundcloud.com/stereo-foo/cohete-amigo/download')
file.filename
=> "Stereo_Foo_-_Cohete_Amigo.wav"

关于Ruby - 如何使用 open-uri 获取文件的名称?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13393725/

相关文章:

ruby-on-rails - 如何将长日期转换为日期?

web-services - REST API 设计 : different granularity for receiving and updating resources

javascript - node-fetch 接收空主体

http - 如何在没有网络延迟的情况下计算 HTTP 请求处理时间?

cocoa - 如何使用 Cocoa 获取具有给定 ID 的包的 URL,反之亦然?

java - Web应用程序URL访问java

ruby - 在 ruby​​ 中获取图像的尺寸

ruby - 在 Ruby 中,有没有办法使用类似 hash.each_with_index do |[k,v], i| 的方法?

c# - 如何使用 http 网络请求对字符串进行编码?

ruby - 给定一个 Ruby 元类,我如何获取它所附加的实例?