instructure/canvas-lms · error

Needs self.item_class to be set in #

Error message

Needs self.item_class to be set in #{self}

What it means

Importers::Importer subclasses forward class-level helpers (translate/t) to their item_class, but only if item_class is set via the class-level accessor. Calling translate on a subclass whose item_class was never assigned raises this RuntimeError naming the offending class, because there is no target to forward the call to.

Solutions

  1. Add an item_class declaration to the importer class, e.g. item_class 'CalendarEvent', inside the subclass body
  2. If the class shouldn't forward translations, override translate/logger locally instead of relying on the shared implementation
  3. Check git history for importer classes that lost their item_class assignment during a refactor

Example fix

// before
class Importers::DiscussionTopicImporter < Importers::Importer
end
// after
class Importers::DiscussionTopicImporter < Importers::Importer
  item_class 'DiscussionTopic'
end
Defensive patterns

Strategy: validation

Validate before calling

raise 'importer missing item_class' unless MyImporter.item_class

Type guard

def usable_importer?(klass)
  klass.is_a?(Class) && klass < Importers::Importer && !klass.item_class.nil?
end

Try / catch

begin
  importer.translate(payload)
rescue RuntimeError => e
  raise unless e.message.start_with?('Needs self.item_class')
  Rails.logger.error("misconfigured importer: #{e.message}")
end

Prevention

When it happens

Trigger: Calling SomeImporter.translate (or .t) on an importer subclass that defines no self.item_class = '...' assignment — typically a newly written or partially ported importer that relies on the inherited translate without registering its item class.

Common situations: Writing a new content importer and forgetting `item_class 'DiscussionTopic'` (or equivalent) in the class body; older importer classes predating the item_class refactor being invoked through the new forwarding path.

Understand the failure class

Background: "is required", "must be set", "missing required field": configuration validation errors across open-source libraries — this error's family across 36 libraries.

Related errors


AI-assisted analysis of instructure/canvas-lms@1c9f0bb801 (2026-09-15). Data as JSON: /api/errors/d309dd2c1c4d660f. Report an issue: GitHub.

Appendix: source

Thrown at app/models/importers.rb:50

  def self.disable_live_events!
    ActiveRecord::Base.observers.disable LiveEventsObserver
    yield
  ensure
    enable_live_events!
  end

  def self.enable_live_events!
    ActiveRecord::Base.observers.enable LiveEventsObserver
  end

  class Importer
    class << self
      attr_accessor :item_class

      # forward translations to CalendarEvent; they used to live there.
      def translate(*)
        raise "Needs self.item_class to be set in #{self}" unless item_class

        item_class.translate(*)
      end
      alias_method :t, :translate

      def logger(*)
        raise "Needs self.item_class to be set in #{self}" unless item_class

        item_class.logger(*)
      end
    end
  end

  register_content_importer(AccountContentImporter)
  register_content_importer(CourseContentImporter)
end

View on GitHub (pinned to 1c9f0bb801)