Problems with FasterCSV (Ruby) - ruby

I'm writing a program, that creates a csv-File. And I have a problem right at the beginning.
So, my code is
def create_csv
destfile = Rails.root.join("public", "reports", "statistic_csv#{id}.csv")
csv_string = FasterCSV.generate do |out|
out << ["row", "of", "CSV", "data"]
end
FasterCSV.open(destfile, "w") do |csv|
csv << csv_string
end
end
I thought, I will get 4 columns in the output file, smth like this row|of|csv|data. But what I get is "row,of,CSV,data" in one cell A1. How can i solve the Problem? Thanks in advance!
PS. I use ruby 1.8.7 and FasterCSV 1.5.5

You are encoding the CSV string twice. This should work:
def create_csv
destfile = Rails.root.join("public", "reports", "statistic_csv#{id}.csv")
FasterCSV.open(destfile, "wb") do |csv|
csv << ["row", "of", "CSV", "data"]
end
end
You can also specify a custom column separator:
FasterCSV.open(destfile, "wb", { :col_sep => "|" }) do |csv|
# ...
end

I presume you're opening this in Excel. Excel may not be detecting the file as a CSV file. Try importing the data into an excel workbook as opposed to opening the file in Excel.

Related

Is there a way to make Ruby CSV gem generate CSVs with Windows (CR LF) End Of Lines?

For some reason CSV gem is generating CSVs with Unix EOL (see screenshot) here:
https://www.dropbox.com/s/4re7tpp4pj9psov/ice_screenshot_20171230-162304.png?dl=0
Screenshot made in Notepad++ (View all Characters)
Code I use:
require 'csv'
all_the_things = []
all_the_things << ["item1.1","item1.2","item1.3"]
all_the_things << ["item2.1","item2.1","item2.1"]
all_the_things << ["item3.1","item3.1","item3.1"]
CSV.open("test.csv", "wb" ) do |row|
row << ["Column1", "Column2", "Column3"] #just headers
all_the_things.each do |data|
row << data
end
end
Is there a way to make it use Windows EOL (CR LF) instead of UNIX (LF) ones ?
I'm using Windows 10, and if I just output some lines to file using puts everything working just fine (albeight managing proper data structure without CSV gem is nightmare):
....
File.open("test.csv", "w") do |line|
myarray.each do |data|
line.puts data
end
end
Thank you in advance for any ideas and Happy New Year !
As it is clearly stated in the documentation, one might use the row_sep option to specify the row separator:
require 'csv'
# ⇓⇓⇓⇓⇓⇓⇓⇓⇓⇓⇓⇓⇓⇓⇓ here
CSV.open("/tmp/file.csv", "wb", row_sep: "\r\n") do |csv|
csv << %w|1 2 3 4|
csv << %w|a b c d|
end
Also, there is no “CSV gem,” it’s ruby standard library.

Adding Headers to a created CSV file in Ruby - keep getting errors

I've been trying to use Ruby to create a CSV file from json data. I was able to create the file, but I need to add a few headers. I tried following suggestions and answers from similar questions posted here on Stack Overflow, but I keep getting errors. Can anyone give me some pointers?
Here's my code.
require 'csv'
require 'json'
CSV.open("your_csv.csv", "w") do |csv|
JSON.parse(File.open("tojson.txt").read).each do |hash|
csv << hash.values
#csv.each { |line| line['New_header'] = line[0].to_i + line[1].to_i }
end
end
And here is the error I'm getting:
Anyone have any suggestions?
This is not how you add headers to a csv file. When you generate csv content, a header row is just a regular row. And should be generated as such. Example:
CSV.open("your_csv.csv", "w") do |csv|
csv << ['new_header', 'value1', 'value2'] # the headers
JSON.parse(File.open("tojson.txt").read).each do |hash|
row = [generate, values, for, headers, above]
csv << row
end
end
You don't have a #csv variable. You have a csv one.

How do I create a CSV file without the CSV class?

I'm using a Mac OSX version 10.8
I'm trying to create a CSV file the old fashion way, but there is a bug in my code. It should create a spreadsheet with three rows, i.e., header, and two rows of data beneath it:
File.open('table.csv', 'w') do |f|
f.puts.each {|line| puts line}
'Date','Open','High','Low','Close','Volume','Adj Close'
'10/8/2013','1676.22','1676.79','1655.03','1655.45','3569230000','1655.45'
'10/7/2013','1687.15','1687.15','1674.7','1676.12','2678490000','1676.12'
end
Can someone fix this so that it works and explain what I am doing wrong.
Thanks
File.open('table.csv', 'w') do |csv|
csv << ["Date","Open","High","Low","Close","Volume","Adj Close"]
csv << ["10/8/2013","1676.22","1676.79","1655.03","1655.45","3569230000","1655.45"]
csv << ["10/7/2013","1687.15","1687.15","1674.7","1676.12","2678490000","1676.12"]
end
This should work. You don't need an array.
Try putting your data in an array and then loop over it like this:
data = [
['Date','Open','High','Low','Close','Volume','Adj Close'],
['10/8/2013','1676.22','1676.79','1655.03','1655.45','3569230000','1655.45']
['10/7/2013','1687.15','1687.15','1674.7','1676.12','2678490000','1676.12'],
]
File.open('table.csv', 'w') do |f|
data.each{|line| f.puts line.join(',')}
end

Split output data using CSV in Ruby 1.9

I have a csv file that has 7000+ records that I process/manipulate and export to a new csv file. I have no issues doing that and everything works as expected.
I would like to change the process to where it breaks the output into multiple files. So instead of writing all 7000+ rows to the new csv file it would write the first 1000 rows to newexport1.csv and the next 1000 rows to newexport2.csv until it reaches the end of the data.
Is there an easy way to do this with CSV in Ruby 1.9?
My current write method:
CSV.open("#{PATH_TO_EXPORT_FILE}/newexport.csv", "w+", :col_sep => '|', :headers => true) do |f|
export_rows.each do |row|
f << row
The short answer is "no". You'll want to adjust your current code to split up the set and then dump each subset to a different file. This ought to be pretty close:
export_rows.each_slice(1000).with_index do |rows, idx|
CSV.open("#{PATH_TO_EXPORT_FILE}/newexport-#{idx.to_s}.csv", "w+", :col_sep => '|', :headers => true) do |f|
rows.each { |row| f << row }
end
end
Yes, there is.
It's embedded in Ruby 1.9
Check this link
To read:
CSV.foreach("path/to/file.csv") do |row|
# manipulate the content
end
To write:
CSV.open("path/to/file.csv", "wb") do |csv|
csv << ["row", "of", "CSV", "data"]
csv << ["another", "row"]
# something else
end
I think that you'll need to combine one inside the other.
FasterCSV is the standard CSV library since ruby 1.9, you can find a lot of example code in the examples folder:
https://github.com/JEG2/faster_csv/tree/master/examples
For the example code to work, you should change:
require "faster_csv"
for
require "csv"

Ruby 1.9.2 export a CSV string without generating a file

I just can't get the 'To a String' example under 'Writing' example in the documentation to work at all.
ruby -v returns:
ruby 1.9.2p290 (2011-07-09 revision 32553) [x86_64-darwin10.8.0]
The example from the documentation I can't working is here:
csv_string = CSV.generate do |csv|
csv << ["row", "of", "CSV", "data"]
csv << ["another", "row"]
end
The error I get is:
wrong number of arguments (0 for 1)
So it seems like I am missing an argument, in the documentation here it states:
This method wraps a String you provide, or an empty default String
But when I pass in a empty string, it gives me the following error:
No such file or directory -
I am not looking to generate a csv file, I just wanted to create a string of csv that I send as text to the user.
Here is code I know works against Ruby 1.9.2 with Rails 3.0.1
def export_csv(filename, header, rows)
require 'csv'
file = CSV.generate do |csv|
csv << header if not header.blank?
rows.map {|row| csv << row}
end
send_data file, :type => 'text/csv; charset=iso-8859-1; header=present', :disposition => "attachment;filename=#{filename}.csv"
end

Resources