Uploaded image for project: 'Moodle'
  1. Moodle
  2. MDL-36789

Corrupt modinfo in course table [problem and a fix]

    XMLWordPrintable

    Details

    • Type: Bug
    • Status: Closed
    • Priority: Critical
    • Resolution: Fixed
    • Affects Version/s: 2.2.6, 2.4.3
    • Fix Version/s: 2.4.6, 2.5.2
    • Component/s: Course
    • Labels:
    • Testing Instructions:
      Hide

      Test 1. Self-rebuild of corrupted cache.

      In order to test the change you need to have a corrupted course modinfo cache.

      Easy way to emulate a corrupt cache:

      1. Create course and couple of modules in it. View the course.
      2. Manually copy the contents of mdl_course.modinfo for this course into buffer
      3. Delete one of the modules. View the course
      4. Manually paste the old contents back into mdl_course.modinfo

      Corrupting the cache similar to production environment is also described in my comment below: https://tracker.moodle.org/browse/MDL-36789?focusedCommentId=237301&page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel#comment-237301

      1. After the cache is corrupted try viewing the course page
      2. Make sure the debugging message is displayed and course can be viewed.

      Test 2. Performance and potential regressions (on 2.4 and 2.5)

      1. Enrol student in multiple courses
      2. Add in your config.php define('MAX_MODINFO_CACHE_SIZE', 10); - set the number less than number of courses where student is enrolled
      3. View each course page and /my/ page, make sure everything is displayed correctly.
      4. Compare the performance numbers of course view page and /my/ page with and without patch.
      Show
      Test 1. Self-rebuild of corrupted cache. In order to test the change you need to have a corrupted course modinfo cache. Easy way to emulate a corrupt cache: Create course and couple of modules in it. View the course. Manually copy the contents of mdl_course.modinfo for this course into buffer Delete one of the modules. View the course Manually paste the old contents back into mdl_course.modinfo Corrupting the cache similar to production environment is also described in my comment below: https://tracker.moodle.org/browse/MDL-36789?focusedCommentId=237301&page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel#comment-237301 After the cache is corrupted try viewing the course page Make sure the debugging message is displayed and course can be viewed. Test 2. Performance and potential regressions (on 2.4 and 2.5) Enrol student in multiple courses Add in your config.php define('MAX_MODINFO_CACHE_SIZE', 10); - set the number less than number of courses where student is enrolled View each course page and /my/ page, make sure everything is displayed correctly. Compare the performance numbers of course view page and /my/ page with and without patch.
    • Workaround:
      Hide
      1. Open course edit page /course/edit.php?id=XXX
      2. Save without making any changes

      This action calls rebuilding of course cache.

      Show
      Open course edit page /course/edit.php?id=XXX Save without making any changes This action calls rebuilding of course cache.
    • Affected Branches:
      MOODLE_22_STABLE, MOODLE_24_STABLE
    • Fixed Branches:
      MOODLE_24_STABLE, MOODLE_25_STABLE
    • Pull Master Branch:
      wip-MDL-36789-master
    • Sprint:
      BACKEND Sprint 3

      Description

      Moodle returns an error when viewing a given course at the URI: /course/view.php .
      E.g. https://moodledebug.hi.is/course/view.php?id=929

      The method to reproduce this error is only one step:
      1: https://example.moodle.site/course/view.php?id=929

      Moodle reports this error:
      Can not find data record in database table course_modules.

      Please bear in mind that that the very nature of this error means that it is not repeatable, yet it is consistent, in the sense that anybody could repeat the error and the fix if they had the database with the corrupt data.

      Web server logs show this, (when debugging is on):
      Default exception handler:

      Can not find data record in database table course_modules.
       Debug: 
      SELECT id,course FROM {course_modules} 
      WHERE id = ?\n[array (\n  0 => '20624',\n)]\n* 
      line 1272 of /lib/dml/moodle_database.php: dml_missing_record_exception thrown\n* 
      line 1249 of /lib/dml/moodle_database.php: call to moodle_database->get_record_select()\n* 
      line 6526 of /lib/accesslib.php: call to moodle_database->get_record()\n* 
      line 1019 of /lib/modinfolib.php: call to context_module::instance()\n* 
      line 1006 of /lib/modinfolib.php: call to cm_info->is_user_access_restricted_by_group()\n* 
      line 980 of /lib/modinfolib.php: call to cm_info->update_user_visible()\n* 
      line 272 of /lib/modinfolib.php: call to cm_info->obtain_dynamic_data()\n* 
      line 1123 of /lib/modinfolib.php: call to course_modinfo->__construct()\n* 
      line 1630 of /lib/navigationlib.php: call to get_fast_modinfo()\n* 
      line 1692 of /lib/navigationlib.php: call to global_navigation->generate_sections_and_activities()\n* 
      line 47 of /course/format/weeks/lib.php: call to global_navigation->load_generic_course_sections()\n* 
      line 1605 of /lib/navigationlib.php: call to callback_weeks_load_content()\n* 
      line 1155 of /lib/navigationlib.php: call to global_navigation->load_course_sections()\n* 
      line 2679 of /lib/navigationlib.php: call to global_navigation->initialise()\n* 
      line 659 of /lib/pagelib.php: call to navbar->has_items()\n* 
      line 4 of /theme/lbhi/layout/general.php: call to moodle_page->has_navbar()\n* 
      line 685 of /lib/outputrenderers.php: call to include()\n* 
      line 637 of /lib/outputrenderers.php: call to core_renderer->render_page_layout()\n* 
      line 217 of /course/view.php: call to core_renderer->header()\n

      The explanation for this error might be that Moodle builds up a cache in the moodle db, most likely for speeding up the database search. The cache is in the course table and the column is modinfo. Try to have a look at the content in this column. Here is one example:

       select modinfo from mdl_course where id = 923; 

      And it goes like this:

      course.modinfo

       a:23:{i:19867;O:8:"stdClass":10:{s:2:"id";s:4:"2800";s:2:"cm";s:5:"19867";s:3:"mod";s:5:"forum";s:7:"section";s:1:"0";s:9:"sectionid";s:4:"8
      945";s:6:"module";s:1:"7";s:5:"added";s:10:"1345668034";s:7:"visible";s:1:"1";s:10:"visibleold";s:1:"1";s:4:"name";s:20:"Tilkynningar kennara";}i:20923;O:8:"stdClass":12:s:2:"id";s:4:"7591";s:2:"cm";s:5:"20923";s:3:"mod";s:8:"resource";s:


      and it goes on and on like this for pages. :-/

      Now if this cache is somehow corrupted - and we have numerous proofs that it does, yet we do not know how it happens or what causes it - the corruption does not corrupt the database itself, but rather the function of the Moodle system.
      This cache can easily be reset for diagnostics.
      In the database, modinfo can be reset without any loss of data. Here is what we do:

       update mdl_course set modinfo='' where id = 929;

      In this example the course number is 929, the same number as in the url when viewing the course. Now if I am impatient, I tend to just reset the cache for all courses in the database like this:

       update mdl_course set modinfo='' where id > 0 and id < 2000;

      Doing this does defeat the purpose of the database cache in modinfo, thus slowing the system down. But for debugging problems, and to recover courses that seem to get lost, this procedure sometimes makes the sysadmin job a little bit easier.
      Good luck.

        Attachments

          Issue Links

            Activity

              People

              • Votes:
                9 Vote for this issue
                Watchers:
                18 Start watching this issue

                Dates

                • Created:
                  Updated:
                  Resolved:
                  Fix Release Date:
                  9/Sep/13