[Haskell-cafe] MissingH bracketCD (aka bracketCWD) bug -- this is
the infamous lazy io, right?
Thomas Hartman
tphyahoo at gmail.com
Mon Mar 23 04:08:41 EDT 2009
I got bitten by a bug (well, I call it bug) in bracketCD from
HSH/MissingH demonstrated by the following code
bracketCD is very useful for sysadminny one-offs, I use it all the
time, but..... I suspect that unless people are very careful, this
behavior will affect other users of bracketCD, in potentially very
subtle and tricky ways.
1) -- is there a more elegant way to deal with lazy io than the hack
below? (putStrLn the last character)
2) -- should MissingH function bracketCD be fixed, and if so how?
import System.FilePath.Find (find)
import System.Directory (getDirectoryContents, getCurrentDirectory,
setCurrentDirectory)
import System.Path (bracketCWD) -- from MissingH
-- the fixed function, a more restrictive type than bracketCWD which
lets you do any io, not just showables
myBracketCWD :: Show a => FilePath -> IO a -> IO a
myBracketCWD fp action =
do oldcwd <- getCurrentDirectory
setCurrentDirectory fp
a <- action
putStrLn $ show . last . show $ a -- force evaluation
setCurrentDirectory oldcwd
return a
-- rather than listing "/", lists dir this module is in
tWrong = bracketCWD "/" $ return . take 2 =<< listCurrentWithFind
-- this lists filesystem root
tRight = myBracketCWD "/" $ return . take 2 =<< listCurrentWithFind
listCurrentWithFind = System.FilePath.Find.find (return True) (return True) "."
-- for some reason, bracketCWD does the right thing with get
tGetContents = myBracketCWD "/" $ return . take 2 =<< getDirectoryContents "."
Actual code for bracketCWD in MissingH:
-- this is from MissingH, seems there's a bug when attempt to wrap a
find command
bracketCWD :: FilePath -> IO a -> IO a
bracketCWD fp action =
do oldcwd <- getCurrentDirectory
setCurrentDirectory fp
finally action (setCurrentDiurectory oldcwd)
More information about the Haskell-Cafe
mailing list