14 import Control.Arrow.ArrowIO
15 import Control.Concurrent.STM
17 import Control.Monad.Trans
20 import Rakka.Storage.DefaultPage
21 import Subversion.Types
22 import System.Directory
23 import System.FilePath
24 import System.Log.Logger
25 import Subversion.Repository
26 import Text.HyperEstraier
30 import Data.Encoding.UTF8
31 import qualified Data.ByteString.Lazy.Char8 as C8
34 logger = "Rakka.Storage"
39 stoIndexRevLocked :: !(TVar Bool)
40 , stoIndexRevFile :: !FilePath
41 , stoIndexDB :: !Database
42 , stoRepository :: !Repository
43 , stoMakeDraft :: !(Page -> IO Document)
47 mkStorage :: FilePath -> Repository -> (Page -> IO Document) -> IO Storage
48 mkStorage lsdir repos mkDraft
49 = do let indexDir = lsdir `combine` "index"
50 revFile = lsdir `combine` "indexRev"
52 revLocked <- newTVarIO False
53 indexDB <- openIndex indexDir revFile
56 stoIndexRevLocked = revLocked
57 , stoIndexRevFile = revFile
58 , stoIndexDB = indexDB
59 , stoRepository = repos
60 , stoMakeDraft = mkDraft
67 getPage :: MonadIO m => Storage -> PageName -> m (Maybe Page)
69 = liftIO $ loadDefaultPage name -- FIXME
72 putPage :: MonadIO m => Storage -> Maybe RevNum -> Page -> m ()
73 putPage sto oldRev page
74 = error "FIXME: not implemented"
77 getPageA :: ArrowIO a => Storage -> a PageName (Maybe Page)
78 getPageA = arrIO . getPage
81 putPageA :: ArrowIO a => Storage -> a (Maybe RevNum, Page) ()
82 putPageA = arrIO2 . putPage
85 findAllPages :: Storage -> RevNum -> IO (Set PageName)
86 findAllPages sto revNum
87 = findAllDefaultPages -- FIXME
90 -- casket を R/W モードで開く。成功したらそのまま返し、失敗したら
91 -- indexDir と revFile を削除してから casket を R/W モードで開く。
92 openIndex :: FilePath -> FilePath -> IO Database
93 openIndex indexDir revFile
94 = do ret <- openDatabase indexDir (Writer [])
97 -> do debugM logger ("Opened an H.E. database on " ++ indexDir)
101 -> do warningM logger ("Failed to open an H.E. database on "
102 ++ indexDir ++ ": " ++ show err)
104 indexExists <- doesDirectoryExist indexDir
106 $ removeDirectoryRecursive indexDir
108 revFileExists <- doesFileExist revFile
112 Right db <- openDatabase indexDir (Writer [Create []])
113 noticeM logger ("Created an H.E. database on " ++ indexDir)
118 syncIndex :: Storage -> IO ()
120 = do Just page <- getPage sto "MainPage"
121 doc <- stoMakeDraft sto page
122 putStrLn "*** dumping draft..."
123 dumpDraft doc >>= C8.putStr . encodeLazy UTF8
124 putStrLn "*** dumped"