diff --git a/course/format/classes/base.php b/course/format/classes/base.php
index 30e7f300858..291072cfcab 100644
--- a/course/format/classes/base.php
+++ b/course/format/classes/base.php
@@ -371,7 +371,7 @@ abstract class base {
      * This method ensures that 3rd party course format plugins that still use 'numsections' continue to
      * work but at the same time we no longer expect formats to have 'numsections' property.
      *
-     * @return int
+     * @return int The last section number, or -1 if sections are entirely missing
      */
     public function get_last_section_number() {
         $course = $this->get_course();
@@ -380,6 +380,12 @@ abstract class base {
         }
         $modinfo = get_fast_modinfo($course);
         $sections = $modinfo->get_section_info_all();
+
+        // Sections seem to be missing entirely. Avoid subsequent errors and return early.
+        if (count($sections) === 0) {
+            return -1;
+        }
+
         return (int)max(array_keys($sections));
     }
 
diff --git a/course/format/tests/base_test.php b/course/format/tests/base_test.php
index 55ca4d7c602..c6a1f6d1ece 100644
--- a/course/format/tests/base_test.php
+++ b/course/format/tests/base_test.php
@@ -14,14 +14,13 @@
 // You should have received a copy of the GNU General Public License
 // along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
 
-defined('MOODLE_INTERNAL') || die();
-
 /**
  * Course related unit tests
  *
  * @package    core_course
  * @copyright  2014 Marina Glancy
  * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
+ * @coversDefaultClass \core_courseformat\base
  */
 class base_test extends advanced_testcase {
 
@@ -348,6 +347,32 @@ class base_test extends advanced_testcase {
         );
     }
 
+    /**
+     * Test that retrieving last section number for a course
+     *
+     * @covers ::get_last_section_number
+     */
+    public function test_get_last_section_number(): void {
+        global $DB;
+
+        $this->resetAfterTest();
+
+        // Course with two additional sections.
+        $courseone = $this->getDataGenerator()->create_course(['numsections' => 2]);
+        $this->assertEquals(2, course_get_format($courseone)->get_last_section_number());
+
+        // Course without additional sections, section zero is the "default" section that always exists.
+        $coursetwo = $this->getDataGenerator()->create_course(['numsections' => 0]);
+        $this->assertEquals(0, course_get_format($coursetwo)->get_last_section_number());
+
+        // Course without additional sections, manually remove section zero, as "course_delete_section" prevents that. This
+        // simulates course data integrity issues that previously triggered errors.
+        $coursethree = $this->getDataGenerator()->create_course(['numsections' => 0]);
+        $DB->delete_records('course_sections', ['course' => $coursethree->id, 'section' => 0]);
+
+        $this->assertEquals(-1, course_get_format($coursethree)->get_last_section_number());
+    }
+
     /**
      * Test for the default delete format data behaviour.
      *