cvsimport
[hcoop/zz_old/portal.git] / quotas.sml
CommitLineData
7347efe8 1structure Quotas :> QUOTAS =
2struct
3 fun getQuotas uname =
4 let
5 val proc = Unix.execute ("/bin/sh", ["-c", "/usr/bin/vos listvol -long deleuze"])
6 val inf = Unix.textInstreamOf proc
7
8 fun eatUntilBlankLine () =
9 case TextIO.inputLine inf of
10 NONE => ()
11 | SOME "\n" => ()
12 | SOME _ => eatUntilBlankLine ()
13
14 val suffix = "." ^ uname
15
16 fun loop acc =
17 case TextIO.inputLine inf of
18 NONE => acc
19 | SOME line =>
20 case String.tokens Char.isSpace line of
21 [vol, _, _, kbs, _, _] =>
22 if String.isSuffix suffix vol then
23 let
24 val _ = TextIO.inputLine inf
25 val _ = TextIO.inputLine inf
26 in
27 case TextIO.inputLine inf of
28 NONE => loop acc
29 | SOME line =>
30 let
31 val quota =
32 case String.tokens Char.isSpace line of
33 [_, quota, _] => quota
34 | _ => raise Fail "Bad quota string"
35 in
36 eatUntilBlankLine ();
37 loop ({vol = vol,
38 used = valOf (Int.fromString kbs),
39 quota = valOf (Int.fromString quota)}
40 :: acc)
41 end
42 end
43 else
44 (eatUntilBlankLine ();
45 loop acc)
46 | _ => acc
47
48 val _ = TextIO.inputLine inf
49 in
50 loop []
51 before ignore (Unix.reap proc)
52 end
53
54 fun goofy s =
55 if size s < 2 then
56 raise Fail "Username too short"
57 else
58 String.concat [String.substring (s, 0, 1), "/",
59 String.substring (s, 0, 2), "/",
60 s]
61
62 fun splitVol vol =
63 let
64 val (befor, after) = Substring.splitl (fn ch => ch <> #".") (Substring.full vol)
65 in
66 (Substring.string befor,
67 Substring.string (Substring.slice (after, 1, NONE)))
68 end
69
70 fun path vol =
71 let
72 val (kind, uname) = splitVol vol
73 in
74 case kind of
75 "user" => "/afs/hcoop.net/user/" ^ goofy uname
76 | "db" => "/afs/hcoop.net/.databases/" ^ goofy uname
77 | "mail" => "/afs/hcoop.net/user/" ^ goofy uname ^ "/Maildir"
78 | _ => raise Fail ("Don't know how to find mount point for volume " ^ vol)
79 end
80
81end