Skip to content

Commit c89b30b

Browse files
committed
WIP: change models to allow multiple teachers
1 parent b79ef4a commit c89b30b

13 files changed

+146
-34
lines changed

app/controllers/api/class_members_controller.rb

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,10 @@ def index
1313

1414
if result.success?
1515
@class_members = result[:class_members]
16+
puts "the class members are:"
17+
@class_members.each do |class_member|
18+
pp class_member
19+
end
1620
render :index, formats: [:json], status: :ok
1721
else
1822
render json: { error: result[:error] }, status: :unprocessable_entity

app/controllers/api/school_classes_controller.rb

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,15 +12,15 @@ def index
1212
end
1313

1414
def show
15-
@school_class_with_teacher = @school_class.with_teacher
15+
@school_class_with_teachers = @school_class.with_teachers
1616
render :show, formats: [:json], status: :ok
1717
end
1818

1919
def create
2020
result = SchoolClass::Create.call(school: @school, school_class_params:)
2121

2222
if result.success?
23-
@school_class_with_teacher = result[:school_class].with_teacher
23+
@school_class_with_teachers = result[:school_class].with_teachers
2424
render :show, formats: [:json], status: :created
2525
else
2626
render json: { error: result[:error] }, status: :unprocessable_entity
@@ -32,7 +32,7 @@ def update
3232
result = SchoolClass::Update.call(school_class:, school_class_params:)
3333

3434
if result.success?
35-
@school_class_with_teacher = result[:school_class].with_teacher
35+
@school_class_with_teachers = result[:school_class].with_teachers
3636
render :show, formats: [:json], status: :ok
3737
else
3838
render json: { error: result[:error] }, status: :unprocessable_entity

app/models/ability.rb

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,12 @@ def define_school_teacher_abilities(user:, school:)
7474
can(%i[read], School, id: school.id)
7575
can(%i[read], :school_member)
7676
can(%i[create], SchoolClass, school: { id: school.id })
77-
can(%i[read update destroy], SchoolClass, school: { id: school.id }, teacher_id: user.id)
77+
# can(%i[read update destroy], SchoolClass) do |school_class|
78+
# school_class.school.id == school.id && school_class.teacher_ids.include?(user.id)
79+
# end
80+
# can read update or destroy the class if user is one of the teachers of the class
81+
# can(%i[read update destroy], SchoolClass, school: { id: school.id }, teacher_ids: )
82+
can(%i[read update destroy], SchoolClass, id: SchoolClass.with_class_teacher(user.id).select(:id), school: { id: school.id })
7883
can(%i[read create create_batch destroy], ClassMember,
7984
school_class: { school: { id: school.id }, teacher_id: user.id })
8085
can(%i[read], :school_owner)

app/models/class_member.rb renamed to app/models/class_student.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
# frozen_string_literal: true
22

3-
class ClassMember < ApplicationRecord
3+
class ClassStudent < ApplicationRecord
44
belongs_to :school_class
55
delegate :school, to: :school_class
66
attr_accessor :student

app/models/class_teacher.rb

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
# frozen_string_literal: true
2+
3+
class ClassTeacher < ApplicationRecord
4+
belongs_to :school_class
5+
delegate :school, to: :school_class
6+
attr_accessor :teacher
7+
8+
validates :teacher_id, presence: true, uniqueness: {
9+
scope: :school_class_id,
10+
case_sensitive: false
11+
}
12+
13+
validate :teacher_has_the_school_teacher_role_for_the_school
14+
15+
has_paper_trail(
16+
meta: {
17+
meta_school_id: ->(cm) { cm.school_class&.school_id }
18+
}
19+
)
20+
21+
private
22+
23+
def teacher_has_the_school_teacher_role_for_the_school
24+
return unless teacher_id_changed? && errors.blank? && teacher.present?
25+
26+
return if teacher.school_teacher?(school)
27+
28+
msg = "'#{teacher.id}' does not have the 'school-teacher' role for organisation '#{school.id}'"
29+
errors.add(:teacher, msg)
30+
end
31+
end

app/models/school_class.rb

Lines changed: 23 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -2,35 +2,43 @@
22

33
class SchoolClass < ApplicationRecord
44
belongs_to :school
5-
has_many :members, class_name: :ClassMember, inverse_of: :school_class, dependent: :destroy
5+
has_many :students, class_name: :ClassStudent, inverse_of: :school_class, dependent: :destroy
6+
has_many :class_teachers, class_name: :ClassTeacher, inverse_of: :school_class, dependent: :destroy
67
has_many :lessons, dependent: :nullify
8+
accepts_nested_attributes_for :class_teachers
79

8-
validates :teacher_id, presence: true
10+
scope :with_class_teacher, ->(user_id) { joins(:class_teachers).where(class_teachers: { id: user_id }) }
11+
12+
# validates :teacher_id, presence: true
913
validates :name, presence: true
10-
validate :teacher_has_the_school_teacher_role_for_the_school
14+
# validate :teacher_has_the_school_teacher_role_for_the_school
1115

1216
def self.teachers
13-
User.from_userinfo(ids: pluck(:teacher_id))
17+
User.from_userinfo(ids: ClassTeacher.pluck(:teacher_id))
1418
end
1519

1620
def self.with_teachers
1721
by_id = teachers.index_by(&:id)
18-
all.map { |instance| [instance, by_id[instance.teacher_id]] }
22+
all.map { |instance| [instance, instance.teacher_ids.map { |teacher_id| by_id[teacher_id] }] }
23+
end
24+
25+
def teacher_ids
26+
class_teachers.pluck(:teacher_id)
1927
end
2028

21-
def with_teacher
22-
[self, User.from_userinfo(ids: teacher_id).first]
29+
def with_teachers
30+
[self, User.from_userinfo(ids: teacher_ids)]
2331
end
2432

25-
private
33+
# private
2634

27-
def teacher_has_the_school_teacher_role_for_the_school
28-
return unless teacher_id_changed? && errors.blank?
35+
# def teacher_has_the_school_teacher_role_for_the_school
36+
# return unless teacher_id_changed? && errors.blank?
2937

30-
user = User.new(id: teacher_id)
31-
return if user.school_teacher?(school)
38+
# user = User.new(id: teacher_id)
39+
# return if user.school_teacher?(school)
3240

33-
msg = "'#{teacher_id}' does not have the 'school-teacher' role for organisation '#{school.id}'"
34-
errors.add(:user, msg)
35-
end
41+
# msg = "'#{teacher_id}' does not have the 'school-teacher' role for organisation '#{school.id}'"
42+
# errors.add(:user, msg)
43+
# end
3644
end
Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,21 @@
11
# frozen_string_literal: true
22

3-
json.array!(@school_classes_with_teachers) do |school_class, teacher|
3+
json.array!(@school_classes_with_teachers) do |school_class, teachers|
44
json.call(
55
school_class,
66
:id,
77
:description,
88
:school_id,
9-
:teacher_id,
109
:name,
1110
:created_at,
1211
:updated_at
1312
)
1413

15-
json.teacher_name(teacher&.name)
14+
json.teachers(teachers) do |teacher|
15+
json.call(
16+
teacher,
17+
:id,
18+
:name
19+
)
20+
end
1621
end
Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,21 @@
11
# frozen_string_literal: true
22

3-
school_class, teacher = @school_class_with_teacher
3+
school_class, teachers = @school_class_with_teachers
44

55
json.call(
66
school_class,
77
:id,
88
:description,
99
:school_id,
10-
:teacher_id,
1110
:name,
1211
:created_at,
1312
:updated_at
1413
)
1514

16-
json.teacher_name(teacher&.name)
15+
json.teachers(teachers) do |teacher|
16+
json.call(
17+
teacher,
18+
:id,
19+
:name
20+
)
21+
end
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
class CreateClassTeachers < ActiveRecord::Migration[7.1]
2+
def change
3+
create_table :class_teachers, id: :uuid do |t|
4+
t.references :school_class, type: :uuid, foreign_key: true, index: true, null: false
5+
t.uuid :teacher_id, null: false
6+
t.timestamps
7+
end
8+
9+
add_index :class_teachers, :teacher_id
10+
add_index :class_teachers, %i[school_class_id teacher_id], unique: true
11+
end
12+
end
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
class MoveTeacherDataToClassTeachersTable < ActiveRecord::Migration[7.1]
2+
def up
3+
SchoolClass.find_each do |school_class|
4+
ClassTeacher.create!(school_class: school_class, teacher_id: school_class.teacher_id)
5+
end
6+
end
7+
8+
def down
9+
ClassTeacher.destroy_all
10+
end
11+
end
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
class RemoveClassTeacherId < ActiveRecord::Migration[7.1]
2+
def up
3+
remove_column :school_classes, :teacher_id
4+
end
5+
6+
def down
7+
add_column :school_classes, :teacher_id, :uuid, null: false
8+
SchoolTeacher.find_each do |school_teacher|
9+
school_class = school_teacher.school_classes.first
10+
school_class.update!(teacher_id: school_teacher.teacher_id)
11+
end
12+
end
13+
end
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
class RenameClassMembersToClassStudents < ActiveRecord::Migration[7.1]
2+
def up
3+
rename_table :class_members, :class_students
4+
end
5+
6+
def down
7+
rename_table :class_students, :class_members
8+
end
9+
end

db/schema.rb

Lines changed: 17 additions & 8 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)