@@ -218,6 +218,122 @@ Further, the `git gc` command should not be combined with
218
218
but does not take the lock in the same way as `git maintenance run`. If
219
219
possible, use `git maintenance run --task=gc` instead of `git gc`.
220
220
221
+ The following sections describe the mechanisms put in place to run
222
+ background maintenance by `git maintenance start` and how to customize
223
+ them.
224
+
225
+ BACKGROUND MAINTENANCE ON POSIX SYSTEMS
226
+ ---------------------------------------
227
+
228
+ The standard mechanism for scheduling background tasks on POSIX systems
229
+ is cron(8). This tool executes commands based on a given schedule. The
230
+ current list of user-scheduled tasks can be found by running `crontab -l`.
231
+ The schedule written by `git maintenance start` is similar to this:
232
+
233
+ -----------------------------------------------------------------------
234
+ # BEGIN GIT MAINTENANCE SCHEDULE
235
+ # The following schedule was created by Git
236
+ # Any edits made in this region might be
237
+ # replaced in the future by a Git command.
238
+
239
+ 0 1-23 * * * "/<path>/git" --exec-path="/<path>" for-each-repo --config=maintenance.repo maintenance run --schedule=hourly
240
+ 0 0 * * 1-6 "/<path>/git" --exec-path="/<path>" for-each-repo --config=maintenance.repo maintenance run --schedule=daily
241
+ 0 0 * * 0 "/<path>/git" --exec-path="/<path>" for-each-repo --config=maintenance.repo maintenance run --schedule=weekly
242
+
243
+ # END GIT MAINTENANCE SCHEDULE
244
+ -----------------------------------------------------------------------
245
+
246
+ The comments are used as a region to mark the schedule as written by Git.
247
+ Any modifications within this region will be completely deleted by
248
+ `git maintenance stop` or overwritten by `git maintenance start`.
249
+
250
+ The `crontab` entry specifies the full path of the `git` executable to
251
+ ensure that the executed `git` command is the same one with which
252
+ `git maintenance start` was issued independent of `PATH`. If the same user
253
+ runs `git maintenance start` with multiple Git executables, then only the
254
+ latest executable is used.
255
+
256
+ These commands use `git for-each-repo --config=maintenance.repo` to run
257
+ `git maintenance run --schedule=<frequency>` on each repository listed in
258
+ the multi-valued `maintenance.repo` config option. These are typically
259
+ loaded from the user-specific global config. The `git maintenance` process
260
+ then determines which maintenance tasks are configured to run on each
261
+ repository with each `<frequency>` using the `maintenance.<task>.schedule`
262
+ config options. These values are loaded from the global or repository
263
+ config values.
264
+
265
+ If the config values are insufficient to achieve your desired background
266
+ maintenance schedule, then you can create your own schedule. If you run
267
+ `crontab -e`, then an editor will load with your user-specific `cron`
268
+ schedule. In that editor, you can add your own schedule lines. You could
269
+ start by adapting the default schedule listed earlier, or you could read
270
+ the crontab(5) documentation for advanced scheduling techniques. Please
271
+ do use the full path and `--exec-path` techniques from the default
272
+ schedule to ensure you are executing the correct binaries in your
273
+ schedule.
274
+
275
+
276
+ BACKGROUND MAINTENANCE ON MACOS SYSTEMS
277
+ ---------------------------------------
278
+
279
+ While macOS technically supports `cron`, using `crontab -e` requires
280
+ elevated privileges and the executed process does not have a full user
281
+ context. Without a full user context, Git and its credential helpers
282
+ cannot access stored credentials, so some maintenance tasks are not
283
+ functional.
284
+
285
+ Instead, `git maintenance start` interacts with the `launchctl` tool,
286
+ which is the recommended way to schedule timed jobs in macOS. Scheduling
287
+ maintenance through `git maintenance (start|stop)` requires some
288
+ `launchctl` features available only in macOS 10.11 or later.
289
+
290
+ Your user-specific scheduled tasks are stored as XML-formatted `.plist`
291
+ files in `~/Library/LaunchAgents/`. You can see the currently-registered
292
+ tasks using the following command:
293
+
294
+ -----------------------------------------------------------------------
295
+ $ ls ~/Library/LaunchAgents/org.git-scm.git*
296
+ org.git-scm.git.daily.plist
297
+ org.git-scm.git.hourly.plist
298
+ org.git-scm.git.weekly.plist
299
+ -----------------------------------------------------------------------
300
+
301
+ One task is registered for each `--schedule=<frequency>` option. To
302
+ inspect how the XML format describes each schedule, open one of these
303
+ `.plist` files in an editor and inspect the `<array>` element following
304
+ the `<key>StartCalendarInterval</key>` element.
305
+
306
+ `git maintenance start` will overwrite these files and register the
307
+ tasks again with `launchctl`, so any customizations should be done by
308
+ creating your own `.plist` files with distinct names. Similarly, the
309
+ `git maintenance stop` command will unregister the tasks with `launchctl`
310
+ and delete the `.plist` files.
311
+
312
+ To create more advanced customizations to your background tasks, see
313
+ launchctl.plist(5) for more information.
314
+
315
+
316
+ BACKGROUND MAINTENANCE ON WINDOWS SYSTEMS
317
+ -----------------------------------------
318
+
319
+ Windows does not support `cron` and instead has its own system for
320
+ scheduling background tasks. The `git maintenance start` command uses
321
+ the `schtasks` command to submit tasks to this system. You can inspect
322
+ all background tasks using the Task Scheduler application. The tasks
323
+ added by Git have names of the form `Git Maintenance (<frequency>)`.
324
+ The Task Scheduler GUI has ways to inspect these tasks, but you can also
325
+ export the tasks to XML files and view the details there.
326
+
327
+ Note that since Git is a console application, these background tasks
328
+ create a console window visible to the current user. This can be changed
329
+ manually by selecting the "Run whether user is logged in or not" option
330
+ in Task Scheduler. This change requires a password input, which is why
331
+ `git maintenance start` does not select it by default.
332
+
333
+ If you want to customize the background tasks, please rename the tasks
334
+ so future calls to `git maintenance (start|stop)` do not overwrite your
335
+ custom tasks.
336
+
221
337
222
338
GIT
223
339
---
0 commit comments