git.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] Remove empty directories when checking out a commit with fewer submodules
@ 2010-01-11  2:59 Peter Collingbourne
  2010-01-11  8:57 ` Johannes Schindelin
  0 siblings, 1 reply; 5+ messages in thread
From: Peter Collingbourne @ 2010-01-11  2:59 UTC (permalink / raw)
  To: git; +Cc: Peter Collingbourne

Change the unlink_entry function to use rmdir to remove submodule
directories.  Currently we try to use unlink, which will never succeed.

Of course rmdir will only succeed for empty (i.e. not checked out)
submodule directories.  Behaviour if a submodule is checked out stays
essentially the same: print a warning message and keep the submodule
directory.

Signed-off-by: Peter Collingbourne <peter@pcc.me.uk>
---
 t/t7400-submodule-basic.sh |    9 +++++++++
 unpack-trees.c             |   12 ++++++++++--
 2 files changed, 19 insertions(+), 2 deletions(-)

diff --git a/t/t7400-submodule-basic.sh b/t/t7400-submodule-basic.sh
index a0cc99a..1a4dc5f 100755
--- a/t/t7400-submodule-basic.sh
+++ b/t/t7400-submodule-basic.sh
@@ -299,6 +299,15 @@ test_expect_success 'ls-files gracefully handles trailing slash' '
 
 '
 
+test_expect_success 'moving to a commit without submodule does not leave empty dir' '
+	rm -rf init &&
+	mkdir init &&
+	git reset --hard &&
+	git checkout initial &&
+	test ! -d init &&
+	git checkout second
+'
+
 test_expect_success 'submodule <invalid-path> warns' '
 
 	git submodule no-such-submodule 2> output.err &&
diff --git a/unpack-trees.c b/unpack-trees.c
index dd5999c..b69847d 100644
--- a/unpack-trees.c
+++ b/unpack-trees.c
@@ -61,8 +61,16 @@ static void unlink_entry(struct cache_entry *ce)
 {
 	if (has_symlink_or_noent_leading_path(ce->name, ce_namelen(ce)))
 		return;
-	if (unlink_or_warn(ce->name))
-		return;
+	if (S_ISGITLINK(ce->ce_mode)) {
+		if (rmdir(ce->name)) {
+			warning("unable to rmdir %s: %s",
+				ce->name, strerror(errno));
+			return;
+		}
+	}
+	else
+		if (unlink_or_warn(ce->name))
+			return;
 	schedule_dir_for_removal(ce->name, ce_namelen(ce));
 }
 
-- 
1.6.5

^ permalink raw reply related	[flat|nested] 5+ messages in thread

* Re: [PATCH] Remove empty directories when checking out a commit with fewer submodules
  2010-01-11  2:59 [PATCH] Remove empty directories when checking out a commit with fewer submodules Peter Collingbourne
@ 2010-01-11  8:57 ` Johannes Schindelin
  2010-01-11  9:32   ` Johan Herland
  2010-01-11  9:53   ` Junio C Hamano
  0 siblings, 2 replies; 5+ messages in thread
From: Johannes Schindelin @ 2010-01-11  8:57 UTC (permalink / raw)
  To: Peter Collingbourne; +Cc: git

Hi,

On Mon, 11 Jan 2010, Peter Collingbourne wrote:

> Change the unlink_entry function to use rmdir to remove submodule
> directories.

NAK.  We should not even try to _unlink_ submodule subdirectories; it 
would be _way_ too easy to lose data that way.  Remember, submodules are a 
totally different beast from regular files.  They can contain valuable, 
yet uncommitted data, that is not even meant to be committed.

So you say if the submodule directories are empty, it is safe?  Not so.  
They will never be empty: there is always .git/, and _that_ can contain 
valuable information that you do not want to throw away, too.  Think of 
unpushed branches, for example.  That would be _fatal_ if you rmdir() that 
for me.

So please, no,
Dscho

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH] Remove empty directories when checking out a commit with fewer submodules
  2010-01-11  8:57 ` Johannes Schindelin
@ 2010-01-11  9:32   ` Johan Herland
  2010-01-11  9:45     ` Johannes Schindelin
  2010-01-11  9:53   ` Junio C Hamano
  1 sibling, 1 reply; 5+ messages in thread
From: Johan Herland @ 2010-01-11  9:32 UTC (permalink / raw)
  To: Johannes Schindelin; +Cc: git, Peter Collingbourne

On Monday 11 January 2010, Johannes Schindelin wrote:
> Hi,
>
> On Mon, 11 Jan 2010, Peter Collingbourne wrote:
> > Change the unlink_entry function to use rmdir to remove submodule
> > directories.
>
> NAK.  We should not even try to _unlink_ submodule subdirectories; it
> would be _way_ too easy to lose data that way.  Remember, submodules
> are a totally different beast from regular files.  They can contain
> valuable, yet uncommitted data, that is not even meant to be
> committed.
>
> So you say if the submodule directories are empty, it is safe?  Not
> so. They will never be empty: there is always .git/, and _that_ can
> contain valuable information that you do not want to throw away, too.
>  Think of unpushed branches, for example.  That would be _fatal_ if
> you rmdir() that for me.
>
> So please, no,

I believe what Peter is referring to is the _empty_ directories (and 
that includes no .git/) that are placeholders for submodules that are 
deliberately not cloned/checked out. This lets you do things like:

	git clone url:to/some/project
	cd project
	git checkout some-other-branch-with-different-submodules
	git submodule update --init

Of course, once you clone/checkout a submodule, there will be contents 
in that directory (including the .git/), and Git should not try to 
remove it.


Have fun! :)

...Johan



-- 
Johan Herland, <johan@herland.net>
www.herland.net

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH] Remove empty directories when checking out a commit with fewer submodules
  2010-01-11  9:32   ` Johan Herland
@ 2010-01-11  9:45     ` Johannes Schindelin
  0 siblings, 0 replies; 5+ messages in thread
From: Johannes Schindelin @ 2010-01-11  9:45 UTC (permalink / raw)
  To: Johan Herland; +Cc: git, Peter Collingbourne

Hi,

On Mon, 11 Jan 2010, Johan Herland wrote:

> On Monday 11 January 2010, Johannes Schindelin wrote:
> > Hi,
> >
> > On Mon, 11 Jan 2010, Peter Collingbourne wrote:
> > > Change the unlink_entry function to use rmdir to remove submodule
> > > directories.
> >
> > NAK.  We should not even try to _unlink_ submodule subdirectories; it
> > would be _way_ too easy to lose data that way.  Remember, submodules
> > are a totally different beast from regular files.  They can contain
> > valuable, yet uncommitted data, that is not even meant to be
> > committed.
> >
> > So you say if the submodule directories are empty, it is safe?  Not
> > so. They will never be empty: there is always .git/, and _that_ can
> > contain valuable information that you do not want to throw away, too.
> >  Think of unpushed branches, for example.  That would be _fatal_ if
> > you rmdir() that for me.
> >
> > So please, no,
> 
> I believe what Peter is referring to is the _empty_ directories (and 
> that includes no .git/) that are placeholders for submodules that are 
> deliberately not cloned/checked out. This lets you do things like:
> 
> 	git clone url:to/some/project
> 	cd project
> 	git checkout some-other-branch-with-different-submodules
> 	git submodule update --init
> 
> Of course, once you clone/checkout a submodule, there will be contents 
> in that directory (including the .git/), and Git should not try to 
> remove it.

Yes, this might very well have been my confusion.  Peter, could you please 
refer to such submodules as "uninitialized" rather than "empty" in the 
future?  This would help simple minds like mine to understand you better.

Ciao,
Dscho

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH] Remove empty directories when checking out a commit with fewer submodules
  2010-01-11  8:57 ` Johannes Schindelin
  2010-01-11  9:32   ` Johan Herland
@ 2010-01-11  9:53   ` Junio C Hamano
  1 sibling, 0 replies; 5+ messages in thread
From: Junio C Hamano @ 2010-01-11  9:53 UTC (permalink / raw)
  To: Johannes Schindelin; +Cc: Peter Collingbourne, git

Johannes Schindelin <Johannes.Schindelin@gmx.de> writes:

> NAK.  We should not even try to _unlink_ submodule subdirectories; it 
> would be _way_ too easy to lose data that way.  Remember, submodules are a 
> totally different beast from regular files.  They can contain valuable, 
> yet uncommitted data, that is not even meant to be committed.
>
> So you say if the submodule directories are empty, it is safe?  Not so.  
> They will never be empty: there is always .git/...

NACK on NAK.

Don't worry, your data will be safe.  The only case rmdir would actually
remove it is (1) you check out superproject that has submodule A, but you
choose not to "submodule init/update" it, because you don't need a
checkout of that part of the tree for your job, and then (2) you switch to
a different version of the superproject that doesn't anymore (or didn't
back then) have that submodule.  In such a use case, you will have only an
empty directory for A in step (1).  The unnecessary empty directory A will
be left behind, even after switching to a version that shouldn't have the
directory there in step (2), if you do not rmdir it.  So the patch is a
strict bugfix (it attempted to unlink, which is a bug; it really meant
"rmdir" and not "rm -rf" which you seem to be worried about).

It is a separate matter to _enhance_ the codepath to actually either (A)
refuse to overwrite (if the version of the superproject you are switching
to in step (2) had a regular file or a directory that is part of the
superproject there, and/or (B) move it away to somewhere safe (recall the
discussion of ".git/modules/$submodule" hierarchy of the superproject?)
automatically when it will disappear.  Such enhancements will help people
who _do_ "submodule init/update" the submodule in step (1) and switch to a
version of the superproject that lacks it in step (2).

^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2010-01-11  9:53 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2010-01-11  2:59 [PATCH] Remove empty directories when checking out a commit with fewer submodules Peter Collingbourne
2010-01-11  8:57 ` Johannes Schindelin
2010-01-11  9:32   ` Johan Herland
2010-01-11  9:45     ` Johannes Schindelin
2010-01-11  9:53   ` Junio C Hamano

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).