]> git.e2factory.org Git - e2factory.git/commitdiff
Move e2project config handling into project module.
authorTobias Ulmer <tu@emlix.com>
Wed, 26 Feb 2014 14:46:50 +0000 (15:46 +0100)
committerTobias Ulmer <tu@emlix.com>
Wed, 16 Nov 2016 14:41:17 +0000 (15:41 +0100)
Signed-off-by: Tobias Ulmer <tu@emlix.com>
local/Makefile
local/e2-ls-project.lua
local/e2build.lua
local/e2tool.lua
local/project.lua [new file with mode: 0644]
plugins/collect_project.lua

index 3cfa2d419e0190d5f370bc16e6603d89443b9a19..7da1dd6a98b20a9d6cf0384325220233b8f349da 100644 (file)
@@ -41,7 +41,7 @@ LOCALLUATOOLS = e2-build e2-dlist e2-dsort e2-fetch-sources \
                e2-build-numbers e2-cf e2-help
 
 LOCALLUALIBS= digest.lua e2build.lua e2tool.lua environment.lua \
-             policy.lua scm.lua licence.lua chroot.lua
+             policy.lua scm.lua licence.lua chroot.lua project.lua
 LOCALTOOLS = $(LOCALLUATOOLS)
 
 .PHONY: all install uninstall local install-local doc install-doc
index 1a1c1dc0a3d7be704a9011feb776c0acae1c3252..195f8dcbc11c6b4e9b3e706866f9a9709a297d65 100644 (file)
@@ -40,6 +40,7 @@ local licence = require("licence")
 local policy = require("policy")
 local scm = require("scm")
 local chroot = require("chroot")
+local project = require("project")
 
 local function e2_ls_project(arg)
     local rc, re = e2lib.init()
@@ -168,7 +169,7 @@ local function e2_ls_project(arg)
 
     if opts.dot or opts["dot-sources"] then
         local arrow = "->"
-        console.infof("digraph \"%s\" {\n", info.project.name)
+        console.infof("digraph \"%s\" {\n", project.name())
         for _, r in pairs(results) do
             local res = info.results[r]
             local deps, re = e2tool.dlist(info, r)
@@ -208,7 +209,7 @@ local function e2_ls_project(arg)
     --------------- project name
     local s1 = "|"
     local s2 = "|"
-    p0(s1, s2, info.project.name)
+    p0(s1, s2, project.name())
 
     --------------- servers
     local s1 = "|"
index aca12263a506ce43a5d3e123cd98c1db23575506..5e21f2ce9e45f533dc2271c05b13120b3bce6864 100644 (file)
@@ -42,6 +42,7 @@ local strict = require("strict")
 local tools = require("tools")
 local transport = require("transport")
 local chroot = require("chroot")
+local project = require("project")
 
 -- Table driving the build process, see documentation at the bottom.
 local build_process = {}
@@ -53,7 +54,7 @@ local function linklast(info, r, return_flags)
     local e = err.new("creating link to last results")
     -- calculate the path to the result
     local server, location = res.build_mode.storage(info.project_location,
-        info.project.release_id)
+        project.release_id())
 
     local buildid, re = e2tool.buildid(info, r)
     if not buildid then
@@ -127,7 +128,7 @@ local function result_available(info, r, return_flags)
         return true, nil
     end
     local server, location =
-        res.build_mode.storage(info.project_location, info.project.release_id)
+        res.build_mode.storage(info.project_location, project.release_id())
     local dep_set = res.build_mode.dep_set(buildid)
 
     -- cache the result
@@ -215,20 +216,14 @@ function e2build.build_config(info, r)
         buildconfig.PATCHLEVEL, e2lib.globals.osenv["USER"])
     local builddir = "tmp/e2"
 
-    bc.base = e2lib.join(tmpdir, info.project.name, r)
+    bc.base = e2lib.join(tmpdir, project.name(), r)
     bc.c = e2lib.join(bc.base, "chroot")
     bc.chroot_marker = e2lib.join(bc.base, "e2factory-chroot")
     bc.chroot_lock = e2lib.join(bc.base, "e2factory-chroot-lock")
-    bc.T = e2lib.join(tmpdir, info.project.name, r, "chroot", builddir)
+    bc.T = e2lib.join(tmpdir, project.name(), r, "chroot", builddir)
     bc.Tc = e2lib.join("/", builddir)
     bc.r = r
-    if info.chroot_call_prefix[info.project.chroot_arch] == "" then
-        -- escape only if non-empty, otherwise we fail to start "''"
-        tab.chroot_call_prefix = ""
-    else
-        tab.chroot_call_prefix =
-            e2lib.shquote(info.chroot_call_prefix[info.project.chroot_arch])
-    end
+    bc.chroot_call_prefix = info.chroot_call_prefix[project.chroot_arch()]
     bc.buildlog = string.format("%s/log/build.%s.log", info.root, r)
     bc.scriptdir = "script"
     bc.build_driver = ""
@@ -239,8 +234,8 @@ function e2build.build_config(info, r)
     bc.builtin_env = environment.new()
     bc.builtin_env:set("E2_TMPDIR", bc.Tc)
     bc.builtin_env:set("E2_RESULT", r)
-    bc.builtin_env:set("E2_RELEASE_ID", info.project.release_id)
-    bc.builtin_env:set("E2_PROJECT_NAME", info.project.name)
+    bc.builtin_env:set("E2_RELEASE_ID", project.release_id())
+    bc.builtin_env:set("E2_PROJECT_NAME", project.name())
     bc.builtin_env:set("E2_BUILDID", buildid)
     bc.builtin_env:set("T", bc.Tc)
     bc.builtin_env:set("r", r)
@@ -368,12 +363,15 @@ function e2build.enter_playground(info, r, chroot_command)
     end
 
     cmd = {
-        res.build_config.chroot_call_prefix,
         e2_su,
         "chroot_2_3",
         res.build_config.base,
     }
 
+    if #res.build_config.chroot_call_prefix > 0 then
+        table.insert(cmd, 1, res.build_config.chroot_call_prefix)
+    end
+
     if chroot_command then
         table.insert(cmd, "/bin/sh")
         table.insert(cmd, "-c")
@@ -461,7 +459,6 @@ local function runbuild(info, r, return_flags)
     e2tool.set_umask(info)
 
     local cmd = {
-        res.build_config.chroot_call_prefix,
         e2_su,
         "chroot_2_3",
         res.build_config.base,
@@ -471,6 +468,10 @@ local function runbuild(info, r, return_flags)
             res.build_config.build_driver_file)
     }
 
+    if #res.build_config.chroot_call_prefix > 0 then
+        table.insert(cmd, 1, res.build_config.chroot_call_prefix)
+    end
+
     rc, re = e2lib.callcmd_capture(cmd, logto)
     if not rc then
         eio.fclose(out)
@@ -560,7 +561,7 @@ function e2build.unpack_result(info, r, dep, destdir)
 
     local dep_set = d.build_mode.dep_set(buildid)
     local server, location =
-        d.build_mode.storage(info.project_location, info.project.release_id)
+        d.build_mode.storage(info.project_location, project.release_id())
     e2lib.logf(3, "searching for dependency %s in %s:%s", dep, server, location)
     local location1 = e2lib.join(location, dep, dep_set, "result.tar")
     local cache_flags = {}
@@ -915,7 +916,7 @@ local function deploy(info, r, tmpdir)
     end
     table.insert(files, "checksums")
     local server, location = res.build_mode.deploy_storage(
-        info.project_location, info.project.release_id)
+        info.project_location, project.release_id())
 
     -- do not re-deploy if this release was already done earlier
     local location1 = e2lib.join(location, r, "checksums")
@@ -1035,7 +1036,7 @@ local function store_result(info, r, return_flags)
         return false, e:cat(re)
     end
     local server, location = res.build_mode.storage(info.project_location,
-        info.project.release_id)
+        project.release_id())
 
     local buildid, re = e2tool.buildid(info, r)
     if not buildid then
index 70dd804d3f42a3c675b102a223b579c994167796..2726763943bc1e3669518609861eeefd0898a526 100644 (file)
@@ -50,6 +50,7 @@ local tools = require("tools")
 local transport = require("transport")
 local url = require("url")
 local chroot = require("chroot")
+local project = require("project")
 
 -- Build function table, see end of file for details.
 local e2tool_ftab = {}
@@ -377,7 +378,7 @@ local function check_result(info, resultname)
             end
         end
     end
-    for _,r in ipairs(info.project.deploy_results) do
+    for r in project.deploy_results_iter() do
         if r == resultname then
             res._deploy = true
             break
@@ -932,76 +933,6 @@ local function load_result_configs(info)
     return true
 end
 
---- Read project configuration file.
--- @return True on success, false on error.
--- @return Error object on failure.
-local function read_project_config(info)
-
-    --- Project configuration table (e2project).
-    -- @table info.project
-    -- @field release_id Release identifier, usually a git tag (string).
-    -- @field name Name of project (string).
-    -- @field deploy_results List of results that should be archived on
-    --                       --release builds (table containing strings).
-    -- @field default_results List of results that are built by default
-    --                        (table containing strings).
-    -- @field chroot_arch Chroot architecture (string).
-
-    local rc, re, e
-
-    rc, re = load_user_config(info, e2lib.join(info.root, "proj/config"),
-        info, "project", "e2project")
-    if not rc then
-        return false, re
-    end
-
-    e = err.new("in project configuration:")
-    if not info.project.release_id then
-        e:append("key is not set: release_id")
-    end
-    if not info.project.name then
-        e:append("key is not set: name")
-    end
-    if not info.project.default_results then
-        e2lib.warnf("WDEFAULT", "in project configuration:")
-        e2lib.warnf("WDEFAULT",
-            "default_results is not set. Defaulting to empty list.")
-        info.project.default_results = {}
-    end
-    rc, re = e2lib.vrfy_listofstrings(info.project.deploy_results,
-        "deploy_results", true, true)
-    if not rc then
-        e:append("deploy_results is not a valid list of strings")
-        e:cat(re)
-    end
-    rc, re = e2lib.vrfy_listofstrings(info.project.default_results,
-        "default_results",  true, false)
-    if not rc then
-        e:append("default_results is not a valid list of strings")
-        e:cat(re)
-    end
-    if not info.project.chroot_arch then
-        e2lib.warnf("WDEFAULT", "in project configuration:")
-        e2lib.warnf("WDEFAULT", " chroot_arch defaults to x86_32")
-        info.project.chroot_arch = "x86_32"
-    end
-    if not info.chroot_call_prefix[info.project.chroot_arch] then
-        e:append("chroot_arch is set to an invalid value")
-    end
-    local host_system_arch, re = e2lib.get_sys_arch()
-    if not host_system_arch then
-        e:cat(re)
-    elseif info.project.chroot_arch == "x86_64" and
-        host_system_arch ~= "x86_64" then
-        e:append("running on x86_32: switching to x86_64 mode is impossible.")
-    end
-    if e:getcount() > 1 then
-        return false, e
-    end
-
-    return true
-end
-
 --- check source.
 local function check_source(info, sourcename)
     local src = info.sources[sourcename]
@@ -1054,12 +985,12 @@ local function check_project_info(info)
     if not rc then
         return false, e:cat(re)
     end
-    for _, r in ipairs(info.project.default_results) do
+    for r in project.default_results_iter() do
         if not info.results[r] then
             e:append("default_results: No such result: %s", r)
         end
     end
-    for _, r in ipairs(info.project.deploy_results) do
+    for r in project.deploy_results_iter() do
         if not info.results[r] then
             e:append("deploy_results: No such result: %s", r)
         end
@@ -1192,7 +1123,7 @@ function e2tool.collect_project_info(info, skip_load_config)
     end
 
     -- read project configuration
-    rc, re = read_project_config(info)
+    rc, re = project.load_project_config(info)
     if not rc then
         return false, e:cat(re)
     end
@@ -1303,7 +1234,7 @@ function e2tool.collect_project_info(info, skip_load_config)
         local dirty, mismatch
 
         rc, re, mismatch = generic_git.verify_head_match_tag(info.root,
-            info.project.release_id)
+            project.release_id())
         if not rc then
             if mismatch then
                 e:append("project repository tag does not match " ..
@@ -1326,7 +1257,7 @@ function e2tool.collect_project_info(info, skip_load_config)
 
     if e2option.opts["check-remote"] then
         rc, re = generic_git.verify_remote_tag(
-            e2lib.join(info.root, ".git"), info.project.release_id)
+            e2lib.join(info.root, ".git"), project.release_id())
         if not rc then
             e:append("verifying remote tag failed")
             return false, e:cat(re)
@@ -1435,7 +1366,11 @@ end
 -- @return Error object on failure.
 -- @see e2tool.dlist_recursive
 function e2tool.dsort(info)
-    return e2tool.dlist_recursive(info, info.project.default_results)
+    local dr = {}
+    for r in project.default_results_iter() do
+        table.insert(dr, r)
+    end
+    return e2tool.dlist_recursive(info, dr)
 end
 
 --- verify that a file addressed by server name and location matches the
@@ -1505,11 +1440,11 @@ local function projid(info)
             if not rc then return false, re end
         end
     end
-    rc, re = hash.hash_line(hc, info.project.release_id)
+    rc, re = hash.hash_line(hc, project.release_id())
     if not rc then return false, re end
-    rc, re = hash.hash_line(hc, info.project.name)
+    rc, re = hash.hash_line(hc, project.name())
     if not rc then return false, re end
-    rc, re = hash.hash_line(hc, info.project.chroot_arch)
+    rc, re = hash.hash_line(hc, project.chroot_arch())
     if not rc then return false, re end
     rc, re = hash.hash_line(hc, buildconfig.VERSION)
     if not rc then return false, re end
diff --git a/local/project.lua b/local/project.lua
new file mode 100644 (file)
index 0000000..79f58c7
--- /dev/null
@@ -0,0 +1,204 @@
+--- Project module. Handle e2project configuration.
+-- @module local.project
+
+-- Copyright (C) 2007-2014 emlix GmbH, see file AUTHORS
+--
+-- This file is part of e2factory, the emlix embedded build system.
+-- For more information see http://www.e2factory.org
+--
+-- e2factory is a registered trademark of emlix GmbH.
+--
+-- e2factory is free software: you can redistribute it and/or modify it under
+-- the terms of the GNU General Public License as published by the
+-- Free Software Foundation, either version 3 of the License, or (at your
+-- option) any later version.
+--
+-- This program is distributed in the hope that it will be useful, but WITHOUT
+-- ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+-- FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+-- more details.
+
+local project = {}
+local e2lib = require("e2lib")
+local e2tool = require("e2tool")
+local err = require("err")
+local strict = require("strict")
+
+local _prj = {}
+local _config_loaders = {}
+
+--- Check and load e2project callback function signature.
+-- @function load_project_config_cb
+-- @param prj Unchecked e2project table. Remove all keys that are private
+--            to your use.
+-- @return True on success, false on error
+-- @return Error object on failure.
+
+--- Register a function that gets called when the project config is
+-- loaded. Functions get called in order of registration.
+-- @param func load_project_config_cb function.
+-- @return True on success, false on error.
+-- @return Error object on failure.
+-- @see load_project_config_cb
+function project.register_load_project_config(func)
+    assert(type(func) == "function")
+    table.insert(_config_loaders, func)
+
+    return true
+end
+
+--- Main e2project config check and init callback.
+-- @param prj e2project table.
+-- @return True on success, false on error.
+-- @return Error object on failure.
+local function load_prj_cfg(prj)
+    local rc, re, e, info
+
+    info = e2tool.info()
+    assert(info)
+
+    rc, re = e2lib.vrfy_dict_exp_keys(prj, "e2project",
+        { "name", "release_id", "deploy_results",
+        "default_results", "chroot_arch" })
+    if not rc then
+        return false, re
+    end
+
+    if not prj.release_id then
+        return false, err.new("key is not set: release_id")
+    end
+    if not prj.name then
+        return false, err.new("key is not set: name")
+    end
+    if not prj.default_results then
+        e2lib.warnf("WDEFAULT", "in project configuration:")
+        e2lib.warnf("WDEFAULT",
+            "default_results is not set. Defaulting to empty list.")
+        prj.default_results = {}
+    end
+    rc, re = e2lib.vrfy_listofstrings(prj.deploy_results,
+        "deploy_results", true, true)
+    if not rc then
+        e = err.new("deploy_results is not a valid list of strings")
+        e:cat(re)
+        return false, e
+    end
+
+    rc, re = e2lib.vrfy_listofstrings(prj.default_results,
+        "default_results",  true, false)
+    if not rc then
+        e = err.new("default_results is not a valid list of strings")
+        e:cat(re)
+        return false, e
+    end
+
+    if not prj.chroot_arch then
+        e2lib.warnf("WDEFAULT", "in project configuration:")
+        e2lib.warnf("WDEFAULT", " chroot_arch defaults to x86_32")
+        prj.chroot_arch = "x86_32"
+    end
+    if not info.chroot_call_prefix[prj.chroot_arch] then
+        return false, err.new("chroot_arch is set to an invalid value")
+    end
+    if prj.chroot_arch == "x86_64" and e2lib.host_system_arch ~= "x86_64" then
+        return false,
+            err.new("running on x86_32: switching to x86_64 mode is impossible.")
+    end
+
+    _prj = prj
+    return true
+end
+
+--- Initialise the project module, load and check proj/config. Needs to be
+-- called before using name() etc.
+-- @param info Info table.
+-- @return True on success, false on error.
+-- @return Error object on failure.
+function project.load_project_config(info)
+    local rc, re, e
+    local path, prj
+
+    -- register the main e2project load_project_config function last
+    rc, re = project.register_load_project_config(load_prj_cfg)
+    if not rc then
+        return false, re
+    end
+
+    path = e2lib.join(info.root, "proj/config")
+
+    prj = nil
+    local g = {
+        e2project = function(data) prj = data end,
+        env = info.env,
+        string = e2lib.safe_string_table(),
+    }
+
+    rc, re = e2lib.dofile2(path, g)
+    if not rc then
+        return false, re
+    end
+
+    e = err.new("in project configuration:")
+
+    if type(prj) ~= "table" then
+        return false, e:append("Invalid or empty e2project configuration")
+    end
+
+    for _,load_project_config_cb in ipairs(_config_loaders) do
+        rc, re = load_project_config_cb(prj)
+        if not rc then
+            return false, e:cat(re)
+        end
+    end
+
+    return true
+end
+
+--- Get project name.
+-- @return Name.
+function project.name()
+    assert(type(_prj.name) == "string")
+    return _prj.name
+end
+
+--- Get project ReleaseID.
+-- @return ReleaseID as a string.
+function project.release_id()
+    assert(type(_prj.release_id) == "string")
+    return _prj.release_id
+end
+
+--- Get chroot architecture. For multi-arch systems.
+-- @return Chroot architecture as a string.
+function project.chroot_arch()
+    assert(type(_prj.chroot_arch) == "string")
+    return _prj.chroot_arch
+end
+
+--- Iterator that returns the deploy results as string.
+-- @return Iterator function.
+function project.deploy_results_iter()
+    assert(type(_prj.deploy_results) == "table")
+    local i = 0
+
+    return function ()
+        i = i + 1
+        return _prj.deploy_results[i]
+    end
+end
+
+--- Iterator that returns the default results as string.
+-- @return Iterator function.
+function project.default_results_iter()
+    assert(type(_prj.default_results) == "table")
+    local i = 0
+
+    return function ()
+        i = i + 1
+        return _prj.default_results[i]
+    end
+end
+
+return strict.lock(project)
+
+-- vim:sw=4:sts=4:et:
index fdc8053daa34d2a4533d783082babff98eafdb1d..2f99200c44cadd01d8c0ae44e6335d6df34b0c4c 100644 (file)
@@ -31,6 +31,7 @@ local scm = require("scm")
 local strict = require("strict")
 local licence = require("licence")
 local chroot = require("chroot")
+local project = require("project")
 
 --- Collect_project result config. This result config table lives in
 -- info.results[resultname]. The fields are merged with e2tool.result
@@ -257,11 +258,11 @@ local function build_collect_project(info, resultname, return_flags)
 
     -- write project configuration
     out = {
-        string.format("name='%s'\n", info.project.name),
-        string.format("release_id='%s'\n", info.project.release_id),
+        string.format("name='%s'\n", project.name()),
+        string.format("release_id='%s'\n", project.release_id()),
         string.format("default_results='%s'\n",
             res.collect_project_default_result),
-        string.format("chroot_arch='%s'\n", info.project.chroot_arch)
+        string.format("chroot_arch='%s'\n", project.chroot_arch())
     }
 
     local file, destdir