Class: Lcms::Engine::Resource

Inherits:
ApplicationRecord show all
Includes:
Navigable, Searchable
Defined in:
app/models/lcms/engine/resource.rb

Constant Summary collapse

MEDIA_TYPES =
%i(video podcast).map { |t| resource_types[t] }.freeze
GENERIC_TYPES =
%i(text_set quick_reference_guide resource_other).map { |t| resource_types[t] }.freeze
SUBJECTS =
%w(ela math lead).freeze
HIERARCHY =
%i(subject grade module unit lesson).freeze

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.find_by_directory(*dir) ⇒ Object



94
95
96
97
98
99
100
101
# File 'app/models/lcms/engine/resource.rb', line 94

def find_by_directory(*dir)
  dir = dir&.flatten&.select(&:present?)
  return unless dir.present?

  type = hierarchy[dir.size - 1]
  meta = (dir).to_json
  where('metadata @> ?', meta).where(curriculum_type: type).first
end

.find_podcast_by_url(url) ⇒ Object



103
104
105
# File 'app/models/lcms/engine/resource.rb', line 103

def find_podcast_by_url(url)
  podcast.where(url: url).first
end

.find_video_by_url(url) ⇒ Object



107
108
109
110
# File 'app/models/lcms/engine/resource.rb', line 107

def find_video_by_url(url)
  video_id = MediaEmbed.video_id(url)
  video.where("url ~ '#{video_id}(&|$)'").first
end

.hierarchyObject



112
113
114
# File 'app/models/lcms/engine/resource.rb', line 112

def hierarchy
  Lcms::Engine::Resource::HIERARCHY
end

.metadata_from_dir(dir) ⇒ Object



89
90
91
92
# File 'app/models/lcms/engine/resource.rb', line 89

def (dir)
  pairs = hierarchy[0...dir.size].zip(dir)
  pairs.to_h.compact.stringify_keys
end

.ransackable_scopes(_auth_object = nil) ⇒ Object

used for ransack search on the admin



117
118
119
# File 'app/models/lcms/engine/resource.rb', line 117

def ransackable_scopes(_auth_object = nil)
  %i(grades)
end

.tree(name = nil) ⇒ Object

return resources tree by a curriculum name if no argument is provided, then it’s any curriculum tree.



123
124
125
126
127
128
129
130
131
# File 'app/models/lcms/engine/resource.rb', line 123

def tree(name = nil)
  if name.present?
    joins(:curriculum).where('curriculums.name = ? OR curriculums.slug = ?', name, name)
  elsif (default = Lcms::Engine::Curriculum.default)
    where(curriculum_id: default.id)
  else
    where(nil)
  end
end

.where_metadata_in(key, arr) ⇒ Object



133
134
135
136
137
# File 'app/models/lcms/engine/resource.rb', line 133

def (key, arr)
  arr = Array.wrap(arr).compact.map(&:downcase)
  clauses = Array.new(arr.count) { "lower(resources.metadata->>'#{key}') = ?" }.join(' OR ')
  where(clauses, *arr)
end

Instance Method Details

#assessment?Boolean

Returns:

  • (Boolean)


156
157
158
# File 'app/models/lcms/engine/resource.rb', line 156

def assessment?
  ['assessment'].present?
end

#copyrightsObject



253
254
255
# File 'app/models/lcms/engine/resource.rb', line 253

def copyrights
  copyright_attributions
end

#directoryObject



177
178
179
180
181
# File 'app/models/lcms/engine/resource.rb', line 177

def directory
  @directory ||= Lcms::Engine::Resource.hierarchy.map do |key|
    key == :grade ? grades.average(abbr: false) : [key.to_s]
  end.compact
end

#do_not_skip_indexing?Object



225
# File 'app/models/lcms/engine/resource.rb', line 225

alias do_not_skip_indexing? should_index?

#documentObject



257
258
259
# File 'app/models/lcms/engine/resource.rb', line 257

def document
  documents.actives.order(updated_at: :desc).first
end

#document?Boolean

Returns:

  • (Boolean)


261
262
263
# File 'app/models/lcms/engine/resource.rb', line 261

def document?
  document.present?
end

#download_categoriesObject



206
207
208
209
210
211
212
# File 'app/models/lcms/engine/resource.rb', line 206

def download_categories
  @download_categories ||=
    resource_downloads.includes(:download_category).includes(:download)
      .sort_by { |rd| rd.download_category&.position.to_i }
      .group_by { |d| d.download_category&.title.to_s }
      .transform_values { |v| v.sort_by { |d| [d.download.main ? 0 : 1, d.download.title] } }
end

#filtered_named_tagsObject



243
244
245
246
247
# File 'app/models/lcms/engine/resource.rb', line 243

def filtered_named_tags
  filtered_named_tags = named_tags
  stds = named_tags[:ccss_standards].map { |n| Standard.filter_ccss_standards(n, subject) }.compact
  filtered_named_tags.merge(ccss_standards: stds)
end

#generic?Boolean

Returns:

  • (Boolean)


164
165
166
# File 'app/models/lcms/engine/resource.rb', line 164

def generic?
  %w(text_set quick_reference_guide resource_other).include?(resource_type)
end

#gradesObject



187
188
189
# File 'app/models/lcms/engine/resource.rb', line 187

def grades
  Grades.new(self)
end

#grades=(gds) ⇒ Object



191
192
193
# File 'app/models/lcms/engine/resource.rb', line 191

def grades=(gds)
  .merge! 'grade' => gds
end

#lesson_numberObject



195
196
197
# File 'app/models/lcms/engine/resource.rb', line 195

def lesson_number
  @lesson_number ||= short_title.match(/(\d+)/)&.[](1).to_i
end

#media?Boolean

Returns:

  • (Boolean)


160
161
162
# File 'app/models/lcms/engine/resource.rb', line 160

def media?
  %w(video podcast).include? resource_type
end

#named_tagsObject



230
231
232
233
234
235
236
237
238
239
240
241
# File 'app/models/lcms/engine/resource.rb', line 230

def named_tags
  {
    keywords: (tag_list + topic_list).compact.uniq,
    resource_type: resource_type,
    ell_appropriate: ell_appropriate,
    ccss_standards: tag_standards,
    ccss_domain: nil, # resource.standards.map { |std| std.domain.try(:name) }.uniq
    ccss_cluster: nil, #  resource.standards.map { |std| std.cluster.try(:name) }.uniq
    authors: reading_assignment_texts.map { |t| t.author.try(:name) }.compact.uniq,
    texts: reading_assignment_texts.map(&:name).uniq
  }
end

#next_hierarchy_levelObject



265
266
267
268
# File 'app/models/lcms/engine/resource.rb', line 265

def next_hierarchy_level
  index = Lcms::Engine::Resource.hierarchy.index(curriculum_type.to_sym)
  Lcms::Engine::Resource.hierarchy[index + 1]
end

#opr?Boolean

Returns:

  • (Boolean)


169
170
171
# File 'app/models/lcms/engine/resource.rb', line 169

def opr?
  tag_list.include?('opr')
end

#pdf_downloads?(category = nil) ⇒ Boolean

Returns:

  • (Boolean)


214
215
216
217
218
219
220
221
222
223
# File 'app/models/lcms/engine/resource.rb', line 214

def pdf_downloads?(category = nil)
  if category.present?
    resource_downloads.joins(:download)
      .where(download_category: category)
      .where(downloads: { content_type: 'application/pdf' })
      .exists?
  else
    downloads.where(content_type: 'application/pdf').exists?
  end
end

#prerequisite?Boolean

Returns:

  • (Boolean)


173
174
175
# File 'app/models/lcms/engine/resource.rb', line 173

def prerequisite?
  tag_list.include?('prereq')
end


199
200
201
202
203
204
# File 'app/models/lcms/engine/resource.rb', line 199

def related_resources
  @related_resources ||= resource_related_resources
                           .includes(:related_resource)
                           .order(:position)
                           .map(&:related_resource)
end

#self_and_ancestors_not_persistedObject



274
275
276
277
278
279
# File 'app/models/lcms/engine/resource.rb', line 274

def self_and_ancestors_not_persisted
  # during create we can't call self_and_ancestors directly on the resource
  # because this query uses the associations on resources_hierarchies
  # which are only created after the resource is persisted
  [self] + parent&.self_and_ancestors.to_a
end

#should_index?Boolean

Returns:

  • (Boolean)


226
227
228
# File 'app/models/lcms/engine/resource.rb', line 226

def should_index?
  do_not_skip_indexing? && (tree? || media? || generic?)
end

#subjectObject



183
184
185
# File 'app/models/lcms/engine/resource.rb', line 183

def subject
  ['subject']
end

#tag_standardsObject



249
250
251
# File 'app/models/lcms/engine/resource.rb', line 249

def tag_standards
  standards.map(&:alt_names).flatten.uniq
end

#tree?Boolean

Returns:

  • (Boolean)


152
153
154
# File 'app/models/lcms/engine/resource.rb', line 152

def tree?
  curriculum_id.present?
end

#unit_bundles?Boolean

Returns:

  • (Boolean)


270
271
272
# File 'app/models/lcms/engine/resource.rb', line 270

def unit_bundles?
  unit? && document_bundles.any?
end

#update_metadataObject



281
282
283
284
285
286
287
# File 'app/models/lcms/engine/resource.rb', line 281

def 
  meta = self_and_ancestors_not_persisted
           .each_with_object({}) do |r, obj|
    obj[r.curriculum_type] = r.short_title
  end.compact
  .merge! meta if meta.present?
end

#update_positionObject



289
290
291
# File 'app/models/lcms/engine/resource.rb', line 289

def update_position
  self.hierarchical_position = HierarchicalPosition.new(self).position
end