如何将文件 url 传递给中间人的辅助方法
How to pass file url to helper method in middleman
我正在编写一个辅助方法,以便在需要时将图像转换为 base64 字符串。下面是代码
# config.rb
helpers do
def base64_url(img_link, file_type: "jpg")
require "base64"
if file_type =="jpg"
"data:image/jpg;base64,#{Base64.encode64(open(img_link).to_a.join)}"
elsif file_type =="png"
"data:image/jpg;base64,#{Base64.encode64(open(img_link).to_a.join)}"
else
link
end
end
end
在page.html.erb
<%= image_tag base64_url('/images/balcozy-logo.jpg') %>
现在的问题是当 ruby 读取 '/images/balcozy-logo.jpg'
它从系统根目录而不是项目根目录读取文件。
错误信息如下
Errno::ENOENT at /
No such file or directory @ rb_sysopen - /images/balcozy-logo.jpg
如何解决这个问题并从 project_root/source/images
传递正确的图像 url
在 Middleman app.root
returns 应用程序的根目录。还有 app.root_path
,它的作用相同,但 return 是一个 Pathname 对象,稍微方便一些:
full_path = app.root_path.join("source", img_link.gsub(/^\//, ''))
如果 img_link
以 /
开头,则 gsub
是必需的,因为它将被解释为文件系统的根目录。
我冒昧地对你的方法做了一些修改:
require "base64"
helpers do
def base64_url(path, file_type: "jpg")
return path unless ["jpg", "png"].include?(file_type)
full_path = app.root_path.join("source", path.gsub(/^\//, ''))
data_encoded = File.open(full_path, 'r') do |file|
Base64.urlsafe_encode64(file.read)
end
"data:image/#{file_type};base64,#{data_encoded}"
end
end
我在这里做了一些事情:
移动require "base64"
到文件顶部;它不属于方法内部。
在方法的最开始检查file_type
,如果不在列出的类型中,则尽早检查return。
而不是 open(filename).to_a.join
(或更简洁的 open(filename).read
),使用 File.open
。 OpenURI(提供您正在使用的 open
方法)对于从本地文件系统读取来说是多余的。
使用 Base64.urlsafe_encode64
而不是 encode64
。可能没有必要,但也无妨。
删除不需要的if
;因为我们知道 file_type
将是 jpg
或 png
我们可以直接在数据 URI 中使用它。
可能有更优雅的方法来获取 file_path
或使用 Middleman 的 built-in 资产系统确定文件的 MIME 类型,但是对文档的非常简短的搜索没有找到任何结果。
我正在编写一个辅助方法,以便在需要时将图像转换为 base64 字符串。下面是代码
# config.rb
helpers do
def base64_url(img_link, file_type: "jpg")
require "base64"
if file_type =="jpg"
"data:image/jpg;base64,#{Base64.encode64(open(img_link).to_a.join)}"
elsif file_type =="png"
"data:image/jpg;base64,#{Base64.encode64(open(img_link).to_a.join)}"
else
link
end
end
end
在page.html.erb
<%= image_tag base64_url('/images/balcozy-logo.jpg') %>
现在的问题是当 ruby 读取 '/images/balcozy-logo.jpg'
它从系统根目录而不是项目根目录读取文件。
错误信息如下
Errno::ENOENT at /
No such file or directory @ rb_sysopen - /images/balcozy-logo.jpg
如何解决这个问题并从 project_root/source/images
在 Middleman app.root
returns 应用程序的根目录。还有 app.root_path
,它的作用相同,但 return 是一个 Pathname 对象,稍微方便一些:
full_path = app.root_path.join("source", img_link.gsub(/^\//, ''))
如果 img_link
以 /
开头,则 gsub
是必需的,因为它将被解释为文件系统的根目录。
我冒昧地对你的方法做了一些修改:
require "base64"
helpers do
def base64_url(path, file_type: "jpg")
return path unless ["jpg", "png"].include?(file_type)
full_path = app.root_path.join("source", path.gsub(/^\//, ''))
data_encoded = File.open(full_path, 'r') do |file|
Base64.urlsafe_encode64(file.read)
end
"data:image/#{file_type};base64,#{data_encoded}"
end
end
我在这里做了一些事情:
移动
require "base64"
到文件顶部;它不属于方法内部。在方法的最开始检查
file_type
,如果不在列出的类型中,则尽早检查return。而不是
open(filename).to_a.join
(或更简洁的open(filename).read
),使用File.open
。 OpenURI(提供您正在使用的open
方法)对于从本地文件系统读取来说是多余的。使用
Base64.urlsafe_encode64
而不是encode64
。可能没有必要,但也无妨。删除不需要的
if
;因为我们知道file_type
将是jpg
或png
我们可以直接在数据 URI 中使用它。
可能有更优雅的方法来获取 file_path
或使用 Middleman 的 built-in 资产系统确定文件的 MIME 类型,但是对文档的非常简短的搜索没有找到任何结果。