Skip to content

Commit

Permalink
Merge pull request canonical#1813 from ogayot/target-not-mounted-error
Browse files Browse the repository at this point in the history
shutdown: do not try to unmount /target if install was not started
  • Loading branch information
ogayot committed Oct 2, 2023
2 parents d99a348 + abef051 commit 143d8e3
Show file tree
Hide file tree
Showing 2 changed files with 39 additions and 1 deletion.
12 changes: 11 additions & 1 deletion subiquity/server/controllers/filesystem.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import logging
import os
import pathlib
import subprocess
import time
from typing import Any, Callable, Dict, List, Optional, Union

Expand Down Expand Up @@ -1532,6 +1533,15 @@ def make_autoinstall(self):

async def _pre_shutdown(self):
if not self.reset_partition_only:
await self.app.command_runner.run(["umount", "--recursive", "/target"])
# /target is mounted only if the installation was actually started.
try:
await self.app.command_runner.run(["mountpoint", "/target"])
except subprocess.CalledProcessError:
log.debug(
"/target does not exist or is not mounted,"
" skipping call to umount --recursive"
)
else:
await self.app.command_runner.run(["umount", "--recursive", "/target"])
if len(self.model._all(type="zpool")) > 0:
await self.app.command_runner.run(["zpool", "export", "-a"])
28 changes: 28 additions & 0 deletions subiquity/server/controllers/tests/test_filesystem.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.

import copy
import subprocess
import uuid
from unittest import IsolatedAsyncioTestCase, mock

Expand Down Expand Up @@ -89,6 +90,7 @@ class TestSubiquityControllerFilesystem(IsolatedAsyncioTestCase):
def setUp(self):
self.app = make_app()
self.app.opts.bootloader = "UEFI"
self.app.command_runner = mock.AsyncMock()
self.app.report_start_event = mock.Mock()
self.app.report_finish_event = mock.Mock()
self.app.prober = mock.Mock()
Expand Down Expand Up @@ -343,6 +345,32 @@ async def test_v2_edit_partition_POST(self):
self.assertTrue(self.fsc.locked_probe_data)
handler.assert_called_once()

async def test__pre_shutdown_install_started(self):
self.fsc.reset_partition_only = False
run = mock.patch.object(self.app.command_runner, "run")
_all = mock.patch.object(self.fsc.model, "_all")
with run as mock_run, _all:
await self.fsc._pre_shutdown()
mock_run.assert_has_calls(
[
mock.call(["mountpoint", "/target"]),
mock.call(["umount", "--recursive", "/target"]),
]
)
self.assertEqual(len(mock_run.mock_calls), 2)

async def test__pre_shutdown_install_not_started(self):
async def fake_run(cmd, **kwargs):
if cmd == ["mountpoint", "/target"]:
raise subprocess.CalledProcessError(cmd=cmd, returncode=1)

self.fsc.reset_partition_only = False
run = mock.patch.object(self.app.command_runner, "run", side_effect=fake_run)
_all = mock.patch.object(self.fsc.model, "_all")
with run as mock_run, _all:
await self.fsc._pre_shutdown()
mock_run.assert_called_once_with(["mountpoint", "/target"])


class TestGuided(IsolatedAsyncioTestCase):
boot_expectations = [
Expand Down

0 comments on commit 143d8e3

Please sign in to comment.