Rails запрашивает взаимосвязанные модели, чтобы попасть в метод - PullRequest
0 голосов
/ 09 марта 2020

Не нарушая имеющуюся архитектуру данных, я пытаюсь запросить список связей между несколько разобщенными моделями.

Структура модели выглядит следующим образом:

class Course
  has_many :course_groups
end
class CourseGroup
  belongs_to :course
  has_many :assignments
end
class Assignments
  belongs_to :course_group
  has_many :assignment_tasks, dependent: :destroy
  has_many :user_assignments

  def completed_by?(user)
    UserAssignment.find_by(user: user, assignment: self)&.completed
  end
end
class AssignmentTask
  has_many :task_files
  belongs_to :assignment
  has_one :task_evaluation
end
class UserAssignments
  belongs_to :assignment
  belongs_to :user
end
class User
  has_many :user_assignments
end

Я пытаюсь выяснить, сколько CourseGroups Пользователь имеет . Особенно те пользователи, которые завершили все группы CourseGroup, которые связаны с ними. Я не нахожу ничего конкретного, что позволило бы мне получить эту информацию.

Я думал, что смогу создать несколько соединений для получения соединения, например:

User.joins(user_assignments: { assignment: :course_group })

Получается список пользователей. В моей модели CourseGroup у меня есть следующая модель:

def completed_by?(user)
  assigns = assignments.map(&:id)
  completed = true
  assigns.each do |assign|
    rec = UserAssignment.find_by(assignment_id: assign, user_id: user.id)
    completed = false if rec.nil? || rec.completed == false
  end
  completed
end

Я не могу понять, как получить этот метод на модели User, чтобы запросить его или как лучше перестроить его.

Моей первой мыслью было, возможно, что я мог бы построить свой первоначальный запрос как область действия и что я мог бы получить метод таким способом, но область действия не удалась, что написано:

scope :course_user, -> { joins(user_assignments: { assignment: :course_group }) } Я имею в виду в идеале я мог бы поместить в область действия метода.

Есть ли способ получить метод в области действия, или я должен просто создать на пользовательской модели метод с запросом, а затем воссоздать метод, который я Придется разобраться.

РЕДАКТИРОВАТЬ : добавлено больше классов и метод, который используется в Назначениях. CourseGroup традиционно не помечается как завершенная. Назначения не появляются в списке пользователя, пока он фактически не завершен. Вместо этого они полностью назначены для CourseGroup. Таким образом, завершенная группа CourseGroup полагается на все задания, которые должны быть помечены как выполненные.

Итак, от CourseGroup есть завершенная_by? метод, на который затем ссылается помощник:

def groups_completed(user)
  CourseGroup.ordered.select { |group| group.completed_by?(user) }
end

def groups_incomplete(user)
  CourseGroup.ordered.select { |group| group.completed_by?(user) == false }
end

Не очень легко узнать, завершил ли пользователь группу CourseGroup, пока он не выполнил все задания, а затем те были добавлены в его учетную запись.

EDIT : обновлена ​​модель User с некоторыми изменениями для перспективы того, где находится код.

has_many :user_assignments
has_many :assignments, through: :user_assignments, source: :assignment
has_many :course_groups, through: :assignments, source: :course_group

def completed_ipp_courses
  completed = true
  all_users = User.joins(:course_groups)
  all_users.each do |group|
  completed = false unless group.course_completion?
  end
  return self if completed

  return nil
end

def course_completion?(user)
  collection = User.all.each do |top|
    top.course_groups.each do |list|
      list.assignments.map(&:id)
    end
  end

  completed = true
  collection.each do |assign|
    rec = UserAssignment.find_by(assignment_id: assign, user_id: user.id)
    completed = false if rec.nil? || rec.completed == false
  end
end

Идея состоит в том, что завершенный метод выполняет соединение и проверяет завершено в рамках завершения? метод. Завершение? Метод запускает всех пользователей и выполняет проверку UserAssignments для завершения. Нет ошибок, пока ... re c line. Теперь он возвращает неопределенную локальную переменную или метод для пользователя

1 Ответ

0 голосов
/ 09 марта 2020

попробуйте использовать это

class User
  has_many :user_assignments
  has_many :assignments, through: :user_assignments, source: :assignment
  has_many :course_groups, through: :assignments, source: :course_group
end

user = User.last
user.course_groups

Переходя ко второй части, где вы хотите Particularly those users that have completed all the CourseGroups that are connected to them. Я бы сказал, нужно больше подробностей о том, каковы условия для completing a CourseGroup.

РЕДАКТИРОВАТЬ

Имена переменных вводят в заблуждение, например

def completed_ipp_courses
  completed = true
  all_users = User.joins(:course_groups)
  all_users.each do |group|
  completed = false unless group.course_completion?
  end
  return self if completed

  return nil
end


def course_completion?(user)
  collection = User.all.each do |top|
    top.course_groups.each do |list|
      list.assignments.map(&:id)
    end
  end

  completed = true
  collection.each do |assign|
    rec = UserAssignment.find_by(assignment_id: assign, user_id: user.id)
    completed = false if rec.nil? || rec.completed == false
  end
end
  1. Вы получаете пользователей от -> all_users = User.joins(:course_groups)
  2. The you l oop over all_users, который называется group.
  3. Теперь group.course_completion? вызывает метод в User модели, но если I go by variable name it должен go до Group model.
  4. Поскольку group в l oop является экземпляром пользователя, он попытается вызвать course_completion? в User модели.
  5. Опять же, вы вызываете course_completion? для user экземпляра, который принимает параметр user, но не передается из того места, где вы вызываете метод.

Предложение: Лучшее именование уже может избежать многих проблем, таких как:

def completed_ipp_courses
  completed = true
  users = User.joins(:course_groups)
  users.each do |user|
    break unless completed
    completed = false unless user.course_completion?
  end
  completed ? self : nil
end
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...