如何获取ruby中的位图图像?
How to get a bitmap image in ruby?
google 愿景 API 需要将位图作为参数发送。我正在尝试将 png 从 URL 转换为位图以传递给 google api:
require "google/cloud/vision"
PROJECT_ID = Rails.application.secrets["project_id"]
KEY_FILE = "#{Rails.root}/#{Rails.application.secrets["key_file"]}"
google_vision = Google::Cloud::Vision.new project: PROJECT_ID, keyfile: KEY_FILE
img = open("https://www.google.com/images/branding/googlelogo/2x/googlelogo_color_272x92dp.png").read
image = google_vision.image img
ArgumentError: string contains null byte
这是gem的源码处理:
def self.from_source source, vision = nil
if source.respond_to?(:read) && source.respond_to?(:rewind)
return from_io(source, vision)
end
# Convert Storage::File objects to the URL
source = source.to_gs_url if source.respond_to? :to_gs_url
# Everything should be a string from now on
source = String source
# Create an Image from a HTTP/HTTPS URL or Google Storage URL.
return from_url(source, vision) if url? source
# Create an image from a file on the filesystem
if File.file? source
unless File.readable? source
fail ArgumentError, "Cannot read #{source}"
end
return from_io(File.open(source, "rb"), vision)
end
fail ArgumentError, "Unable to convert #{source} to an Image"
end
https://github.com/GoogleCloudPlatform/google-cloud-ruby
为什么它告诉我字符串包含空字节?如何在 ruby 中获取位图?
记得阅读二进制格式的东西:
open("https://www.google.com/..._272x92dp.png",'r:BINARY').read
如果您忘记了它,它可能会尝试将其作为 UTF-8 文本数据打开,这会导致很多问题。
根据 documentation(公平地说,如果不深入研究源代码就很难找到),Google::Cloud::Vision#image
不需要原始图像字节,它需要某种路径或 URL:
Use Vision::Project#image
to create images for the Cloud Vision service.
You can provide a file path:
[...]
Or any publicly-accessible image HTTP/HTTPS URL:
[...]
Or, you can initialize the image with a Google Cloud Storage URI:
所以你想说这样的话:
image = google_vision.image "https://www.google.com/images/branding/googlelogo/2x/googlelogo_color_272x92dp.png"
而不是自己读取图像数据。
您不想使用 write
,而是使用 IO.copy_stream
,因为它将下载直接流式传输到文件系统,而不是将整个文件读入内存然后写入:
require 'open-uri'
require 'tempfile'
uri = URI("https://www.google.com/images/branding/googlelogo/2x/googlelogo_color_272x92dp.png")
tmp_img = Tempfile.new(uri.path.split('/').last)
IO.copy_stream(open(uri), tmp_img)
请注意,您不需要设置 'r:BINARY'
标志,因为字节只是流式传输而没有实际读取文件。
然后您可以通过以下方式使用该文件:
require "google/cloud/vision"
# Use fetch as it raises an error if the key is not present
PROJECT_ID = Rails.application.secrets.fetch("project_id")
# Rails.root is a Pathname object so use `.join` to construct paths
KEY_FILE = Rails.root.join(Rails.application.secrets.fetch("key_file"))
google_vision = Google::Cloud::Vision.new(
project: PROJECT_ID,
keyfile: KEY_FILE
)
image = google_vision.image(File.absolute_path(tmp_img))
完成后调用 tmp_img.unlink
进行清理。
google 愿景 API 需要将位图作为参数发送。我正在尝试将 png 从 URL 转换为位图以传递给 google api:
require "google/cloud/vision"
PROJECT_ID = Rails.application.secrets["project_id"]
KEY_FILE = "#{Rails.root}/#{Rails.application.secrets["key_file"]}"
google_vision = Google::Cloud::Vision.new project: PROJECT_ID, keyfile: KEY_FILE
img = open("https://www.google.com/images/branding/googlelogo/2x/googlelogo_color_272x92dp.png").read
image = google_vision.image img
ArgumentError: string contains null byte
这是gem的源码处理:
def self.from_source source, vision = nil
if source.respond_to?(:read) && source.respond_to?(:rewind)
return from_io(source, vision)
end
# Convert Storage::File objects to the URL
source = source.to_gs_url if source.respond_to? :to_gs_url
# Everything should be a string from now on
source = String source
# Create an Image from a HTTP/HTTPS URL or Google Storage URL.
return from_url(source, vision) if url? source
# Create an image from a file on the filesystem
if File.file? source
unless File.readable? source
fail ArgumentError, "Cannot read #{source}"
end
return from_io(File.open(source, "rb"), vision)
end
fail ArgumentError, "Unable to convert #{source} to an Image"
end
https://github.com/GoogleCloudPlatform/google-cloud-ruby
为什么它告诉我字符串包含空字节?如何在 ruby 中获取位图?
记得阅读二进制格式的东西:
open("https://www.google.com/..._272x92dp.png",'r:BINARY').read
如果您忘记了它,它可能会尝试将其作为 UTF-8 文本数据打开,这会导致很多问题。
根据 documentation(公平地说,如果不深入研究源代码就很难找到),Google::Cloud::Vision#image
不需要原始图像字节,它需要某种路径或 URL:
Use
Vision::Project#image
to create images for the Cloud Vision service.You can provide a file path:
[...]
Or any publicly-accessible image HTTP/HTTPS URL:
[...]
Or, you can initialize the image with a Google Cloud Storage URI:
所以你想说这样的话:
image = google_vision.image "https://www.google.com/images/branding/googlelogo/2x/googlelogo_color_272x92dp.png"
而不是自己读取图像数据。
您不想使用 write
,而是使用 IO.copy_stream
,因为它将下载直接流式传输到文件系统,而不是将整个文件读入内存然后写入:
require 'open-uri'
require 'tempfile'
uri = URI("https://www.google.com/images/branding/googlelogo/2x/googlelogo_color_272x92dp.png")
tmp_img = Tempfile.new(uri.path.split('/').last)
IO.copy_stream(open(uri), tmp_img)
请注意,您不需要设置 'r:BINARY'
标志,因为字节只是流式传输而没有实际读取文件。
然后您可以通过以下方式使用该文件:
require "google/cloud/vision"
# Use fetch as it raises an error if the key is not present
PROJECT_ID = Rails.application.secrets.fetch("project_id")
# Rails.root is a Pathname object so use `.join` to construct paths
KEY_FILE = Rails.root.join(Rails.application.secrets.fetch("key_file"))
google_vision = Google::Cloud::Vision.new(
project: PROJECT_ID,
keyfile: KEY_FILE
)
image = google_vision.image(File.absolute_path(tmp_img))
完成后调用 tmp_img.unlink
进行清理。