wip(build): moved changelog into build as a container
This commit is contained in:
parent
ee8d4f1bd4
commit
74d7ceea1b
423
build/conventi/conventi.sh
Executable file
423
build/conventi/conventi.sh
Executable file
@ -0,0 +1,423 @@
|
|||||||
|
#!/usr/bin/env sh
|
||||||
|
|
||||||
|
config_file=.version.json
|
||||||
|
changelog_file=CHANGELOG.md
|
||||||
|
changelog_header="# Changelog
|
||||||
|
|
||||||
|
All notable changes to this project will be documented in this file. See [Conventional Commits](https://www.conventionalcommits.org/en/v1.0.0/) for commit guidelines.
|
||||||
|
|
||||||
|
This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||||
|
|
||||||
|
----
|
||||||
|
"
|
||||||
|
|
||||||
|
reverse() {
|
||||||
|
if which tac >/dev/null 2>&1; then
|
||||||
|
tac
|
||||||
|
else
|
||||||
|
tail -r
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
generate_config() {
|
||||||
|
jq --null-input \
|
||||||
|
--arg version "0.0.0" \
|
||||||
|
--arg sha "" \
|
||||||
|
--arg url "$1" \
|
||||||
|
'{ "version": $version, "sha": $sha, "url": $url}' >$config_file
|
||||||
|
}
|
||||||
|
|
||||||
|
update_config() {
|
||||||
|
# store in a var as reading and writing in one go to one file is not good
|
||||||
|
config=$(jq '.sha |= $sha | .version |= $version' --arg sha "$1" --arg version "$2" $config_file)
|
||||||
|
echo "$config" >$config_file
|
||||||
|
}
|
||||||
|
|
||||||
|
get_config_version() {
|
||||||
|
jq '.version' <$config_file | tr -d '"'
|
||||||
|
}
|
||||||
|
|
||||||
|
get_config_sha() {
|
||||||
|
jq '.sha' <$config_file | tr -d '"'
|
||||||
|
}
|
||||||
|
|
||||||
|
get_config_url() {
|
||||||
|
jq '.url' <$config_file | tr -d '"'
|
||||||
|
}
|
||||||
|
|
||||||
|
split_version_string() {
|
||||||
|
version_number=$(echo "$1" | cut -d'-' -f1 | cut -d'+' -f1)
|
||||||
|
pre_release=$(echo "$1" | cut -d'-' -f2 | cut -d'+' -f1)
|
||||||
|
build=$(echo "$1" | cut -d'-' -f2 | cut -d'+' -f2)
|
||||||
|
if [ "$pre_release" = "$1" ]; then
|
||||||
|
pre_release=""
|
||||||
|
fi
|
||||||
|
if [ "$build" = "$1" ] || [ "$build" = "$pre_release" ]; then
|
||||||
|
build=""
|
||||||
|
fi
|
||||||
|
|
||||||
|
major=$(echo "$version_number" | cut -d'.' -f1)
|
||||||
|
minor=$(echo "$version_number" | cut -d'.' -f2)
|
||||||
|
patch=$(echo "$version_number" | cut -d'.' -f3)
|
||||||
|
pre_release_id=$(echo "$pre_release." | cut -d'.' -f2)
|
||||||
|
|
||||||
|
echo "${major:-0} ${minor:-0} ${patch:-0} $build $pre_release_id"
|
||||||
|
}
|
||||||
|
|
||||||
|
calculate_version() {
|
||||||
|
version_string=$(split_version_string "$1")
|
||||||
|
major=$(echo "$version_string" | cut -d' ' -f1)
|
||||||
|
minor=$(echo "$version_string" | cut -d' ' -f2)
|
||||||
|
patch=$(echo "$version_string" | cut -d' ' -f3)
|
||||||
|
pre_release_id=$(echo "$version_string" | cut -d' ' -f5)
|
||||||
|
pre_release=""
|
||||||
|
build=""
|
||||||
|
|
||||||
|
if [ "$2" -ge 100 ]; then
|
||||||
|
major=$((major + 1))
|
||||||
|
minor=0
|
||||||
|
patch=0
|
||||||
|
elif [ "$2" -ge 10 ]; then
|
||||||
|
minor=$((minor + 1))
|
||||||
|
patch=0
|
||||||
|
elif [ "$2" -ge 1 ]; then
|
||||||
|
patch=$((patch + 1))
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$3" = "rc" ]; then
|
||||||
|
if [ -z "$pre_release_identifier" ]; then
|
||||||
|
pre_release_identifier=1
|
||||||
|
else
|
||||||
|
pre_release_identifier=$((pre_release_identifier + 1))
|
||||||
|
fi
|
||||||
|
pre_release="rc.$pre_release_identifier"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$4" = "build" ]; then
|
||||||
|
build="$(git rev-parse --short HEAD)"
|
||||||
|
fi
|
||||||
|
|
||||||
|
version_number="${major}.${minor}.${patch}"
|
||||||
|
if [ -n "$pre_release" ]; then
|
||||||
|
pre_release="-$pre_release"
|
||||||
|
fi
|
||||||
|
if [ -n "$build" ]; then
|
||||||
|
build="+$build"
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "${version_number}${pre_release}${build}"
|
||||||
|
}
|
||||||
|
|
||||||
|
get_git_url() {
|
||||||
|
url=$(git config --get remote.origin.url)
|
||||||
|
if ! echo "$url" | grep -q "^http"; then
|
||||||
|
url=$(echo "$url" | cut -d@ -f2 | sed 's/:/\//')
|
||||||
|
url="https://${url:-localhost}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "$url" | sed 's/\.git$//'
|
||||||
|
}
|
||||||
|
|
||||||
|
get_git_commits() {
|
||||||
|
since_hash=$(get_config_sha)
|
||||||
|
if [ -n "$since_hash" ]; then
|
||||||
|
git rev-list "$since_hash..HEAD"
|
||||||
|
else
|
||||||
|
git rev-list HEAD
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
get_git_commit_hash() {
|
||||||
|
git rev-parse --short "$1"
|
||||||
|
}
|
||||||
|
|
||||||
|
get_git_first_commit_hash() {
|
||||||
|
git rev-list --max-parents=0 --abbrev-commit HEAD
|
||||||
|
}
|
||||||
|
|
||||||
|
get_git_commit_subject() {
|
||||||
|
git show -s --format=%s "$1"
|
||||||
|
}
|
||||||
|
|
||||||
|
get_git_commit_body() {
|
||||||
|
git show -s --format=%b "$1"
|
||||||
|
}
|
||||||
|
|
||||||
|
get_commit_type() {
|
||||||
|
echo "$1" | sed -r -n 's/([a-z]+)(\(?|:?).*/\1/p' | tr '[:upper:]' '[:lower:]'
|
||||||
|
}
|
||||||
|
|
||||||
|
get_commit_scope() {
|
||||||
|
echo "$1" | sed -r -n 's/[a-z]+\(([^)]+)\).*/\1/p'
|
||||||
|
}
|
||||||
|
|
||||||
|
get_commit_description() {
|
||||||
|
echo "$1" | sed -r -n 's/.*:[ ]+(.*)/\1/p'
|
||||||
|
}
|
||||||
|
|
||||||
|
get_commit_footer() {
|
||||||
|
with_colon=$(echo "$1" | sed -n '/^[A-Za-z-]\{1,\}: /,//{p;}')
|
||||||
|
with_hash=$(echo "$1" | sed -n '/^[A-Za-z-]\{1,\} #/,//{p;}')
|
||||||
|
fallback=$(echo "$1" | reverse | awk '/^$/{exit}1' | reverse)
|
||||||
|
|
||||||
|
if [ -z "$with_colon" ] && [ -z "$with_hash" ]; then
|
||||||
|
echo "$fallback"
|
||||||
|
elif [ ${#with_colon} -gt ${#with_hash} ]; then
|
||||||
|
echo "$with_colon"
|
||||||
|
else
|
||||||
|
echo "$with_hash"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
get_commit_body() {
|
||||||
|
pattern=$(get_commit_footer "$1" | head -n 1)
|
||||||
|
if [ -n "$pattern" ]; then
|
||||||
|
echo "$1" | sed -e "/$pattern/,\$d"
|
||||||
|
else
|
||||||
|
echo "$1"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
is_breaking_change() {
|
||||||
|
if echo "$1" | grep -q '!' || echo "$2" | grep -q 'BREAKING[ -]CHANGE: '; then
|
||||||
|
echo 1
|
||||||
|
else
|
||||||
|
echo 0
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
get_breaking_change() {
|
||||||
|
with_colon=$(echo "$1" | sed -n '/^BREAKING[ -]CHANGE: /,/^[A-Za-z-]\{1,\}: /{ s/BREAKING[ -]CHANGE: \(.*\)/\1/; /^[A-Za-z-]\{1,\}: /!p;}')
|
||||||
|
with_hash=$(echo "$1" | sed -n '/^BREAKING[ -]CHANGE: /,/^[A-Za-z-]\{1,\} #/{ s/BREAKING[ -]CHANGE: \(.*\)/\1/; /^[A-Za-z-]\{1,\} #/!p;}')
|
||||||
|
if [ -n "$with_colon" ] && ! echo "$with_colon" | grep -q '[A-Za-z-]\{1,\} #'; then
|
||||||
|
echo "$with_colon"
|
||||||
|
else
|
||||||
|
echo "$with_hash"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
format_entry_line() {
|
||||||
|
line=""
|
||||||
|
if [ -n "$2" ]; then
|
||||||
|
line="**$2:**"
|
||||||
|
fi
|
||||||
|
line="$line $1"
|
||||||
|
|
||||||
|
echo "$line ([$3]($(get_config_url)/commit/$3))" | sed -e '2,$s/^[ ]*/ /'
|
||||||
|
}
|
||||||
|
|
||||||
|
breaking_change_lines=""
|
||||||
|
feature_lines=""
|
||||||
|
bugfix_lines=""
|
||||||
|
build_lines=""
|
||||||
|
chore_lines=""
|
||||||
|
ci_lines=""
|
||||||
|
doc_lines=""
|
||||||
|
style_lines=""
|
||||||
|
refactor_lines=""
|
||||||
|
perf_lines=""
|
||||||
|
test_lines=""
|
||||||
|
revert_lines=""
|
||||||
|
|
||||||
|
add_changelog_entry_line() {
|
||||||
|
case "$1" in
|
||||||
|
feat)
|
||||||
|
feature_lines=$(printf '%s\n* %s\n' "$feature_lines" "$2")
|
||||||
|
;;
|
||||||
|
|
||||||
|
fix)
|
||||||
|
bugfix_lines=$(printf '%s\n* %s\n' "$bugfix_lines" "$2")
|
||||||
|
;;
|
||||||
|
|
||||||
|
build)
|
||||||
|
build_lines="$build_lines\n* $2\n"
|
||||||
|
;;
|
||||||
|
|
||||||
|
chore)
|
||||||
|
chore_lines="$chore_lines\n* $2\n"
|
||||||
|
;;
|
||||||
|
|
||||||
|
ci)
|
||||||
|
ci_lines="$ci_lines\n* $2\n"
|
||||||
|
;;
|
||||||
|
|
||||||
|
doc_lines)
|
||||||
|
doc_lines="$doc_lines\n* $2\n"
|
||||||
|
;;
|
||||||
|
|
||||||
|
style)
|
||||||
|
style_lines="$style_lines\n* $2\n"
|
||||||
|
;;
|
||||||
|
|
||||||
|
refactor)
|
||||||
|
refactor_lines="$refactor_lines\n* $2\n"
|
||||||
|
;;
|
||||||
|
|
||||||
|
perf)
|
||||||
|
perf_lines="$perf_lines\n* $2\n"
|
||||||
|
;;
|
||||||
|
|
||||||
|
test)
|
||||||
|
test_lines="$test_lines\n* $2\n"
|
||||||
|
;;
|
||||||
|
|
||||||
|
revert)
|
||||||
|
revert_lines="$revert_lines\n* $2\n"
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
}
|
||||||
|
|
||||||
|
format_entry() {
|
||||||
|
entry=""
|
||||||
|
if [ -n "$breaking_change_lines" ]; then
|
||||||
|
entry="$entry### BREAKING CHANGES\n$breaking_change_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$bugfix_lines" ]; then
|
||||||
|
entry="$entry### Bug fixes\n$bugfix_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$feature_lines" ]; then
|
||||||
|
#entry="$entry### Features\n$feature_lines\n\n"
|
||||||
|
entry=$(printf '%s### Features\n%s\n\n' "$entry" "$feature_lines")
|
||||||
|
fi
|
||||||
|
if [ -n "$revert_lines" ]; then
|
||||||
|
entry="$entry### Reverts\n$revert_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$build_lines" ]; then
|
||||||
|
entry="$entry### Build System\n$build_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$chore_lines" ]; then
|
||||||
|
entry="$entry### Chores\n$chore_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$ci_lines" ]; then
|
||||||
|
entry="$entry### CIs\n$ci_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$doc_lines" ]; then
|
||||||
|
entry="$entry### Docs\n$doc_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$test_lines" ]; then
|
||||||
|
entry="$entry### Tests\n$test_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$style_lines" ]; then
|
||||||
|
entry="$entry### Styles\n$style_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$refactor_lines" ]; then
|
||||||
|
entry="$entry### Refactors\n$refactor_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$perf_lines" ]; then
|
||||||
|
entry="$entry### Perfs\n$perf_lines\n\n"
|
||||||
|
fi
|
||||||
|
if [ -n "$entry" ]; then
|
||||||
|
entry="## [$version]($(get_config_url)/compare/$from_hash...$to_hash) ($(date '+%Y-%m-%d'))\n\n\n$entry"
|
||||||
|
fi
|
||||||
|
echo "$entry"
|
||||||
|
}
|
||||||
|
|
||||||
|
generate_changelog_entry() {
|
||||||
|
is_major=0
|
||||||
|
is_minor=0
|
||||||
|
is_patch=0
|
||||||
|
|
||||||
|
version=$(get_config_version)
|
||||||
|
from_hash=$(get_config_sha)
|
||||||
|
if [ -z "$from_hash" ]; then
|
||||||
|
from_hash=$(get_git_first_commit_hash)
|
||||||
|
fi
|
||||||
|
to_hash=$(get_git_commit_hash HEAD)
|
||||||
|
|
||||||
|
for commit in $(get_git_commits); do
|
||||||
|
git_subject=$(get_git_commit_subject "$commit")
|
||||||
|
git_body=$(get_git_commit_body "$commit")
|
||||||
|
hash=$(get_git_commit_hash "$commit")
|
||||||
|
|
||||||
|
type=$(get_commit_type "$git_subject")
|
||||||
|
scope=$(get_commit_scope "$git_subject")
|
||||||
|
description=$(get_commit_description "$git_subject")
|
||||||
|
body=$(get_commit_body "$git_body")
|
||||||
|
footer=$(get_commit_footer "$git_body")
|
||||||
|
breaking_change=$(get_breaking_change "$footer")
|
||||||
|
is_breaking=$(is_breaking_change "$git_subject" "$footer")
|
||||||
|
line=$(format_entry_line "$description" "$scope" "$hash")
|
||||||
|
|
||||||
|
if [ "$is_breaking" -eq 1 ] && [ -z "$breaking_change" ]; then
|
||||||
|
breaking_change="$body"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$is_breaking" -eq 1 ]; then
|
||||||
|
is_major=1
|
||||||
|
breaking_change=$(echo "$breaking_change" | sed -e '2,$s/^[ ]*/ /')
|
||||||
|
breaking_change_lines="$breaking_change_lines\n* $breaking_change\n"
|
||||||
|
fi
|
||||||
|
|
||||||
|
case "$type" in
|
||||||
|
feat)
|
||||||
|
is_minor=1
|
||||||
|
;;
|
||||||
|
|
||||||
|
fix)
|
||||||
|
is_patch=1
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
add_changelog_entry_line "$type" "$line"
|
||||||
|
done
|
||||||
|
|
||||||
|
version_update=$((is_major * 100 + is_minor * 10 + is_patch))
|
||||||
|
if [ $version_update -gt 0 ]; then
|
||||||
|
version=$(calculate_version "$version" "$version_update")
|
||||||
|
else
|
||||||
|
# no version change, no need to generate changelog
|
||||||
|
return
|
||||||
|
fi
|
||||||
|
|
||||||
|
update_config "$to_hash" "$version"
|
||||||
|
|
||||||
|
format_entry
|
||||||
|
}
|
||||||
|
|
||||||
|
new_changelog() {
|
||||||
|
echo "$changelog_header" >$changelog_file
|
||||||
|
}
|
||||||
|
|
||||||
|
new_changelog_entry() {
|
||||||
|
entry=$(generate_changelog_entry)
|
||||||
|
if [ -z "$entry" ]; then
|
||||||
|
return
|
||||||
|
fi
|
||||||
|
|
||||||
|
changelog=$(sed -n '/^----/,//{/^----/!p;}' <$changelog_file)
|
||||||
|
if [ -n "$changelog" ]; then
|
||||||
|
changelog="$changelog_header\n$entry\n$changelog"
|
||||||
|
else
|
||||||
|
changelog="$changelog_header\n$entry"
|
||||||
|
fi
|
||||||
|
echo "$changelog" >$changelog_file
|
||||||
|
}
|
||||||
|
|
||||||
|
init() {
|
||||||
|
if [ "$1" = "--help" ]; then
|
||||||
|
echo "$(basename "$0") [--help] [init|get_version]"
|
||||||
|
exit 0
|
||||||
|
elif [ "$1" = "init" ]; then
|
||||||
|
echo "Generating a config ... "
|
||||||
|
echo "We guessed that the url for git links will be: $(get_git_url)"
|
||||||
|
echo "Please change inside the '${config_file}' file if needed!"
|
||||||
|
generate_config "$(get_git_url)"
|
||||||
|
new_changelog
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ ! -f "$config_file" ]; then
|
||||||
|
echo >&2 "ERROR: config file is missing to generate changelog entry"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$1" = "get_version" ]; then
|
||||||
|
get_config_version
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "Using existing config to generate changelog entry"
|
||||||
|
new_changelog_entry
|
||||||
|
}
|
||||||
|
|
||||||
|
init "$@"
|
||||||
@ -1,379 +0,0 @@
|
|||||||
#!/usr/bin/env sh
|
|
||||||
|
|
||||||
config_file=.version.json
|
|
||||||
changelog_file=CHANGELOG.md
|
|
||||||
changelog_header="# Changelog
|
|
||||||
|
|
||||||
All notable changes to this project will be documented in this file. See [Conventional Commits](https://www.conventionalcommits.org/en/v1.0.0/) for commit guidelines.
|
|
||||||
|
|
||||||
This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
||||||
|
|
||||||
----
|
|
||||||
"
|
|
||||||
|
|
||||||
reverse() {
|
|
||||||
if which tac >/dev/null 2>&1; then
|
|
||||||
tac
|
|
||||||
else
|
|
||||||
tail -r
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
generate_config() {
|
|
||||||
jq --null-input --arg version "0.0.0" --arg sha "" --arg url "$1" '{ "version": $version, "sha": $sha, "url": $url}' > $config_file
|
|
||||||
}
|
|
||||||
|
|
||||||
update_config() {
|
|
||||||
config=$(jq '.sha |= $sha | .version |= $version' --arg sha "$1" --arg version "$2" $config_file)
|
|
||||||
echo "$config" > $config_file
|
|
||||||
}
|
|
||||||
|
|
||||||
calculate_version() {
|
|
||||||
version_number=$(echo "$1" | cut -d'-' -f1 | cut -d'+' -f1)
|
|
||||||
pre_release=$(echo "$1" | cut -d'-' -f2 | cut -d'+' -f1)
|
|
||||||
build=$(echo "$1" |cut -d'-' -f2 | cut -d'+' -f2)
|
|
||||||
if [ "$pre_release" = "$1" ]; then
|
|
||||||
pre_release=""
|
|
||||||
fi
|
|
||||||
if [ "$build" = "$1" ] || [ "$build" = "$pre_release" ]; then
|
|
||||||
build=""
|
|
||||||
fi
|
|
||||||
|
|
||||||
major=$(echo "$version_number" | cut -d'.' -f1)
|
|
||||||
minor=$(echo "$version_number" | cut -d'.' -f2)
|
|
||||||
patch=$(echo "$version_number" | cut -d'.' -f3)
|
|
||||||
pre_release_identifier=$(echo "$pre_release." | cut -d'.' -f2)
|
|
||||||
|
|
||||||
pre_release=""
|
|
||||||
build=""
|
|
||||||
|
|
||||||
case "$2" in
|
|
||||||
major)
|
|
||||||
if [ -n "$major" ]; then
|
|
||||||
major=$((major+1))
|
|
||||||
minor=0
|
|
||||||
patch=0
|
|
||||||
fi
|
|
||||||
;;
|
|
||||||
|
|
||||||
minor)
|
|
||||||
if [ -n "$minor" ]; then
|
|
||||||
minor=$((minor+1))
|
|
||||||
patch=0
|
|
||||||
fi
|
|
||||||
;;
|
|
||||||
|
|
||||||
patch)
|
|
||||||
if [ -n "$patch" ]; then
|
|
||||||
patch=$((patch+1))
|
|
||||||
fi
|
|
||||||
;;
|
|
||||||
|
|
||||||
rc)
|
|
||||||
if [ -z "$pre_release_identifier" ]; then
|
|
||||||
pre_release_identifier=1
|
|
||||||
else
|
|
||||||
pre_release_identifier=$((pre_release_identifier+1))
|
|
||||||
fi
|
|
||||||
pre_release="rc.$pre_release_identifier"
|
|
||||||
;;
|
|
||||||
esac
|
|
||||||
|
|
||||||
if [ "$3" = "build" ]; then
|
|
||||||
build="$(git rev-parse --short HEAD)"
|
|
||||||
fi
|
|
||||||
|
|
||||||
version_number="${major}.${minor}.${patch}"
|
|
||||||
if [ -n "$pre_release" ]; then
|
|
||||||
pre_release="-$pre_release"
|
|
||||||
fi
|
|
||||||
if [ -n "$build" ]; then
|
|
||||||
build="+$build"
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo "${version_number}${pre_release}${build}"
|
|
||||||
}
|
|
||||||
|
|
||||||
get_git_url() {
|
|
||||||
url=$(git config --get remote.origin.url)
|
|
||||||
if ! echo "$url" | grep -q "^http"; then
|
|
||||||
url=$(echo "$url" | cut -d@ -f2 | sed 's/:/\//')
|
|
||||||
url="https://$url"
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo "$url" | sed 's/\.git$//'
|
|
||||||
}
|
|
||||||
|
|
||||||
get_git_commits() {
|
|
||||||
since_hash="$(jq '.sha' < $config_file | tr -d '"')"
|
|
||||||
if [ -n "$since_hash" ]; then
|
|
||||||
git rev-list "$since_hash..HEAD"
|
|
||||||
else
|
|
||||||
git rev-list HEAD
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
get_git_commit_hash() {
|
|
||||||
git rev-parse --short "$1"
|
|
||||||
}
|
|
||||||
|
|
||||||
get_git_first_commit_hash() {
|
|
||||||
git rev-list --max-parents=0 --abbrev-commit HEAD
|
|
||||||
}
|
|
||||||
|
|
||||||
get_git_commit_subject() {
|
|
||||||
git show -s --format=%s "$1"
|
|
||||||
}
|
|
||||||
|
|
||||||
get_git_commit_body() {
|
|
||||||
git show -s --format=%b "$1"
|
|
||||||
}
|
|
||||||
|
|
||||||
get_commit_type() {
|
|
||||||
echo "$1" | sed -r -n 's/([a-z]+)(\(?|:?).*/\1/p' | tr '[:upper:]' '[:lower:]'
|
|
||||||
}
|
|
||||||
|
|
||||||
get_commit_scope() {
|
|
||||||
echo "$1" | sed -r -n 's/[a-z]+\(([^)]+)\).*/\1/p'
|
|
||||||
}
|
|
||||||
|
|
||||||
get_commit_description() {
|
|
||||||
echo "$1" | sed -r -n 's/.*:[ ]+(.*)/\1/p'
|
|
||||||
}
|
|
||||||
|
|
||||||
get_commit_footer() {
|
|
||||||
with_colon=$(echo "$1" | sed -n '/^[A-Za-z-]\{1,\}: /,//{p;}')
|
|
||||||
with_hash=$(echo "$1" | sed -n '/^[A-Za-z-]\{1,\} #/,//{p;}')
|
|
||||||
fallback=$(echo "$1" | reverse | awk '/^$/{exit}1' | reverse)
|
|
||||||
|
|
||||||
if [ -z "$with_colon" ] && [ -z "$with_hash" ]; then
|
|
||||||
echo "$fallback"
|
|
||||||
elif [ ${#with_colon} -gt ${#with_hash} ]; then
|
|
||||||
echo "$with_colon"
|
|
||||||
else
|
|
||||||
echo "$with_hash"
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
get_commit_body() {
|
|
||||||
pattern=$(get_commit_footer "$1" | head -n 1)
|
|
||||||
if [ -n "$pattern" ]; then
|
|
||||||
echo "$1" | sed -e "/$pattern/,\$d"
|
|
||||||
else
|
|
||||||
echo "$1"
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
is_breaking_change() {
|
|
||||||
if echo "$1" | grep -q '!' || echo "$2" | grep -q 'BREAKING[ -]CHANGE: '; then
|
|
||||||
echo 1
|
|
||||||
else
|
|
||||||
echo 0
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
get_breaking_change() {
|
|
||||||
with_colon=$(echo "$1" | sed -n '/^BREAKING[ -]CHANGE: /,/^[A-Za-z-]\{1,\}: /{ s/BREAKING[ -]CHANGE: \(.*\)/\1/; /^[A-Za-z-]\{1,\}: /!p;}')
|
|
||||||
with_hash=$(echo "$1" | sed -n '/^BREAKING[ -]CHANGE: /,/^[A-Za-z-]\{1,\} #/{ s/BREAKING[ -]CHANGE: \(.*\)/\1/; /^[A-Za-z-]\{1,\} #/!p;}')
|
|
||||||
if [ -n "$with_colon" ] && ! echo "$with_colon" | grep -q '[A-Za-z-]\{1,\} #'; then
|
|
||||||
echo "$with_colon"
|
|
||||||
else
|
|
||||||
echo "$with_hash"
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
format_entry_line() {
|
|
||||||
if [ -n "$2" ]; then
|
|
||||||
line="**$2:** $1"
|
|
||||||
else
|
|
||||||
line="$1"
|
|
||||||
fi
|
|
||||||
|
|
||||||
url="$(jq '.url' < $config_file | tr -d '"')"
|
|
||||||
|
|
||||||
echo "$line ([$3]($url/commit/$3))" | sed -e '2,$s/^[ ]*/ /'
|
|
||||||
}
|
|
||||||
|
|
||||||
generate_changelog_entry() {
|
|
||||||
is_major=0
|
|
||||||
is_minor=0
|
|
||||||
is_patch=0
|
|
||||||
|
|
||||||
version=$(jq '.version' < $config_file | tr -d '"')
|
|
||||||
from_hash=$(jq '.sha' < $config_file | tr -d '"')
|
|
||||||
if [ -z "$from_hash" ]; then
|
|
||||||
from_hash=$(get_git_first_commit_hash)
|
|
||||||
fi
|
|
||||||
to_hash=$(get_git_commit_hash HEAD)
|
|
||||||
|
|
||||||
breakingchanges=""
|
|
||||||
features=""
|
|
||||||
bugfixes=""
|
|
||||||
builds=""
|
|
||||||
chores=""
|
|
||||||
cis=""
|
|
||||||
docs=""
|
|
||||||
styles=""
|
|
||||||
refactors=""
|
|
||||||
perfs=""
|
|
||||||
tests=""
|
|
||||||
reverts=""
|
|
||||||
|
|
||||||
for commit in $(get_git_commits); do
|
|
||||||
git_subject=$(get_git_commit_subject "$commit")
|
|
||||||
git_body=$(get_git_commit_body "$commit")
|
|
||||||
hash=$(get_git_commit_hash "$commit")
|
|
||||||
|
|
||||||
type=$(get_commit_type "$git_subject")
|
|
||||||
scope=$(get_commit_scope "$git_subject")
|
|
||||||
description=$(get_commit_description "$git_subject")
|
|
||||||
body=$(get_commit_body "$git_body")
|
|
||||||
footer=$(get_commit_footer "$git_body")
|
|
||||||
breakingchange=$(get_breaking_change "$footer")
|
|
||||||
is_breaking=$(is_breaking_change "$git_subject" "$footer")
|
|
||||||
line=$(format_entry_line "$description" "$scope" "$hash")
|
|
||||||
|
|
||||||
if [ "$is_breaking" -eq 1 ] && [ -z "$breakingchange" ]; then
|
|
||||||
breakingchange="$body"
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ "$is_breaking" -eq 1 ]; then
|
|
||||||
is_major=1
|
|
||||||
breakingchange=$(echo "$breakingchange" | sed -e '2,$s/^[ ]*/ /')
|
|
||||||
breakingchanges="$breakingchanges\n* $breakingchange\n"
|
|
||||||
fi
|
|
||||||
|
|
||||||
case "$type" in
|
|
||||||
feat)
|
|
||||||
is_minor=1
|
|
||||||
features="$features\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
fix)
|
|
||||||
is_patch=1
|
|
||||||
bugfixes="$bugfixes\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
build)
|
|
||||||
builds="$builds\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
chore)
|
|
||||||
chores="$chores\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
ci)
|
|
||||||
cis="$cis\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
docs)
|
|
||||||
docs="$docs\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
style)
|
|
||||||
styles="$styles\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
refactor)
|
|
||||||
refactors="$refactors\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
perf)
|
|
||||||
perfs="$perfs\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
test)
|
|
||||||
tests="$tests\n* $line\n"
|
|
||||||
;;
|
|
||||||
|
|
||||||
revert)
|
|
||||||
reverts="$reverts\n* $line\n"
|
|
||||||
;;
|
|
||||||
esac
|
|
||||||
done
|
|
||||||
|
|
||||||
if [ $is_major -eq 1 ]; then
|
|
||||||
version=$(calculate_version "$version" "major")
|
|
||||||
elif [ $is_minor -eq 1 ]; then
|
|
||||||
version=$(calculate_version "$version" "minor")
|
|
||||||
elif [ $is_patch -eq 1 ]; then
|
|
||||||
version=$(calculate_version "$version" "patch")
|
|
||||||
fi
|
|
||||||
|
|
||||||
update_config "$to_hash" "$version"
|
|
||||||
|
|
||||||
entry=""
|
|
||||||
if [ -n "$breakingchanges" ]; then
|
|
||||||
entry="$entry### BREAKING CHANGES\n$breakingchanges\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$bugfixes" ]; then
|
|
||||||
entry="$entry### Bug fixes\n$bugfixes\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$features" ]; then
|
|
||||||
entry="$entry### Features\n$features\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$reverts" ]; then
|
|
||||||
entry="$entry### Reverts\n$reverts\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$builds" ]; then
|
|
||||||
entry="$entry### Build System\n$builds\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$chores" ]; then
|
|
||||||
entry="$entry### Chores\n$chores\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$cis" ]; then
|
|
||||||
entry="$entry### CIs\n$cis\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$docs" ]; then
|
|
||||||
entry="$entry### Docs\n$docs\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$tests" ]; then
|
|
||||||
entry="$entry### Tests\n$tests\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$styles" ]; then
|
|
||||||
entry="$entry### Styles\n$styles\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$refactors" ]; then
|
|
||||||
entry="$entry### Refactors\n$refactors\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$perfs" ]; then
|
|
||||||
entry="$entry### Perfs\n$perfs\n\n"
|
|
||||||
fi
|
|
||||||
if [ -n "$entry" ]; then
|
|
||||||
url="$(jq '.url' < $config_file | tr -d '"')"
|
|
||||||
entry="## [$version]($url/compare/$from_hash...$to_hash) ($(date '+%Y-%m-%d'))\n\n\n$entry"
|
|
||||||
fi
|
|
||||||
echo "$entry"
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
new_changelog() {
|
|
||||||
echo "$changelog_header" > $changelog_file
|
|
||||||
}
|
|
||||||
|
|
||||||
new_changelog_entry() {
|
|
||||||
entry=$(generate_changelog_entry)
|
|
||||||
if [ -n "$entry" ]; then
|
|
||||||
changelog=$(sed -n '/^----/,//{/^----/!p;}' < $changelog_file)
|
|
||||||
if [ -n "$changelog" ]; then
|
|
||||||
changelog="$changelog_header\n$entry\n$changelog"
|
|
||||||
else
|
|
||||||
changelog="$changelog_header\n$entry"
|
|
||||||
fi
|
|
||||||
echo "$changelog" > $changelog_file
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
init() {
|
|
||||||
if [ ! -f "$config_file" ]; then
|
|
||||||
echo "Generating a config ... "
|
|
||||||
generate_config "$(get_git_url)"
|
|
||||||
new_changelog
|
|
||||||
else
|
|
||||||
echo "Using existing config"
|
|
||||||
fi
|
|
||||||
|
|
||||||
new_changelog_entry
|
|
||||||
}
|
|
||||||
|
|
||||||
init
|
|
||||||
Loading…
Reference in New Issue
Block a user