# # patch "git.cc" # from [50c5d10e1b35b85ed19c15bd5f2e3bc3a733d116] # to [9733a6e845cdc90bee06202e756516d524e7c7de] # # patch "tests/t_gitimport2.at" # from [5351d6293994c30ffed4a20f275017abc598db59] # to [5e6468769849148102d613b0827581d2ce35569f] # ======================================================================== --- git.cc 50c5d10e1b35b85ed19c15bd5f2e3bc3a733d116 +++ git.cc 9733a6e845cdc90bee06202e756516d524e7c7de @@ -118,7 +118,7 @@ ticker n_revs; ticker n_objs; - string base_branch; + string branch; git_history(const system_path & path); }; @@ -320,7 +320,7 @@ // we want to import them again, just to add our branch membership to them. // (TODO) set heads; - get_branch_heads(git.base_branch, app, heads); + get_branch_heads(git.branch, app, heads); for (set::const_iterator i = heads.begin(); i != heads.end(); ++i) frontier.push(*i); @@ -373,7 +373,7 @@ // All the ancestry should be at least already in our branch, so there is // no need to work over the whole database. set heads; - get_branch_heads(git.base_branch, app, heads); + get_branch_heads(git.branch, app, heads); for (set::const_iterator i = heads.begin(); i != heads.end(); ++i) frontier.push(*i); @@ -614,7 +614,7 @@ ++git.n_objs; packet_db_writer dbw(app); - cert_revision_in_branch(rid, cert_value(git.base_branch), app, dbw); + cert_revision_in_branch(rid, cert_value(git.branch), app, dbw); cert_revision_author(rid, author.name, app, dbw); cert_revision_changelog(rid, logmsg, app, dbw); cert_revision_date_time(rid, commit_time, app, dbw); @@ -629,7 +629,56 @@ return rid; } +class +heads_tree_walker + : public absolute_tree_walker +{ + git_history & git; + app_state & app; +public: + heads_tree_walker(git_history & g, app_state & a) + : git(g), app(a) + { + } + virtual void visit_file(system_path const & path) + { + L(F("Processing head file '%s'") % path); + data refdata; + read_data(path, refdata); + + // We can't just .leaf() - there can be heads like "net/ipv4" and such. + // XXX: My head hurts from all those temporary variables. + system_path spheadsdir = git.db.path / "refs/heads"; + fs::path headsdir(spheadsdir.as_external(), fs::native); + fs::path headpath(path.as_external(), fs::native); + std::string strheadpath = headpath.string(), strheadsdir = headsdir.string(); + + N(strheadpath.substr(0, strheadsdir.length()) == strheadsdir, + F("heads directory name screwed up - %s does not being with %s") + % strheadpath % strheadsdir); + std::string headname(strheadpath.substr(strheadsdir.length() + 1)); // + '/' + + git.branch = app.branch_name(); + if (headname != "master") + git.branch += "." + headname; + + set revs_exclude; + git_heads_on_branch(git, app, revs_exclude); + stack revs = git.db.load_revs(headname, revs_exclude); + + while (!revs.empty()) + { + ui.set_tick_trailer(revs.top()()); + import_git_commit(git, app, revs.top()); + revs.pop(); + } + ui.set_tick_trailer(""); + } + virtual ~heads_tree_walker() {} +}; + + static void import_git_tag(git_history &git, app_state &app, git_object_id gittid, git_object_id &targetobj) @@ -784,23 +833,17 @@ N(app.branch_name() != "", F("need base --branch argument for importing")); git_history git(gitrepo); - git.base_branch = app.branch_name(); { + system_path heads_tree = gitrepo / "refs/heads"; + N(directory_exists(heads_tree), + F("path %s is not a directory") % heads_tree); + transaction_guard guard(app.db); app.db.ensure_open(); - set revs_exclude; - git_heads_on_branch(git, app, revs_exclude); - stack revs = git.db.load_revs("master", revs_exclude); - - while (!revs.empty()) - { - ui.set_tick_trailer(revs.top()()); - import_git_commit(git, app, revs.top()); - revs.pop(); - } - ui.set_tick_trailer(""); + heads_tree_walker walker(git, app); + walk_tree_absolute(heads_tree, walker); guard.commit(); } ======================================================================== --- tests/t_gitimport2.at 5351d6293994c30ffed4a20f275017abc598db59 +++ tests/t_gitimport2.at 5e6468769849148102d613b0827581d2ce35569f @@ -49,7 +49,7 @@ AT_CHECK(cat .git/HEAD >.git/refs/tags/commit/c2) AT_CHECK(cp importme.3 importme) AT_CHECK(git-update-cache importme, [], [ignore], [ignore]) -AT_CHECK(echo 'commit 3' | git-commit-tree $(git-write-tree) -p $(cat .git/HEAD) >.git/HEAD, [], [ignore], [ignore]) +AT_CHECK(echo 'commit 3' | git-commit-tree $(git-write-tree) -p $(cat .git/HEAD) >.git/refs/heads/alt, [], [ignore], [ignore]) # import into monotone and check presence of files @@ -66,6 +66,9 @@ AT_CHECK(cmp taglist taglist.t) AT_CHECK(MONOTONE checkout --branch=testbranch mtcodir, [], [ignore], [ignore]) +AT_CHECK(cmp importme.2 mtcodir/importme) +AT_CHECK(rm -rf mtcodir) +AT_CHECK(MONOTONE checkout --branch=testbranch.alt mtcodir, [], [ignore], [ignore]) AT_CHECK(cmp importme.3 mtcodir/importme) AT_CLEANUP