# Generic Automatic Version Increment System for Any Repository

Here's a generalized implementation guide for adding automatic versioning to any project:

## Core Concept
**Automatic patch version increment with each build** - Every build automatically increments the patch version: v0.1.0 → v0.1.1 → v0.1.2, etc.

## Implementation Steps

### 1. Add Version Increment Function to Build Script
Add this function to your build script (bash example):

```bash
# Function to automatically increment version
increment_version() {
    echo "[INFO] Incrementing version..."
    
    # Check if we're in a git repository
    if ! git rev-parse --git-dir > /dev/null 2>&1; then
        echo "[WARNING] Not in a git repository - skipping version increment"
        return 0
    fi
    
    # Get the highest version tag (not chronologically latest)
    LATEST_TAG=$(git tag -l 'v*.*.*' | sort -V | tail -n 1 || echo "v0.1.0")
    if [[ -z "$LATEST_TAG" ]]; then
        LATEST_TAG="v0.1.0"
    fi
    
    # Extract version components (remove 'v' prefix)
    VERSION=${LATEST_TAG#v}
    
    # Parse major.minor.patch using regex
    if [[ $VERSION =~ ^([0-9]+)\.([0-9]+)\.([0-9]+)$ ]]; then
        MAJOR=${BASH_REMATCH[1]}
        MINOR=${BASH_REMATCH[2]}
        PATCH=${BASH_REMATCH[3]}
    else
        echo "[ERROR] Invalid version format in tag: $LATEST_TAG"
        echo "[ERROR] Expected format: v0.1.0"
        return 1
    fi
    
    # Increment patch version
    NEW_PATCH=$((PATCH + 1))
    NEW_VERSION="v${MAJOR}.${MINOR}.${NEW_PATCH}"
    
    echo "[INFO] Current version: $LATEST_TAG"
    echo "[INFO] New version: $NEW_VERSION"
    
    # Create new git tag
    if git tag "$NEW_VERSION" 2>/dev/null; then
        echo "[SUCCESS] Created new version tag: $NEW_VERSION"
    else
        echo "[WARNING] Tag $NEW_VERSION already exists - using existing version"
        NEW_VERSION=$LATEST_TAG
    fi
    
    # Update VERSION file for compatibility
    echo "${NEW_VERSION#v}" > VERSION
    echo "[SUCCESS] Updated VERSION file to ${NEW_VERSION#v}"
}
```

### 2. Generate Version Header Files (For C/C++ Projects)
Add this to the increment_version function:

```bash
# Generate version.h header file (adjust path as needed)
cat > src/version.h << EOF
/*
 * Auto-Generated Version Header
 * DO NOT EDIT THIS FILE MANUALLY - Generated by build script
 */

#ifndef VERSION_H
#define VERSION_H

#define VERSION_MAJOR ${MAJOR}
#define VERSION_MINOR ${MINOR}
#define VERSION_PATCH ${NEW_PATCH}
#define VERSION_STRING "${MAJOR}.${MINOR}.${NEW_PATCH}"
#define VERSION_TAG "${NEW_VERSION}"

/* Build information */
#define BUILD_DATE "$(date +%Y-%m-%d)"
#define BUILD_TIME "$(date +%H:%M:%S)"
#define BUILD_TIMESTAMP "$(date '+%Y-%m-%d %H:%M:%S')"

/* Git information */
#define GIT_HASH "$(git rev-parse --short HEAD 2>/dev/null || echo 'unknown')"
#define GIT_BRANCH "$(git rev-parse --abbrev-ref HEAD 2>/dev/null || echo 'unknown')"

/* Display versions */
#define VERSION_DISPLAY "${NEW_VERSION}"
#define VERSION_FULL_DISPLAY "${NEW_VERSION} ($(date '+%Y-%m-%d %H:%M:%S'), $(git rev-parse --short HEAD 2>/dev/null || echo 'unknown'))"

/* Version API functions */
const char* get_version(void);
const char* get_version_full(void);
const char* get_build_info(void);

#endif /* VERSION_H */
EOF

# Generate version.c implementation file
cat > src/version.c << EOF
/*
 * Auto-Generated Version Implementation
 * DO NOT EDIT THIS FILE MANUALLY - Generated by build script
 */

#include "version.h"

const char* get_version(void) {
    return VERSION_TAG;
}

const char* get_version_full(void) {
    return VERSION_FULL_DISPLAY;
}

const char* get_build_info(void) {
    return "Built on " BUILD_DATE " at " BUILD_TIME " from commit " GIT_HASH " on branch " GIT_BRANCH;
}
EOF
```

### 3. Generate Version File for Other Languages

**Python (`src/__version__.py`):**
```bash
cat > src/__version__.py << EOF
"""Auto-generated version file"""
__version__ = "${MAJOR}.${MINOR}.${NEW_PATCH}"
__version_tag__ = "${NEW_VERSION}"
__build_date__ = "$(date +%Y-%m-%d)"
__build_time__ = "$(date +%H:%M:%S)"
__git_hash__ = "$(git rev-parse --short HEAD 2>/dev/null || echo 'unknown')"
__git_branch__ = "$(git rev-parse --abbrev-ref HEAD 2>/dev/null || echo 'unknown')"
EOF
```

**JavaScript/Node.js (update `package.json`):**
```bash
# Update package.json version field
if [ -f package.json ]; then
    sed -i "s/\"version\": \".*\"/\"version\": \"${MAJOR}.${MINOR}.${NEW_PATCH}\"/" package.json
fi
```

**Rust (update `Cargo.toml`):**
```bash
if [ -f Cargo.toml ]; then
    sed -i "s/^version = \".*\"/version = \"${MAJOR}.${MINOR}.${NEW_PATCH}\"/" Cargo.toml
fi
```

**Go (generate `version.go`):**
```bash
cat > version.go << EOF
// Auto-generated version file
package main

const (
    VersionMajor = ${MAJOR}
    VersionMinor = ${MINOR}
    VersionPatch = ${NEW_PATCH}
    VersionString = "${MAJOR}.${MINOR}.${NEW_PATCH}"
    VersionTag = "${NEW_VERSION}"
    BuildDate = "$(date +%Y-%m-%d)"
    BuildTime = "$(date +%H:%M:%S)"
    GitHash = "$(git rev-parse --short HEAD 2>/dev/null || echo 'unknown')"
    GitBranch = "$(git rev-parse --abbrev-ref HEAD 2>/dev/null || echo 'unknown')"
)
EOF
```

**Java (generate `Version.java`):**
```bash
cat > src/main/java/Version.java << EOF
// Auto-generated version class
public class Version {
    public static final int VERSION_MAJOR = ${MAJOR};
    public static final int VERSION_MINOR = ${MINOR};
    public static final int VERSION_PATCH = ${NEW_PATCH};
    public static final String VERSION_STRING = "${MAJOR}.${MINOR}.${NEW_PATCH}";
    public static final String VERSION_TAG = "${NEW_VERSION}";
    public static final String BUILD_DATE = "$(date +%Y-%m-%d)";
    public static final String BUILD_TIME = "$(date +%H:%M:%S)";
    public static final String GIT_HASH = "$(git rev-parse --short HEAD 2>/dev/null || echo 'unknown')";
    public static final String GIT_BRANCH = "$(git rev-parse --abbrev-ref HEAD 2>/dev/null || echo 'unknown')";
}
EOF
```

### 4. Integrate into Build Targets
Call `increment_version` before your main build commands:

```bash
build_library() {
    increment_version
    echo "[INFO] Building library..."
    # Your actual build commands here
    make clean && make
}

build_release() {
    increment_version
    echo "[INFO] Building release..."
    # Your release build commands
}

build_package() {
    increment_version
    echo "[INFO] Building package..."
    # Your packaging commands
}
```

### 5. Update .gitignore
Add generated version files to `.gitignore`:

```gitignore
# Auto-generated version files
src/version.h
src/version.c
src/__version__.py
version.go
src/main/java/Version.java
VERSION
```

### 6. Update Build System Files

**For Makefile projects:**
```makefile
# Add version.c to your source files
SOURCES = main.c utils.c version.c
```

**For CMake projects:**
```cmake
# Add version files to your target
target_sources(your_target PRIVATE src/version.c)
```

**For Node.js projects:**
```json
{
  "scripts": {
    "build": "node build.js && increment_version",
    "version": "node -e \"console.log(require('./package.json').version)\""
  }
}
```

### 7. Create Initial Version Tag
```bash
# Start with initial version
git tag v0.1.0
```

## Usage Pattern
```bash
./build.sh          # v0.1.0 → v0.1.1
./build.sh release  # v0.1.1 → v0.1.2
./build.sh package  # v0.1.2 → v0.1.3
```

## Manual Version Control

### Major/Minor Version Bumps
```bash
# For feature releases (minor bump)
git tag v0.2.0  # Next build: v0.2.1

# For breaking changes (major bump)
git tag v1.0.0  # Next build: v1.0.1
```

### Version Reset
```bash
# Delete incorrect tags (if needed)
git tag -d v0.2.1
git push origin --delete v0.2.1  # If pushed to remote

# Create correct base version
git tag v0.2.0

# Next build will create v0.2.1
```

## Example Build Script Template
```bash
#!/bin/bash
set -e

# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
NC='\033[0m'

print_status() { echo -e "${BLUE}[INFO]${NC} $1"; }
print_success() { echo -e "${GREEN}[SUCCESS]${NC} $1"; }
print_warning() { echo -e "${YELLOW}[WARNING]${NC} $1"; }
print_error() { echo -e "${RED}[ERROR]${NC} $1"; }

# Insert increment_version function here

case "${1:-build}" in
    build)
        increment_version
        print_status "Building project..."
        # Your build commands
        ;;
    clean)
        print_status "Cleaning build artifacts..."
        # Your clean commands
        ;;
    test)
        print_status "Running tests..."
        # Your test commands (no version increment)
        ;;
    release)
        increment_version
        print_status "Building release..."
        # Your release commands
        ;;
    *)
        echo "Usage: $0 {build|clean|test|release}"
        exit 1
        ;;
esac
```

## Benefits
1. **Zero maintenance** - No manual version editing
2. **Build traceability** - Every build has unique version + metadata
3. **Git integration** - Automatic version tags
4. **Language agnostic** - Adapt generation for any language
5. **CI/CD friendly** - Works in automated environments
6. **Rollback friendly** - Easy to revert to previous versions

## Troubleshooting

### Version Not Incrementing
- Ensure you're in a git repository
- Check that git tags exist: `git tag --list`
- Verify tag format matches `v*.*.*` pattern

### Tag Already Exists
If a tag already exists, the build continues with existing version:
```
[WARNING] Tag v0.2.1 already exists - using existing version
```

### Missing Git Information
If git is unavailable, version files show "unknown" for git hash and branch.
