Ruby on rails Rails模型-使用模板创建
在我的应用程序中,我有能力创建“课程”,每个课程包含几个“组件”。现在,我正在尝试实现从模板创建课程的功能,以便它可以将模板中的组件复制/重新创建到新课程中 我的Ruby on rails Rails模型-使用模板创建,ruby-on-rails,ruby,Ruby On Rails,Ruby,在我的应用程序中,我有能力创建“课程”,每个课程包含几个“组件”。现在,我正在尝试实现从模板创建课程的功能,以便它可以将模板中的组件复制/重新创建到新课程中 我的组件的数据结构如下所示: { id: 123, type: Section, content: "abc", section_id: null }, { id: 124, type: Question, content: "abc?", section_id: 123 }, { id: 125,
组件的数据结构如下所示:
{
id: 123,
type: Section,
content: "abc",
section_id: null
},
{
id: 124,
type: Question,
content: "abc?",
section_id: 123
},
{
id: 125,
type: Section,
content: "defg",
section_id: null
},
{
id: 126,
type: Outcome,
content: "defg?",
section_id: 125
},
预期结果:
{
id: 993,
type: Section,
content: "abc",
section_id: null
},
{
id: 994,
type: Question,
content: "abc?",
section_id: 993
},
{
id: 995,
type: Section,
content: "defg",
section_id: null
},
{
id: 996,
type: Outcome,
content: "defg?",
section_id: 995
},
您可以看到问题
/结果
与部分
到部分
之间存在关联
在我的课程模型中,我循环遍历模板的组件,并为新创建的课程组件获取它们的属性
class Lesson
attr_accessor :lesson_template_id
# == Callbacks ==============================
after_create :create_template_components, if: :lesson_template_id_present?
def lesson_template
if @lesson_template_id != ''
LessonTemplate.find(@lesson_template_id)
else
nil
end
end
private
def lesson_template_id_present?
!!@lesson_template_id
end
def create_template_components
if lesson_template
lesson_template.components.each do |c|
self.components.create!({
type: c.type,
content: c.content,
section_id: c.section_id
})
end
end
end
但是问题是节的id
不正确,因为新创建的节将有一个新的/不同的id
。如何修改模型以确保正确创建组件?创建部分
对象的浅层副本,然后创建它并将其附加到新组件
def create_template_components
if lesson_template
lesson_template.components.each do |c|
newSection = if c.type == 'Question'
c.section && c.section.dup
else
nil
end
newSection.save if newSection
self.components.create!({
type: c.type,
content: c.content,
section_id: newSection.try(:id)
})
end
end
end
被复制的对象没有分配id,并被视为新记录。注
这是一个“浅”副本,因为它复制对象的属性
只是,不是它的关联。“深度”副本的范围取决于应用程序
特定的,因此留给应用程序来实现
根据需要。dup方法不保留时间戳
(创建|更新)|(在|上)
创建部分
对象的浅层副本,然后创建它并将其附加到新组件
def create_template_components
if lesson_template
lesson_template.components.each do |c|
newSection = if c.type == 'Question'
c.section && c.section.dup
else
nil
end
newSection.save if newSection
self.components.create!({
type: c.type,
content: c.content,
section_id: newSection.try(:id)
})
end
end
end
被复制的对象没有分配id,并被视为新记录。注
这是一个“浅”副本,因为它复制对象的属性
只是,不是它的关联。“深度”副本的范围取决于应用程序
特定的,因此留给应用程序来实现
根据需要。dup方法不保留时间戳
(创建|更新)|(在|上)
我的想法是一个复制部分的外部循环。当在内部循环中重新创建其他组件(结果和问题)时,将使用新的部分id,这将保持关联的更新和正确
lesson_template.sections.each do |old_section|
# outer loop: recreate section
new_section = self.sections.create!({
content: old_section.content
})
old_section.components.each do |old_non_section_component|
# inner loop: recreate all components belonging to section
self.component.create!({
type: old_non_section_component.type,
content: old_non_section_component.content,
# use id from newly-created section, keeping correct association
section_id: new_section.id # <-- IMPORTANT
})
end
end
lesson_template.sections.each do|old_节|
#外循环:重新创建节
新建分区=self.sections.create!({
内容:旧_section.content
})
old_section.components.每个do|old_non_section_组件|
#内部循环:重新创建属于节的所有组件
self.component.create!({
类型:旧的\u非\u节\u组件.type,
内容:旧的\u非\u节\u component.content,
#使用新创建的节中的id,保持正确的关联
section_id:new_section.id#我的想法是一个复制节的外部循环。new节id用于在内部循环中重新创建其他组件(结果和问题),这将保持关联的更新和正确
lesson_template.sections.each do |old_section|
# outer loop: recreate section
new_section = self.sections.create!({
content: old_section.content
})
old_section.components.each do |old_non_section_component|
# inner loop: recreate all components belonging to section
self.component.create!({
type: old_non_section_component.type,
content: old_non_section_component.content,
# use id from newly-created section, keeping correct association
section_id: new_section.id # <-- IMPORTANT
})
end
end
lesson_template.sections.each do|old_节|
#外循环:重新创建节
新建分区=self.sections.create({
内容:旧_section.content
})
old_section.components.每个do|old_non_section_组件|
#内部循环:重新创建属于节的所有组件
self.component.create({
类型:旧的\u非\u节\u组件.type,
内容:旧的\u非\u节\u component.content,
#使用新创建的节中的id,保持正确的关联
section\u id:new\u section.id#你的意思是section\u id:c.section\u id
总是错误的?很抱歉,我没有遇到问题。你能告诉我更多吗?是的,使用创建模板\u组件
,section\u id
总是123(例如),即使section\u id
将是新的。你的意思是section\u id:c.section\u id
总是错误的?很抱歉,我没有遇到问题。你能告诉我更多吗?是的,使用create\u template\u components
,section\u id
总是123(例如),即使部分\u id
将是新的。如果我有多个部分(123和125),该怎么办,以及与这些节关联的单独组件?例如,与节123关联的组件124和与节125关联的组件126。@jj008从模板组件复制时是否始终要创建一个新节?如果不希望,何时要创建一个新节?是的,我要在创建新节时创建一个新节因此,如果我创建新课程,我希望组件994与第993节关联,组件996与第995节关联(例如)好的,那么我给出的代码,总是创建新的节..newSection=c.section&&c.section.dup.create
对于c.section
,你的意思是c.type='section'
?另外,我收到一个错误,说undefined methodcreate
如果我有多个节(123和125),该怎么办,以及与这些节关联的单独组件?例如,与节123关联的组件124和与节125关联的组件126。@jj008从模板组件复制时是否始终要创建一个新节?如果不希望,何时要创建一个新节?是的,我要在创建新节时创建一个新节因此,如果我创建新课程,我希望组件994与第993节关联,组件996与第995节关联(例如)好的,那么我给出的代码,总是创建新的部分。newSection=c.section&&c.section.dup.create
对于c.section
,你的意思是c.type='section'
?另外,我收到一个错误,说undefined methodcreate
,我想这和我要找的很接近,但主要的问题是,当我创建一个新组件,我如何使用正确和新的节id(当我有不同的节和不同的组件关联时)