diff options
Diffstat (limited to 'lib/gall/tag.lua')
-rw-r--r-- | lib/gall/tag.lua | 97 |
1 files changed, 97 insertions, 0 deletions
diff --git a/lib/gall/tag.lua b/lib/gall/tag.lua new file mode 100644 index 0000000..707af31 --- /dev/null +++ b/lib/gall/tag.lua @@ -0,0 +1,97 @@ +-- gall.tag +-- +-- Git Abstraction Layer for Lua -- Tag object interface +-- +-- Copyright 2012 Daniel Silverstone <dsilvers@digital-scurf.org> +-- +-- + +local ll = require "gall.ll" + +local objs = setmetatable({}, {__mode="k"}) +local repos = setmetatable({}, {__mode="k"}) +local parsed = setmetatable({}, {__mode="k"}) + +local _new + +local function parse_person(pers) + local real, email, when, tz = pers:match("^(.-) <([^>]+)> ([0-9]+) ([+-][0-9]+)$") + return { + realname = real, + email = email, + unixtime = when, + timezone = tz + } +end + +local function tagindex(tag, field) + if not parsed[tag] then + local raw = objs[tag].raw + local headers, body, signature = {}, "" + local state = "headers" + + for l in raw:gmatch("([^\n]*)\n") do + if state == "headers" then + local first, second = l:match("^([^ ]+) (.+)$") + if first then + if headers[first] then + headers[first][#headers[first]+1] = second + else + headers[first] = { second } + end + else + state = "message" + end + elseif state == "message" then + if l == PGP_SIG_START then + signature = l .. "\n" + state = "signature" + else + body = body .. l .. "\n" + end + else + signature = signature .. l .. "\n" + end + end + + -- there's always one object + rawset(tag, "object", repos[tag]:get(headers.object[1])) + -- Always one type + rawset(tag, "type", headers.type[1]) + -- Always one tag name + rawset(tag, "tag", headers.tag[1]) + -- Always one tagger + rawset(tag, "tagger", parse_person(headers.tag[1])) + -- A message + rawset(tag, "message", body) + -- And an optional signature + rawset(tag, "signature", signature) + -- Promote the SHA + rawset(tag, "sha", objs[tag].sha) + + -- Signal we are parsed + parsed[tag] = true + end + + return rawget(tag, field) +end + +local function tagtostring(tag) + return "<GitTag(" .. tostring(objs[tag].sha) .. ") in " .. tostring(repos[tag]) .. ">" +end + +local tagmeta = { + __index = tagindex, + __tostring = tagtostring +} + +function _new(repo, obj) + local ret = setmetatable({}, tagmeta) + objs[ret] = obj + repos[ret] = repo + return ret +end + +return { + new = _new +} |