Reputation: 141
I'm trying to bulk load a CSV file with a rake task in ruby on rails 5.
I have a simple model that will be a list of movies. I have the rails app running and can successfully create a new movie w/ the web app. When I run the rake task, it fails with UnknownAttributeError: unknown attribute 'Title' for Movie
here's my schema:
create_table "movies", force: :cascade do |t|
t.string "Title"
t.string "Genre"
t.string "Rating"
<snip>
end
here's my create method (straight out of scaffolding...)
def create
@movie = Movie.new(movie_params)
respond_to do |format|
if @movie.save
format.html { redirect_to @movie, notice: 'Movie was successfully created.' }
format.json { render :show, status: :created, location: @movie }
else
format.html { render :new }
format.json { render json: @movie.errors, status: :unprocessable_entity }
end
end
end
here's my rake task:
desc "bulk load movies in the db"
task :upload_movies => [ :environment] do
require 'csv'
f = "#{Rails.root}/tmp/movies.csv"
raise "#{f} does not exist. Stoping import of movies" if !File.exists?(f)
CSV.foreach(f, :headers => true) do |row|
Movie.create!(row.to_hash)
end
end
when I add movie via the app, the server console shows it working correctly like this:
(0.1ms) BEGIN SQL (1.3ms) INSERT INTO "movies" ("Title", "Genre", "Rating", "Lead", "Director", "Year", "Type", "Duration", "Theater", "created_at", "updated_at") VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11) RETURNING "id" [["Title", "the ballerina"], ["Genre", "sci fi"], ["Rating", "PG"], ["Lead", "random"], ["Director", "local"], ["Year", 2010], ["Type", "3D"], ["Duration", 90], ["Theater", "3/4"], ["created_at", 2016-12-24 15:05:21 UTC], ["updated_at", 2016-12-24 15:05:21 UTC]] (0.6ms) COMMIT Redirected to http://localhost:3000/movies/1
the top of my CSV file looks like this:
Title,Genre,Rating,Lead,Director,Year,Type,Duration,Theater
The Avengers: Age of Ultron 3D,Action,PG-13,Robert Downey Jr.,Joss Whedon,2015,3D,141,3/4
Here's the output of the rake task -- (I ran migrate for this example, just so this community would know my db is up to date...)
$ rake db:migrate
$ rake upload_movies
rake aborted!
ActiveModel::UnknownAttributeError: unknown attribute 'Title' for Movie.
/Users/ustonma/dev/stone/gl7movies/lib/tasks/movieUpload.rake:11:in `block (2 levels) in <top (required)>'
/Users/ustonma/dev/stone/gl7movies/lib/tasks/movieUpload.rake:10:in `block in <top (required)>'
Tasks: TOP => upload_movies
(See full trace by running task with --trace)
$
What am I missing? -thanks.
Upvotes: 1
Views: 298
Reputation: 141
this was actually a problem with encoding of the CSV file. The file was saved using MS Excel with the format at CSV - UTF-8 (Comma delimited) (.csv)
When CSV.foreach
started reading the file the first position of the file is a byte string indicating UTF-8. I used text mate to "save as" Unicode - UTF-8
and it worked. I also used excel to save as Comma Separated Values (.csv)
and it also worked.
CSV in Ruby (2.3.1) on Rails 5 doesn't seem to like that that other UTF-8 encoding.
Upvotes: 0
Reputation: 54
can you try to see the columns of your Movie table created on migration?
rails c
Movie.new
and show us the result
Upvotes: 0
Reputation: 7878
Are you sure the hash you try to create the movie with is valid? for example if Title is capital lettered it will blow up activerecord. Try it like this perhaps:
{title: row[0], genre: row[1], ...}
Upvotes: 0