Avoid crashing when run in a bare git repo that somehow contains an index file

Do not populate the keys database with associated files,
because a bare repo has no working tree, and so it does not make sense to
populate it.

Queries of associated files in the keys database always return empty lists
in a bare repo, even if it's somehow populated. One way it could be
populated is if a user converts a non-bare repo to a bare repo.

Note that Git.Config.isBare does a string comparison, so this is not free!
But, that string comparison is very small compared to a sqlite query.

Sponsored-by: Erik Bjäreholt on Patreon
This commit is contained in:
Joey Hess 2022-01-11 13:01:49 -04:00
parent c031d19c32
commit f54c58f0df
No known key found for this signature in database
GPG key ID: DB12DB0FF05F8F38
4 changed files with 48 additions and 4 deletions

View file

@ -49,6 +49,7 @@ import Git.Sha
import Git.CatFile
import Git.Branch (writeTreeQuiet, update')
import qualified Git.Ref
import qualified Git.Config
import Config.Smudge
import qualified Utility.RawFilePath as R
@ -154,11 +155,23 @@ addAssociatedFile k f = runWriterIO $ SQL.addAssociatedFile k f
{- Note that the files returned were once associated with the key, but
- some of them may not be any longer. -}
getAssociatedFiles :: Key -> Annex [TopFilePath]
getAssociatedFiles = runReaderIO . SQL.getAssociatedFiles
getAssociatedFiles k = emptyWhenBare $ runReaderIO $ SQL.getAssociatedFiles k
{- Queries for associated files never return anything when in a bare
- repository, since without a work tree there can be no associated files.
-
- Normally the keys database is not even populated with associated files
- in a bare repository, but it might happen if a non-bare repo got
- converted to bare. -}
emptyWhenBare :: Annex [a] -> Annex [a]
emptyWhenBare a = ifM (Git.Config.isBare <$> gitRepo)
( return []
, a
)
{- Include a known associated file along with any recorded in the database. -}
getAssociatedFilesIncluding :: AssociatedFile -> Key -> Annex [RawFilePath]
getAssociatedFilesIncluding afile k = do
getAssociatedFilesIncluding afile k = emptyWhenBare $ do
g <- Annex.gitRepo
l <- map (`fromTopFilePath` g) <$> getAssociatedFiles k
return $ case afile of
@ -168,7 +181,7 @@ getAssociatedFilesIncluding afile k = do
{- Gets any keys that are on record as having a particular associated file.
- (Should be one or none but the database doesn't enforce that.) -}
getAssociatedKey :: TopFilePath -> Annex [Key]
getAssociatedKey = runReaderIO . SQL.getAssociatedKey
getAssociatedKey f = emptyWhenBare $ runReaderIO $ SQL.getAssociatedKey f
removeAssociatedFile :: Key -> TopFilePath -> Annex ()
removeAssociatedFile k = runWriterIO . SQL.removeAssociatedFile k
@ -233,7 +246,7 @@ isInodeKnown i s = or <$> runReaderIO ((:[]) <$$> SQL.isInodeKnown i s)
- is an associated file.
-}
reconcileStaged :: H.DbQueue -> Annex ()
reconcileStaged qh = do
reconcileStaged qh = unlessM (Git.Config.isBare <$> gitRepo) $ do
gitindex <- inRepo currentIndexFile
indexcache <- fromRawFilePath <$> fromRepo gitAnnexKeysDbIndexCache
withTSDelta (liftIO . genInodeCache gitindex) >>= \case