I am working on a course creator website where a track
can have multiple courses
and they in turn, can have multiple assignments
The domain classes are defined as the following.
class Track {
String name
static hasMany = [courses: Course]
static constraints = {
name minSize: 2
courses nullable: true
}
@Override
String toString() {
return name
}
}
and
class Course {
String name
static hasMany = [assignments: Assignment]
static belongsTo = Track
static constraints = {
name nullable: false
assignments nullable: true
}
@Override
String toString() {
return name
}
}
and
class Assignment {
String name
String description
String url
static belongsTo = Course
static constraints = {
name nullable: false
description minSize: 20, widget: 'textarea'
url nullable: true, url: true
}
@Override
String toString() {
return name
}
}
While the final goal is to make a many to many relationship.
The bootstrap.groovy file has the following code.
Assignment assignment1 = new Assignment(name: "Read Software Craftsman", description: "Software Craftsman " +
"by Sandro Mancuso is one of the mandatory readings at Incubyte",
url: "https://www.amazon.in/s?k=software+craftsmanship&sprefix=software+craftsman%2Caps%2C231&ref=nb_sb_ss_ts-doa-p_1_18")
Assignment assignment2 = new Assignment(name: "Read Clean Coder", description: "Principles of clean coding is vital for the code readability. ",
url: "https://www.amazon.in/Clean-Coder-Robert-C-Martin/dp/813178696X/ref=sr_1_1?crid=187IC46P73OZ7&keywords=clean+coder&qid=1654424906&sprefix=clean+coder%2Caps%2C451&sr=8-1")
Course course = new Course(name: "Values and Practices of Software Development")
Track track = new Track(name: "Practices").addToCourses(course)
course.addToAssignments(assignment1).addToAssignments(assignment2)
track.save()
course.save()
assignment1.save()
assignment2.save()
println track.getErrors()
While each one of the domain objects is being saved successfully, one to many relationship is not being persisted, and thus mapping tables TRACK_COURSE and COURSE_ASSIGNMENT have no data.
While each one of the domain objects is being saved successfully, one to many relationship is not being persisted, and thus mapping tables TRACK_COURSE and COURSE_ASSIGNMENT have no data.
I cannot reproduce that but the project at https://github.com/jeffbrown/sapgormrelationships may help you.
I have pasted your code directly from the question into that project. At startup you will see the following written to stdout:
Hibernate: insert into track (id, version, name) values (default, ?, ?)
Hibernate: insert into course (id, version, name) values (default, ?, ?)
Hibernate: insert into assignment (id, version, url, name, description) values (default, ?, ?, ?, ?)
Hibernate: insert into assignment (id, version, url, name, description) values (default, ?, ?, ?, ?)
org.grails.datastore.mapping.validation.ValidationErrors: 0 errors
Hibernate: insert into track_course (track_courses_id, course_id) values (?, ?)
Hibernate: insert into course_assignment (course_assignments_id, assignment_id) values (?, ?)
Hibernate: insert into course_assignment (course_assignments_id, assignment_id) values (?, ?)
You can see inserts into both course_assignment
and track_course
. You can also validate that the data is there by interacting with the default scaffolding pages in the app.
grails-app/init/sapgormrelationships/BootStrap.groovy#L14-L30
@Transactional
void populateData() {
Assignment assignment1 = new Assignment(name: "Read Software Craftsman", description: "Software Craftsman " +
"by Sandro Mancuso is one of the mandatory readings at Incubyte",
url: "https://www.amazon.in/s?k=software+craftsmanship&sprefix=software+craftsman%2Caps%2C231&ref=nb_sb_ss_ts-doa-p_1_18")
Assignment assignment2 = new Assignment(name: "Read Clean Coder", description: "Principles of clean coding is vital for the code readability. ",
url: "https://www.amazon.in/Clean-Coder-Robert-C-Martin/dp/813178696X/ref=sr_1_1?crid=187IC46P73OZ7&keywords=clean+coder&qid=1654424906&sprefix=clean+coder%2Caps%2C451&sr=8-1")
Course course = new Course(name: "Values and Practices of Software Development")
Track track = new Track(name: "Practices").addToCourses(course)
course.addToAssignments(assignment1).addToAssignments(assignment2)
track.save()
course.save()
assignment1.save()
assignment2.save()
println track.getErrors()
}
You have not provided enough information to know for sure, but I suspect that a transaction isn't being properly managed. If you remove @Transactional
from my example, I expect you may see the same behavior you reported above.