Reputation: 2849
I am currently working on a web app for social networking site but it seems as if getting my nested resources to work correctly is impossible. If you can help me out that would be great and I would be very thankful.
Here are my routes. I would like to have the url structure like mysite.com/username/photos /(new, edit, etc). The url structure is like so but I get an error when trying to access the forms or page. Down below I have posted what I have so far.
routes.rb
resources :users do
resources :photos
end
photo.rb
belongs_to :users
user.rb
has_many :photos, :foreign_key => "id", :dependent => :destroy
_form.html.erb This form has an attachment using paperclip. There is a <% before statement I removed it because it would not show the entire code below on here.
form_for(@photos,@user) :html => {:multipart => true} do |f| %>
photos_controller.rb
def new
@photo = Photo.new(params[:photo])
end
Upvotes: 2
Views: 567
Reputation: 2859
What is the error that you get and where?
A couple things:
in photo.rb
:
belongs_to :user
instead of users
Are you trying to create photos from users#new
page? If so, try to look at accepts_nested_attributes_for
usage:
in user.rb
has_many :photos, :dependent => :destroy
accepts_nested_attributes_for :photo
And then, on your users#new
form:
<%= form_for @user, :html => {:multipart => true} do |f| %>
# ... user attributes ...
<%= f.fields_for :photo do |p| %>
<%= p.file_field :name %>
<% end %>
<% end%>
Also, consider using carrierwave instead of paperclip for your uploads. Here is the railcast. Good luck.
Upvotes: 0
Reputation: 15056
You need to create a before_filter to get the user, and the form posts to create, not new. Your photo controller should look something like:
before_filter :get_user
...
def new
@photo = @user.photos.build
end
def create
@photo = @user.photos.build(params[:photo])
respond_to do |format|
if @photo.save
format.html {redirect_to [@user, @photo], notice: "Photo saved!"}
else
format.html {render action: "new"}
end
end
end
...
private
def get_user
@user = User.find(params[:user_id])
end
Here, the before_filter grabs the user. In nested routes, the parent resource ID will be in params[:parent_id]
or in this case, params[:user_id]
. Then inside the create controller, you want to build a photo from the @user.photos
collection. This will automatically create the reference between the photo and the user.
Also, your form_for has the relations backwards. It should be form_for([@user, @photo]) ...
, not the other way around.
Upvotes: 1
Reputation: 5706
Not certain that this is the problem but it appears that your form_for
tag is in the wrong format. You are closing the parentheses on the form_for
tag after specifying your user, and thus it is ignoring the :html
part. I would try this:
<%= form_for([@photos, @user], :html => {:multipart => true}) do |f| %>
The @photos
and @user
must be passed in as an array.
Also, Not sure why the @photos
param would be plural. Shouldn't it be [@photo, @user]
? I may be wrong on that part though.
Upvotes: 1