From several posts I've seen, I am trying this

x = Base64.decode64("data:image/png;base64,iVBOR....") File.open('test.png','wb') {|file| file.write x} 

But then I can't open the image with a viewer, do I have to do something more?

1

4 Answers

Your problem is that you're trying to decode the 'data:image/png;base64,' prefix as Base64 data; that prefix is perfectly valid Base64 data but it is not the Base64 representation of a PNG file. The result is that your test.png file contains a bunch of nonsense followed by some bits that actually are a PNG file. Strip off the data URL prefix before decoding the PNG:

data_url = "data:image/png;base64,iVBOR...." png = Base64.decode64(data_url['data:image/png;base64,'.length .. -1]) File.open('test.png', 'wb') { |f| f.write(png) } 
7

mu_is_too_short answer is pretty close, but it assumes that base64 stream will contain PNG data. This is not always the case so I suggest to use mime types library to establish correct file extension:

REGEXP = /\Adata:([-\w]+\/[-\w\+\.]+)?;base64,(.*)/m data_uri_parts = data_url.match(REGEXP) || [] extension = MIME::Types[data_uri_parts[1]].first.preferred_extension file_name = "myfilename.#{extension}" File.open(file_name, 'wb') do |file| file.write(Base64.decode64(data_uri_parts[2])) end 

Instead of using a Regexp, you can also make use of the simple String#index method.

Returns the index of the first occurrence of the given substring or pattern (regexp) in str. Returns nil if not found.

If you have a reasonably sane data source (like JavaScript's .toDataURL() on a canvas), you can rely on the fact that common mimetypes will not contain commas.

dataURL = "data:image/png;base64,iVBOR...." start = dataURL.index(',') + 1 # .index used here x = Base64.decode64 dataURL[start..-1] File.open('test.png','wb') {|file| file.write x} 

If you're working with a free-form user file upload, beware that a few uncommon mime types do contain commas (e.g.: text/x-java-source,java). You can use the more conservative:

start = dataURL.index(';base64,') + 8 

If you don't know if you have unprefixed base64 or data URL base64, you can use #index as test:

start = dataURL.index ';base64,' dataURL = dataURL[(start+8)..-1] if start x = Base64.decode64 dataURL 

that's a little script about how to open base64 image,vacio.txt is the file when i have the base64 text.

require 'base64' entry="data:image/jpeg;base64,/9j/4AAQSkZJRgABAQE....." File.open("vacio.txt","r") do |fichero| while linea=fichero.gets regex=/(data:image\/\D*\d*,)/ m=regex.match(linea) png=Base64.decode64(linea[m.to_s.length .. -1]) File.open('test.jpeg','wb'){|f|f.write(png)} end end 

Your Answer

Sign up or log in

Sign up using Google Sign up using Facebook Sign up using Email and Password

Post as a guest

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.