From 48e9a010ae9cfee5cc2daae2bf20d510ab9c108f Mon Sep 17 00:00:00 2001 From: "Shawn O. Pearce" Date: Thu, 28 Jan 2010 11:10:52 -0800 Subject: [PATCH] Add unsetSection to Config to remove an entire block The unsetSection method can be used to delete an entire configuration block, such as a [branch ""] or [remote ""] section in a file. Change-Id: I93390c9b2187eb1b0d51353518feaed83bed2aad Signed-off-by: Shawn O. Pearce Signed-off-by: Robin Rosenberg --- .../jgit/lib/RepositoryConfigTest.java | 41 ++++++++++++++++++ .../src/org/eclipse/jgit/lib/Config.java | 42 +++++++++++++++++++ 2 files changed, 83 insertions(+) diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/RepositoryConfigTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/RepositoryConfigTest.java index 203b7c825..41c4971a0 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/RepositoryConfigTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/lib/RepositoryConfigTest.java @@ -271,6 +271,47 @@ public void testEmptyString() throws ConfigInvalidException { assertEquals("[my]\n\tempty =\n", c.toText()); } + public void testUnsetBranchSection() throws ConfigInvalidException { + Config c = parse("" // + + "[branch \"keep\"]\n" + + " merge = master.branch.to.keep.in.the.file\n" + + "\n" + + "[branch \"remove\"]\n" + + " merge = this.will.get.deleted\n" + + " remote = origin-for-some-long-gone-place\n" + + "\n" + + "[core-section-not-to-remove-in-test]\n" + + " packedGitLimit = 14\n"); + c.unsetSection("branch", "does.not.exist"); + c.unsetSection("branch", "remove"); + assertEquals("" // + + "[branch \"keep\"]\n" + + " merge = master.branch.to.keep.in.the.file\n" + + "\n" + + "[core-section-not-to-remove-in-test]\n" + + " packedGitLimit = 14\n", c.toText()); + } + + public void testUnsetSingleSection() throws ConfigInvalidException { + Config c = parse("" // + + "[branch \"keep\"]\n" + + " merge = master.branch.to.keep.in.the.file\n" + + "\n" + + "[single]\n" + + " merge = this.will.get.deleted\n" + + " remote = origin-for-some-long-gone-place\n" + + "\n" + + "[core-section-not-to-remove-in-test]\n" + + " packedGitLimit = 14\n"); + c.unsetSection("single", null); + assertEquals("" // + + "[branch \"keep\"]\n" + + " merge = master.branch.to.keep.in.the.file\n" + + "\n" + + "[core-section-not-to-remove-in-test]\n" + + " packedGitLimit = 14\n", c.toText()); + } + private void assertReadLong(long exp) throws ConfigInvalidException { assertReadLong(exp, String.valueOf(exp)); } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/lib/Config.java b/org.eclipse.jgit/src/org/eclipse/jgit/lib/Config.java index d66aa74c8..0d0c377f8 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/lib/Config.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/lib/Config.java @@ -576,6 +576,43 @@ public void unset(final String section, final String subsection, . emptyList()); } + /** + * Remove all configuration values under a single section. + * + * @param section + * section name, e.g "branch" + * @param subsection + * optional subsection value, e.g. a branch name + */ + public void unsetSection(String section, String subsection) { + State src, res; + do { + src = state.get(); + res = unsetSection(src, section, subsection); + } while (!state.compareAndSet(src, res)); + } + + private State unsetSection(final State srcState, final String section, + final String subsection) { + final int max = srcState.entryList.size(); + final ArrayList r = new ArrayList(max); + + boolean lastWasMatch = false; + for (Entry e : srcState.entryList) { + if (e.match(section, subsection)) { + // Skip this record, it's for the section we are removing. + lastWasMatch = true; + continue; + } + + if (lastWasMatch && e.section == null && e.subsection == null) + continue; // skip this padding line in the section. + r.add(e); + } + + return newState(r); + } + /** * Set a configuration value. * @@ -1104,6 +1141,11 @@ && eqSameCase(subsection, aSubsection) && eqIgnoreCase(name, aKey); } + boolean match(final String aSection, final String aSubsection) { + return eqIgnoreCase(section, aSection) + && eqSameCase(subsection, aSubsection); + } + private static boolean eqIgnoreCase(final String a, final String b) { if (a == null && b == null) return true;