How to fix fatal: could not read Username for 'https://github.com': terminal prompts disabled in Git
The 'terminal prompts disabled' error occurs when Git needs to prompt for credentials but runs in a non-interactive environment. This commonly happens in CI/CD pipelines, scripts, or automated processes where there's no terminal to receive user input.
Quick fix
Fixes fatal: could not read Username for 'https://github.com': terminal prompts disabled
# In your workflow file
steps:
- name: Clone private repo
run: |
git clone https://x-access-token:${{ secrets.GITHUB_TOKEN }}@github.com/owner/repo.git- Use a Personal Access Token in CI/CD environments
- Configure SSH authentication for automated access
- Set credentials before Git operations in scripts
- Fix Docker builds with git authentication
# In your workflow filesteps:- name: Clone private reporun: |git clone https://x-access-token:${{ secrets.GITHUB_TOKEN }}@github.com/owner/repo.gitfatal: could not read Username for 'https://github.com': terminal prompts disabled
What this error means
This error indicates that Git attempted to authenticate with a remote repository but couldn't prompt for credentials because terminal prompts have been disabled. Git sets the environment variable `GIT_TERMINAL_PROMPT=0` automatically in certain contexts, or you may have set it manually. When Git needs credentials to access a repository over HTTPS and no cached credentials are available, it normally prompts for a username and password. However, in non-interactive environments like: - CI/CD pipelines (GitHub Actions, GitLab CI, Jenkins, etc.) - Scripts running without a TTY - Docker builds - Cron jobs - Background processes Git cannot display a prompt or read user input, so it fails with this error instead of hanging indefinitely waiting for input that will never come. The error specifically tells you Git tried to read a "Username" but couldn't because it had no way to ask you for it. This is a safety feature - without it, automated processes would hang forever waiting for credentials.
Typical symptoms
- Git clone, fetch, push, or pull fails in CI/CD pipelines
- Automated scripts fail when accessing private repositories
- Docker builds fail during git clone operations
- Cron jobs that use git report authentication failures
- SSH into a server and running git commands without proper credential setup fails
- Submodule updates fail in automated environments
- Error only appears when running non-interactively; works fine in terminal
- GitHub Actions or GitLab CI jobs fail on git operations
Common causes
- Running git in a non-interactive environment without pre-configured credentials
- GIT_TERMINAL_PROMPT environment variable set to 0
- No credential helper configured for automated access
- CI/CD environment lacks authentication tokens or SSH keys
- Docker container running git without mounted credentials
- Git attempting HTTPS authentication without cached credentials
- SSH agent not available or not forwarded in remote sessions
- Repository URL is HTTPS but only SSH keys are configured
- Missing or expired Personal Access Token in CI/CD secrets
- Submodule URLs requiring authentication not configured with tokens
How to fix "fatal: could not read Username for 'https://github.com': terminal prompts disabled"
The most common solution for CI/CD pipelines is to use a Personal Access Token (PAT) embedded in the repository URL or provided via environment variables.
Method 1: URL with embedded token (GitHub Actions example):
# In your workflow file
steps:
- name: Clone private repo
run: |
git clone https://x-access-token:${{ secrets.GITHUB_TOKEN }}@github.com/owner/repo.gitMethod 2: Configure Git to use token for all HTTPS requests:
# Set up credential helper with token
git config --global credential.helper '!f() { echo "password=${GH_TOKEN}"; }; f'
# Or use the URL directly
git config --global url."https://${GH_TOKEN}@github.com/".insteadOf "https://github.com/"For GitHub Actions specifically:
- name: Checkout with token
uses: actions/checkout@v4
with:
token: ${{ secrets.PAT_TOKEN }}
submodules: recursiveGenerate a PAT on GitHub:
1. Go to Settings > Developer settings > Personal access tokens
2. Generate new token with repo scope
3. Add it as a secret in your CI/CD system
SSH keys don't require terminal prompts, making them ideal for automated environments.
Step 1: Generate a deploy key (for CI/CD):
ssh-keygen -t ed25519 -C "ci@example.com" -f ./deploy_key -N ""Step 2: Add public key to GitHub repository:
1. Go to repository Settings > Deploy keys
2. Add the contents of deploy_key.pub
3. Enable "Allow write access" if pushing is needed
Step 3: Configure CI/CD to use the key:
# GitHub Actions example
steps:
- name: Setup SSH
run: |
mkdir -p ~/.ssh
echo "${{ secrets.DEPLOY_KEY }}" > ~/.ssh/id_ed25519
chmod 600 ~/.ssh/id_ed25519
ssh-keyscan github.com >> ~/.ssh/known_hosts
- name: Clone via SSH
run: git clone git@github.com:owner/repo.gitFor GitLab CI:
before_script:
- eval $(ssh-agent -s)
- echo "$SSH_PRIVATE_KEY" | ssh-add -
- mkdir -p ~/.ssh && chmod 700 ~/.ssh
- ssh-keyscan gitlab.com >> ~/.ssh/known_hostsWhen running Git in scripts, pre-configure credentials before any git commands run.
Using git credential fill:
#!/bin/bash
# Pre-fill credentials before git commands
echo "protocol=https
host=github.com
username=${GIT_USERNAME}
password=${GIT_TOKEN}" | git credential approve
# Now git commands will use these credentials
git clone https://github.com/owner/private-repo.gitUsing .netrc file (Unix/Linux/macOS):
# Create or update ~/.netrc
cat > ~/.netrc << EOF
machine github.com
login ${GIT_USERNAME}
password ${GIT_TOKEN}
EOF
chmod 600 ~/.netrc
# Git will automatically use .netrc for authentication
git clone https://github.com/owner/repo.gitUsing Git askpass helper:
# Create a helper script
echo '#!/bin/bash
echo "${GIT_PASSWORD}"' > /tmp/git-askpass.sh
chmod +x /tmp/git-askpass.sh
# Set environment variables
export GIT_ASKPASS=/tmp/git-askpass.sh
export GIT_PASSWORD="your-token-here"
# Git will now use the askpass script instead of prompting
git clone https://github.com/owner/repo.gitDocker builds are non-interactive by default. Here's how to handle git authentication:
Method 1: Build arguments with token:
# Dockerfile
ARG GIT_TOKEN
RUN git config --global url."https://${GIT_TOKEN}@github.com/".insteadOf "https://github.com/"
RUN git clone https://github.com/owner/private-repo.git# Build with token
docker build --build-arg GIT_TOKEN=$GH_TOKEN .Method 2: SSH mount (Docker BuildKit):
# syntax=docker/dockerfile:1
FROM alpine
RUN apk add --no-cache git openssh-client
RUN mkdir -p -m 0700 ~/.ssh && ssh-keyscan github.com >> ~/.ssh/known_hosts
RUN --mount=type=ssh git clone git@github.com:owner/repo.git# Build with SSH agent
DOCKER_BUILDKIT=1 docker build --ssh default .Method 3: Secret mount (Docker BuildKit):
# syntax=docker/dockerfile:1
FROM alpine
RUN apk add --no-cache git
RUN --mount=type=secret,id=gittoken \
GIT_TOKEN=$(cat /run/secrets/gittoken) && \
git clone https://x-access-token:${GIT_TOKEN}@github.com/owner/repo.gitecho "your-token" > .gittoken
DOCKER_BUILDKIT=1 docker build --secret id=gittoken,src=.gittoken .Important: Never bake tokens into image layers - use multi-stage builds or secrets.
Submodules often cause this error because each submodule may require separate authentication.
Configure submodule URLs to use tokens:
# Replace HTTPS URLs with token-embedded URLs
git config --global url."https://x-access-token:${GH_TOKEN}@github.com/".insteadOf "https://github.com/"
# Initialize and update submodules
git submodule update --init --recursiveUsing .gitmodules URL rewriting:
# In your CI script, before submodule init
git config submodule.path/to/submodule.url "https://token@github.com/owner/submodule.git"
git submodule update --initGitHub Actions with submodules:
- uses: actions/checkout@v4
with:
submodules: recursive
token: ${{ secrets.PAT_WITH_REPO_ACCESS }}Note: The default GITHUB_TOKEN only has access to the current repository. For private submodules in other repos, you need a PAT with broader access.
Convert submodules to SSH (if using SSH auth):
# In .gitmodules, change:
# url = https://github.com/owner/repo.git
# to:
# url = git@github.com:owner/repo.gitIf you're still having issues, use these commands to debug:
Check if terminal prompts are disabled:
echo $GIT_TERMINAL_PROMPT
# If this outputs "0", prompts are disabledEnable verbose Git output:
GIT_TRACE=1 GIT_CURL_VERBOSE=1 git clone https://github.com/owner/repo.gitCheck credential helper configuration:
git config --list --show-origin | grep credentialTest credential helper manually:
echo "protocol=https
host=github.com" | git credential fillVerify SSH connectivity (if using SSH):
ssh -vT git@github.comTemporarily enable prompts for testing:
# Unset the variable
unset GIT_TERMINAL_PROMPT
# Or explicitly enable
export GIT_TERMINAL_PROMPT=1Check if running in a TTY:
if [ -t 0 ]; then
echo "Running interactively"
else
echo "Running non-interactively - need pre-configured credentials"
fiAdvanced notes
### Understanding GIT_TERMINAL_PROMPT
Git automatically sets GIT_TERMINAL_PROMPT=0 in certain scenarios:
- When stdin is not a terminal (TTY)
- In some CI/CD environments
- When running as a subprocess of certain tools
You can control this behavior:
# Force disable prompts (useful for scripts that should fail fast)
export GIT_TERMINAL_PROMPT=0
# Force enable prompts
export GIT_TERMINAL_PROMPT=1### GitHub Actions Specifics
The GITHUB_TOKEN has limitations:
- Only works for the repository running the workflow
- Cannot access other private repositories
- Cannot trigger other workflows
For accessing multiple repos, create a PAT:
1. Use fine-grained tokens for specific repositories
2. Or classic tokens with repo scope for broader access
# Using PAT for multiple repo access
env:
GH_TOKEN: ${{ secrets.PAT_TOKEN }}
steps:
- run: |
git config --global url."https://x-access-token:${GH_TOKEN}@github.com/".insteadOf "https://github.com/"### GitLab CI Specifics
GitLab provides CI_JOB_TOKEN automatically:
script:
- git clone https://gitlab-ci-token:${CI_JOB_TOKEN}@gitlab.com/group/project.gitFor cross-project access, use deploy tokens or personal access tokens stored in CI/CD variables.
### Jenkins Pipeline
pipeline {
agent any
environment {
GIT_CREDENTIALS = credentials('git-credentials-id')
}
stages {
stage('Clone') {
steps {
sh '''
git config --global credential.helper '!f() { echo "password=${GIT_CREDENTIALS_PSW}"; }; f'
git clone https://${GIT_CREDENTIALS_USR}@github.com/owner/repo.git
'''
}
}
}
}### Security Best Practices
1. Never commit tokens to repositories - Use CI/CD secrets
2. Use short-lived tokens - Set expiration dates
3. Principle of least privilege - Only grant necessary scopes
4. Rotate tokens regularly - Especially after any potential exposure
5. Use deploy keys for single-repo access - More secure than PATs
6. Consider GitHub App tokens - More granular and auditable
### Troubleshooting Hanging Git Commands
If git hangs instead of failing (prompts not properly disabled):
# Set timeout for git operations
timeout 60 git clone https://github.com/owner/repo.git
# Or with environment variable
export GIT_TERMINAL_PROMPT=0### Working with Git LFS
Git LFS also respects terminal prompts settings:
# Configure LFS to use the same credentials
git config --global lfs.https://github.com/.access basic
git config --global credential.helper '!f() { echo "password=${GH_TOKEN}"; }; f'Frequently asked questions
- What does "fatal: could not read Username for 'https://github.com': terminal prom" mean?
- This error indicates that Git attempted to authenticate with a remote repository but couldn't prompt for credentials because terminal prompts have been disabled. Git sets the environment variable GIT_TERMINAL_PROMPT=0 automatically in certain contexts, or you may have set it manually. When Git needs credentials to access a repository over HTTPS and no cached credentials are available, it normally prompts for a username and password.
- How do I fix "fatal: could not read Username for 'https://github.com': terminal prom"?
- The 'terminal prompts disabled' error occurs when Git needs to prompt for credentials but runs in a non-interactive environment. This commonly happens in CI/CD pipelines, scripts, or automated processes where there's no terminal to receive user input.
- What causes "fatal: could not read Username for 'https://github.com': terminal prom"?
- Running git in a non-interactive environment without pre-configured credentials GIT_TERMINAL_PROMPT environment variable set to 0 No credential helper configured for automated access
- Is the "fatal: could not read Username for 'https://github.com': terminal prom" error serious?
- It is a medium-severity error — more of a blocker than a risk. The steps above resolve it.
Official resources & further reading
- 📚Git Official Documentation
- 📖Git Documentation - GIT_TERMINAL_PROMPT(Official Docs)
- 📖GitHub Docs - Automatic token authentication(Official Docs)
- 📖GitHub Docs - Managing Personal Access Tokens(Official Docs)
- 💬
- 💬Stack Overflow - Git clone in Docker container(Stack Overflow)
- 📖GitLab Docs - CI/CD job token(Official Docs)