• Stars
    star
    564
  • Rank 78,449 (Top 2 %)
  • Language
    Rust
  • License
    MIT License
  • Created about 8 years ago
  • Updated over 1 year ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

The Git Commit Message and Changelog Generation Framework 📖

git-journal 📖

Build Status Build status Coverage Status dependency status Crates.io doc.rs master doc gitjournal License MIT Join the chat at https://gitter.im/git-journal/Lobby

The Git Commit Message and Changelog Generation Framework

Table of contents:


TL;DR

Maintaining changelogs can be time-consuming, especially when multiple persons work on the same project. If you maintain a separate file, merge conflicts and additional release work is sure to follow.

Sometimes complete entries are lost during merge conflict resolution, people forget to mention something or links between issues and actual commits are missing.

It would be great, if we could use the commit history of git to generate a beautiful changelog without any additional work needed.

This is where git-journal jumps in.

To ensure this auto-generation a framework to write more sensible commit messages is needed. Single commit messages should contain one logical change of the project which is described in a standardized way. This results in a much cleaner git history and provides contributors more information about the actual change.

The theoretical base consists of two RFCs:

Installation

To use git-journal as a git extension a Rust installation is needed including the package manager cargo. Different package managers will provide these as well, for example via Pacman on Arch Linux:

sudo pacman -S rust cargo

For a super easy installation it is also possible to use rustup. Once these two dependencies are installed, git-journal can be installed via:

cargo install git-journal

After adapting your $PATH variable to search also within ~/.cargo/bin it should be possible to run it by invoking git journal.

Usage

The binary git-journal depends on the Rust library gitjournal, which also can be used independently from the binary application to write customized solutions. This repository will be used as an example for the following explanations.

Default output

If you run git journal anywhere inside this repository, the output will be a nice looking Markdown formatted changelog based on your repositories git log:

> git journal
[git-journal] [INFO] Skipping commit: Summary parsing: 'Merge branch 'test_branch''
[git-journal] [OKAY] Parsing done.

# Unreleased (2016-09-18):
- [Added] file4 again
    This paragraph explains the change in detail
    - [Fixed] multiple issues
    - [Removed] not needed things
- [Removed] file4.txt
- [Added] file4.txt
- [Added] file1.txt again
- [Removed] file1.txt

Fixes:
#1, #2

# v2 (2016-09-12):
- [Added] file3.txt

All commits are sorted by time, which means that the newest elements occur at the top. The parsing of the commit message will be done regarding RFC0001, which describes the different syntax elements within a commit message. Categories ([Added], [Fixed], ...) are automatically wrapped in square brackets if available. It is also possible to define own categories within the configuration file. The journal automatically lists the log from the last release and the unreleased entries.

The footers of the commit messages (described in RFC0001) are automatically accumulated and printed after the changelog list ordered by their values. It is also possible to skip the unreleased entries:

> git journal -u
[git-journal] [OKAY] Parsing done.

# v2 (2016-09-12):
- [Added] file3.txt

Using a specific commit range in the format REV..REV or a different starting point than HEAD for parsing can also be done:

> git journal v1
> git journal v2
> git journal v1...HEAD^

It is also possible to print all releases (git tags) with -a, the past n releases via -n <COUNT>:

> git journal -a
[git-journal] [INFO] Skipping commit: Summary parsing: 'Merge branch 'test_branch''
[git-journal] [OKAY] Parsing done.

# Unreleased (2016-09-18):
- [Added] file4 again
    This paragraph explains the change in detail
    - [Fixed] multiple issues
    - [Removed] not needed things
- [Removed] file4.txt
- [Added] file4.txt
- [Added] file1.txt again
- [Removed] file1.txt

# v2 (2016-09-12):
- [Added] file3.txt

# v1 (2016-09-12):
- [Added] file2.txt
- [Added] file1.txt
> git journal -un1
[git-journal] [OKAY] Parsing done.

# v2 (2016-09-12):
- [Added] file3.txt

Beside the usual detailed log a short version (-s) exists, which just uses the commit summary:

> git journal -as
[git-journal] [INFO] Skipping commit: Summary parsing: 'Merge branch 'test_branch''
[git-journal] [OKAY] Parsing done.

# Unreleased (2016-09-18):
- [Added] file4 again
- [Removed] file4.txt
- [Added] file4.txt
- [Added] file1.txt again
- [Removed] file1.txt

# v2 (2016-09-12):
- [Added] file3.txt

# v1 (2016-09-12):
- [Added] file2.txt
- [Added] file1.txt

It also possible to append the output of the journal to a file (-o), which will be separated by a newline (---) for each git journal invocation. Git tags with a specific patterns like rc will be excluded automatically, which can be customized via -e.

For more information please refer to the help git journal -h.

Template output

The design of commit message templates is described in RFC0002. From now on we are using this template for the test repository:

[[tag]]
tag = "default"
name = "Default"

[[tag]]
tag = "tag1"
name = "Section 1"

[[tag]]
[[tag.subtag]]
tag = "tag2"
name = "Subsection 1"
footers = ["Fixes"]

To use such a template just use the -t option:

> git journal -t CHANGELOG.toml
[git-journal] [INFO] Skipping commit: Summary parsing: 'Merge branch 'test_branch''
[git-journal] [OKAY] Parsing done.

# Unreleased (2016-09-21):
## Default
- [Removed] file3.txt
- [Removed] file4.txt
- [Removed] file5.txt
- [Added] new .gitjournal
- [Improved] file5.txt
- [Fixed] this
- [Removed] that
- [Added] .gitjournal.toml file
- [Removed] not needed things
- [Removed] file4.txt
- [Added] file4.txt
- [Added] file1.txt again
- [Removed] file1.txt

## Section 1
- [Added] file4 again
- This paragraph explains the change in detail

### Subsection 1
- [Fixed] multiple issues

Fixes:
#1, #2, #1, #2, #3, #5, #6, #7

# v2 (2016-09-12):
## Default
- [Added] file3.txt

Everything which is untagged will go into the default section. The name of tag1 will be mapped to Section 1 and tag2 is a subtag of tag1 (see the markdown header). This also means that it is now possible that list items are uncategorized since the templating engine gives the possibility to split commits into multiple pieces. Parsed paragraphs are converted to single list items to always provide a clean markdown. The footers are specified as an toml array of strings which will output the selected footer keys at the correct position of the log. Please consider that the accumulation of the footers are related to the complete tag, not just the section where there printed. Other command line options like in the default output are available as well.

It is also possible to add a custom header or footer text to every output or every tag. For more information please read RFC0002.

Commit message preparation and verification

To use the automatic commit message preparation and verification the git journal setup has to be executed on every local repository:

> git journal setup
[git-journal] [OKAY] Defaults written to '.gitjournal.toml' file.
[git-journal] [OKAY] Git hook installed to '.git/hooks/commit-msg'.
[git-journal] [OKAY] Git hook installed to '.git/hooks/prepare-commit-msg'.
[git-journal] [OKAY] Installed bash completions to the path.
[git-journal] [OKAY] Installed fish completions to the path.
[git-journal] [OKAY] Installed zsh completions to the path.

If there already exists these hooks git-journal tries to append the needed commands, which has to be verified by hand afterwards. The generated command line completions for bash and fish needs to be put in the correct directory of your shell. The default configuration file is a toml file which represents this structure. A default configuration with comments can also be found here.

If the setup is done git-journal will verify your inserted commit message as well as doing a commit message preparation. For example, if we are now trying to commit something which can not be parsed:

> touch my_file
> git add my_file
> git commit -m "This commit contains no cactegory"
[git-journal] [ERROR] Commit message preparation failed: GitJournal: Parser: Summary parsing: 'This commit contains no cactegory'

Since we are using the -m flag there is no chance for the user to edit the message any more and git-journal will reject it. If we are using a commit message editor via the usual git commit without the -m we will get a default commit message template:

JIRA-1234 Added ...

# Add a more detailed description if needed

# - Added ...
# - Changed ...
# - Fixed ...
# - Improved ...
# - Removed ...

The JIRA-1234 prefix is just the default and can be configured via the .gitjournal.toml file. If the submitted commit message is also invalid we will get an error like this:

[git-journal] [ERROR] Commit message invalid: GitJournal: Parser: Summary parsing: 'This commit message is also invalid'

If everything went fine it should look like this:

> git commit -m "Added my_file"
[git-journal] [OKAY] Commit message prepared.
[git-journal] [OKAY] Commit message valid.
[master 1b1fcad] Added my_file
 1 file changed, 0 insertions(+), 0 deletions(-)
 create mode 100644 my_file

If a default template is configured then git-journal will also check the available tags of the template against your commit message tags. So there will be an error if one of the tags within the commit message is not available within the defined template:

[git-journal] [WARN] These tags are not part of the default template: 'tag1'.
[git-journal] [ERROR] Commit message invalid: GitJournal: Verify: Not all tags exists in the default template.

This means in detail that git-journal will build up two gates (one for preparation and one for verification) during doing the commit by the user. This graphic will sum up where git-journal will take influence on the local git repository:

Current Features

  • General
    • Generation of completions for bash, fish and zsh shell during setup.
    • Custom category support for commit preparation, validation and output (categories).
    • Automatic multi threading support for the parsing.
  • Journal generation and output
    • Automatic up-level repository search if a sub path of a git repository was specified.
    • Custom commit ranges or different git commit starting points for parsing.
    • Run in a different specified path than the current working directory (-p).
    • Parse and print the complete history (-a) or the past n releases (-n).
    • Print a short version of the commit history based on the commit message summary (-s).
    • Output the parsed log in valid Markdown to the command line or a file (-o).
    • Custom git tag exclude pattern, e.g. rc tags (-e).
    • Enable/Disable debug message output (enable_debug).
    • Enable/Disable colored output via the command line (colored_output).
    • Automatic wrapping of commit message categories in square brackets.
    • Templating support including tag and name mapping (default_template).
    • Support for accumulating footer data (also for templating engine).
    • Different sorting methods ("date" and "name") for the default and template based output (sort_by).
    • Support for custom header and footer fields within templates with multiple or single output.
    • Generation of default templates based on the parsing results (-g).
    • Commit hash links for commits in standard and template output (show_commit_hash).
    • Support for custom category delimiters (category_delimiters).
  • Preparation and Verification of commit messages
    • Automatic installation of git hooks inside the local repository.
    • Generation of default configuration file during setup.
    • Commit message validation based on implemented parser.
    • Message preparation with custom commit prefix (template_prefix).
    • Differentiation between amended and new commits.
    • Use the tags from the default template for the commit message verification.

Planned features and improvements

  • There are no bigger features planned yet.

Contributing

You want to contribute to this project? Wow, thanks! So please just fork it and send me a pull request.

More Repositories

1

webapp.rs

A web application completely written in Rust. 🌍
Rust
2,160
star
2

kubernix

Single dependency Kubernetes clusters for local testing, experimenting and development
Rust
710
star
3

demystifying-containers

A series of blog posts and talks about the world of containers 📦
Python
699
star
4

indextree

Arena based tree 🌲 structure by using indices instead of reference counted pointers
Rust
533
star
5

demo

A framework for performing live pre-recorded command line demos in the wild 📼
Go
272
star
6

nn

A tiny neural network 🧠
Haskell
121
star
7

rain

Visualize vertical data inside your terminal 💦
Rust
88
star
8

ccli

Command line parsing in go, with coloring support 🌈
Go
83
star
9

func

Functional additions to C
C++
55
star
10

dotfiles

My hand crafted .dotfiles 🤚🛠❤️
Shell
48
star
11

performabot

Continuous performance analysis reports for software projects 🤖
Haskell
41
star
12

kmod

A Linux kernel module written in Rust
Rust
34
star
13

craft

Cargo inspired build system for C based projects
Rust
32
star
14

kubeflow-data-science-on-steroids

The blog post about Kubeflow, including all materials
Jupyter Notebook
30
star
15

go-modiff

Command line tool for diffing go module dependency changes between versions 📔
Go
29
star
16

yew-router

Router extension to yew
Rust
27
star
17

peel-ip

Packet parsing for the Internet Protocol Suite 📦
Rust
26
star
18

microservice-rs

Microservice template using Rust and Cap'n Proto RPCs.
Rust
26
star
19

peel

Dynamic packet parsing within trees 🌲🌳🌴
Rust
22
star
20

fosdem20

Demo material used for the Podman talk at FOSDEM 2020
Go
22
star
21

stm32h7-rs

Rust on STM32H7 Microcontrollers
Rust
14
star
22

syscall-recorder

ebpf syscall recording demo project
C
9
star
23

unibar

A GPU accelerated status bar written in Rust 🦄
Rust
8
star
24

seer

A collaborative resource planning tool 🔮
Haskell
5
star
25

fastcmp

A fast byte slice comparison library
Rust
5
star
26

path

IP based connection identification and tracing 👟
Rust
5
star
27

webapp.hs

Haskell
4
star
28

umask-observe

umask observability based on bpftrace for OpenShift nodes
Shell
3
star
29

mowl

My own little logger ✏️
Rust
3
star
30

crio-demos

CRI-O Demonstration Material
Go
3
star
31

failure

Pure and type driven error handling for Haskell
Haskell
2
star
32

build-rust

The Docker based Rust build toolchain
Dockerfile
2
star
33

pidwatch-rs

C
2
star
34

rapidc

Rust
2
star
35

kubeflow-notebook-gpu

Kubeflow GPU Notebook Container Image
Dockerfile
2
star
36

pinns.rs

A simple utility to pin Linux namespaces
Rust
2
star
37

backingFsBlockDev

Go
1
star
38

peeler

Peel your network traffic
Rust
1
star
39

tunneldevice

Playing around with tunnel devices in Rust
Rust
1
star
40

build-haskell

The Docker based Haskell build toolchain
Dockerfile
1
star
41

go-docgen

A markdown and man page documentation generator for go applications
Go
1
star
42

netfilter_kmod

Playing around with the netfilter within the kernel
C
1
star
43

ci

Haskell
1
star
44

netlink_kmod

Playing around with routing netlinks inside the kernel
C
1
star
45

seccomp-oci-artifact-demo

Go
1
star
46

byopki

Bring Your Own Public Key Infrastructure for container signing and verification demo
Shell
1
star