diff options
Diffstat (limited to 'Presence/ConfigFiles.hs')
-rw-r--r-- | Presence/ConfigFiles.hs | 111 |
1 files changed, 67 insertions, 44 deletions
diff --git a/Presence/ConfigFiles.hs b/Presence/ConfigFiles.hs index 808e6dd8..b745094f 100644 --- a/Presence/ConfigFiles.hs +++ b/Presence/ConfigFiles.hs | |||
@@ -18,32 +18,42 @@ import Data.List (partition) | |||
18 | import Data.Maybe (catMaybes,isJust) | 18 | import Data.Maybe (catMaybes,isJust) |
19 | 19 | ||
20 | type User = ByteString | 20 | type User = ByteString |
21 | type Profile = String | ||
21 | 22 | ||
22 | configDir = ".presence" | 23 | configDir, buddyFile, subscriberFile, |
23 | buddyFile = "buddies" | 24 | otherFile, pendingFile, solicitedFile, |
25 | secretsFile :: FilePath | ||
26 | |||
27 | configDir = ".presence" | ||
28 | buddyFile = "buddies" | ||
24 | subscriberFile = "subscribers" | 29 | subscriberFile = "subscribers" |
25 | otherFile = "others" | 30 | otherFile = "others" |
26 | pendingFile = "pending" | 31 | pendingFile = "pending" |
27 | solicitedFile = "solicited" | 32 | solicitedFile = "solicited" |
33 | secretsFile = "secrets" | ||
28 | 34 | ||
29 | 35 | ||
30 | configPath :: User -> String -> IO String | 36 | configPath :: User -> Profile -> String -> IO String |
31 | configPath user filename = do | 37 | configPath user "." filename = do |
32 | ue <- getUserEntryForName (unpack user) | 38 | ue <- getUserEntryForName (unpack user) |
33 | return $ (++("/"++configDir++"/"++filename)) $ homeDirectory ue | 39 | return $ (++("/"++configDir++"/"++filename)) $ homeDirectory ue |
40 | configPath user profile filename = do | ||
41 | ue <- getUserEntryForName (unpack user) | ||
42 | return $ (++("/"++configDir++"/"++profile++"/"++filename)) $ homeDirectory ue | ||
34 | 43 | ||
35 | 44 | createConfigFile :: ByteString -> FilePath -> IO () | |
36 | createConfigFile tag path = do | 45 | createConfigFile tag path = do |
37 | let dir = dropFileName path | 46 | let dir = dropFileName path |
38 | doesDirectoryExist dir >>= flip unless (do | 47 | doesDirectoryExist dir >>= flip unless (do |
39 | createDirectory dir | 48 | createDirectory dir |
40 | ) | 49 | ) |
41 | withFile path WriteMode $ \h -> do | 50 | withFile path WriteMode $ \h -> do |
42 | L.hPutStrLn h tag | 51 | L.hPutStrLn h tag |
43 | 52 | ||
53 | addItem :: ByteString -> ByteString -> FilePath -> IO () | ||
44 | addItem item tag path = | 54 | addItem item tag path = |
45 | let doit = do | 55 | let doit = do |
46 | handle (\e -> when (isDoesNotExistError e) | 56 | handle (\e -> when (isDoesNotExistError e) |
47 | (createConfigFile tag path >> doit)) | 57 | (createConfigFile tag path >> doit)) |
48 | $ do exists <- fileExist path | 58 | $ do exists <- fileExist path |
49 | if exists | 59 | if exists |
@@ -55,16 +65,27 @@ addItem item tag path = | |||
55 | in doit | 65 | in doit |
56 | 66 | ||
57 | 67 | ||
68 | -- | Modify a presence configuration file. This function will iterate over all | ||
69 | -- items in the file and invoke a test function. If the function returns | ||
70 | -- Nothing, that item is removed from the file. Otherwise, the function may | ||
71 | -- rename the item by returning the new name. | ||
72 | -- | ||
73 | -- If the last argument is populated, it is a new item to append to the end of | ||
74 | -- the file. | ||
75 | -- | ||
76 | -- Note that the entire file is read in, processed, and then rewritten from | ||
77 | -- scratch. | ||
58 | modifyFile :: | 78 | modifyFile :: |
59 | (ByteString,FilePath) | 79 | (ByteString,FilePath) |
60 | -> ByteString | 80 | -> User |
61 | -> (ByteString -> IO (Maybe ByteString)) | 81 | -> Profile |
62 | -> Maybe ByteString | 82 | -> (ByteString -> IO (Maybe ByteString)) -- Returns Just for each item you want to keep. |
83 | -> Maybe ByteString -- Optionally append this item. | ||
63 | -> IO Bool -- Returns True if test function ever returned Nothing | 84 | -> IO Bool -- Returns True if test function ever returned Nothing |
64 | modifyFile (tag,file) user test appending = configPath user file >>= doit | 85 | modifyFile (tag,file) user profile test appending = configPath user profile file >>= doit |
65 | where | 86 | where |
66 | doit path = do | 87 | doit path = do |
67 | handle (\e -> if (isDoesNotExistError e) | 88 | handle (\e -> if (isDoesNotExistError e) |
68 | then (createConfigFile tag path >> doit path) | 89 | then (createConfigFile tag path >> doit path) |
69 | else return False) | 90 | else return False) |
70 | $ do exists <- fileExist path | 91 | $ do exists <- fileExist path |
@@ -85,46 +106,48 @@ modifyFile (tag,file) user test appending = configPath user file >>= doit | |||
85 | withFile path WriteMode $ \h -> do | 106 | withFile path WriteMode $ \h -> do |
86 | L.hPutStrLn h tag | 107 | L.hPutStrLn h tag |
87 | withJust appending (L.hPutStrLn h) | 108 | withJust appending (L.hPutStrLn h) |
88 | return False | 109 | return False |
89 | |||
90 | 110 | ||
91 | modifySolicited = modifyFile ("<? solicited ?>" , solicitedFile) | 111 | modifySolicited, modifyBuddies, modifyOthers, modifyPending, modifySubscribers |
92 | modifyBuddies = modifyFile ("<? buddies ?>" , buddyFile) | 112 | :: User -> Profile -> (ByteString -> IO (Maybe ByteString)) -> Maybe ByteString -> IO Bool |
93 | modifyOthers = modifyFile ("<? others ?>" , otherFile) | ||
94 | modifyPending = modifyFile ("<? pending ?>" , pendingFile) | ||
95 | modifySubscribers = modifyFile ("<? subscribers ?>", subscriberFile) | ||
96 | 113 | ||
97 | addBuddy :: User -> ByteString -> IO () | 114 | modifySolicited = modifyFile ("<? solicited ?>" , solicitedFile) |
98 | addBuddy user buddy = | 115 | modifyBuddies = modifyFile ("<? buddies ?>" , buddyFile) |
99 | configPath user buddyFile >>= addItem buddy "<? buddies ?>" | 116 | modifyOthers = modifyFile ("<? others ?>" , otherFile) |
117 | modifyPending = modifyFile ("<? pending ?>" , pendingFile) | ||
118 | modifySubscribers = modifyFile ("<? subscribers ?>" , subscriberFile) | ||
100 | 119 | ||
101 | addSubscriber :: User -> ByteString -> IO () | 120 | addBuddy :: User -> Profile -> ByteString -> IO () |
102 | addSubscriber user subscriber = | 121 | addBuddy user profile buddy = |
103 | configPath user subscriberFile >>= addItem subscriber "<? subscribers ?>" | 122 | configPath user profile buddyFile >>= addItem buddy "<? buddies ?>" |
104 | 123 | ||
105 | addSolicited :: User -> ByteString -> IO () | 124 | addSubscriber :: User -> Profile -> ByteString -> IO () |
106 | addSolicited user solicited = | 125 | addSubscriber user profile subscriber = |
107 | configPath user solicitedFile >>= addItem solicited "<? solicited ?>" | 126 | configPath user profile subscriberFile >>= addItem subscriber "<? subscribers ?>" |
108 | 127 | ||
128 | addSolicited :: User -> Profile -> ByteString -> IO () | ||
129 | addSolicited user profile solicited = | ||
130 | configPath user profile solicitedFile >>= addItem solicited "<? solicited ?>" | ||
109 | 131 | ||
110 | getConfigList path = | 132 | getConfigList :: FilePath -> IO [ByteString] |
133 | getConfigList path = | ||
111 | handle (\e -> if isDoesNotExistError e then (return []) else throw e) | 134 | handle (\e -> if isDoesNotExistError e then (return []) else throw e) |
112 | $ withFile path ReadMode $ | 135 | $ withFile path ReadMode $ |
113 | L.hGetContents | 136 | L.hGetContents |
114 | >=> return . Prelude.tail . L.lines | 137 | >=> return . Prelude.tail . L.lines |
115 | >=> (\a -> seq (rnf a) (return a)) | 138 | >=> (\a -> seq (rnf a) (return a)) |
116 | 139 | ||
117 | getBuddies :: User -> IO [ByteString] | 140 | getBuddies :: User -> Profile -> IO [ByteString] |
118 | getBuddies user = configPath user buddyFile >>= getConfigList | 141 | getBuddies user profile = configPath user profile buddyFile >>= getConfigList |
119 | 142 | ||
120 | getSubscribers :: User -> IO [ByteString] | 143 | getSubscribers :: User -> Profile -> IO [ByteString] |
121 | getSubscribers user = configPath user subscriberFile >>= getConfigList | 144 | getSubscribers user profile = configPath user profile subscriberFile >>= getConfigList |
122 | 145 | ||
123 | getOthers :: User -> IO [ByteString] | 146 | getOthers :: User -> Profile -> IO [ByteString] |
124 | getOthers user = configPath user otherFile >>= getConfigList | 147 | getOthers user profile = configPath user profile otherFile >>= getConfigList |
125 | 148 | ||
126 | getPending :: User -> IO [ByteString] | 149 | getPending :: User -> Profile -> IO [ByteString] |
127 | getPending user = configPath user pendingFile >>= getConfigList | 150 | getPending user profile = configPath user profile pendingFile >>= getConfigList |
128 | 151 | ||
129 | getSolicited :: User -> IO [ByteString] | 152 | getSolicited :: User -> Profile -> IO [ByteString] |
130 | getSolicited user = configPath user solicitedFile >>= getConfigList | 153 | getSolicited user profile = configPath user profile solicitedFile >>= getConfigList |