Rails have Nested Resources for a while, and it has been heavy used (or overused). Say we have two model, Article and Comment.
class Article < ActiveRecord::Base
has_many :ments
end
class Comment < ActiveRecord::Base
belongs_to :article
end
Define the Nested Resource in routes.rb
resources :articles do
resources :ments
end
So now, we can list ments by specific article: http://localhost:3000/articles/1/ments
But Spine can only make url for post request to create Article and Comment like this:
/articles
/ments
How to make Spine's url for Ajax request like this?
/articles/1/ments
I know I can override the url() in Comment Model for retrieval ments, but what about creating a new record?
I also go through the source code as well, what I found is that the create() method in Spine's Ajax module doesn't care about the custom url() function in instance of Comment. what I want is just pass the article_id and using it with my custom url() function to generate url, then I can posting to server for create.
Does it possible without fork and modified version of Spine fo my own?
btw: sorry for my English, wish all of you guys can understand what I want to say about :-)
Thank you and best regards,
Rails have Nested Resources for a while, and it has been heavy used (or overused). Say we have two model, Article and Comment.
class Article < ActiveRecord::Base
has_many :ments
end
class Comment < ActiveRecord::Base
belongs_to :article
end
Define the Nested Resource in routes.rb
resources :articles do
resources :ments
end
So now, we can list ments by specific article: http://localhost:3000/articles/1/ments
But Spine can only make url for post request to create Article and Comment like this:
/articles
/ments
How to make Spine's url for Ajax request like this?
/articles/1/ments
I know I can override the url() in Comment Model for retrieval ments, but what about creating a new record?
I also go through the source code as well, what I found is that the create() method in Spine's Ajax module doesn't care about the custom url() function in instance of Comment. what I want is just pass the article_id and using it with my custom url() function to generate url, then I can posting to server for create.
Does it possible without fork and modified version of Spine fo my own?
btw: sorry for my English, wish all of you guys can understand what I want to say about :-)
Thank you and best regards,
Share edited Dec 15, 2011 at 5:33 Daniel Lv asked Dec 14, 2011 at 14:05 Daniel LvDaniel Lv 8656 silver badges10 bronze badges5 Answers
Reset to default 2The model's url property can be a value or a function. So you could do:
class Comment extends Spine.Model
@configure "ment", "article_id"
@extend Spine.Model.Ajax
@url: ->
"articles/#{article_id}/ments"
or something similar. The ajax module will evaluate this property and use it as the resource end point when building requests.
add
#= require spine/relation
to app/javascript/app/views/index.js.cofee
to add the relation extension
class App.Project extends Spine.Model
@configure 'Project', 'name'
@extend Spine.Model.Ajax
@hasMany 'pages', 'projects/page'
class App.Page extends Spine.Model
@configure 'Page', 'name', 'content'
@extend Spine.Model.Ajax
@belongsTo 'project', 'Project'
in javascript console
App.Project.find(the_id).pages().create({name:"asd"})
more info in http://spinejs./docs/relations
the link is at the bottom of spinejs model documentation
I have a solution:
http://groups.google./group/spinejs/browse_thread/thread/6a5327cdb8afdc69?tvc=2
https://github./SpoBo/spine
I made a fork which overrides how url's are generated in the ajax module. This allows the create url to contain bits of the model's instance data. For example: /articles/1/ments. Works with create, update, etc.
class App.Post extends Spine.Model
@configure 'Post', 'channel_id', 'title'
@extend Spine.Model.Ajax
resourceUrl: ->
"channels/#{@channel_id}/posts"
@hasOne 'channel', 'App.Channel'
I have the same problem as this seems to be one of the biggest problems with Spine.
It is fairly straightforward to implement with BackBone due to it's simplicity, but Spine's internals are quite plex making it quite difficult.
I am trying to implement stand will e back if I have a solution.
Following bit of code worked for me BUT then it didn't...(and I modified this answer). So this is NOT a good solution because Ajax-requests are queued by Spine. It always worked for a first ment but not for subsequent calls since the call to super would return without having sent the PUT/POST.
class Comment extends Spine.Model
@configure "ment", "article_id"
@extend Spine.Model.Ajax
# hack for nested: @article_id is only set correctly during save
@article_id = "?"
@url: =>"/articles/#{@article_id}/ments"
save: ()=>
# hack for nested resources (see @url)
Comment.article_id = @article_id
super
Comment.article_id = "?"