* [PATCH] t4030: Don't use echo -n
From: Brian Gernhardt @ 2008-10-30 22:12 UTC (permalink / raw)
To: Git List; +Cc: Shawn O Pearce
Signed-off-by: Brian Gernhardt <benji@silverinsanity.com>
---
t/t4030-diff-textconv.sh | 5 ++---
1 files changed, 2 insertions(+), 3 deletions(-)
diff --git a/t/t4030-diff-textconv.sh b/t/t4030-diff-textconv.sh
index 3945731..7ec244f 100755
--- a/t/t4030-diff-textconv.sh
+++ b/t/t4030-diff-textconv.sh
@@ -96,16 +96,15 @@ cat >expect.typechange <<'EOF'
-1
diff --git a/file b/file
new file mode 120000
-index ad8b3d2..67be421
+index ad8b3d2..8e4020b
--- /dev/null
+++ b/file
@@ -0,0 +1 @@
+frotz
-\ No newline at end of file
EOF
# make a symlink the hard way that works on symlink-challenged file systems
test_expect_success 'textconv does not act on symlinks' '
- echo -n frotz > file &&
+ echo frotz > file &&
git add file &&
git ls-files -s | sed -e s/100644/120000/ |
git update-index --index-info &&
--
1.6.0.3.523.g304d0
^ permalink raw reply related
* [RFC PATCH v2 0/2] Detection of directory renames
From: Yann Dirson @ 2008-10-30 22:16 UTC (permalink / raw)
To: git
This is an update of my previous patch. It brings:
* a couple of fixes to annoying segfaults
* a testsuite showing where we're standing.
* getting rid of POSIX dirname
* improvement of debug messages
The code is still full of FIXME's, not ready for inclusin into any
branch whatsoever, and I'd be happy to hear about it if you can make
it break in a way or another - at least in a way not yet shown by the
testsuite :)
--
Yann Dirson <ydirson@altern.org> |
Debian-related: <dirson@debian.org> | Support Debian GNU/Linux:
| Freedom, Power, Stability, Gratis
http://ydirson.free.fr/ | Check <http://www.debian.org/>
^ permalink raw reply
* [PATCH 1/2] Introduce rename factorization in diffcore.
From: Yann Dirson @ 2008-10-30 22:16 UTC (permalink / raw)
To: git
In-Reply-To: <20081030220532.3325.54457.stgit@gandelf.nowhere.earth>
Rename factorization tries to group together files moving from and to
identical directories - the most common case being directory renames.
This feature is activated by the new --factorize-renames diffcore
flag.
This is only the first step, adding the basic functionnality and
adding support to raw diff output (and it breaks unified-diff output
which does not know how to handle that stuff yet).
Even the output format may not be kept as is. For now both the result
of "mv a b" and "mv a/* b/" are displayed as "Rnnn a/ b/", which is
probably not what we want. "Rnnn a/* b/" could be a good choice for
the latter if we want them to be distinguished, and even if we want
them to look the same.
Other future developements to be made on top of this include:
* extension of unified-diff format to express this
* application of such new diffs
* teach git-svn (and others ?) to make use of that flag
* merge correctly in case of addition into a moved dir
* detect "directory splits" so merge can flag a conflict on file adds
* use inexact dir renames to bump score of below-threshold renames
from/to same locations
* add yours here
---
diff-lib.c | 6 +
diff.c | 5 +
diff.h | 3 +
diffcore-rename.c | 227 +++++++++++++++++++++++++++++++++++++++++++++++++++--
diffcore.h | 1
tree-diff.c | 4 +
6 files changed, 235 insertions(+), 11 deletions(-)
diff --git a/diff-lib.c b/diff-lib.c
index ae96c64..dcc4c2c 100644
--- a/diff-lib.c
+++ b/diff-lib.c
@@ -179,7 +179,8 @@ int run_diff_files(struct rev_info *revs, unsigned int option)
changed = ce_match_stat(ce, &st, ce_option);
if (!changed) {
ce_mark_uptodate(ce);
- if (!DIFF_OPT_TST(&revs->diffopt, FIND_COPIES_HARDER))
+ if (!DIFF_OPT_TST(&revs->diffopt, FIND_COPIES_HARDER) &&
+ !DIFF_OPT_TST(&revs->diffopt, FACTORIZE_RENAMES))
continue;
}
oldmode = ce->ce_mode;
@@ -310,7 +311,8 @@ static int show_modified(struct oneway_unpack_data *cbdata,
oldmode = old->ce_mode;
if (mode == oldmode && !hashcmp(sha1, old->sha1) &&
- !DIFF_OPT_TST(&revs->diffopt, FIND_COPIES_HARDER))
+ !DIFF_OPT_TST(&revs->diffopt, FIND_COPIES_HARDER) &&
+ !DIFF_OPT_TST(&revs->diffopt, FACTORIZE_RENAMES))
return 0;
diff_change(&revs->diffopt, oldmode, mode,
diff --git a/diff.c b/diff.c
index e368fef..f91fcf6 100644
--- a/diff.c
+++ b/diff.c
@@ -2437,6 +2437,11 @@ int diff_opt_parse(struct diff_options *options, const char **av, int ac)
DIFF_OPT_SET(options, REVERSE_DIFF);
else if (!strcmp(arg, "--find-copies-harder"))
DIFF_OPT_SET(options, FIND_COPIES_HARDER);
+ else if (!strcmp(arg, "--factorize-renames")) {
+ DIFF_OPT_SET(options, FACTORIZE_RENAMES);
+ if (!options->detect_rename)
+ options->detect_rename = DIFF_DETECT_RENAME;
+ }
else if (!strcmp(arg, "--follow"))
DIFF_OPT_SET(options, FOLLOW_RENAMES);
else if (!strcmp(arg, "--color"))
diff --git a/diff.h b/diff.h
index a49d865..db1658b 100644
--- a/diff.h
+++ b/diff.h
@@ -65,6 +65,7 @@ typedef void (*diff_format_fn_t)(struct diff_queue_struct *q,
#define DIFF_OPT_IGNORE_SUBMODULES (1 << 18)
#define DIFF_OPT_DIRSTAT_CUMULATIVE (1 << 19)
#define DIFF_OPT_DIRSTAT_BY_FILE (1 << 20)
+#define DIFF_OPT_FACTORIZE_RENAMES (1 << 21)
#define DIFF_OPT_TST(opts, flag) ((opts)->flags & DIFF_OPT_##flag)
#define DIFF_OPT_SET(opts, flag) ((opts)->flags |= DIFF_OPT_##flag)
#define DIFF_OPT_CLR(opts, flag) ((opts)->flags &= ~DIFF_OPT_##flag)
@@ -220,6 +221,8 @@ extern void diffcore_std(struct diff_options *);
" -C detect copies.\n" \
" --find-copies-harder\n" \
" try unchanged files as candidate for copy detection.\n" \
+" --factorize-renames\n" \
+" factorize renames of all files of a directory.\n" \
" -l<n> limit rename attempts up to <n> paths.\n" \
" -O<file> reorder diffs according to the <file>.\n" \
" -S<string> find filepair whose only one side contains the string.\n" \
diff --git a/diffcore-rename.c b/diffcore-rename.c
index 1b2ebb4..fc789bc 100644
--- a/diffcore-rename.c
+++ b/diffcore-rename.c
@@ -52,6 +52,32 @@ static struct diff_rename_dst *locate_rename_dst(struct diff_filespec *two,
return &(rename_dst[first]);
}
+static struct diff_rename_dst *locate_rename_dst_dir(struct diff_filespec *dir)
+{
+ /* code mostly duplicated from locate_rename_dst - not sure we
+ * could merge them efficiently,though
+ */
+ int first, last;
+ int dirlength = strlen(dir->path);
+
+ first = 0;
+ last = rename_dst_nr;
+ while (last > first) {
+ int next = (last + first) >> 1;
+ struct diff_rename_dst *dst = &(rename_dst[next]);
+ int cmp = strncmp(dir->path, dst->two->path, dirlength);
+ if (!cmp)
+ return dst;
+ if (cmp < 0) {
+ last = next;
+ continue;
+ }
+ first = next+1;
+ }
+ /* not found */
+ return NULL;
+}
+
/* Table of rename/copy src files */
static struct diff_rename_src {
struct diff_filespec *one;
@@ -409,6 +435,165 @@ static void record_if_better(struct diff_score m[], struct diff_score *o)
m[worst] = *o;
}
+struct diff_dir_rename {
+ struct diff_filespec *one;
+ struct diff_filespec *two;
+ int discarded;
+ struct diff_dir_rename* next;
+};
+
+/*
+ * Marks as such file_rename if it is made uninteresting by dir_rename.
+ * Returns -1 if the file_rename is outside of the range in which given
+ * renames concerned by dir_rename are to be found (ie. end of loop),
+ * 0 otherwise.
+ */
+static int maybe_mark_uninteresting(struct diff_rename_dst* file_rename,
+ struct diff_dir_rename* dir_rename,
+ int one_len, int two_len)
+{
+ if (!file_rename->pair) /* file add */
+ return 0;
+ if (strncmp(file_rename->two->path,
+ dir_rename->two->path, two_len))
+ return -1;
+ if (strncmp(file_rename->pair->one->path,
+ dir_rename->one->path, one_len) ||
+ !basename_same(file_rename->pair->one, file_rename->two) ||
+ file_rename->pair->score != MAX_SCORE)
+ return 0;
+
+ file_rename->pair->uninteresting_rename = 1;
+ fprintf (stderr, "[DBG] %s* -> %s* makes %s -> %s uninteresting\n",
+ dir_rename->one->path, dir_rename->two->path,
+ file_rename->pair->one->path, file_rename->two->path);
+ return 0;
+}
+
+// FIXME: prevent possible overflow
+/*
+ * Copy dirname of src into dst, with final "/".
+ * Only handles relative paths since there is no relative path in a git repo.
+ * Writes "./" when there is no "/" in src.
+ * May overwrite more chars than really needed, if src ends with a "/".
+ */
+static const char* copy_dirname(char* dst, const char* src)
+{
+ char* lastslash = strrchr(src, '/');
+ if (!lastslash)
+ return strcpy(dst, "./");
+ strncpy(dst, src, lastslash - src + 1);
+ dst[lastslash - src + 1] = '\0';
+
+ // if src ends with a "/" strip the last component
+ if (lastslash[1] == '\0') {
+ lastslash = strrchr(dst, '/');
+ if (!lastslash)
+ return strcpy(dst, ".");
+ lastslash[1] = '\0';
+ }
+
+ return dst;
+}
+
+/*
+ * FIXME: we could optimize the 100%-rename case by preventing
+ * recursion to unfold what we know we would refold here.
+ * FIXME: do we want to replace linked list with sorted array ?
+ * FIXME: this prototype only handles renaming of dirs without
+ * a subdir.
+ * FIXME: leaks like hell.
+ * FIXME: ideas to evaluate a similarity score, anyone ?
+ * 10% * tree similarity + 90% * moved files similarity ?
+ */
+static struct diff_dir_rename* factorization_candidates = NULL;
+static void diffcore_factorize_renames(void)
+{
+ char one_parent_path[PATH_MAX], two_parent_path[PATH_MAX];
+ int i;
+
+ for (i = 0; i < rename_dst_nr; i++) {
+ // FIXME: what are those ?
+ if (!rename_dst[i].pair)
+ continue;
+ // dummy renames used by copy detection
+ if (!strcmp(rename_dst[i].pair->one->path, rename_dst[i].pair->two->path))
+ continue;
+
+ copy_dirname(one_parent_path, rename_dst[i].pair->one->path);
+
+ struct diff_filespec* one_parent = alloc_filespec(one_parent_path);
+ fill_filespec(one_parent, null_sha1 /*FIXME*/, S_IFDIR);
+
+ if (!locate_rename_dst_dir(one_parent)) {
+ // one_parent_path is empty in result tree
+
+ // already considered ?
+ struct diff_dir_rename* seen;
+ for (seen=factorization_candidates; seen; seen = seen->next)
+ if (!strcmp(seen->one->path, one_parent_path)) break;
+ if (!seen) {
+ // record potential dir rename
+ copy_dirname(two_parent_path, rename_dst[i].pair->two->path);
+
+ seen = xmalloc(sizeof(*seen));
+ seen->one = one_parent;
+ seen->two = alloc_filespec(two_parent_path);
+ fill_filespec(seen->two, null_sha1 /*FIXME*/, S_IFDIR);
+ seen->discarded = 0;
+ seen->next = factorization_candidates;
+ factorization_candidates = seen;
+ fprintf (stderr, "[DBG] %s -> %s suggests possible rename from %s to %s\n",
+ rename_dst[i].pair->one->path,
+ rename_dst[i].pair->two->path,
+ one_parent_path, two_parent_path);
+ fflush(stdout);
+ continue;
+ }
+ if (seen->discarded)
+ continue;
+ // check that seen entry matches this rename
+ copy_dirname(two_parent_path, rename_dst[i].pair->two->path);
+ if (strcmp(two_parent_path, seen->two->path)) {
+ fprintf (stderr, "[DBG] discarding dir split of %s from renames (into %s and %s)\n",
+ one_parent_path, two_parent_path, seen->two->path);
+ seen->discarded = 1;
+ }
+
+ /* all checks ok, we keep that entry */
+ }
+ }
+
+ // turn candidates into real renames
+ struct diff_dir_rename* candidate;
+ for (candidate=factorization_candidates; candidate; candidate = candidate->next) {
+ int two_idx, i, one_len, two_len;
+ if (candidate->discarded)
+ continue;
+
+ if (!locate_rename_dst_dir(candidate->two)) {
+ fprintf (stderr, "PANIC: %s candidate of rename not in target tree (from %s)\n",
+ candidate->two->path, candidate->one->path);
+ }
+ // bisect to an entry within candidate dst dir
+ two_idx = locate_rename_dst_dir(candidate->two) - rename_dst;
+
+ // now remove extraneous 100% files inside.
+ one_len = strlen(candidate->one->path);
+ two_len = strlen(candidate->two->path);
+ for (i = two_idx; i < rename_dst_nr; i++)
+ if (maybe_mark_uninteresting (rename_dst+i, candidate,
+ one_len, two_len) < 0)
+ break;
+ for (i = two_idx-1; i >= 0; i--)
+ if (maybe_mark_uninteresting (rename_dst+i, candidate,
+ one_len, two_len) < 0)
+ break;
+ }
+
+ return;
+}
+
void diffcore_rename(struct diff_options *options)
{
int detect_rename = options->detect_rename;
@@ -446,13 +631,22 @@ void diffcore_rename(struct diff_options *options)
p->one->rename_used++;
register_rename_src(p->one, p->score);
}
- else if (detect_rename == DIFF_DETECT_COPY) {
- /*
- * Increment the "rename_used" score by
- * one, to indicate ourselves as a user.
- */
- p->one->rename_used++;
- register_rename_src(p->one, p->score);
+ else {
+ if (detect_rename == DIFF_DETECT_COPY) {
+ /*
+ * Increment the "rename_used" score by
+ * one, to indicate ourselves as a user.
+ */
+ p->one->rename_used++;
+ register_rename_src(p->one, p->score);
+ }
+ if (DIFF_OPT_TST(options, FACTORIZE_RENAMES)) {
+ /* similarly, rename factorization needs to
+ * see all files from second tree
+ */
+ //p->two->rename_used++; // FIXME: would we need that ?
+ locate_rename_dst(p->two, 1);
+ }
}
}
if (rename_dst_nr == 0 || rename_src_nr == 0)
@@ -561,8 +755,24 @@ void diffcore_rename(struct diff_options *options)
/* At this point, we have found some renames and copies and they
* are recorded in rename_dst. The original list is still in *q.
*/
+
+ /* Now possibly factorize those renames and copies. */
+ if (DIFF_OPT_TST(options, FACTORIZE_RENAMES))
+ diffcore_factorize_renames();
+
outq.queue = NULL;
outq.nr = outq.alloc = 0;
+
+ // first, turn factorization_candidates into real renames
+ struct diff_dir_rename* candidate;
+ for (candidate=factorization_candidates; candidate; candidate = candidate->next) {
+ struct diff_filepair* pair;
+ if (candidate->discarded) continue;
+ pair = diff_queue(&outq, candidate->one, candidate->two);
+ pair->score = MAX_SCORE;
+ pair->renamed_pair = 1;
+ }
+
for (i = 0; i < q->nr; i++) {
struct diff_filepair *p = q->queue[i];
struct diff_filepair *pair_to_free = NULL;
@@ -577,7 +787,8 @@ void diffcore_rename(struct diff_options *options)
struct diff_rename_dst *dst =
locate_rename_dst(p->two, 0);
if (dst && dst->pair) {
- diff_q(&outq, dst->pair);
+ if (!dst->pair->uninteresting_rename)
+ diff_q(&outq, dst->pair);
pair_to_free = p;
}
else
diff --git a/diffcore.h b/diffcore.h
index 713cca7..6d2e65b 100644
--- a/diffcore.h
+++ b/diffcore.h
@@ -66,6 +66,7 @@ struct diff_filepair {
unsigned broken_pair : 1;
unsigned renamed_pair : 1;
unsigned is_unmerged : 1;
+ unsigned uninteresting_rename : 1;
};
#define DIFF_PAIR_UNMERGED(p) ((p)->is_unmerged)
diff --git a/tree-diff.c b/tree-diff.c
index 9f67af6..872f757 100644
--- a/tree-diff.c
+++ b/tree-diff.c
@@ -49,7 +49,9 @@ static int compare_tree_entry(struct tree_desc *t1, struct tree_desc *t2, const
show_entry(opt, "+", t2, base, baselen);
return 1;
}
- if (!DIFF_OPT_TST(opt, FIND_COPIES_HARDER) && !hashcmp(sha1, sha2) && mode1 == mode2)
+ if (!DIFF_OPT_TST(opt, FIND_COPIES_HARDER) &&
+ !DIFF_OPT_TST(opt, FACTORIZE_RENAMES) &&
+ !hashcmp(sha1, sha2) && mode1 == mode2)
return 0;
/*
^ permalink raw reply related
* [PATCH 2/2] Add testcases for the --factorize-renames diffcore flag.
From: Yann Dirson @ 2008-10-30 22:16 UTC (permalink / raw)
To: git
In-Reply-To: <20081030220532.3325.54457.stgit@gandelf.nowhere.earth>
This notably includes a couple of tests for cases known not to be
working correctly yet.
---
t/t4030-diff-rename-factorize.sh | 209 ++++++++++++++++++++++++++++++++++++++
1 files changed, 209 insertions(+), 0 deletions(-)
create mode 100755 t/t4030-diff-rename-factorize.sh
diff --git a/t/t4030-diff-rename-factorize.sh b/t/t4030-diff-rename-factorize.sh
new file mode 100755
index 0000000..fcf8fb6
--- /dev/null
+++ b/t/t4030-diff-rename-factorize.sh
@@ -0,0 +1,209 @@
+#!/bin/sh
+#
+# Copyright (c) 2008 Yann Dirson
+# Copyright (c) 2005 Junio C Hamano
+#
+
+test_description='Test rename factorization in diff engine.
+
+'
+. ./test-lib.sh
+. "$TEST_DIRECTORY"/diff-lib.sh
+
+test_expect_success \
+ 'commit the index.' \
+ 'git update-ref HEAD $(echo "original empty commit" | git commit-tree $(git write-tree))'
+
+mkdir a
+echo >a/path0 'Line 1
+Line 2
+Line 3
+Line 4
+Line 5
+Line 6
+Line 7
+Line 8
+Line 9
+Line 10
+line 11
+Line 12
+Line 13
+Line 14
+Line 15
+'
+sed <a/path0 >a/path1 s/Line/Record/
+sed <a/path0 >a/path2 s/Line/Stuff/
+sed <a/path0 >a/path3 s/Line/Blurb/
+
+test_expect_success \
+ 'update-index --add file inside a directory.' \
+ 'git update-index --add a/path*'
+
+test_expect_success \
+ 'write that tree.' \
+ 'tree=$(git write-tree) && test -n "$tree"'
+
+test_expect_success \
+ 'commit the index.' \
+ 'git update-ref HEAD $(echo "original set of files" | git commit-tree $tree)'
+
+mv a b
+test_expect_success \
+ 'renamed the directory.' \
+ 'git update-index --add --remove a/path0 a/path1 a/path2 a/path3 b/path*'
+
+test_expect_success \
+ 'git diff-index --factorize-renames after directory move.' \
+ 'git diff-index --factorize-renames $tree >current'
+grep -v "^\[DBG\] " <current >current.filtered
+cat >expected <<\EOF
+:040000 040000 0000000000000000000000000000000000000000 0000000000000000000000000000000000000000 R100 a/ b/
+EOF
+
+test_expect_success \
+ 'validate the output for directory move.' \
+ 'compare_diff_patch current.filtered expected'
+
+# now test non-100% renames
+
+echo 'Line 16' >> b/path0
+mv b/path2 b/2path
+rm b/path3
+echo anything > b/path100
+test_expect_success \
+ 'edited dir contents.' \
+ 'git update-index --add --remove b/* b/path2 b/path3'
+
+test_expect_success \
+ 'git diff-index --factorize-renames after directory move and content changes.' \
+ 'git diff-index --factorize-renames $tree >current'
+grep -v "^\[DBG\] " <current >current.filtered
+cat >expected <<\EOF
+:040000 040000 0000000000000000000000000000000000000000 0000000000000000000000000000000000000000 R100 a/ b/
+:100644 000000 c6971ab9f08a6cd9c89a0f87d94ae347aad6144a 0000000000000000000000000000000000000000 D a/path3
+:100644 100644 dbde7141d737c8aa0003672c1bc21ded48c6c3b9 dbde7141d737c8aa0003672c1bc21ded48c6c3b9 R100 a/path2 b/2path
+:100644 100644 fdbec444a77953b1bcc899d9fabfa202e5e68f08 4db595d12886f90e36765fc1732c17bccb836663 R093 a/path0 b/path0
+:000000 100644 0000000000000000000000000000000000000000 1ba4650885513e62386fd3e23aeb45beeb67d3bb A b/path100
+EOF
+
+test_expect_success \
+ 'validate the output for directory move and content changes.' \
+ 'compare_diff_patch current.filtered expected'
+
+git reset --hard
+
+# now test bulk moves that are not directory moves (get consensus before going further ?)
+
+mkdir c
+for i in 0 1 2; do cp a/path$i c/apath$i; done
+test_expect_success \
+ 'add files into a new directory.' \
+ 'git update-index --add c/apath*'
+
+test_expect_success \
+ 'commit all this.' \
+ 'git commit -m "first set of changes"'
+
+mv c/* a/
+test_expect_success \
+ 'move all of the new dir contents into a preexisting dir.' \
+ 'git update-index --add --remove a/* c/apath0 c/apath1 c/apath2'
+
+test_expect_success \
+ 'git diff-index --factorize-renames without full-dir rename.' \
+ 'git diff-index --factorize-renames HEAD >current'
+grep -v "^\[DBG\] " <current >current.filtered
+cat >expected <<\EOF
+:040000 040000 0000000000000000000000000000000000000000 0000000000000000000000000000000000000000 R100 c/* a/
+EOF
+
+test_expect_failure \
+ 'validate the output for bulk rename without full-dir rename.' \
+ 'compare_diff_patch current.filtered expected'
+
+git reset --hard
+
+# now test moves to toplevel (seriously broken)
+
+mv c/* .
+test_expect_success \
+ 'move all of the new dir contents into toplevel.' \
+ 'git update-index --add --remove apath* c/apath0 c/apath1 c/apath2'
+
+test_expect_success \
+ 'git diff-index --factorize-renames files bulk-moved to toplevel.' \
+ 'git diff-index --factorize-renames HEAD >current'
+grep -v "^\[DBG\] " <current >current.filtered
+cat >expected <<\EOF
+:040000 040000 0000000000000000000000000000000000000000 0000000000000000000000000000000000000000 R100 c/* ./
+EOF
+
+test_expect_failure \
+ 'validate the output for files bulk-moved to toplevel.' \
+ 'compare_diff_patch current.filtered expected'
+
+git reset --hard
+
+# now test renaming with subdirs (lacks hiding of renamed subdirs)
+
+mv c a/
+test_expect_success \
+ 'move the new dir as subdir of another.' \
+ 'git update-index --add --remove a/c/* c/apath0 c/apath1 c/apath2'
+
+test_expect_success \
+ 'commit all this.' \
+ 'git commit -m "move as subdir"'
+
+mv a b
+echo foo >> b/c/apath0
+test_expect_success \
+ 'rename the directory with some changes.' \
+ 'git update-index --add --remove a/path0 a/path1 a/path2 a/path3 a/c/apath0 a/c/apath1 a/c/apath2 b/path* b/c/apath*'
+
+test_expect_success \
+ 'git diff-index --factorize-renames on a move including a subdir.' \
+ 'git diff-index --factorize-renames HEAD >current'
+grep -v "^\[DBG\] " <current >current.filtered
+cat >expected <<\EOF
+:040000 040000 0000000000000000000000000000000000000000 0000000000000000000000000000000000000000 R100 a/ b/
+:100644 100644 fdbec444a77953b1bcc899d9fabfa202e5e68f08 00084e5ea68b5ae339b7c4b429e4a70fe25d069b R096 a/c/apath0 b/c/apath0
+EOF
+
+test_expect_failure \
+ 'validate the output for a move including a subdir.' \
+ 'compare_diff_patch current.filtered expected'
+
+# now test moving all files from toplevel into subdir (does not hides file moves) (needs consensus on syntax)
+#FIXME: maybe handle this as special case of move of a dir into one of its own subdirs ?
+
+git reset --hard HEAD~2
+
+mv a/* .
+test_expect_success \
+ 'rename the directory with some changes.' \
+ 'git update-index --add --remove a/path0 a/path1 a/path2 a/path3 path*'
+
+test_expect_success \
+ 'commit all this.' \
+ 'git commit -m "move all files to toplevel"'
+
+mkdir z
+mv path* z/
+test_expect_success \
+ 'rename the directory with some changes.' \
+ 'git update-index --add --remove path0 path1 path2 path3 z/path*'
+
+test_expect_success \
+ 'git diff-index --factorize-renames everything from toplevel.' \
+ 'git diff-index --factorize-renames HEAD >current'
+grep -v "^\[DBG\] " <current >current.filtered
+cat >expected <<\EOF
+:040000 040000 0000000000000000000000000000000000000000 0000000000000000000000000000000000000000 R100 ./* z/
+EOF
+
+test_expect_failure \
+ 'validate the output for a move of everything from toplevel.' \
+ 'compare_diff_patch current.filtered expected'
+
+test_done
^ permalink raw reply related
* Re: [PATCH] Documentation: add a planning document for the next CLI revamp
From: Yann Dirson @ 2008-10-30 22:46 UTC (permalink / raw)
To: Nicolas Pitre
Cc: Sam Vilain, Pierre Habouzit, Mike Hommey, Shawn O. Pearce, git
In-Reply-To: <alpine.LFD.2.00.0810301423520.13034@xanadu.home>
On Thu, Oct 30, 2008 at 02:28:35PM -0400, Nicolas Pitre wrote:
> > It's not about magic, it's about sensible defaults. Currently this use
> > case is an error, and the resultant command is very long to type, and
> > involves typing the branch name twice. I end up writing things like:
> >
> > git checkout -b {,origin/}wr34251-do-something
> >
> > For the user who doesn't know to use the ksh-style {} blocks this is
> > voodoo. The longer form is cumbersome.
>
> This is no excuse for promoting semantics only useful in such special
> cases.
It is really not so rare to have an upstream repo with branches such
as "stable", "next" and the like. This syntax extension would make is
as straightforward to work on "stable" as it is on remote HEAD
(usually master, which has already been magically setup for you).
BTW this use case reminds me that the remote HEAD has its own special
treatment for "clone", which AFAIK cannot be overriden from
command-line (I still sometimes lack what cogito provided as "cg clone
URL#branch").
> As long as it checks it out with a detached head if it is a remote
> branch then I have no issue.
Yes it is possible, but that does not necessarily make a UI
improvement worthless.
Best regards,
--
Yann
^ permalink raw reply
* Re: [PATCH 1/2] Add --verbose|-v to test-chmtime
From: Jeff King @ 2008-10-30 22:58 UTC (permalink / raw)
To: Alex Riesen; +Cc: Git Mailing List, Junio C Hamano, René Scharfe
In-Reply-To: <81b0412b0810300426u2ccbe51at1bf5f989b6333ed1@mail.gmail.com>
On Thu, Oct 30, 2008 at 12:26:24PM +0100, Alex Riesen wrote:
> This allows us replace perl when getting the mtime of a file because
> of time zone conversions, though at the moment only one platform which
> does this has been identified: Cygwin when used with ActiveState Perl
> (as usual).
> [...]
> test-chmtime -v +0 filename1 | cut -f 1
Personally, I would have:
- split the argument refactoring and the addition of the "-v" argument
into two patches to make reviewers lives easier
- just used a special timespec that means "don't change anything, but
show show"
but I think those are mostly nitpicks, so I am OK with the series as-is.
-Peff
^ permalink raw reply
* Re: Using the --track option when creating a branch
From: Jakub Narebski @ 2008-10-30 23:24 UTC (permalink / raw)
To: git
In-Reply-To: <2008-10-30-15-23-16+trackit+sam@rfc1149.net>
[Cc: Samuel Tardieu <sam@rfc1149.net>, Andreas Ericsson <ae@op5.se>,
git@vger.kernel.org]
Samuel Tardieu wrote:
> * Andreas Ericsson <ae@op5.se> [2008-10-30 15:06:16 +0100]
>
>> --all pushes all refs, even the non-matching ones, which is very
>> rarely desirable and only accidentally sometimes the same as "push all
>> matching refs".
>>
>>> I know that I've never had the intent to push all the refs without
>>> thinking about it first. Most of the time, I intend to push only
>>> the current branch I am in.
>>
>> Then say so. There's a very simple command syntax for it:
>> "git push <remote> <current-branch>"
>
> I update the branches I'm working in maybe 20 times a day, sometimes
> more. When I make a change and all the tests pass, I prefer to call
>
> git push
>
> rather than
>
> git push origin 2.0-beta1
>
> (and "2.0-beta1" is a short name here, some branches have much longer
> names)
You can use
$ git push origin HEAD
and I think (but I am not sure) that there is DWIM-mery allowing
to simply say
$ git push HEAD
and it would use configured branch.$(git symbolic-ref HEAD).remote
And if it is not as I said, the patches would better made it so, instead of
changing default behavior from push matching refspecs to push current
branch only.
--
Jakub Narebski
Warsaw, Poland
ShadeHawk on #git
^ permalink raw reply
* Re: [PATCH] Documentation: add a planning document for the next CLI revamp
From: Theodore Tso @ 2008-10-30 23:27 UTC (permalink / raw)
To: Sam Vilain; +Cc: git, Sam Vilain
In-Reply-To: <1225389068.19891.28.camel@maia.lan>
On Thu, Oct 30, 2008 at 10:51:08AM -0700, Sam Vilain wrote:
>
> Well, I don't have strong feelings on the exact command name used; I
> suggested "undo", probably also ambiguous. But still, a significant
> number of users are surprised when they type 'git revert' and they get a
> backed out patch.
Yeah, that's why I suggested "git revert-file". It's less ambiguous
than "undo", and it's easier for people used to "hg revert" and "svn
revert" to find "git revert-file". And, it won't be run accidentally
by old-timers who are used to the old (to be deprecated) "git revert".
But I'm not that picky about the name; I just missed the "git undo"
proposal in your patch.
> Making it plain "revert" would violate expectations of existing users;
> it seems a better idea to just deprecate it, and point the users to the
> new method - cherry-pick --revert - or the command they might have meant
> - whatever that becomes.
Yup, I agree; that's why I suggested "git revert-file".
- Ted
^ permalink raw reply
* Re: [PATCH] Documentation: add a planning document for the next CLI revamp
From: Sam Vilain @ 2008-10-30 23:28 UTC (permalink / raw)
To: Nicolas Pitre; +Cc: Pierre Habouzit, Mike Hommey, Shawn O. Pearce, git
In-Reply-To: <alpine.LFD.2.00.0810301423520.13034@xanadu.home>
On Thu, 2008-10-30 at 14:28 -0400, Nicolas Pitre wrote:
> > For the case where the thing you type is a resolvable reference, it
> > would just check it out, as now.
> As long as it checks it out with a detached head if it is a remote
> branch then I have no issue.
Absolutely - if you've already got a branch "master", then
"git checkout master" should definitely give it to you. If you go
"git checkout origin/master", you get a floating head. But I quite often
find myself wanting to check out a remote branch, and give it a name just
like on the remote. I want "git checkout blah" to assume that's
what I mean, until I make a local branch "blah".
> By default, git creates a branch called "master. Hence, by default, if
> you clone that repository, this branch will be called origin/master. So
> by default $foo is already ambiguous.
Right - 'master' in this case resolves to something. The ambiguity is
resolved by defaulting to the thing that resolves. The fall-back
behaviour is only triggered if you asked for something that is currently
an error. Because breaking expectations sucks.
Sam.
^ permalink raw reply
* Re: [PATCH] Documentation: add a planning document for the next CLI revamp
From: Jakub Narebski @ 2008-10-30 23:55 UTC (permalink / raw)
To: git
In-Reply-To: <1225387882.19891.9.camel@maia.lan>
Sam Vilain wrote:
> It's not about magic, it's about sensible defaults. Currently this use
> case is an error, and the resultant command is very long to type, and
> involves typing the branch name twice. I end up writing things like:
>
> git checkout -b {,origin/}wr34251-do-something
Can't you use currently
git checkout --track origin/wr34251-do-something
P.S. Somehow I don't see first message in this thread on GMane...
--
Jakub Narebski
Warsaw, Poland
ShadeHawk on #git
^ permalink raw reply
* Re: [PATCH] t4030: Don't use echo -n
From: Ian Hilt @ 2008-10-30 23:52 UTC (permalink / raw)
To: Brian Gernhardt; +Cc: Git Mailing List
In-Reply-To: <1225404776-51748-1-git-send-email-benji@silverinsanity.com>
On Thu, Oct 30, 2008 at 06:12:56PM -0400, Brian Gernhardt wrote:
> Signed-off-by: Brian Gernhardt <benji@silverinsanity.com>
No commit message???
> ---
> t/t4030-diff-textconv.sh | 5 ++---
> 1 files changed, 2 insertions(+), 3 deletions(-)
>
> diff --git a/t/t4030-diff-textconv.sh b/t/t4030-diff-textconv.sh
> index 3945731..7ec244f 100755
> --- a/t/t4030-diff-textconv.sh
> +++ b/t/t4030-diff-textconv.sh
> @@ -96,16 +96,15 @@ cat >expect.typechange <<'EOF'
> -1
> diff --git a/file b/file
> new file mode 120000
> -index ad8b3d2..67be421
> +index ad8b3d2..8e4020b
> --- /dev/null
> +++ b/file
> @@ -0,0 +1 @@
> +frotz
> -\ No newline at end of file
> EOF
> # make a symlink the hard way that works on symlink-challenged file systems
> test_expect_success 'textconv does not act on symlinks' '
> - echo -n frotz > file &&
> + echo frotz > file &&
> git add file &&
> git ls-files -s | sed -e s/100644/120000/ |
> git update-index --index-info &&
> --
> 1.6.0.3.523.g304d0
This doesn't apply for me. My tip is up-to-date, but it doesn't even have
this file it t/.
A little bewildered,
Ian
^ permalink raw reply
* [PATCH] bash completion: add doubledash to "git show"
From: Markus Heidelberg @ 2008-10-31 0:04 UTC (permalink / raw)
To: gitster; +Cc: git
Signed-off-by: Markus Heidelberg <markus.heidelberg@web.de>
---
contrib/completion/git-completion.bash | 2 ++
1 files changed, 2 insertions(+), 0 deletions(-)
diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index eebe734..de193ba 100755
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -1398,6 +1398,8 @@ _git_shortlog ()
_git_show ()
{
+ __git_has_doubledash && return
+
local cur="${COMP_WORDS[COMP_CWORD]}"
case "$cur" in
--pretty=*)
--
1.6.0.3.524.g3adb7d
^ permalink raw reply related
* Re: [JGIT PATCH 0/3] Improved object validation
From: Robin Rosenberg @ 2008-10-31 0:01 UTC (permalink / raw)
To: Shawn O. Pearce; +Cc: git
In-Reply-To: <1225388785-26818-1-git-send-email-spearce@spearce.org>
torsdagen den 30 oktober 2008 18.46.22 skrev Shawn O. Pearce:
> This is mostly a resend as I haven't heard anything on the series.
> One new patch at the end, to handle '.' and '..' cases.
Ack, pushed now. I never got to the push action, because I wanted
to do some testing on the bundlewriter (which you did not resubmit) and
the I went to a warmer place for a few days.
These patches and the bundlewrite + a small unit test for it now pushed.
-- robin
^ permalink raw reply
* Re: [JGIT RFC PATCH 3/3] Rate limit warnings spewed by RepositoryTestCase.recursiveDelete
From: Robin Rosenberg @ 2008-10-31 0:16 UTC (permalink / raw)
To: Jonas Fonseca; +Cc: Shawn O. Pearce, git
In-Reply-To: <20081030104620.GB17131@diku.dk>
torsdagen den 30 oktober 2008 11.46.20 skrev Jonas Fonseca:
> Robin Rosenberg <robin.rosenberg@dewire.com> wrote Fri, Oct 24, 2008:
> > onsdagen den 22 oktober 2008 10.34.20 skrev Jonas Fonseca:
> > > On Windows XP / NTFS / NetBeans 6.1 / Java 5 a lot of warnings are
> > > printed. In most cases the path is in fact deleted and it seems to
> > > just be a timing bug or something Windows or NTFS specific.
> >
> > The problem is actually flaws in the unit tests and in the supporting
> > RepositoryTestCase. I think I'll fix that instead.
>
> Thanks. Any progress on this? Can I help in any way?
Ok here is a W-I-P. One test case is not cleaning up properly. You may note that I
still give some room for gc not to unmap immediately, but at the end of the program
we hope that will be the case and I think the missing case is just a bug and not GC
being delayed. The counter testcount is only here for debugging this problem.
-- robin
>From b3907a11bec0158a99bc77a7655379725203da9c Mon Sep 17 00:00:00 2001
From: Robin Rosenberg <robin.rosnberg@dewire.com>
Date: Thu, 23 Oct 2008 01:27:50 +0200
Subject: [EGIT PATCH] Make the cleanup less verbose when it fails to delete temporary stuff.
---
.../org/spearce/jgit/lib/RepositoryTestCase.java | 57 +++++++++++++++-----
1 files changed, 44 insertions(+), 13 deletions(-)
diff --git a/org.spearce.jgit.test/tst/org/spearce/jgit/lib/RepositoryTestCase.java b/org.spearce.jgit.test/tst/org/spearce/jgit/lib/RepositoryTestCase.java
index 9d7d133..8015a18 100644
--- a/org.spearce.jgit.test/tst/org/spearce/jgit/lib/RepositoryTestCase.java
+++ b/org.spearce.jgit.test/tst/org/spearce/jgit/lib/RepositoryTestCase.java
@@ -47,6 +47,7 @@
import java.io.Reader;
import junit.framework.TestCase;
+
import org.spearce.jgit.util.JGitTestUtil;
public abstract class RepositoryTestCase extends TestCase {
@@ -66,22 +67,34 @@
jcommitter = new PersonIdent("J. Committer", "jcommitter@example.com");
}
- protected static void recursiveDelete(final File dir) {
+ protected static boolean recursiveDelete(final File dir) {
+ return recursiveDelete(dir, false);
+ }
+
+ protected static boolean recursiveDelete(final File dir, boolean silent) {
+ if (!dir.exists())
+ return silent;
final File[] ls = dir.listFiles();
if (ls != null) {
for (int k = 0; k < ls.length; k++) {
final File e = ls[k];
if (e.isDirectory()) {
- recursiveDelete(e);
+ silent = recursiveDelete(e, silent);
} else {
- e.delete();
+ if (!e.delete()) {
+ if (!silent)
+ System.out.println("Warning: Failed to delete " + e);
+ silent = true;
+ }
}
}
}
- dir.delete();
- if (dir.exists()) {
- System.out.println("Warning: Failed to delete " + dir);
+ if (!dir.delete()) {
+ if (!silent)
+ System.out.println("Warning: Failed to delete " + dir);
+ silent = true;
}
+ return silent;
}
protected static void copyFile(final File src, final File dst)
@@ -121,19 +134,31 @@ protected static void checkFile(File f, final String checkData)
protected Repository db;
+ private static int testcount;
+ private static Thread shutdownhook;
+
public void setUp() throws Exception {
super.setUp();
- recursiveDelete(trashParent);
- trash = new File(trashParent,"trash"+System.currentTimeMillis());
+ System.gc();
+ trash = new File(trashParent,"xtrash"+System.currentTimeMillis()+"."+(testcount++));
+ recursiveDelete(trashParent, true);
trash_git = new File(trash, ".git");
-
+ if (shutdownhook == null) {
+ shutdownhook = new Thread() {
+ @Override
+ public void run() {
+ System.gc();
+ recursiveDelete(trashParent, false);
+ }
+ };
+ Runtime.getRuntime().addShutdownHook(shutdownhook);
+ }
Runtime.getRuntime().addShutdownHook(new Thread() {
@Override
public void run() {
- recursiveDelete(trashParent);
+ recursiveDelete(trash);
}
});
-
db = new Repository(trash_git);
db.create();
@@ -170,12 +195,18 @@ protected void tearDown() throws Exception {
* @throws IOException
*/
protected Repository createNewEmptyRepo() throws IOException {
- File newTestRepo = new File(trashParent, "new"+System.currentTimeMillis()+"/.git");
+ final File newTestRepo = new File(trashParent, "new"+System.currentTimeMillis()+"."+(testcount++)+"/.git");
assertFalse(newTestRepo.exists());
- File unusedDir = new File(trashParent, "tmp"+System.currentTimeMillis());
+ File unusedDir = new File(trashParent, "tmp"+System.currentTimeMillis()+"."+(testcount++));
assertTrue(unusedDir.mkdirs());
final Repository newRepo = new Repository(newTestRepo);
newRepo.create();
+ Runtime.getRuntime().addShutdownHook(new Thread() {
+ @Override
+ public void run() {
+ recursiveDelete(newTestRepo);
+ }
+ });
return newRepo;
}
--
1.6.0.2.308.gef4a
^ permalink raw reply related
* Re: git adds some text file as binary file by mistake
From: Robin Rosenberg @ 2008-10-31 0:29 UTC (permalink / raw)
To: Ping Yin; +Cc: Michael J Gruber, Git Mailing List
In-Reply-To: <46dff0320810292332y34ea0daemde05b58572946497@mail.gmail.com>
torsdagen den 30 oktober 2008 07.32.47 skrev Ping Yin:
> On Fri, Oct 24, 2008 at 9:30 PM, Ping Yin <pkufranky@gmail.com> wrote:
> > On Fri, Oct 24, 2008 at 8:54 PM, Michael J Gruber
> > <git@drmicha.warpmail.net> wrote:
> >> Ping Yin venit, vidit, dixit 24.10.2008 14:37:
> >>> So what should i do if i want it added as text file?
> >>
> >> You should give us more detail on the file ;)
> >> What's the extension, what's the typical content? It may be a simple
> >> matter of specifying attributes.
> >> Do ordinary diff and grep recognize your files as text?
> >>
> >> Michael
> >>
> >
> > It's just an xml file. I guess maybe there are some hidden characters
> > at the beginning. I will figure it out later because i have no access
> > to that file right now.
> >
> > Ping Yin
> >
>
> I have figured it out. It's just because the BOM characters feff00 in
> the beginning of the utf-8 xml file.
The UTF-8 BOM is EF BB BF, (no NUL.). FEFF is UTF-16 BE (and the third
byte would be 00 for an XML file). I think git currently regards just about
any UTF-16 file as binary becuase of the NUL bytes.
-- robin
^ permalink raw reply
* Re: [PATCH] Documentation: add a planning document for the next CLI revamp
From: Jeff King @ 2008-10-31 0:31 UTC (permalink / raw)
To: Sam Vilain
Cc: git, Johannes Schindelin, Scott Chacon, Tom Preston-Werner, J.H.,
Christian Couder, Kai Blin
In-Reply-To: <20081030002239.D453B21D14E@mail.utsl.gen.nz>
On Wed, Oct 29, 2008 at 05:22:00PM -0700, Sam Vilain wrote:
> Some suggestions, which have been briefly scanned over by some of the
> (remaining) GitTogether attendees. Please keep it constructive! :)
Thanks for putting this together.
> + * 'git stage' would do what 'git add' does now.
> +
> + * 'git unstage' would do what 'git reset --' does now
These seem reasonable.
> + * 'git status' would encourage the user to use
> + 'git diff --staged' to see staged changes as a patch
I notice the commit template message getting longer and longer. Maybe it
is time for status.verbosetemplate (which could default to true, I just
want to be able to turn it off).
> + * 'git commit' with no changes should give useful information about
> + using 'git stage', 'git commit -a' or 'git commit filename ...'
There is already infrastructure that figures out exactly what the
situation is (no changes versus changes in untracked files versus
changes in unstaged files), so it should just be a matter of tweaking
the messages.
> + * 'git add' and 'git rm': no change
> +
> + * 'git update-index' considered plumbing, not changed
Definitely.
> + * 'git revert' deprecated in favour of 'git cherry-pick --revert'
I think I would make it "-R, --reverse", since it really is analagous to
"git diff -R".
> + * 'git undo' would do what 'git checkout HEAD --' does now
This is an awful name, IMHO. It doesn't point out _what_ you're undoing,
so it leaves me with the feeling that you can undo arbitrary things.
I think the name needs to be considered along with related operations.
So think of us as having three "spots": the HEAD (H), the "stage"[1] (S),
and the working tree (W). And we want commands for moving content
between them. Now we have:
W->S: add
H->S: reset --
S->W: checkout --
S->H: commit (no paths)
And if you want to include things that jump the staging area:
W->H: commit (paths or -a)
H->W: checkout HEAD --
So I think with your stage/unstage, we have:
W->S: stage
H->S: unstage
S->W: ?
S->H: commit (no paths)
W->H: commit (paths or -a)
H->W: ?
So I think we can note something: movement commands are related based on
their _destination_. So since both of the missing ones impact the
working tree, they should have a related name.
But do note the difference between "stage vs unstage" as opposed to
"commit versus commit -a". I think this is because the stage sits in the
middle. So it is mentally "which direction are changes coming from" and
not "how _far_ are changes coming from".
So by that rationale, we should have a single command which says "put
stuff in the working tree", with a flag for "from HEAD" versus "from the
staging area." And that's what we have right now with "git checkout".
The real problem with it is that it is an overload of checkout's other
behavior of switching branches.
So what I am saying is "git undo" _must_ support both "put index content
into working tree" as well as "put HEAD content into working tree", or
it will be a step backwards in consistency.
So I guess that doesn't really suggest a name. But "undo" is awful. ;P
Side note: there are actually _other_ places you might want to move
content. Like a stash. So now you can think of it as:
stash
^ ^
/ \
/ \
v v
HEAD <--> stage <--> working tree
So maybe we just need a "git content" command. And then you can "git
content --from=HEAD --to=tree <paths>" or "git content --from=tree
--to=stash", with all equally supporting "--interactive". And of course
I am kidding, because typing that would be awful. But I think
conceptually, it makes sense. To me, anyway.
> + * 'git branch --switch' : alternative to checkout
Blech. I think switching branches is the one thing that checkout does
unconfusedly. And this is much more typing. Not to mention that So I
would rather see "git switch" if checkout is somehow unpalatable.
But I don't know that it is. This seems like an attempt to say "branch
operations should all be part of 'git branch'". But checkout isn't
necessarily a branch operation. Consider detaching HEAD to a tag. Should
it be "git tag --switch"?
> + * 'git push --matching' does what 'git push' does today (without
> + explicit configuration)
I think this is reasonable even without other changes, just to override
any configuration.
> + * 'git push' with no ref args and no 'push =' configuration does
> + what:
> + 'git push origin $(git symbolic-ref HEAD | sed "s!refs/heads/!!")'
> + does today. ie, it only pushes the current branch.
> + If a branch was defined in branch.<name>.push, push to that ref
> + instead of the matching one. If there is no matching ref, and
> + there is a branch.<name>.merge, push back there.
There was a thread between me and Junio some months ago that touched on
this. I don't remember all of the arguments, but it was resolved to keep
the current behavior. Any proposal along these lines should at least
revisit and respond to those arguments.
> + * 'git push' to checked out branch of non-bare repository not
> + allowed without special configuration. Configuration available
I have this patch done and sitting in my repo, but I need to add the
"without special configuration" bit and add tests and docs.
> +Informational
> +-------------
> +
> + * 'git branch' should default to '--color=auto -v'
This should at least be configurable (even if it defaults to "on"). "-v"
is more expensive, and not always wanted.
I, for one, just use "git branch" to get the current branch. I don't
know of a more obvious way to ask for it (and please don't mention an
ever-changing bash prompt).
> + * 'git tag -l' should show more information
I remember somebody talking about this, but not the details. Which
information?
> + * 'git am -3' the default; with global option to make it not the
> + default for those that prefer the speed of -2
I would prefer that personally. I think Linus has been very reasonable
in the past about recognizing that his workflow and speed requirements
aren't always typical, and being willing to accept setting a
configuration flag in those cases. So I think if he ack'd such a patch,
nobody else would complain.
> + * 'git export' command that does what
> + 'git archive --format=tar --prefix=dir | tar x' does now
I agree, if you mean "does what ... does now" means "looks to the user
like ... is happening". This is much more sanely done using
git-checkout-index (though somebody suggested "remote export", which
would need to use tar itself).
> + * 'git init --server' (or similar) should do everything required for
> + exporting::
> +----
> +chmod -R a+rX
> +touch git-daemon-export-ok
> +git gc
> +git update-server-info
> +chmod u+x .git/hooks/post-update
> +git config core.sharedrepository=1
> +----
But not all of those things are necessarily related, and some of them
have security implications. I would hate to get a bug report like "I
used --server because I wanted to share my content via dumb http, but my
repo was p0wned because of too-loose group permissions."
-Peff
^ permalink raw reply
* Re: [PATCH] Documentation: add a planning document for the next CLI revamp
From: Jeff King @ 2008-10-31 0:34 UTC (permalink / raw)
To: Pierre Habouzit; +Cc: Sam Vilain, git, Sam Vilain
In-Reply-To: <20081030132453.GB24098@artemis.corp>
On Thu, Oct 30, 2008 at 02:24:53PM +0100, Pierre Habouzit wrote:
> > + * 'git stage' would do what 'git add' does now.
> -> git stage -i/-p shall do what git add -i/-p does.
Yes, and that is obviously easy.
> > + * 'git unstage' would do what 'git reset --' does now
> -> likely we need a git unstage -i/-p to interactively unstage some
> bits.
Agreed, though this is a bit harder. But I think this should go hand in
hand with "git stash -i" and "git stash apply -i" (as I mentioned in my
other mail in this thread).
-Peff
^ permalink raw reply
* Re: [RFC] gitweb: add 'historyfollow' view that follows renames
From: Jakub Narebski @ 2008-10-31 1:19 UTC (permalink / raw)
To: Blucher, Guy; +Cc: ming.m.lin, robert.moore, git
In-Reply-To: <054F21930D24A0428E5B4588462C7AED0149B4B8@ednex512.dsto.defence.gov.au>
I'm sorry for the delay in reviewing this patch...
On Mon, 27 Oct 2008, Huy Blucher wrote:
[Please try do not lose attributions...]
> > >
> > > What should we add to automatically get all file history?
>
> > While the 'commitdiff' view would, in default gitweb configuration,
> > contain information about file renames, currently 'history' view does
> > not support '--follow' option to git-log. It wouldn't be too hard to
> > add it, but it just wasn't done (well, add to this the fact that
> > --follow works only for simple cases).
>
> We also ran up against this issue because renaming of files in our
> project is a useful bit of information while browsing file history.
>
> I hacked gitweb to add a 'historyfollow' viewing option in addition to
> the 'history' option. Yes, '--follow' is expensive so I didn't just
> make it the default 'history' behaviour.
I would prefer if instead of adding new 'historyfollow' action, which
goes against stated in TODO goal of uniquifying log-like views handling,
the patch added support for '--follow' as extra option to 'history'
view (i.e. a=history;opt=--follow)... on the other hand 'historyfollow'
(or simply 'follow') can be used in pure path_info gitweb URL... Hmm...
>
> The only problem with doing it was that parse_commits in gitweb.perl
> uses git rev-list which doesn't support the '--follow' option like
> git-log does. A bit of hacking to use 'git log --pretty=raw -z' to make
> the output look close to that from rev-list means only minor
> shoe-horning is required (perhaps it would be better to make rev-list
> understand --follow though?).
Either that, or use --pretty=format:<sth> which mimics current use of
"git-rev-list <opts>" output in parse_commits exactly.
And either move parse_commits to use git-log, change git-rev-parse to
understand '--follow', or make parse_commits use git-log with --follow,
git-rev-list otherwise.
>
> I wasn't originally prepared to publish the work here because I don't
> really think it's the best solution. But considering it's come up... I
> include a patch inline against gitweb.perl from v1.6.0.3 that implements
> a 'historyfollow' view.
RFC (usually marked [RFC/PATCH]) patches are good because they allow
others to test and comment on your solution: early review, better to
spot bugs etc. earlier.
>
> Feel free to do with it what you will. It would need some substantial
> tidying up by someone who knows much more about perl than me :)
>
> We use it such that anywhere a 'history' link is provided a
> 'historyfollow' link is also provided next to it - This patch doesn't
> implement that bit though.
>
> Hope it helps.
>
> Cheers,
> Guy.
It would be nice though if such [RFC/PATCH] followed guidelines from
SubmittingPatches on commit messages...
>
> ---
Diffstat?
>
> --- a/gitweb/gitweb.perl
> +++ b/gitweb/gitweb.perl
> @@ -478,6 +478,7 @@ my %actions = (
> "forks" => \&git_forks,
> "heads" => \&git_heads,
> "history" => \&git_history,
> + "historyfollow" => \&git_history_follow,
> "log" => \&git_log,
> "rss" => \&git_rss,
> "atom" => \&git_atom,
> @@ -2311,25 +2312,39 @@ sub parse_commit {
> }
>
> sub parse_commits {
> - my ($commit_id, $maxcount, $skip, $filename, @args) = @_;
> + my ($commit_id, $maxcount, $skip, $mode, $filename, @args) = @_;
Can't you simply pass '--follow' or 'follow' in @args instead of
changing the signature of parse_commits?
> my @cos;
>
> $maxcount ||= 1;
> $skip ||= 0;
>
> local $/ = "\0";
> + # The '--max-count' argument is not available when doing a
> + # '--follow' to 'git log'
> + my $count_arg = ("--max-count=" . $maxcount) ;
> + if (defined $mode && $mode eq "--follow") {
> + $count_arg = "--follow" ;
> + }
I don't understand. Do you mean that
$ git log --max-count=<n> --follow <rev> -- <path>
doesn't work as expected? Hmmm... true, it doesn't work.
Then it is certainly a _BUG_ in git!
>
> - open my $fd, "-|", git_cmd(), "rev-list",
> - "--header",
> +
> + open my $fd, "-|", git_cmd(), "log",
> + "-z",
> + "--pretty=raw",
> @args,
> - ("--max-count=" . $maxcount),
> + ($count_arg ? ($count_arg ) : ()),
Whitespace damage (here visible).
> ("--skip=" . $skip),
> @extra_options,
> $commit_id,
> "--",
> ($filename ? ($filename) : ())
> - or die_error(500, "Open git-rev-list failed");
> + or die_error(500, "Open git-log failed");
> while (my $line = <$fd>) {
> + # Need to put a delimiter on the end of output
> + # 'git-log -z' doesn't put one before EOF like rev-list
> does
> + $line = ($line . '\0');
Doesn't it work if you don't add the above line?
> + # Need to strip the word commit from the start so it
> + # looks like rev-list output
> + $line =~ s/^commit // ;
> my %co = parse_commit_text($line);
Perhaps we should update parse_commit_text instead... or add an option
like parse_commit_text($line, -format=>'log'), or something like that.
> push @cos, \%co;
> }
> @@ -5363,6 +5378,13 @@ sub git_commitdiff_plain {
> }
>
> sub git_history {
> + my $mode = shift || '';
> + my $history_call = "history";
> +
> + if ($mode eq "--follow") {
> + $history_call .= "historyfollow" ;
> + }
> +
I don't quite like this solution...
If '--follow' was passed through @extra_options ('opt') parameter, then
it should be re-used in links thanks to href(..., -replay=>1).
> if (!defined $hash_base) {
> $hash_base = git_get_head_hash($project);
> }
> @@ -5377,7 +5399,7 @@ sub git_history {
> my $limit = sprintf("--max-count=%i", (100 * ($page+1)));
>
> my @commitlist = parse_commits($hash_base, 101, (100 * $page),
> - $file_name, "--full-history")
> + $mode, $file_name,
> "--full-history")
Word wrapped (not only here).
> or die_error(404, "No such file or directory on given
> branch");
>
> if (!defined $hash && defined $file_name) {
> @@ -5398,7 +5420,7 @@ sub git_history {
> my $paging_nav = '';
> if ($page > 0) {
> $paging_nav .=
> - $cgi->a({-href => href(action=>"history",
> hash=>$hash, hash_base=>$hash_base,
> + $cgi->a({-href => href(action=>"$history_call",
> hash=>$hash, hash_base=>$hash_base,
> file_name=>$file_name)},
> "first");
I would add opts=>[@extra_options] instead of changing action=>"history"
to action=>$history_call (the quotes around variable are not needed).
> $paging_nav .= " ⋅ " .
> @@ -5429,6 +5451,11 @@ sub git_history {
> git_footer_html();
> }
>
> +sub git_history_follow {
> + git_history('--follow');
> +}
> +
> +
> sub git_search {
> gitweb_check_feature('search') or die_error(403, "Search is
> disabled");
> if (!defined $searchtext) {
> @@ -5469,7 +5496,7 @@ sub git_search {
> $greptype = "--committer=";
> }
> $greptype .= $searchtext;
> - my @commitlist = parse_commits($hash, 101, (100 *
> $page), undef,
> + my @commitlist = parse_commits($hash, 101, (100 *
> $page), undef, undef,
> $greptype,
> '--regexp-ignore-case',
> $search_use_regexp ?
> '--extended-regexp' : '--fixed-strings');
>
> @@ -5737,7 +5764,7 @@ sub git_feed {
>
> # log/feed of current (HEAD) branch, log of given branch,
> history of file/directory
> my $head = $hash || 'HEAD';
> - my @commitlist = parse_commits($head, 150, 0, $file_name);
> + my @commitlist = parse_commits($head, 150, 0, undef,
> $file_name);
>
> my %latest_commit;
> my %latest_date;
> ---
What I would like to see is the link in the bottom of action bar
(navbar) or just below it, which would list 'follow' as one of possible
'history' view formats (just like '--no-merges' or '--first-parent'
should be).
--
Jakub Narebski
Poland
^ permalink raw reply
* why not TortoiseGit
From: Li Frank-B20596 @ 2008-10-31 1:44 UTC (permalink / raw)
To: git
There are TortoiseCVS, TortoiseSVN, TortoiseBzr, TortoiseHg
Why not ToroiseGit
best regards
Frank Li
^ permalink raw reply
* Re: why not TortoiseGit
From: Jakub Narebski @ 2008-10-31 1:59 UTC (permalink / raw)
To: Li Frank-B20596; +Cc: git
In-Reply-To: <7FD1F85C96D70C4A89DA1DF7667EAE96125890@zch01exm23.fsl.freescale.net>
"Li Frank-B20596" <Frank.Li@freescale.com> writes:
> There are TortoiseCVS, TortoiseSVN, TortoiseBzr, TortoiseHg
> Why not ToroiseGit?
Because GitCheetah
--
Jakub Narebski
Poland
ShadeHawk on #git
^ permalink raw reply
* RE: why not TortoiseGit
From: Li Frank-B20596 @ 2008-10-31 2:02 UTC (permalink / raw)
To: Jakub Narebski; +Cc: git
In-Reply-To: <m3bpx1h6e6.fsf@localhost.localdomain>
GitCheetah seem only GitGui Here and GitBash Here.
TortoiseXXX can show log, diff, commit change ...at explore menu.
Best regards
Frank Li
-----Original Message-----
From: Jakub Narebski [mailto:jnareb@gmail.com]
Sent: Friday, October 31, 2008 9:59 AM
To: Li Frank-B20596
Cc: git@vger.kernel.org
Subject: Re: why not TortoiseGit
"Li Frank-B20596" <Frank.Li@freescale.com> writes:
> There are TortoiseCVS, TortoiseSVN, TortoiseBzr, TortoiseHg Why not
> ToroiseGit?
Because GitCheetah
--
Jakub Narebski
Poland
ShadeHawk on #git
^ permalink raw reply
* Re: why not TortoiseGit
From: George Shammas @ 2008-10-31 3:07 UTC (permalink / raw)
To: Li Frank-B20596; +Cc: Jakub Narebski, git
In-Reply-To: <7FD1F85C96D70C4A89DA1DF7667EAE9612589D@zch01exm23.fsl.freescale.net>
The very very blunt answer is, TortoiseGit doesn't exist because no
one has created it. And this may partly be do to the fact that git is
more powerful then the programs who have it, so its a bigger project
to make it stupid proof.
-G
On Thu, Oct 30, 2008 at 7:02 PM, Li Frank-B20596 <Frank.Li@freescale.com> wrote:
> GitCheetah seem only GitGui Here and GitBash Here.
> TortoiseXXX can show log, diff, commit change ...at explore menu.
>
> Best regards
> Frank Li
>
> -----Original Message-----
> From: Jakub Narebski [mailto:jnareb@gmail.com]
> Sent: Friday, October 31, 2008 9:59 AM
> To: Li Frank-B20596
> Cc: git@vger.kernel.org
> Subject: Re: why not TortoiseGit
>
> "Li Frank-B20596" <Frank.Li@freescale.com> writes:
>
>> There are TortoiseCVS, TortoiseSVN, TortoiseBzr, TortoiseHg Why not
>> ToroiseGit?
>
> Because GitCheetah
>
> --
> Jakub Narebski
> Poland
> ShadeHawk on #git
> --
> To unsubscribe from this list: send the line "unsubscribe git" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at http://vger.kernel.org/majordomo-info.html
>
^ permalink raw reply
* Re: why not TortoiseGit
From: Miles Bader @ 2008-10-31 3:53 UTC (permalink / raw)
To: George Shammas; +Cc: Li Frank-B20596, Jakub Narebski, git
In-Reply-To: <dfdaadcd0810302007q658d74c4wfb278999ea10885d@mail.gmail.com>
"George Shammas" <georgyo@gmail.com> writes:
> The very very blunt answer is, TortoiseGit doesn't exist because no
> one has created it. And this may partly be do to the fact that git is
> more powerful then the programs who have it, so its a bigger project
> to make it stupid proof.
... and from what I've seen of tortoise* users, "stupid proof" is very,
very, very, necessary...
-Miles
--
Immortality, n. A toy which people cry for, And on their knees apply for,
Dispute, contend and lie for, And if allowed Would be right proud
Eternally to die for.
^ permalink raw reply
* [PATCH] git-svn: change dashed git-commit-tree to git commit-tree
From: Deskin Miller @ 2008-10-31 4:10 UTC (permalink / raw)
To: git; +Cc: normalperson, gitster
Signed-off-by: Deskin Miller <deskinm@umich.edu>
---
Once again I'm using a copy of git-svn.perl directly, and this fails to exec.
I looked at it more closely and it fails because git binary calls setup_path,
which puts the libexec path into $PATH; of course, this doesn't happen when
git-svn is called directly.
git-svn.perl | 2 +-
1 files changed, 1 insertions(+), 1 deletions(-)
diff --git a/git-svn.perl b/git-svn.perl
index 2e68c68..56238da 100755
--- a/git-svn.perl
+++ b/git-svn.perl
@@ -2202,7 +2202,7 @@ sub do_git_commit {
}
die "Tree is not a valid sha1: $tree\n" if $tree !~ /^$::sha1$/o;
- my @exec = ('git-commit-tree', $tree);
+ my @exec = ('git', 'commit-tree', $tree);
foreach ($self->get_commit_parents($log_entry)) {
push @exec, '-p', $_;
}
--
1.6.0.3.515.g304f
^ permalink raw reply related
* Re: [PATCH] t4030: Don't use echo -n
From: Brian Gernhardt @ 2008-10-31 5:02 UTC (permalink / raw)
To: Ian Hilt; +Cc: Git Mailing List
In-Reply-To: <20081030235215.GB18221@sys-0.hiltweb.site>
On Oct 30, 2008, at 7:52 PM, Ian Hilt wrote:
> On Thu, Oct 30, 2008 at 06:12:56PM -0400, Brian Gernhardt wrote:
>> Signed-off-by: Brian Gernhardt <benji@silverinsanity.com>
>
> No commit message???
>>
"Don't use echo -n" seemed simple enough to me, as it's the only thing
it does. And the reason is that echo -n isn't portable, as has been
determined previously in git. I'll update this and use the better
replacement "printf" anyway.
> This doesn't apply for me. My tip is up-to-date, but it doesn't
> even have
> this file it t/.
This is based on next and is for a file that isn't in master.
~~ Brian
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox