-- gitano.copycommand -- -- Gitano repository copy commands -- -- Copyright 2013-2017 Richard Maw -- All rights reserved. -- -- Redistribution and use in source and binary forms, with or without -- modification, are permitted provided that the following conditions -- are met: -- 1. Redistributions of source code must retain the above copyright -- notice, this list of conditions and the following disclaimer. -- 2. Redistributions in binary form must reproduce the above copyright -- notice, this list of conditions and the following disclaimer in the -- documentation and/or other materials provided with the distribution. -- 3. Neither the name of the author nor the names of their contributors -- may be used to endorse or promote products derived from this software -- without specific prior written permission. -- -- THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND -- ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -- IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -- ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE -- FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -- DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -- OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -- HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -- LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -- OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -- SUCH DAMAGE. -- local repository = require "gitano.repository" local log = require "gitano.log" local util = require "gitano.util" local builtin_copy_short = "Copy a repository to a new path" local builtin_copy_helptext = [[ usage: copy Copy a git repository locally. This is quicker than fetching the old repository, creating the new one, then pushing to the new one. ]] local function builtin_copy_validate(config, srcrepo, cmdline) if #cmdline ~= 3 then log.error("usage: copy ") return false end -- Check if source repository is nascent if srcrepo.is_nascent then log.error("Cannot copy a repository which does not exist") return false end -- Create the target repository object local tgtrepo, msg = repository.find(config, cmdline[3]) if not tgtrepo then log.critical("Unable to locate repository.") log.critical(" * " .. (tostring(msg))) log.fatal("Cannot continue") return false end cmdline.tgtrepo = tgtrepo return true end local function builtin_copy_prep(config, srcrepo, cmdline, context) local ctx, action, reason -- Check 1, source repository can be read ctx = util.deep_copy(context) ctx.operation = "read" action, reason = srcrepo:run_lace(ctx) if action ~= "allow" then return action, reason end -- Check 2, target repository can be written to ctx = util.deep_copy(context) ctx.operation = "write" action, reason = cmdline.tgtrepo:run_lace(ctx) if action ~= "allow" then return action, reason end -- Check 3, target repository does not already exist -- We knew this for a while but failing earlier would leak its existence. if not cmdline.tgtrepo.is_nascent then log.error("Repository", cmdline.tgtrepo.name, "already exists") return "deny", "Repository already exists" end -- Check 4, target repository can be created ctx = util.deep_copy(context) ctx.operation = "createrepo" action, reason = cmdline.tgtrepo:run_lace(ctx) if action ~= "allow" then return action, reason end -- Able to read, create, and write; thus can copy return "allow", "Passed all checks, can copy" end local function builtin_copy_run(config, repo, cmdline, env) local ok, msg = repo:copy_to(cmdline.tgtrepo) if not ok then log.error(msg) return "exit", 1 end log.state("Copied", cmdline[2], "to", cmdline[3]) local tgtrepo, msg = repository.find(config, cmdline[3]) if not tgtrepo then log.critical("Unable to locate repository.") log.critical(" * " .. (tostring(msg))) log.fatal("Cannot continue") return false end local owner = env["GITANO_USER"] log.chat("Setting repository owner to", owner) ok, msg = tgtrepo:conf_set_and_save("project.owner", owner, env.GITANO_USER, env.GITANO_ORIG_USER) if not ok then log.error(msg) return "exit", 1 end log.chat("Running checks to ensure hooks etc are configured") ok, msg = tgtrepo:run_checks() if not ok then log.error(msg) return "exit", 1 end log.state("Repository", tgtrepo.name, "copied ok. Remember to configure rules etc.") return "exit", 0 end local function register_commands(reg) assert(reg("copy", builtin_copy_short, builtin_copy_helptext, builtin_copy_validate, builtin_copy_prep, builtin_copy_run, true, false, false)) end return { register = register_commands }