{"record":{"id":"79ce31f1df363811","repo":"instructure/canvas-lms","slug":"error-saving-original-syllabus-version-e-message","errorCode":null,"errorMessage":"Error saving original syllabus version: #{e.message}","messagePattern":"Error saving original syllabus version: #(.+?)","errorType":"console","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"app/models/course.rb","lineNumber":414,"sourceCode":"  before_save :check_if_should_save_original_syllabus_version\n  after_save :save_original_syllabus_version_if_needed\n\n  def check_if_should_save_original_syllabus_version\n    @should_save_original_syllabus_version = syllabus_body_changed? &&\n                                             syllabus_body_was.present? &&\n                                             account&.feature_enabled?(:syllabus_versioning) &&\n                                             unversioned?\n  rescue\n    @should_save_original_syllabus_version = false\n  end\n\n  def save_original_syllabus_version_if_needed\n    return unless @should_save_original_syllabus_version\n\n    original_attributes = attributes.merge(\"syllabus_body\" => syllabus_body_previously_was)\n    versions.create(yaml: original_attributes.except(*simply_versioned_options[:exclude]).to_yaml)\n  rescue => e\n    Rails.logger.warn(\"Error saving original syllabus version: #{e.message}\")\n  end\n\n  simply_versioned exclude: SIMPLY_VERSIONED_EXCLUDE_FIELDS,\n                   keep: 5,\n                   when: lambda { |course|\n                     return false unless course.syllabus_body_changed?\n\n                     begin\n                       !!course.account&.feature_enabled?(:syllabus_versioning)\n                     rescue => e\n                       Rails.logger.warn(\"Error checking syllabus_versioning flag: #{e.message}\")\n                       false\n                     end\n                   },\n                   on_create: lambda { |course, version|\n                     if course.updating_user\n                       begin\n                         yaml_data = YAML.safe_load(version.yaml, permitted_classes: [Time, Date, Symbol, ActiveSupport::TimeWithZone, ActiveSupport::TimeZone])","sourceCodeStart":396,"sourceCodeEnd":432,"githubUrl":"https://github.com/instructure/canvas-lms/blob/1c9f0bb8013ed69c4f2efe11fd483025469b7e6c/app/models/course.rb#L396-L432","documentation":"When a course's syllabus is first versioned under the syllabus_versioning feature, save_original_syllabus_version_if_needed creates a Version from the previously-stored syllabus_body. Any exception during attributes/versions.create is swallowed, logged as this warning, and ignored so the save is not blocked — meaning the original syllabus snapshot may be lost.","triggerScenarios":"@should_save_original_syllabus_version is set (first syllabus edit with syllabus_versioning enabled) and versions.create raises — DB error, serialization failure on oversized syllabus_body, or invalid YAML conversion of attributes.","commonSituations":"Very large syllabus bodies exceeding column/row limits; database connectivity issues; shard/replica problems during course save; migration drift in the versions table.","solutions":["Check the Rails log around this warning for the underlying exception and fix its root cause (DB error, data size)","Verify the versions table is healthy/migrated on the course's shard","Cap or sanitize oversized syllabus_body content before save","After fixing, re-trigger a syllabus save to regenerate the missing original version"],"exampleFix":"// before\nrescue => e\n  Rails.logger.warn(\"Error saving original syllabus version: #{e.message}\")\n// after\nrescue => e\n  Rails.logger.warn(\"Error saving original syllabus version: #{e.message}\")\n  Canvas::Errors.capture(e, course_id: global_id) # surface to error reporting","handlingStrategy":"try-catch","validationCode":"# before relying on the snapshot\nraise 'versions table missing' unless course.connection.table_exists?(:versions)\ncourse.versions # ensure versioning is functional","typeGuard":null,"tryCatchPattern":"begin\n  versions.create(yaml: attrs.to_yaml)\nrescue => e\n  Canvas::Errors.capture(e, course_id: global_id)\nend","preventionTips":["Report swallowed exceptions to error tracking, not just the logger","Watch for oversized syllabus_body content and cap it","Keep the versions table migrated on all shards","Re-save the syllabus after fixing errors to regenerate missing snapshots"],"tags":["versions","syllabus","courses","database"],"backgroundTag":"database-write-failed","analyzedSha":"1c9f0bb8013ed69c4f2efe11fd483025469b7e6c","analyzedAt":"2026-09-15T20:33:18.891Z","contentChangedAt":"2026-09-15T20:33:18.891Z","schemaVersion":2},"datasetVersion":"2026-09-23T02:17:17.105Z"}