screw-up-native
July 3, 2026 ยท View on GitHub
Native CLI that Git versioning metadata dumper/formatter.

What is this?
Wouldn't you like to automatically insert calculated version information from Git tags into your source code or text files? This CLI tool is the perfect little knife for the job.
# Dump Git repository metadata resolved (JSON)
screw-up dump
# Format a template with Git metadata placeholders
echo "This version is '{version}'" | screw-up format
# Format direct template text with Git metadata placeholders
screw-up format -e "This version is '{version}'"
Version numbers are automatically calculated from Git tags and adhere to the screw-up convention. This calculates the version number by measuring the commit height to the current HEAD based on the last applied version tag.

You can use metadata such as version numbers, Git commit hashes, timestamps, and commit messages to format text or output it as JSON:
{
"git": {
"tags": [],
"branches": ["develop"],
"version": "1.13.2",
"commit": {
"hash": "49a4245d6c5ce6604167005f5234c1c4a38a852b",
"shortHash": "49a4245",
"date": "2025-12-05T11:50:38+09:00",
"message": "feat: Added force dump mode."
}
},
"version": "1.13.2",
"buildDate": "2025-12-28T17:30:30+09:00"
}
The CLI command is available via Linux packages (Ubuntu/Debian) and prebuilt Windows binaries, making it easy to use.
Installation
Here is pre-built packages/binaries.
For Ubuntu/Debian:
sudo apt install ./screw-up-ubuntu-noble-amd64-1.2.3.deb
For Windows (64/32bit):
Extract zip file (contains single screw-up.exe file).
Dump Command
Dump computed metadata as JSON:
# Dump current Git repository
screw-up dump
As shown in the following output example, Git commit information is also added:
{
"git": {
"tags": [],
"branches": ["develop"],
"version": "1.13.2",
"commit": {
"hash": "49a4245d6c5ce6604167005f5234c1c4a38a852b",
"shortHash": "49a4245",
"date": "2025-12-05T11:50:38+09:00",
"message": "feat: Added force dump mode."
}
},
"version": "1.13.2",
"buildDate": "2025-12-28T17:30:30+09:00"
}
The dump command:
- Shows the final computed metadata after all processing (workspace inheritance, Git metadata, etc.)
- Useful for debugging and understanding how your package metadata will be resolved
- Outputs clean JSON that can be piped to other tools (ex:
jq)
Options
--no-wds: Disable working directory status check for version increment
Generic usage
For example, combine with jq to generate a C header that embeds version and commit IDs:
# Generate version.h
screw-up dump -f | jq -r '
"#pragma once\n" +
"#define APP_VERSION \"" + (.version // "0.0.1") + "\"\n" +
"#define APP_COMMIT \"" + (.git.commit.shortHash // "unknown") + "\"\n"
' > version.h
Format Command
Replace placeholders in text with computed package metadata.
This command is similar to the dump command, but instead of outputting JSON, it can be used to format text within screw-up. Therefore, it might be easier to handle than processing screw-up output with jq:
# Format stdin template and print to stdout
echo "This version is '{version}'" | screw-up format
# Format direct template text and print to stdout
screw-up format -e "{version}"
# Format a file and write the result to another file
screw-up format -i ./template.txt ./output.txt
# Use custom brackets instead of {...}
screw-up format -i ./template.txt -b "#{,}#"
Placeholders use {field} by default. Dot notation lets you reach nested values such as {repository.url} or {git.commit.hash}.
Input comes from -e/--expression when provided. Otherwise it comes from the file specified by -i/--input, or stdin when -i/--input is not provided. -e/--expression and -i/--input cannot be used together. Output always goes to stdout; if you pass an output path, the formatted text is also written there.
Options
-e, --expression <text>: Template text to format directly-i, --input <path>: Template file to format (defaults to stdin)-b, --bracket <open,close>: Change placeholder brackets (default{,})--no-wds: Disable working directory status check for version increment
Example
For example, prepare an input text file like the following (version.h.in):
#pragma once
#define APP_VERSION "{version}"
#define APP_COMMIT "{git.commit.shortHash}"
By entering the following into screw-up, you can generate C language header files:
screw-up format -i ./version.h.in ./version.h
version.h:
#pragma once
#define APP_VERSION "1.13.2"
#define APP_COMMIT "49a4245"
Self building
In Ubuntu noble:
sudo apt install build-essential git gdb libgit2-dev \
cmake make pkg-config ca-certificates
./build.sh
Build packages
build_package.sh is the single entry point for release package generation.
Linux .deb packages are built inside distro-specific Podman containers prepared by prereq.sh; Windows zip archives are generated through build_win32.sh.
Prerequisites:
sudo apt-get install podman qemu-user-static dpkg-dev binutils \
gcc-mingw-w64-x86-64 gcc-mingw-w64-i686 \
binutils-mingw-w64-x86-64 binutils-mingw-w64-i686 \
cmake make pkg-config git zip curl tar ca-certificates libgit2-dev
Build examples:
# Prepare Linux prerequisite images
./prereq.sh
# Ubuntu 24.04 / amd64 deb package
./build_package.sh --target deb --distro ubuntu --release 24.04 --arch x86_64
# Debian bookworm / arm64 deb package
./build_package.sh --target deb --distro debian --release bookworm --arch arm64
# Windows amd64 zip package
./build_package.sh --target windows --arch amd64
# Full Linux deb matrix and Windows zip packages
./build_package.sh --target all
Notes:
- Supported Linux package matrix:
Debian
bookworm(x86_64,i686,arm64,armv7l), Debiantrixie(x86_64,i686,arm64,armv7l,riscv64), Ubuntu22.04,24.04, and26.04(x86_64,arm64) - Arch aliases:
x86_64|amd64,i686|i386,armv7l|armv7|armhf,arm64|aarch64 - Ubuntu release aliases:
24.04|noble,22.04|jammy - Debug build: add
--debug - Rebuild Linux prerequisite images after dependency or base-image changes:
./prereq.sh --force .deboutputs:artifacts/deb/screw-up-native-<version>-<distro>-<release>-<deb-arch>.deb- Windows outputs:
artifacts/screw-up-native-windows-<arch>-<version>.zip
Batch build for all predefined combos:
./build_package_all.sh
For windows archive
build_win32.sh remains available for direct Windows-only package generation.
Prerequisites:
sudo apt install gcc-mingw-w64-x86-64 gcc-mingw-w64-i686 \
binutils-mingw-w64-x86-64 binutils-mingw-w64-i686 cmake make pkg-config \
git zip curl tar ca-certificates libgit2-dev
Build examples:
./build_win32.sh
Notes:
- Outputs:
artifacts/screw-up-native-windows-<arch>-*.zip
Note
This project was developed as a successor to RelaxVersioner. And screw-up is related to its sibling.
screw-up was designed for use in NPM environments and felt sufficiently practical as-is due to its high portability. However, we discovered that Node.js became somewhat of a hindrance when using it across multiple platforms and architectures.
That's why we decided to create a native CLI written in pure C and dependent only on libgit2.
Discussions and Pull Requests
For discussions, please refer to the GitHub Discussions page. We have currently stopped issue-based discussions.
Pull requests are welcome! Please submit them as diffs against the develop branch and squashed changes before send.
License
Under MIT, excepts libgit2 library (Contains static linking, see libgit2 'COPYING').