Skip to content

Commit a4cb1a2

Browse files
derrickstoleegitster
authored andcommitted
maintenance: create maintenance.strategy config
To provide an on-ramp for users to use background maintenance without several 'git config' commands, create a 'maintenance.strategy' config option. Currently, the only important value is 'incremental' which assigns the following schedule: * gc: never * prefetch: hourly * commit-graph: hourly * loose-objects: daily * incremental-repack: daily These tasks are chosen to minimize disruptions to foreground Git commands and use few compute resources. The 'maintenance.strategy' is intended as a baseline that can be customzied further by manually assigning 'maintenance.<task>.enabled' and 'maintenance.<task>.schedule' config options, which will override any recommendation from 'maintenance.strategy'. This operates similarly to config options like 'feature.experimental' which operate as "meta" config options that change default config values. This presents a way forward for updating the 'incremental' strategy in the future or adding new strategies. For example, a potential strategy could be to include a 'full' strategy that runs the 'gc' task weekly and no other tasks by default. Helped-by: Martin Ågren <[email protected]> Signed-off-by: Derrick Stolee <[email protected]> Signed-off-by: Junio C Hamano <[email protected]>
1 parent 2fec604 commit a4cb1a2

File tree

3 files changed

+90
-2
lines changed

3 files changed

+90
-2
lines changed

Documentation/config/maintenance.txt

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,21 @@ maintenance.auto::
33
`git maintenance run --auto` after doing their normal work. Defaults
44
to true.
55

6+
maintenance.strategy::
7+
This string config option provides a way to specify one of a few
8+
recommended schedules for background maintenance. This only affects
9+
which tasks are run during `git maintenance run --schedule=X`
10+
commands, provided no `--task=<task>` arguments are provided.
11+
Further, if a `maintenance.<task>.schedule` config value is set,
12+
then that value is used instead of the one provided by
13+
`maintenance.strategy`. The possible strategy strings are:
14+
+
15+
* `none`: This default setting implies no task are run at any schedule.
16+
* `incremental`: This setting optimizes for performing small maintenance
17+
activities that do not delete any data. This does not schedule the `gc`
18+
task, but runs the `prefetch` and `commit-graph` tasks hourly and the
19+
`loose-objects` and `incremental-repack` tasks daily.
20+
621
maintenance.<task>.enabled::
722
This boolean config option controls whether the maintenance task
823
with name `<task>` is run when no `--task` option is specified to

builtin/gc.c

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1308,12 +1308,35 @@ static int maintenance_run_tasks(struct maintenance_run_opts *opts)
13081308
return result;
13091309
}
13101310

1311-
static void initialize_task_config(void)
1311+
static void initialize_maintenance_strategy(void)
1312+
{
1313+
char *config_str;
1314+
1315+
if (git_config_get_string("maintenance.strategy", &config_str))
1316+
return;
1317+
1318+
if (!strcasecmp(config_str, "incremental")) {
1319+
tasks[TASK_GC].schedule = SCHEDULE_NONE;
1320+
tasks[TASK_COMMIT_GRAPH].enabled = 1;
1321+
tasks[TASK_COMMIT_GRAPH].schedule = SCHEDULE_HOURLY;
1322+
tasks[TASK_PREFETCH].enabled = 1;
1323+
tasks[TASK_PREFETCH].schedule = SCHEDULE_HOURLY;
1324+
tasks[TASK_INCREMENTAL_REPACK].enabled = 1;
1325+
tasks[TASK_INCREMENTAL_REPACK].schedule = SCHEDULE_DAILY;
1326+
tasks[TASK_LOOSE_OBJECTS].enabled = 1;
1327+
tasks[TASK_LOOSE_OBJECTS].schedule = SCHEDULE_DAILY;
1328+
}
1329+
}
1330+
1331+
static void initialize_task_config(int schedule)
13121332
{
13131333
int i;
13141334
struct strbuf config_name = STRBUF_INIT;
13151335
gc_config();
13161336

1337+
if (schedule)
1338+
initialize_maintenance_strategy();
1339+
13171340
for (i = 0; i < TASK__COUNT; i++) {
13181341
int config_value;
13191342
char *config_str;
@@ -1389,7 +1412,6 @@ static int maintenance_run(int argc, const char **argv, const char *prefix)
13891412
memset(&opts, 0, sizeof(opts));
13901413

13911414
opts.quiet = !isatty(2);
1392-
initialize_task_config();
13931415

13941416
for (i = 0; i < TASK__COUNT; i++)
13951417
tasks[i].selected_order = -1;
@@ -1402,6 +1424,8 @@ static int maintenance_run(int argc, const char **argv, const char *prefix)
14021424
if (opts.auto_flag && opts.schedule)
14031425
die(_("use at most one of --auto and --schedule=<frequency>"));
14041426

1427+
initialize_task_config(opts.schedule);
1428+
14051429
if (argc != 0)
14061430
usage_with_options(builtin_maintenance_run_usage,
14071431
builtin_maintenance_run_options);

t/t7900-maintenance.sh

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -300,6 +300,55 @@ test_expect_success '--schedule inheritance weekly -> daily -> hourly' '
300300
test_subcommand git multi-pack-index write --no-progress <weekly.txt
301301
'
302302

303+
test_expect_success 'maintenance.strategy inheritance' '
304+
for task in commit-graph loose-objects incremental-repack
305+
do
306+
git config --unset maintenance.$task.schedule || return 1
307+
done &&
308+
309+
test_when_finished git config --unset maintenance.strategy &&
310+
git config maintenance.strategy incremental &&
311+
312+
GIT_TRACE2_EVENT="$(pwd)/incremental-hourly.txt" \
313+
git maintenance run --schedule=hourly --quiet &&
314+
GIT_TRACE2_EVENT="$(pwd)/incremental-daily.txt" \
315+
git maintenance run --schedule=daily --quiet &&
316+
317+
test_subcommand git commit-graph write --split --reachable \
318+
--no-progress <incremental-hourly.txt &&
319+
test_subcommand ! git prune-packed --quiet <incremental-hourly.txt &&
320+
test_subcommand ! git multi-pack-index write --no-progress \
321+
<incremental-hourly.txt &&
322+
323+
test_subcommand git commit-graph write --split --reachable \
324+
--no-progress <incremental-daily.txt &&
325+
test_subcommand git prune-packed --quiet <incremental-daily.txt &&
326+
test_subcommand git multi-pack-index write --no-progress \
327+
<incremental-daily.txt &&
328+
329+
# Modify defaults
330+
git config maintenance.commit-graph.schedule daily &&
331+
git config maintenance.loose-objects.schedule hourly &&
332+
git config maintenance.incremental-repack.enabled false &&
333+
334+
GIT_TRACE2_EVENT="$(pwd)/modified-hourly.txt" \
335+
git maintenance run --schedule=hourly --quiet &&
336+
GIT_TRACE2_EVENT="$(pwd)/modified-daily.txt" \
337+
git maintenance run --schedule=daily --quiet &&
338+
339+
test_subcommand ! git commit-graph write --split --reachable \
340+
--no-progress <modified-hourly.txt &&
341+
test_subcommand git prune-packed --quiet <modified-hourly.txt &&
342+
test_subcommand ! git multi-pack-index write --no-progress \
343+
<modified-hourly.txt &&
344+
345+
test_subcommand git commit-graph write --split --reachable \
346+
--no-progress <modified-daily.txt &&
347+
test_subcommand git prune-packed --quiet <modified-daily.txt &&
348+
test_subcommand ! git multi-pack-index write --no-progress \
349+
<modified-daily.txt
350+
'
351+
303352
test_expect_success 'register and unregister' '
304353
test_when_finished git config --global --unset-all maintenance.repo &&
305354
git config --global --add maintenance.repo /existing1 &&

0 commit comments

Comments
 (0)