| 1 | git-interpret-trailers(1) |
| 2 | ========================= |
| 3 | |
| 4 | NAME |
| 5 | ---- |
| 6 | git-interpret-trailers - Add or parse structured information in commit messages |
| 7 | |
| 8 | SYNOPSIS |
| 9 | -------- |
| 10 | [synopsis] |
| 11 | git interpret-trailers [--in-place] [--trim-empty] |
| 12 | [(--trailer (<key>|<key-alias>)[(=|:)<value>])...] |
| 13 | [--parse] [<file>...] |
| 14 | |
| 15 | DESCRIPTION |
| 16 | ----------- |
| 17 | Add or parse _trailer_ lines that look similar to RFC 822 e-mail |
| 18 | headers, at the end of the otherwise free-form part of a commit |
| 19 | message. For example, in the following commit message |
| 20 | |
| 21 | ------------------------------------------------ |
| 22 | subject |
| 23 | |
| 24 | Lorem ipsum dolor sit amet, consectetur adipiscing elit. |
| 25 | |
| 26 | Signed-off-by: Alice <alice@example.com> |
| 27 | Signed-off-by: Bob <bob@example.com> |
| 28 | ------------------------------------------------ |
| 29 | |
| 30 | the last two lines starting with `Signed-off-by` are trailers. |
| 31 | |
| 32 | This command reads commit messages from either the |
| 33 | _<file>_ arguments or the standard input if no _<file>_ is specified. |
| 34 | If `--parse` is specified, the output consists of the parsed trailers |
| 35 | coming from the input, without influencing them with any command line |
| 36 | options or configuration variables. |
| 37 | |
| 38 | Otherwise, this command applies `trailer.<key-alias>` configuration |
| 39 | variables (which could potentially add new trailers, as well as |
| 40 | reposition them), as well as any command line arguments that can |
| 41 | override configuration variables (such as `--trailer=...` which could |
| 42 | also add new trailers), to each input file. The result is emitted on the |
| 43 | standard output. |
| 44 | |
| 45 | This command can also operate on the output of linkgit:git-format-patch[1], |
| 46 | which is more elaborate than a plain commit message. Namely, such output |
| 47 | includes a commit message (as above), a `---` divider line, and a patch part. |
| 48 | For these inputs, the divider and patch parts are not modified by |
| 49 | this command and are emitted as is on the output, unless |
| 50 | `--no-divider` is specified. |
| 51 | |
| 52 | Some configuration variables control the way the `--trailer` arguments |
| 53 | are applied to each input and the way any existing trailer in |
| 54 | the input is changed. They also make it possible to |
| 55 | automatically add some trailers. |
| 56 | |
| 57 | By default, a `<key>=<value>` or `<key>:<value>` argument given |
| 58 | using `--trailer` will be appended after the existing trailers only if |
| 59 | the last trailer has a different (_<key>_, _<value>_) pair (or if there |
| 60 | is no existing trailer). The _<key>_ and _<value>_ parts will be trimmed |
| 61 | to remove starting and trailing whitespace, and the resulting trimmed |
| 62 | _<key>_ and _<value>_ will appear in the output like this: |
| 63 | |
| 64 | ------------------------------------------------ |
| 65 | key: value |
| 66 | ------------------------------------------------ |
| 67 | |
| 68 | This means that the trimmed _<key>_ and _<value>_ will be separated by |
| 69 | "`:`{nbsp}" (one colon followed by one space). |
| 70 | |
| 71 | For convenience, a _<key-alias>_ can be configured to make using `--trailer` |
| 72 | shorter to type on the command line. This can be configured using the |
| 73 | `trailer.<key-alias>.key` configuration variable. The _<key-alias>_ must be a prefix |
| 74 | of the full _<key>_ string, although case sensitivity does not matter. For |
| 75 | example, if you have |
| 76 | |
| 77 | ------------------------------------------------ |
| 78 | trailer.sign.key "Signed-off-by: " |
| 79 | ------------------------------------------------ |
| 80 | |
| 81 | in your configuration, you only need to specify `--trailer="sign: foo"` |
| 82 | on the command line instead of `--trailer="Signed-off-by: foo"`. |
| 83 | |
| 84 | By default the new trailer will appear at the end of all the existing |
| 85 | trailers. If there is no existing trailer, the new trailer will appear |
| 86 | at the end of the input. A blank line will be added before the new |
| 87 | trailer if there isn't one already. |
| 88 | |
| 89 | Existing trailers are extracted from the input by looking for |
| 90 | a group of one or more lines that (i) is all trailers, or (ii) contains at |
| 91 | least one Git-generated or user-configured trailer and consists of at |
| 92 | least 25% trailers. |
| 93 | The group must be preceded by one or more empty (or whitespace-only) lines. |
| 94 | The group must either be at the end of the input or be the last |
| 95 | non-whitespace lines before a line that starts with `---` (followed by a |
| 96 | space or the end of the line). |
| 97 | |
| 98 | When reading trailers, there can be no whitespace before or inside the |
| 99 | _<key>_, but any number of regular space and tab characters are allowed |
| 100 | between the _<key>_ and the separator. There can be whitespaces before, |
| 101 | inside or after the _<value>_. The _<value>_ may be split over multiple lines |
| 102 | with each subsequent line starting with at least one whitespace, like |
| 103 | the "folding" in RFC 822. Example: |
| 104 | |
| 105 | ------------------------------------------------ |
| 106 | key: This is a very long value, with spaces and |
| 107 | newlines in it. |
| 108 | ------------------------------------------------ |
| 109 | |
| 110 | Note that trailers do not follow (nor are they intended to follow) many of the |
| 111 | rules for RFC 822 headers. For example they do not follow the encoding rule. |
| 112 | |
| 113 | OPTIONS |
| 114 | ------- |
| 115 | `--in-place`:: |
| 116 | `--no-in-place`:: |
| 117 | Edit the files in place. The default is `--no-in-place`. |
| 118 | |
| 119 | `--trim-empty`:: |
| 120 | `--no-trim-empty`:: |
| 121 | If the _<value>_ part of any trailer contains only whitespace, |
| 122 | the whole trailer will be removed from the output. |
| 123 | This applies to existing trailers as well as new trailers. |
| 124 | + |
| 125 | The default is `--no-trim-empty`. |
| 126 | |
| 127 | `--trailer=<key>[(=|:)<value>]`:: |
| 128 | `--no-trailer`:: |
| 129 | Specify a (_<key>_, _<value>_) pair that should be applied as a |
| 130 | trailer to the inputs. See the description of this command. Can |
| 131 | be given multiple times. |
| 132 | + |
| 133 | Use `--no-trailer` to reset the list. |
| 134 | |
| 135 | `--where=<placement>`:: |
| 136 | `--no-where`:: |
| 137 | Specify where all new trailers will be added. A setting |
| 138 | provided with `--where` overrides the `trailer.where` and any |
| 139 | applicable `trailer.<key-alias>.where` configuration variables |
| 140 | and applies to all `--trailer` options until the next occurrence of |
| 141 | `--where` or `--no-where`. Possible placements are `after`, |
| 142 | `before`, `end` or `start`. |
| 143 | + |
| 144 | Use `--no-where` to clear the effect of any previous use of `--where`, |
| 145 | such that the relevant configuration variables are no longer overridden. |
| 146 | |
| 147 | `--if-exists=<action>`:: |
| 148 | `--no-if-exists`:: |
| 149 | Specify what action will be performed when there is already at |
| 150 | least one trailer with the same _<key>_ in the input. A setting |
| 151 | provided with `--if-exists` overrides the `trailer.ifExists` and any |
| 152 | applicable `trailer.<key-alias>.ifExists` configuration variables |
| 153 | and applies to all `--trailer` options until the next occurrence of |
| 154 | `--if-exists` or `--no-if-exists`. Possible actions are `addIfDifferent`, |
| 155 | `addIfDifferentNeighbor`, `add`, `replace` and `doNothing`. |
| 156 | + |
| 157 | Use `--no-if-exists` to clear the effect of any previous use of |
| 158 | `--if-exists`, such that the relevant configuration variables are no |
| 159 | longer overridden. |
| 160 | |
| 161 | `--if-missing=<action>`:: |
| 162 | `--no-if-missing`:: |
| 163 | Specify what action will be performed when there is no other |
| 164 | trailer with the same _<key>_ in the input. A setting |
| 165 | provided with `--if-missing` overrides the `trailer.ifMissing` and any |
| 166 | applicable `trailer.<key-alias>.ifMissing` configuration variables |
| 167 | and applies to all `--trailer` options until the next occurrence of |
| 168 | `--if-missing` or `--no-if-missing`. Possible actions are |
| 169 | `doNothing` or `add`. |
| 170 | + |
| 171 | Use `--no-if-missing` to clear the effect of any previous use of |
| 172 | `--if-missing`, such that the relevant configuration variables are no |
| 173 | longer overridden. |
| 174 | |
| 175 | `--only-trailers`:: |
| 176 | `--no-only-trailers`:: |
| 177 | Output only the trailers, not any other parts of the |
| 178 | input. The default is `--no-only-trailers`. |
| 179 | |
| 180 | `--only-input`:: |
| 181 | `--no-only-input`:: |
| 182 | Output only trailers that exist in the input; do not add any |
| 183 | from the command-line or by applying `trailer.<key-alias>` configuration |
| 184 | variables. The default is `--no-only-input`. |
| 185 | |
| 186 | `--unfold`:: |
| 187 | `--no-unfold`:: |
| 188 | If a trailer has a value that runs over multiple lines (aka "folded"), |
| 189 | reformat the value into a single line. The default is `--no-unfold`. |
| 190 | |
| 191 | `--parse`:: |
| 192 | A convenience alias for `--only-trailers --only-input |
| 193 | --unfold`. This makes it easier to only see the trailers coming from the |
| 194 | input without influencing them with any command line options or |
| 195 | configuration variables, while also making the output machine-friendly with |
| 196 | `--unfold`. |
| 197 | + |
| 198 | There is no convenience alias to negate this alias. |
| 199 | |
| 200 | `--divider`:: |
| 201 | `--no-divider`:: |
| 202 | Treat `---` as the end of the commit message. This is the default. |
| 203 | Use `--no-divider` when you know your input contains just the |
| 204 | commit message itself (and not an email or the output of |
| 205 | linkgit:git-format-patch[1]). |
| 206 | |
| 207 | CONFIGURATION VARIABLES |
| 208 | ----------------------- |
| 209 | |
| 210 | include::includes/cmd-config-section-all.adoc[] |
| 211 | |
| 212 | include::config/trailer.adoc[] |
| 213 | |
| 214 | EXAMPLES |
| 215 | -------- |
| 216 | |
| 217 | * Configure a `sign` trailer with a `Signed-off-by` key, and then |
| 218 | add two of these trailers to a commit message file: |
| 219 | + |
| 220 | ------------ |
| 221 | $ git config trailer.sign.key "Signed-off-by" |
| 222 | $ cat msg.txt |
| 223 | subject |
| 224 | |
| 225 | body text |
| 226 | $ git interpret-trailers --trailer 'sign: Alice <alice@example.com>' --trailer 'sign: Bob <bob@example.com>' <msg.txt |
| 227 | subject |
| 228 | |
| 229 | body text |
| 230 | |
| 231 | Signed-off-by: Alice <alice@example.com> |
| 232 | Signed-off-by: Bob <bob@example.com> |
| 233 | ------------ |
| 234 | |
| 235 | * Use the `--in-place` option to edit a commit message file in place: |
| 236 | + |
| 237 | ------------ |
| 238 | $ cat msg.txt |
| 239 | subject |
| 240 | |
| 241 | body text |
| 242 | |
| 243 | Signed-off-by: Bob <bob@example.com> |
| 244 | $ git interpret-trailers --trailer 'Acked-by: Alice <alice@example.com>' --in-place msg.txt |
| 245 | $ cat msg.txt |
| 246 | subject |
| 247 | |
| 248 | body text |
| 249 | |
| 250 | Signed-off-by: Bob <bob@example.com> |
| 251 | Acked-by: Alice <alice@example.com> |
| 252 | ------------ |
| 253 | |
| 254 | * Extract the last commit as a patch, and add a `Cc` and a |
| 255 | `Reviewed-by` trailer to it: |
| 256 | + |
| 257 | ------------ |
| 258 | $ git format-patch -1 |
| 259 | 0001-foo.patch |
| 260 | $ git interpret-trailers --trailer 'Cc: Alice <alice@example.com>' --trailer 'Reviewed-by: Bob <bob@example.com>' 0001-foo.patch >0001-bar.patch |
| 261 | ------------ |
| 262 | |
| 263 | * Configure a `sign` trailer with a command to automatically add a |
| 264 | "`Signed-off-by:`{nbsp}" with the author information only if there is no |
| 265 | "`Signed-off-by:`{nbsp}" already, and show how it works: |
| 266 | + |
| 267 | ------------ |
| 268 | $ cat msg1.txt |
| 269 | subject |
| 270 | |
| 271 | body text |
| 272 | $ git config trailer.sign.key "Signed-off-by: " |
| 273 | $ git config trailer.sign.ifmissing add |
| 274 | $ git config trailer.sign.ifexists doNothing |
| 275 | $ git config trailer.sign.cmd 'echo "$(git config user.name) <$(git config user.email)>"' |
| 276 | $ git interpret-trailers --trailer sign <msg1.txt |
| 277 | subject |
| 278 | |
| 279 | body text |
| 280 | |
| 281 | Signed-off-by: Bob <bob@example.com> |
| 282 | $ cat msg2.txt |
| 283 | subject |
| 284 | |
| 285 | body text |
| 286 | |
| 287 | Signed-off-by: Alice <alice@example.com> |
| 288 | $ git interpret-trailers --trailer sign <msg2.txt |
| 289 | subject |
| 290 | |
| 291 | body text |
| 292 | |
| 293 | Signed-off-by: Alice <alice@example.com> |
| 294 | ------------ |
| 295 | |
| 296 | * Configure a `fix` trailer with a key that contains a `#` and no |
| 297 | space after this character, and show how it works: |
| 298 | + |
| 299 | ------------ |
| 300 | $ git config trailer.separators ":#" |
| 301 | $ git config trailer.fix.key "Fix #" |
| 302 | $ echo "subject" | git interpret-trailers --trailer fix=42 |
| 303 | subject |
| 304 | |
| 305 | Fix #42 |
| 306 | ------------ |
| 307 | |
| 308 | * Configure a `help` trailer with a cmd use a script `glog-find-author` |
| 309 | which search specified author identity from git log in git repository |
| 310 | and show how it works: |
| 311 | + |
| 312 | ------------ |
| 313 | $ cat ~/bin/glog-find-author |
| 314 | #!/bin/sh |
| 315 | test -n "$1" && git log --author="$1" --pretty="%an <%ae>" -1 || true |
| 316 | $ cat msg.txt |
| 317 | subject |
| 318 | |
| 319 | body text |
| 320 | $ git config trailer.help.key "Helped-by: " |
| 321 | $ git config trailer.help.ifExists "addIfDifferentNeighbor" |
| 322 | $ git config trailer.help.cmd "~/bin/glog-find-author" |
| 323 | $ git interpret-trailers --trailer="help:Junio" --trailer="help:Couder" <msg.txt |
| 324 | subject |
| 325 | |
| 326 | body text |
| 327 | |
| 328 | Helped-by: Junio C Hamano <gitster@pobox.com> |
| 329 | Helped-by: Christian Couder <christian.couder@gmail.com> |
| 330 | ------------ |
| 331 | |
| 332 | * Configure a `ref` trailer with a cmd use a script `glog-grep` |
| 333 | to grep last relevant commit from git log in the git repository |
| 334 | and show how it works: |
| 335 | + |
| 336 | ------------ |
| 337 | $ cat ~/bin/glog-grep |
| 338 | #!/bin/sh |
| 339 | test -n "$1" && git log --grep "$1" --pretty=reference -1 || true |
| 340 | $ cat msg.txt |
| 341 | subject |
| 342 | |
| 343 | body text |
| 344 | $ git config trailer.ref.key "Reference-to: " |
| 345 | $ git config trailer.ref.ifExists "replace" |
| 346 | $ git config trailer.ref.cmd "~/bin/glog-grep" |
| 347 | $ git interpret-trailers --trailer="ref:Add copyright notices." <msg.txt |
| 348 | subject |
| 349 | |
| 350 | body text |
| 351 | |
| 352 | Reference-to: 8bc9a0c769 (Add copyright notices., 2005-04-07) |
| 353 | ------------ |
| 354 | |
| 355 | * Configure a `see` trailer with a command to show the subject of a |
| 356 | commit that is related, and show how it works: |
| 357 | + |
| 358 | ------------ |
| 359 | $ cat msg.txt |
| 360 | subject |
| 361 | |
| 362 | body text |
| 363 | |
| 364 | see: HEAD~2 |
| 365 | $ cat ~/bin/glog-ref |
| 366 | #!/bin/sh |
| 367 | git log -1 --oneline --format="%h (%s)" --abbrev-commit --abbrev=14 |
| 368 | $ git config trailer.see.key "See-also: " |
| 369 | $ git config trailer.see.ifExists "replace" |
| 370 | $ git config trailer.see.ifMissing "doNothing" |
| 371 | $ git config trailer.see.cmd "glog-ref" |
| 372 | $ git interpret-trailers --trailer=see <msg.txt |
| 373 | subject |
| 374 | |
| 375 | body text |
| 376 | |
| 377 | See-also: fe3187489d69c4 (subject of related commit) |
| 378 | ------------ |
| 379 | |
| 380 | * Configure a commit template with some trailers with empty values |
| 381 | (using sed to show and keep the trailing spaces at the end of the |
| 382 | trailers), then configure a commit-msg hook that uses |
| 383 | git-interpret-trailers(1) to remove trailers with empty values and to |
| 384 | add a `git-version` trailer: |
| 385 | + |
| 386 | ------------ |
| 387 | $ cat temp.txt |
| 388 | ***subject*** |
| 389 | |
| 390 | ***message*** |
| 391 | |
| 392 | Fixes: Z |
| 393 | Cc: Z |
| 394 | Reviewed-by: Z |
| 395 | Signed-off-by: Z |
| 396 | $ sed -e 's/ Z$/ /' temp.txt > commit_template.txt |
| 397 | $ git config commit.template commit_template.txt |
| 398 | $ cat .git/hooks/commit-msg |
| 399 | #!/bin/sh |
| 400 | git interpret-trailers --trim-empty --trailer "git-version: \$(git describe)" "\$1" > "\$1.new" |
| 401 | mv "\$1.new" "\$1" |
| 402 | $ chmod +x .git/hooks/commit-msg |
| 403 | ------------ |
| 404 | |
| 405 | SEE ALSO |
| 406 | -------- |
| 407 | linkgit:git-commit[1], linkgit:git-format-patch[1], linkgit:git-config[1] |
| 408 | |
| 409 | GIT |
| 410 | --- |
| 411 | Part of the linkgit:git[1] suite |