Mercurial > prosody-hg
comparison tools/erlparse.lua @ 482:b86082df0bc0
ejabberd db dump importer for Prosody
| author | Waqas Hussain <waqas20@gmail.com> |
|---|---|
| date | Sat, 29 Nov 2008 23:59:27 +0500 |
| parents | |
| children | 237cddb1a785 |
comparison
equal
deleted
inserted
replaced
| 478:3abf90751a8f | 482:b86082df0bc0 |
|---|---|
| 1 | |
| 2 local file = nil; | |
| 3 local last = nil; | |
| 4 local function read(expected) | |
| 5 local ch; | |
| 6 if last then | |
| 7 ch = last; last = nil; | |
| 8 else ch = file:read(1); end | |
| 9 if expected and ch ~= expected then error("expected: "..expected.."; got: "..(ch or "nil")); end | |
| 10 return ch; | |
| 11 end | |
| 12 local function pushback(ch) | |
| 13 if last then error(); end | |
| 14 last = ch; | |
| 15 end | |
| 16 local function peek() | |
| 17 if not last then last = read(); end | |
| 18 return last; | |
| 19 end | |
| 20 | |
| 21 local _A, _a, _Z, _z, _0, _9, __, _space = string.byte("AaZz09_ ", 1, 8); | |
| 22 local function isAlpha(ch) | |
| 23 ch = string.byte(ch) or 0; | |
| 24 return (ch >= _A and ch <= _Z) or (ch >= _a and ch <= _z); | |
| 25 end | |
| 26 local function isNumeric(ch) | |
| 27 ch = string.byte(ch) or 0; | |
| 28 return (ch >= _0 and ch <= _9); | |
| 29 end | |
| 30 local function isVar(ch) | |
| 31 ch = string.byte(ch) or 0; | |
| 32 return (ch >= _A and ch <= _Z) or (ch >= _a and ch <= _z) or (ch >= _0 and ch <= _9) or ch == __; | |
| 33 end | |
| 34 local function isSpace(ch) | |
| 35 ch = string.byte(ch) or "x"; | |
| 36 return ch <= _space; | |
| 37 end | |
| 38 | |
| 39 local function readString() | |
| 40 read("\""); -- skip quote | |
| 41 local slash = nil; | |
| 42 local str = ""; | |
| 43 while true do | |
| 44 local ch = read(); | |
| 45 if ch == "\"" and not slash then break; end | |
| 46 str = str..ch; | |
| 47 end | |
| 48 str = str:gsub("\\.", {["\\b"]="\b", ["\\d"]="\d", ["\\e"]="\e", ["\\f"]="\f", ["\\n"]="\n", ["\\r"]="\r", ["\\s"]="\s", ["\\t"]="\t", ["\\v"]="\v", ["\\\""]="\"", ["\\'"]="'", ["\\\\"]="\\"}); | |
| 49 return str; | |
| 50 end | |
| 51 local function readSpecialString() | |
| 52 read("<"); read("<"); -- read << | |
| 53 local str = ""; | |
| 54 if peek() == "\"" then | |
| 55 local str = readString(); | |
| 56 elseif peek() ~= ">" then | |
| 57 error(); | |
| 58 end | |
| 59 read(">"); read(">"); -- read >> | |
| 60 return str; | |
| 61 end | |
| 62 local function readVar() | |
| 63 local var = read(); | |
| 64 while isVar(peek()) do | |
| 65 var = var..read(); | |
| 66 end | |
| 67 return var; | |
| 68 end | |
| 69 local function readNumber() | |
| 70 local num = read(); | |
| 71 while isNumeric(peek()) do | |
| 72 num = num..read(); | |
| 73 end | |
| 74 return tonumber(num); | |
| 75 end | |
| 76 local readItem = nil; | |
| 77 local function readTuple() | |
| 78 local t = {}; | |
| 79 read(); -- read { or [ | |
| 80 while true do | |
| 81 local item = readItem(); | |
| 82 if not item then break; end | |
| 83 table.insert(t, item); | |
| 84 end | |
| 85 read(); -- read } or ] | |
| 86 return t; | |
| 87 end | |
| 88 readItem = function() | |
| 89 local ch = peek(); | |
| 90 if ch == nil then return nil end | |
| 91 if ch == "{" or ch == "[" then | |
| 92 return readTuple(); | |
| 93 elseif isAlpha(ch) then | |
| 94 return readVar(); | |
| 95 elseif isNumeric(ch) then | |
| 96 return readNumber(); | |
| 97 elseif ch == "\"" then | |
| 98 return readString(); | |
| 99 elseif ch == "<" then | |
| 100 return readSpecialString(); | |
| 101 elseif isSpace(ch) or ch == "," then | |
| 102 read(); | |
| 103 return readItem(); | |
| 104 else | |
| 105 --print("Unknown char: "..ch); | |
| 106 return nil; | |
| 107 end | |
| 108 end | |
| 109 local function readChunk() | |
| 110 local x = readItem(); | |
| 111 if x then read("."); end | |
| 112 return x; | |
| 113 end | |
| 114 local function readFile(filename) | |
| 115 file = io.open(filename); | |
| 116 if not file then error("File not found: "..filename); os.exit(0); end | |
| 117 return function() | |
| 118 local x = readChunk(); | |
| 119 if not x and peek() then error("Invalid char: "..peek()); end | |
| 120 return x; | |
| 121 end; | |
| 122 end | |
| 123 | |
| 124 module "erlparse" | |
| 125 | |
| 126 function parseFile(file) | |
| 127 return readFile(file); | |
| 128 end | |
| 129 | |
| 130 return _M; |
