Secure Git Clone in Scripts Without Storing Credentials in Config


2 views



When automating Git operations, we often need to clone repositories with authentication. The naive approach:

git clone https://user:password@host.com/repo.git

While functional, this method permanently stores credentials in .git/config as plaintext, creating security vulnerabilities.

Method 1: Using Git Credential Helpers

Configure Git to use the built-in credential cache:

# Clone with temporary credentials
GIT_ASKPASS=/path/to/echo_script git clone https://host.com/repo.git

# Where echo_script contains:
#!/bin/sh
echo "$GIT_PASSWORD"

Set environment variables before cloning:

export GIT_USERNAME="your_user"
export GIT_PASSWORD="your_pass"
git clone https://$GIT_USERNAME:$GIT_PASSWORD@host.com/repo.git
unset GIT_USERNAME GIT_PASSWORD

Method 2: SSH Key Authentication

For more secure automation:

# Generate SSH key if needed
ssh-keygen -t ed25519 -f ~/.ssh/git_script_key

# Add to ssh-agent
eval "$(ssh-agent -s)"
ssh-add ~/.ssh/git_script_key

# Clone using SSH
git clone git@host.com:user/repo.git

Method 3: Personal Access Tokens (PAT)

For services like GitHub/GitLab:

# Store token in environment variable
export GIT_TOKEN="your_personal_access_token"

# Clone using token
git clone https://oauth2:$GIT_TOKEN@host.com/repo.git

Here's a complete script example using environment variables:

#!/bin/bash

# Read credentials from secure storage
GIT_USER=$(get-secret git-username)
GIT_PASS=$(get-secret git-password)

# Temporary clone URL
CLONE_URL="https://${GIT_USER}:${GIT_PASS}@host.com/repo.git"

# Clone and immediately clean config
git clone "$CLONE_URL" repo_dir \
  && git -C repo_dir remote set-url origin https://host.com/repo.git

# Clear credentials from memory
unset GIT_USER GIT_PASS CLONE_URL

For CI/CD systems, most provide secret management:

# GitHub Actions example
steps:
  - uses: actions/checkout@v3
    with:
      repository: owner/repo
      token: ${{ secrets.GITHUB_TOKEN }}


When automating Git operations in scripts, many developers use the basic authentication approach:

git clone https://username:password@host.com/repo.git

While convenient, this method permanently stores your credentials in the repository's .git/config file, creating security vulnerabilities. Anyone with access to the repository can see your credentials in plain text.

Here are several secure approaches to handle authentication in scripts:

1. Using Git Credential Helpers

The most robust solution is to use Git's built-in credential caching system:

# Cache credentials in memory for 15 minutes
git config --global credential.helper 'cache --timeout=900'

# Then clone without embedded credentials
git clone https://host.com/repo.git

The credentials will be prompted once and cached temporarily.

2. Environment Variables

For CI/CD pipelines, environment variables work well:

#!/bin/bash
export GIT_USERNAME="your_username"
export GIT_PASSWORD="your_password"

git clone https://${GIT_USERNAME}:${GIT_PASSWORD}@host.com/repo.git

This prevents credentials from being stored in config files.

3. SSH Authentication

For better security, use SSH keys:

# Generate SSH key if you don't have one
ssh-keygen -t ed25519 -C "your_email@example.com"

# Add to ssh-agent
eval "$(ssh-agent -s)"
ssh-add ~/.ssh/id_ed25519

# Clone using SSH
git clone git@host.com:repo.git

For persistent but secure storage, use the credential store:

# Configure credential store
git config --global credential.helper 'store --file ~/.git-credentials'

# First time will prompt for credentials
git clone https://host.com/repo.git

The credentials are stored encrypted in the specified file.

  • Never commit scripts with hardcoded credentials
  • Use temporary credential caching for interactive scripts
  • Prefer SSH keys for automation
  • For CI/CD, use environment variables or secret management tools
  • Regularly rotate credentials used in automation