smr/src/lua/tags.lua

70 lines
1.7 KiB
Lua

--[[ md
@name lua/tags
Helper methods for cleaning story tags.
Tags are the main way to search smr, a simple `+<tag>` or `-<tag>` will show all
stories that include (+) or do not include (-) a particular tag.
Tags are stored in the {{table_tags}} and are deleted if the story they are
attached to is deleted. If an author is deleted, all their stories are deleted,
and this will cascade to deleting tags on their stories too.
]]
local sql = require("lsqlite3")
local db = require("db")
local queries = require("queries")
local tags = {}
local stmnt_get_tags, stmnt_ins_tag, stmnt_drop_tags
local oldconfigure = configure
function configure(...)
--Tags for a story
stmnt_ins_tag = assert(db.conn:prepare(queries.insert_tag))
stmnt_get_tags = assert(db.conn:prepare(queries.select_tags))
stmnt_drop_tags = assert(db.conn:prepare(queries.delete_tags))
return oldconfigure(...)
end
function tags.get(id)
local ret = {}
stmnt_get_tags:bind_names{
id = id
}
local err
repeat
err = stmnt_get_tags:step()
if err == sql.BUSY then
coroutine.yield()
elseif err == sql.ROW then
table.insert(ret,stmnt_get_tags:get_value(0))
elseif err == sql.DONE then
stmnt_get_tags:reset()
return ret
else
error(string.format("Failed to get tags for story %d : %d", id, err))
end
until false
end
function tags.set(storyid,tags_list)
assert(stmnt_drop_tags:bind_names{postid = storyid} == sql.OK)
db.do_sql(stmnt_drop_tags)
stmnt_drop_tags:reset()
local err
for _,tag in pairs(tags_list) do
assert(stmnt_ins_tag:bind(1,storyid) == sql.OK)
assert(stmnt_ins_tag:bind(2,tag) == sql.OK)
err = db.do_sql(stmnt_ins_tag)
stmnt_ins_tag:reset()
end
if err ~= sql.DONE then
log(LOG_CRIT,"Failed to save tags on " .. storyid)
end
end
return tags