123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142 |
- local dir = require "pl.dir"
- local path = require "pl.path"
- local store = require "volksdata.store"
- local term = require "volksdata.term"
- local nsm = require "volksdata.namespace"
- -- Read only module properties.
- local PROTECTED = {
- store = true,
- reset_store = true,
- }
- local fpath = debug.getinfo(1, "S").source:sub(2)
- local root_path = path.dirname(path.dirname(fpath))
- local config_path = os.getenv("PKAR_CONFIG_DIR") or
- path.join(root_path .. "/config")
- local config = dofile(path.join(config_path, "app.lua"))
- local store_id = "file://" .. (os.getenv("PKAR_BASE") or config.fs.dres_path)
- -- Fill namespace map from config.
- for pfx, ns in pairs(config.namespace) do nsm.add(pfx, ns) end
- -- Initialize the store. `clear` wipes all data. YOU HAVE BEEN WARNED!
- local store_init = function(clear)
- return store.new(store.MDB, store_id, clear)
- end
- local M = {
- -- Project root path.
- root = root_path,
- config = config,
- default_title = "Pocket Archive",
- store_id = store_id,
- --Logger config.
- logger = require "sllog":init{
- {"err", "%T PKAR %-5L ", "%n", io.stderr},
- {"warn", "%T PKAR %-5L ", "%n", io.stderr},
- {"info", "%T PKAR %-5L ", "%n", io.stderr},
- {"debug", "%T PKAR %-5L%f (%S) ", "%n", io.stderr},
- timefn=(socket or {}).gettime, -- use socket.gettime if available
- report="debug", -- to which level should internal log events be passed?
- hookrequire=true, -- also report calls to require()
- level="debug", -- output levels up to and including "dbg"
- },
- -- Commonly used terms.
- RDF_TYPE = term.new_iriref_ns("rdf:type"),
- DC_TITLE_P = term.new_iriref_ns("dc:title"),
- DC_CREATED_P = term.new_iriref_ns("dc:created"),
- TN_P = term.new_iriref_ns("pas:thumbnail"),
- FIRST_P = term.new_iriref_ns("pas:first"),
- NEXT_P = term.new_iriref_ns("pas:next"),
- PATH_P = term.new_iriref_ns("pas:sourcePath"),
- CONTENT_TYPE_P = term.new_iriref_ns("pas:contentType"),
- ART_T = term.new_iriref_ns("pas:Artifact"),
- PART_T = term.new_iriref_ns("pas:Part"),
- FILE_T = term.new_iriref_ns("pas:File"),
- -- Common namespaces
- PAR_NS = nsm.get_ns("par"),
- PAS_NS = nsm.get_ns("pas"),
- -- Methods.
- -- Escape strings for use in gsub patterns.
- escape_ptn = function(src)
- return src:gsub("[%(%)%.%%%+%-%*%?%[%]%^%$]", "%%%0")
- end,
- }
- --[[
- Generate pairtree directory and file path from an ID string and prefix.
- The directory is created if not existing.
- The ID string can include the `par:` namespace prefix or the fully qualified
- namespace.
- ext is optional, and is appended to the raw path.
- if no_create is not nil or false, the directory will not be checked for
- existence or created.
- return: full file path, with the optional extension if provided.
- --]]
- M.gen_pairtree = function (pfx, id_str, ext, no_create)
- local bare_id = id_str:gsub(M.PAR_NS, ""):gsub("^par:", "")
- local res_dir = path.join(pfx, bare_id:sub(1,2), bare_id:sub(3,4))
- local created, err
- if (path.isdir(res_dir)) or no_create then created = false
- else
- created, err = dir.makepath(res_dir)
- if not created then error(err) end
- end
- local fpath
- if (res_dir) then fpath = path.join(res_dir, bare_id .. (ext or "")) end
- return fpath, created
- end
- -- No more assignments to the module afte here.
- local mt = {
- __index = function(t, k)
- if (k == "store") then
- if not rawget(t, "_store") then
- rawset(t, "_store", store.new(store.MDB, store_id)) end
- return rawget(t, "_store")
- -- WIPE ALL DATA from the store and returns the new empty store handle.
- elseif (k == "reset_store") then
- rawset(t, "_store", store.new(store.MDB, store_id, true))
- return rawget(t, "_store")
- end
- end,
- __newindex = function () return nil, "Module is read only." end
- }
- setmetatable (M, mt)
- -- Initialize random ID generator.
- math.randomseed(M.config.id.seed[1], M.config.id.seed[2])
- return M
|