more improvements to takeover

This commit is contained in:
Joey Hess 2014-12-04 17:30:40 -04:00
parent fd90adc7d3
commit 4be893f0bf
1 changed files with 40 additions and 34 deletions

View File

@ -4,8 +4,8 @@ module Propellor.Property.OS (
preserveNetworkInterfaces, preserveNetworkInterfaces,
preserveRootSshAuthorized, preserveRootSshAuthorized,
grubBoots, grubBoots,
GrubDev(..), GrubDev,
oldOSKernelPreserved, rebootForced,
kernelInstalled, kernelInstalled,
oldOSRemoved, oldOSRemoved,
) where ) where
@ -15,6 +15,7 @@ import qualified Propellor.Property.Debootstrap as Debootstrap
import qualified Propellor.Property.Ssh as Ssh import qualified Propellor.Property.Ssh as Ssh
import qualified Propellor.Property.User as User import qualified Propellor.Property.User as User
import Propellor.Property.Mount import Propellor.Property.Mount
import Propellor.Property.Chroot.Util (stdPATH)
import System.Posix.Files (rename, fileExist) import System.Posix.Files (rename, fileExist)
@ -24,29 +25,29 @@ import System.Posix.Files (rename, fileExist)
-- This can replace one Linux distribution with different one. -- This can replace one Linux distribution with different one.
-- But, it can also fail and leave the system in an unbootable state. -- But, it can also fail and leave the system in an unbootable state.
-- --
-- The files from the old os will be left in /old-os
--
-- To avoid this property being accidentially used, you have to provide -- To avoid this property being accidentially used, you have to provide
-- a Confirmation containing the name of the host that you intend to apply the -- a Confirmation containing the name of the host that you intend to apply
-- property to. -- the property to.
-- --
-- This property only runs once. The cleanly installed system will have -- This property only runs once. The cleanly installed system will have
-- a file /etc/propellor-cleaninstall, which indicates it was cleanly -- a file /etc/propellor-cleaninstall, which indicates it was cleanly
-- installed. -- installed.
--
-- The files from the old os will be left in /old-os
-- --
-- You will typically want to run some more properties after the clean -- You will typically want to run some more properties after the clean
-- install, to bootstrap from the cleanly installed system to a fully -- install succeeds, to bootstrap from the cleanly installed system to
-- working system. For example: -- a fully working system. For example:
-- --
-- > & os (System (Debian Unstable) "amd64") -- > & os (System (Debian Unstable) "amd64")
-- > & cleanInstall (Confirmed "foo.example.com") -- > & cleanInstall (Confirmed "foo.example.com")
-- > `onChange` propertyList "fixing up after clean install" -- > `onChange` propertyList "fixing up after clean install"
-- > [ preserveNetworkInterfaces -- > [ preserveNetworkInterfaces
-- > , preserverRootSshAuthorized -- > , preserverRootSshAuthorized
-- > , oldOSKernelPreserved
-- > -- , kernelInstalled -- > -- , kernelInstalled
-- > -- , grubBoots "hd0" -- > -- , grubBoots "hd0"
-- > -- , oldOsRemoved -- > -- , oldOsRemoved (Confirmed "foo.example.com")
-- > -- , rebootForced
-- > ] -- > ]
-- > & Apt.installed ["ssh"] -- > & Apt.installed ["ssh"]
-- > & User.hasSomePassword "root" -- > & User.hasSomePassword "root"
@ -95,7 +96,26 @@ cleanInstallOnce confirmation = check (not <$> doesFileExist flagfile) $
whenM (not <$> fileExist dest) $ whenM (not <$> fileExist dest) $
rename d dest rename d dest
removeDirectoryRecursive newOSDir removeDirectoryRecursive newOSDir
-- Prepare environment for running additional properties.
liftIO $ writeFile flagfile ""
void $ setEnv "PATH" stdPATH True
return MadeChange return MadeChange
propellorbootstrapped = property "propellor re-debootstrapped in new os" $
return NoChange
-- re-bootstrap propellor in /usr/local/propellor,
-- (using git repo bundle, privdata file, and possibly
-- git repo url, which all need to be arranged to
-- be present in /old-os's /usr/local/propellor)
-- TODO
-- Ensure that MadeChange is returned by the overall property,
-- so that anything hooking in onChange will run afterwards.
finalized = property "clean OS installed" $ return MadeChange
flagfile = "/etc/propellor-cleaninstall"
trickydirs = trickydirs =
-- /tmp can contain X's sockets, which prevent moving it -- /tmp can contain X's sockets, which prevent moving it
@ -105,19 +125,6 @@ cleanInstallOnce confirmation = check (not <$> doesFileExist flagfile) $
, "/proc" , "/proc"
] ]
propellorbootstrapped = property "propellor re-debootstrapped in new os" $
return NoChange
-- re-bootstrap propellor in /usr/local/propellor,
-- (using git repo bundle, privdata file, and possibly
-- git repo url, which all need to be arranged to
-- be present in /old-os's /usr/local/propellor)
finalized = property "clean OS installed" $ do
liftIO $ writeFile flagfile ""
return MadeChange
flagfile = "/etc/propellor-cleaninstall"
data Confirmation = Confirmed HostName data Confirmation = Confirmed HostName
confirmed :: Desc -> Confirmation -> Property confirmed :: Desc -> Confirmation -> Property
@ -129,12 +136,12 @@ confirmed desc (Confirmed c) = property desc $ do
return FailedChange return FailedChange
else return NoChange else return NoChange
-- /etc/network/interfaces is configured to bring up all interfaces that -- | /etc/network/interfaces is configured to bring up all interfaces that
-- are currently up, using the same IP addresses. -- are currently up, using the same IP addresses.
preserveNetworkInterfaces :: Property preserveNetworkInterfaces :: Property
preserveNetworkInterfaces = undefined preserveNetworkInterfaces = undefined
-- Root's .ssh/authorized_keys has added to it any ssh keys that -- | Root's .ssh/authorized_keys has added to it any ssh keys that
-- were authorized in the old OS. Any other contents of the file are -- were authorized in the old OS. Any other contents of the file are
-- retained. -- retained.
preserveRootSshAuthorized :: Property preserveRootSshAuthorized :: Property
@ -146,18 +153,11 @@ preserveRootSshAuthorized = check (doesDirectoryExist oldloc) $
newloc = "/root/.ssh/authorized_keys" newloc = "/root/.ssh/authorized_keys"
oldloc = oldOSDir ++ newloc oldloc = oldOSDir ++ newloc
-- Installs an appropriate kernel from the OS distribution. -- | Installs an appropriate kernel from the OS distribution.
kernelInstalled :: Property kernelInstalled :: Property
kernelInstalled = undefined kernelInstalled = undefined
-- Copies kernel images, initrds, and modules from /old-os -- | Installs grub onto a device to boot the system.
-- into the new system.
--
-- TODO: grub config?
oldOSKernelPreserved :: Property
oldOSKernelPreserved = undefined
-- Installs grub onto a device to boot the system.
-- --
-- You may want to install grub to multiple devices; eg for a system -- You may want to install grub to multiple devices; eg for a system
-- that uses software RAID. -- that uses software RAID.
@ -166,6 +166,12 @@ grubBoots = undefined
type GrubDev = String type GrubDev = String
-- | Forces an immediate reboot, without contacting the init system.
--
-- Can be used after cleanInstallOnce.
rebootForced :: Property
rebootForced = cmdProperty "reboot" [ "--force" ]
-- Removes the old OS's backup from /old-os -- Removes the old OS's backup from /old-os
oldOSRemoved :: Confirmation -> Property oldOSRemoved :: Confirmation -> Property
oldOSRemoved confirmation = check (doesDirectoryExist oldOSDir) $ oldOSRemoved confirmation = check (doesDirectoryExist oldOSDir) $