@matheusbsbs / matheus-bagliano / commits / f56f31af03
Fork 0

sparse-checkout: use new update_sparsity() function

Remove the equivalent of 'git read-tree -mu HEAD' in the sparse-checkout codepaths for setting the SKIP_WORKTREE bits and instead use the new update_sparsity() function. Note that when an issue is hit, the error message splits 'error' and 'Cannot update sparse checkout' on separate lines. For now, we use two greps to find both pieces of the error message but subsequent commits will clean up the messages reported to the user. Reviewed-by: Derrick Stolee <dstolee@microsoft.com> Signed-off-by: Elijah Newren <newren@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>

Elijah Newren committed Mar 27, 2020 at 00:48 UTC f56f31af0301f6446f8689ba1a997d74fb82f45f
2 files changed +39 -40
builtin/sparse-checkout.c
+10 -30
@@ -94,49 +94,35 @@ static int sparse_checkout_list(int argc, const char **argv)
94
95 static int update_working_directory(struct pattern_list *pl)
96 {
97 - int result = 0;
97 + enum update_sparsity_result result;
98 struct unpack_trees_options o;
99 struct lock_file lock_file = LOCK_INIT;
100 - struct object_id oid;
101 - struct tree *tree;
102 - struct tree_desc t;
100 struct repository *r = the_repository;
101
105 - if (repo_read_index_unmerged(r))
106 - die(_("you need to resolve your current index first"));
107 -
108 - if (get_oid("HEAD", &oid))
109 - return 0;
110 -
111 - tree = parse_tree_indirect(&oid);
112 - parse_tree(tree);
113 - init_tree_desc(&t, tree->buffer, tree->size);
114 -
102 memset(&o, 0, sizeof(o));
103 o.verbose_update = isatty(2);
117 - o.merge = 1;
104 o.update = 1;
119 - o.fn = oneway_merge;
105 o.head_idx = -1;
106 o.src_index = r->index;
107 o.dst_index = r->index;
108 o.skip_sparse_checkout = 0;
109 o.pl = pl;
110
126 - resolve_undo_clear_index(r->index);
111 setup_work_tree();
112
129 - cache_tree_free(&r->index->cache_tree);
130 -
113 repo_hold_locked_index(r, &lock_file, LOCK_DIE_ON_ERROR);
114
133 - core_apply_sparse_checkout = 1;
134 - result = unpack_trees(1, &t, &o);
115 + result = update_sparsity(&o);
116
136 - if (!result) {
137 - prime_cache_tree(r, r->index, tree);
117 + if (result == UPDATE_SPARSITY_WARNINGS)
118 + /*
119 + * We don't do any special handling of warnings from untracked
120 + * files in the way or dirty entries that can't be removed.
121 + */
122 + result = UPDATE_SPARSITY_SUCCESS;
123 + if (result == UPDATE_SPARSITY_SUCCESS)
124 write_locked_index(r->index, &lock_file, COMMIT_LOCK);
139 - } else
125 + else
126 rollback_lock_file(&lock_file);
127
128 return result;
@@ -303,8 +289,6 @@ static int sparse_checkout_init(int argc, const char **argv)
289 };
290
291 repo_read_index(the_repository);
306 - require_clean_work_tree(the_repository,
307 - N_("initialize sparse-checkout"), NULL, 1, 0);
292
293 argc = parse_options(argc, argv, NULL,
294 builtin_sparse_checkout_init_options,
@@ -559,8 +543,6 @@ static int sparse_checkout_set(int argc, const char **argv, const char *prefix,
543 };
544
545 repo_read_index(the_repository);
562 - require_clean_work_tree(the_repository,
563 - N_("set sparse-checkout patterns"), NULL, 1, 0);
546
547 argc = parse_options(argc, argv, prefix,
548 builtin_sparse_checkout_set_options,
@@ -576,8 +558,6 @@ static int sparse_checkout_disable(int argc, const char **argv)
558 struct strbuf match_all = STRBUF_INIT;
559
560 repo_read_index(the_repository);
579 - require_clean_work_tree(the_repository,
580 - N_("disable sparse-checkout"), NULL, 1, 0);
561
562 memset(&pl, 0, sizeof(pl));
563 hashmap_init(&pl.recursive_hashmap, pl_hashmap_cmp, NULL, 0);
t/t1091-sparse-checkout-builtin.sh
+29 -10
@@ -277,16 +277,23 @@ test_expect_success 'cone mode: add parent path' '
277 check_files repo a deep folder1
278 '
279
280 -test_expect_success 'revert to old sparse-checkout on bad update' '
280 +test_expect_success 'not-up-to-date does not block rest of sparsification' '
281 test_when_finished git -C repo sparse-checkout disable &&
282 test_when_finished git -C repo reset --hard &&
283 git -C repo sparse-checkout set deep &&
284 +
285 echo update >repo/deep/deeper2/a &&
286 cp repo/.git/info/sparse-checkout expect &&
286 - test_must_fail git -C repo sparse-checkout set deep/deeper1 2>err &&
287 - test_i18ngrep "cannot set sparse-checkout patterns" err &&
288 - test_cmp repo/.git/info/sparse-checkout expect &&
289 - check_files repo/deep a deeper1 deeper2
287 + test_write_lines "!/deep/*/" "/deep/deeper1/" >>expect &&
288 +
289 + git -C repo sparse-checkout set deep/deeper1 2>err &&
290 +
291 + test_i18ngrep "Cannot update sparse checkout" err &&
292 + test_cmp expect repo/.git/info/sparse-checkout &&
293 + check_files repo/deep a deeper1 deeper2 &&
294 + check_files repo/deep/deeper1 a deepest &&
295 + check_files repo/deep/deeper1/deepest a &&
296 + check_files repo/deep/deeper2 a
297 '
298
299 test_expect_success 'revert to old sparse-checkout on empty update' '
@@ -316,16 +323,28 @@ test_expect_success '.gitignore should not warn about cone mode' '
323 test_i18ngrep ! "disabling cone patterns" err
324 '
325
319 -test_expect_success 'sparse-checkout (init|set|disable) fails with dirty status' '
326 +test_expect_success 'sparse-checkout (init|set|disable) warns with dirty status' '
327 git clone repo dirty &&
328 echo dirty >dirty/folder1/a &&
322 - test_must_fail git -C dirty sparse-checkout init &&
323 - test_must_fail git -C dirty sparse-checkout set /folder2/* /deep/deeper1/* &&
324 - test_must_fail git -C dirty sparse-checkout disable &&
329 +
330 + git -C dirty sparse-checkout init 2>err &&
331 + test_i18ngrep "error" err &&
332 + test_i18ngrep "Cannot update sparse checkout" err &&
333 +
334 + git -C dirty sparse-checkout set /folder2/* /deep/deeper1/* 2>err &&
335 + test_i18ngrep "error" err &&
336 + test_i18ngrep "Cannot update sparse checkout" err &&
337 + test_path_is_file dirty/folder1/a &&
338 +
339 + git -C dirty sparse-checkout disable 2>err &&
340 + test_must_be_empty err &&
341 +
342 git -C dirty reset --hard &&
343 git -C dirty sparse-checkout init &&
344 git -C dirty sparse-checkout set /folder2/* /deep/deeper1/* &&
328 - git -C dirty sparse-checkout disable
345 + test_path_is_missing dirty/folder1/a &&
346 + git -C dirty sparse-checkout disable &&
347 + test_path_is_file dirty/folder1/a
348 '
349
350 test_expect_success 'cone mode: set with core.ignoreCase=true' '