instructure/canvas-lms · warning

[LocalTextExtractor] Unsupported MIME type: #

Error message

[LocalTextExtractor] Unsupported MIME type: #{attachment.mimetype}

What it means

FileTextExtractionService's local text extractor only handles 'pdf' and 'docx' MIME types; for any other mimetype it logs '[LocalTextExtractor] Unsupported MIME type' and returns Result.new("", false) — an empty, failed extraction, not an exception. It signals that the local extraction path cannot process the attachment's file type.

Solutions

  1. Check attachment.mimetype before invoking the extractor and skip/route unsupported types to an appropriate extraction backend.
  2. Normalize the mimetype (strip 'application/' prefix, lowercase) if stored values don't match the 'pdf'/'docx' literals expected by the case statement.
  3. Handle the returned Result (success=false, empty text) gracefully rather than assuming extracted text exists.
  4. Extend the case statement to support additional types if those uploads must be indexed, or configure a remote extractor for them.

Example fix

// before
case mimetype
when "pdf" then extract_pdf
when "docx" then extract_docx
else
  Rails.logger.warn("[LocalTextExtractor] Unsupported MIME type: #{attachment.mimetype}")
  Result.new("", false)
end

// after: normalize mimetype and pre-validate
type = attachment.mimetype.to_s.split("/").last.downcase
case type
when "pdf" then extract_pdf
when "vnd.openxmlformats-officedocument.wordprocessingml.document", "docx" then extract_docx
else
  Rails.logger.warn("[LocalTextExtractor] Unsupported MIME type: #{attachment.mimetype}")
  Result.new("", false)
end
Defensive patterns

Strategy: fallback

Validate before calling

// before invoking extraction
SUPPORTED = %w[pdf docx].freeze
type = attachment.mimetype.to_s.split('/').last.downcase
unless SUPPORTED.include?(type)
  Rails.logger.info("Skipping local extraction for attachment #{attachment.id}: #{attachment.mimetype}")
  return
end

Type guard

def extractable?(attachment)
  %w[pdf docx].include?(attachment.mimetype.to_s.split('/').last.downcase)
end

Try / catch

result = FileTextExtractionService.new(attachment: attachment).call
if result.success
  use(result.text)
else
  Rails.logger.info("No text extracted for attachment #{attachment.id}; falling back to remote extractor")
end

Prevention

When it happens

Trigger: Calling the service's #call with an attachment whose mimetype is anything other than pdf or docx (e.g. txt, pptx, xlsx, images, odp), causing the case statement to fall into the else branch.

Common situations: Users upload unsupported file types (plain text, spreadsheets, images) to a context that expects extracted text; mimetypes stored inconsistently (e.g. 'application/pdf' vs 'pdf') causing the case match to miss; feature routes all attachments through the local extractor instead of a remote extraction service.

Related errors


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

Appendix: source

Thrown at app/services/file_text_extraction_service.rb:46

  Result = Struct.new(:text, :contains_images)

  def initialize(attachment:)
    @attachment = attachment
  end

  def call
    memory_limit = Setting.get("attachment_calculate_words_memory_limit", 4.gigabytes.to_s).to_i
    time_limit = Setting.get("attachment_calculate_words_time_limit", 3.minutes.to_s).to_f

    MemoryLimit.apply(memory_limit) do
      Timeout.timeout(time_limit) do
        case mimetype
        when "pdf"
          extract_pdf
        when "docx"
          extract_docx
        else
          Rails.logger.warn("[LocalTextExtractor] Unsupported MIME type: #{attachment.mimetype}")
          Result.new("", false)
        end
      end
    end
  rescue => e
    Rails.logger.error("[LocalTextExtractor] Failed for attachment #{attachment.id}: #{e.message}")
    Result.new("", false)
  end

  private

  attr_reader :attachment

  def mimetype
    return "pdf" if attachment.mimetype == "application/pdf"

    "docx" if %w[
      application/vnd.openxmlformats-officedocument.wordprocessingml.document

View on GitHub (pinned to 1c9f0bb801)