将 REST 就地使用与嵌套属性
REST in Place 是 Jan Varwig 开发的一款出色的 Rails 插件,它使用 AJAX 进行编辑内联对象属性。它非常容易设置、实施,并且通常运行良好。
我已经 在线阅读人们使用带有嵌套属性的 REST in Place 的内容,但我实际上没有发现任何关于它是如何完成的提及。我没想到它会太困难,但我还没有弄清楚(尽管我在非嵌套属性方面没有遇到任何问题)。
我有一个调查模型:
class Survey < ActiveRecord::Base
has_one :question, :dependent => destroy
accepts_nested_attributes_for :question
attr_accessible :description
validates_presence_of :description
end
和一个相应的问题模型:
class Question < ActiveRecord::Base
belongs_to :survey
attr_accessible :title, :contents
validates_presence_of :title, :contents
end
我的尝试产生了三种场景:
1. 使用非嵌套属性实现的 REST in Place — [works]
视图中的代码如下所示:
<span class="rest_in_place" data-url="<%= url_for @survey %>" data-object="survey" data-attribute="description">
<%= @survey.description %>
</span>
并且效果很好。当您单击说明时,会出现一个表单 text_field,其中包含 oldValue(来自内部 HTML)。我可以编辑文本,然后按“Enter”键,表单会提交 AJAX 更新并使用 jQuery 呈现新值。这里一切都很好。
2. 使用嵌套属性实现 REST in Place — [不起作用]
代码如下所示(如果有问题请告诉我)
<span class="rest_in_place" data-url="<%= url_for @survey %>" data-object="survey" data-attribute="question_attributes[title]">
<%= @survey.question.title %>
</span>
这里,加载表单的 javascript 工作正常,但是当我尝试向更新问题标题,我收到错误 ActiveRecord::RecordInvalid (验证失败:问题内容不能为空
),告诉我它要么正在尝试创建一个新问题(这没有意义)因为请求仍将发送到调查控制器中的 update
操作),或者正在重置这两个值
3. 设置嵌套属性 :update_only => true
— [部分]有效]
所以,我认为如果我可以阻止创建新问题,它可能会起作用(尽管这不是一个足够的解决方案,因为我需要为每个新调查创建新问题)。调查模型如下:
class Survey < ActiveRecord::Base
has_one :question, :dependent => destroy
accepts_nested_attributes_for :question, :update_only => true
...
end
然后,有趣的是,AJAX 请求工作得很好 - 当我更改问题属性时,它会在数据库中更新,但由于某种原因它卡在“保存...”上并且从未恢复新更新的属性。重新加载页面当然可以很好地显示新文本,但使用 AJAX 的全部目的是为了防止出现这种情况。
这应该就是一切了。如果您对发生这些问题的原因有任何想法,以及解决这些问题的建议,请告诉我。谢谢!
REST in Place is a fantastic rails plugin by Jan Varwig that uses AJAX to edit object attributes inline. It was very easy to set up, simple to implement, and generally just works well.
I've read around online of people using REST in Place with nested attributes, but I haven't actually found any mentions of how it's done. I wouldn't expect it to be too difficult, but I haven't been able to figure it out yet (although I've had no trouble with non-nested attributes).
I have a Survey model:
class Survey < ActiveRecord::Base
has_one :question, :dependent => destroy
accepts_nested_attributes_for :question
attr_accessible :description
validates_presence_of :description
end
and a corresponding Question model:
class Question < ActiveRecord::Base
belongs_to :survey
attr_accessible :title, :contents
validates_presence_of :title, :contents
end
My attempts have yielded three scenarios:
1. REST in Place implemented with non-nested attributes — [works]
The code in the view looks like this:
<span class="rest_in_place" data-url="<%= url_for @survey %>" data-object="survey" data-attribute="description">
<%= @survey.description %>
</span>
and it works great. When you click on the description, a form text_field appears with the oldValue inside (from the inner HTML). I can edit the text, and on hitting 'Enter', the form submits an AJAX update and renders the new value with jQuery. All is good here.
2. REST in Place implemented with nested attributes — [does not work]
The code looks like this (let me know if there's something wrong)
<span class="rest_in_place" data-url="<%= url_for @survey %>" data-object="survey" data-attribute="question_attributes[title]">
<%= @survey.question.title %>
</span>
Here, the javascript that loads the form works fine, but when I try to submit a new value to update the question title, I receive the error ActiveRecord::RecordInvalid (Validation failed: Question contents can't be blank
, telling me that either it's trying to create a new question (which doesn't make sense since the request is still going to the update
action in the Survey controller), or it's resetting both values.
3. Setting nested attribute :update_only => true
— [partly works]
So, I figured that if I could prevent the creation of new Questions, it might work (even though this is not an adequate solution, since I need new questions to be created for every new survey). I changed the code of the Survey model to the following:
class Survey < ActiveRecord::Base
has_one :question, :dependent => destroy
accepts_nested_attributes_for :question, :update_only => true
...
end
And then, interestingly enough, the AJAX request worked fine — when I changed a question attribute, it was updated in the database, but for some reason it got stuck on "saving…" and never restored the newly updated attribute. Reloading the page of course displays the new text fine, but the whole point of using AJAX is to prevent that necessity.
That should be everything. Please let me know if you have any ideas as to why any of these problems are occurring, and if you have suggestions for fixing them. Thanks!
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
jquery.rest_in_place 的第 84 行
.js
是:您希望发送到服务器的参数包含类似以下内容:
由此看来,正确的解决方案是:
构造 POST 数据时,您应该得到
调查[问题][标题]
,这是update_attributes
所期望的。Line 84 of
jquery.rest_in_place.js
is:You want the params sent to the server to include something like:
From that, it looks like the proper solution is:
When the POST data is constructed, you should get
survey[question][title]
, which is whatupdate_attributes
expects.是否可以定义问题更新的路线?那么看起来你可以写:
Is it possible to define a route for the question updates? Then it looks like you could write: