# calver
A lightweight command-line tool for effortless Calendar Versioning increments.
[](LICENSE)
[](https://github.com/semantic-release/semantic-release)
[](https://crates.io/crates/calver)
[](https://gitlab.com/op_so/projects/calver/pipelines)
## 📖 Overview
CalVer is a simple yet powerful tool that generates calendar-based version numbers. It automatically creates version identifiers using the current date and manages patch increments intelligently, making it perfect for automated builds, daily releases, and development snapshots.
✨ Key Features
- 🗓️ **Date-based versioning** using current UTC time
- 🔢 **Automatic patch increment** from previous versions
- 🎨 **Customizable formats** for date and separators
- 🌍 **Environment variable support** for CI/CD integration
- ⚡ **Zero configuration** - works out of the box
- 🛡️ **Robust error handling** with proper exit codes
## 📊 Use Cases
- **🔄 Continuous Integration**: Automatic version generation in CI/CD pipelines
- **📦 Daily Builds**: Version daily snapshots and releases
- **🏷️ Git Tagging**: Generate consistent tags for repository management
- **🐳 Container Images**: Tag Docker images with date-based versions
- **📂 Artifact Management**: Version build artifacts and deployments
- **🔍 Development Tracking**: Track development progress with dated versions
## 🚀 Quick Start
### 📦 Installation
- Binary file installation on Linux via the [GitLab package registry of the project](https://gitlab.com/op_so/projects/calver/-/packages):
- 2 architectures:
- calver-x86_64-linux-<gnu|musl>.tar.gz : x86_64 (Intel, AMD).
- calver-aarch64-linux-<gnu|musl>.tar.gz : arm64
- 2 C standard library with no dependencies:
- calver-<x86_64|aarch64>-linux-gnu.tar.gz : glibc for Debian, Ubuntu, Fedora...
- calver-<x86_64|aarch64>-linux-musl.tar.gz : musl libc for Alpine
- Docker (coming soon)
```shell
# From Dockerhub
docker run -it --rm jfxs/calver calver help
# From Quay.io
docker run -it --rm quay.io/ifxs/calver calver help
```
- With a Rust environment, running this command will globally install the calver binary from crates.io:
```shell
cargo install calver
```
### 🎯 Basic Usage
```bash
# Basic usage with defaults
$ calver bump
2025.09.15-0
# Custom format and separator
$ calver bump --format "%Y%m%d" --separator "_v"
20250915_v0
# Explicit patch number
$ calver bump --patch 5
2025.09.15-5
# Auto-increment from last version
$ calver bump --last "2025.09.15-3"
2025.09.15-4 # if same date
2025.09.16-0 # if different date
# Using environment variables
$ export CALVER_FORMAT="%Y%m%d"
$ export CALVER_SEPARATOR="_v"
$ calver bump
20250915_v0
```
## 📋 Usage
### Command Syntax
```bash
calver bump [OPTIONS]
```
### Options
| `--format` | `-f` | `CALVER_FORMAT` | Date format string | `%Y.%m.%d` |
| `--separator` | `-s` | `CALVER_SEPARATOR` | Separator between date and patch | `-` |
| `--patch` | `-p` | `CALVER_PATCH` | Explicit patch number (conflicts with --last) | `0` |
| `--last` | `-l` | `CALVER_LAST` | Previous version for auto-increment | None |
### Date Format Examples
| `%Y.%m.%d` | `2025.09.15` | Year.Month.Day (default) |
| `%Y%m%d` | `20250915` | Compact YYYYMMDD |
| `%y.%m.%d` | `25.09.15` | Short year format |
| `%Y-%m-%d` | `2025-09-15` | ISO date format |
| `%Y.%j` | `2025.258` | Year and day of year |
### Separator Examples
| `-` | `2025.09.15-0` | Hyphen (default) |
| `_` | `2025.09.15_0` | Underscore |
| `.` | `2025.09.15.0` | Dot |
| `_v` | `2025.09.15_v0` | Version prefix |
## 🔄 Auto-Increment Logic
The `--last` parameter enables intelligent patch increment:
1. **Same date**: Extracts and increments the patch number
```shell
calver bump --last "2025.09.15-3"
# Output: 2025.09.15-4
```
2. **Different date**: Resets patch to 0
```shell
calver bump --last "2025.09.14-10"
# Output: 2025.09.15-0
```
3. **Invalid format**: Ignores and uses default patch
```shell
calver bump --last "invalid-version"
# Output: 2025.09.15-0
```
## 🌍 Environment Variables
Set default values using environment variables:
```shell
export CALVER_FORMAT="%Y%m%d"
export CALVER_SEPARATOR="_v"
export CALVER_PATCH="1"
calver bump
# Output: 20250915_v1
```
For CI/CD pipelines:
```shell
export CALVER_LAST=$(git tag -l --sort=-version:refname | head -n1)
calver bump
```
## 💡 Examples
### Daily Releases
```shell
# Monday 2025.09.15
calver bump --last "2025.09.12-5"
# Output: 2025.09.15-0 (new day, reset patch)
# Later same day
calver bump --last "2025.09.15-0"
# Output: 2025.09.15-1
```
### Custom Versioning Scheme
```shell
# Compact format for internal builds
calver bump --format "%y%m%d" --separator "."
# Output: 250915.0
```
### CI/CD Integration
```yaml
# GitHub Actions example
- name: Generate Version
run: |
LAST_VERSION=$(git tag -l --sort=-version:refname | head -n1)
NEW_VERSION=$(calver bump --last "$LAST_VERSION")
echo "VERSION=$NEW_VERSION" >> $GITHUB_ENV
echo "Generated version: $NEW_VERSION"
```
### Build Scripts
```shell
#!/bin/bash
# build.sh - Automated build with versioning
set -e
# Get last version from a file
LAST_VERSION=$(cat version.txt 2>/dev/null || echo "")
# Generate new version
NEW_VERSION=$(calver bump --last "$LAST_VERSION")
# Save for next build
echo "$NEW_VERSION" > version.txt
# Build with version
echo "Building version: $NEW_VERSION"
echo "✅ Build completed: $NEW_VERSION"
```
## ⚠️ Error Handling
CalVer provides clear error messages and appropriate exit codes:
### Exit Codes
- `0`: Success
- `1`: Error (patch overflow, invalid input)
### Common Errors
```bash
# Patch overflow
calver bump --last "2025.09.15-65535"
# Error: The patch calculated exceeds the maximum allowed value (65535)
# Exit code: 1
# Success case
calver bump --format "%Y.%m.%d"
# Output: 2025.09.15-0
# Exit code: 0
```
## 🔧 Development
- Clone the source repository: `git clone https://gitlab.com/op_so/projects/calver.git`
- To format and lint:
```shell
cargo fmt # cargo fmt -- --check
cargo clippy # Rust linter
```
- To test:
```shell
cargo build && cargo test # Unit and integration tests
cargo tarpaulin --ignore-tests # Code coverage
cargo audit # Security audit
cargo bench # Statistics-driven benchmarking
```
- To run: `cargo run`
- To build:
```shell
cargo build # Debug binary target/debug/calver
cargo build --release # Release binary target/release/calver
```
## 🤝 Contributing
Contributions are welcome! Please feel free to submit a Pull Request. For major changes, please open an issue first to discuss what you would like to change.
### Development Guidelines
1. **Code Style**: Follow `rustfmt` and `clippy` recommendations
2. **Testing**: Add tests for new features
3. **Documentation**: Update README and code docs
4. **Commits**: Use [commitizen](https://github.com/commitizen/cz-cli) commit messages
## 👥 Authors
- **FX Soubirou** - _Initial work_ - [GitLab repositories](https://gitlab.com/op_so)
## 🙏 Acknowledgments
- [clap](https://crates.io/crates/clap) for excellent CLI parsing
- [chrono](https://crates.io/crates/chrono) for robust date/time handling
- [Calendar Versioning](https://calver.org/) specification for inspiration
## 🔗 Links
- 🏠 [Project Repository](https://gitlab.com/op_so/projects/calver)
- 📦 [Crates.io](https://crates.io/crates/calver)
- 📚 [Documentation](https://docs.rs/calver)
- 🚀 [Releases](https://gitlab.com/op_so/projects/calver/-/packages)
## 📄 License
This program is free software: you can redistribute it and/or modify it under the terms of the MIT License (MIT).
See the [LICENSE](https://opensource.org/licenses/MIT) for details.