What's Actually Happening
Jenkins pipeline execution fails at a specific stage. Pipeline stops and subsequent stages don not execute.
The Error You'll See
Jenkins UI:
Stage 'Build' failed
Error: script returned exit code 1Pipeline log:
[Pipeline] stage
[Pipeline] { (Build)
[Pipeline] sh
+ npm run build
npm ERR! missing script: build
[Pipeline] }
[Pipeline] // stage
[Pipeline] stage
[Pipeline] { (Test) <-- Not executed
Stage 'Test' skipped due to earlier failure(s)Console output:
ERROR: script returned exit code 1
Finished: FAILUREWhy This Happens
- 1.Command failed - Shell command returns non-zero exit code
- 2.Script error - Pipeline script has syntax or runtime error
- 3.Missing dependency - Required tool or file not present
- 4.Timeout exceeded - Stage exceeds configured timeout
- 5.Permission denied - Insufficient permissions for operation
- 6.Agent offline - Build agent not available
Step 1: Check Pipeline Console Output
```bash # View console output in Jenkins UI: # Job -> Build Number -> Console Output
# Or via API: curl -u user:token "http://jenkins/job/myjob/123/consoleText"
# Check full log: curl -u user:token "http://jenkins/job/myjob/123/log" | less
# Filter for errors: curl -u user:token "http://jenkins/job/myjob/123/consoleText" | grep -i "error|failed"
# Check specific stage output: # In UI, click on stage in pipeline visualization
# Download logs: curl -u user:token "http://jenkins/job/myjob/123/consoleText" > pipeline.log ```
Step 2: Check Jenkinsfile Syntax
```groovy # Validate Jenkinsfile: # In Jenkins UI: Pipeline Syntax -> Replay
# Check pipeline structure: pipeline { agent any stages { stage('Build') { steps { sh 'npm run build' } } } }
# Common syntax errors: # Missing braces # Wrong agent declaration # Invalid step syntax
# Use declarative linting: # Pipeline Linter Plugin validates syntax
# Or use Replay to test modified Jenkinsfile: # Job -> Build Number -> Replay -> Edit Jenkinsfile -> Run ```
Step 3: Check Stage Commands
```bash # Check command executed in stage: # In Jenkinsfile: stage('Build') { steps { sh 'npm run build' # This command failed } }
# Test command manually: # SSH to Jenkins agent: ssh jenkins-agent
# Run command: npm run build
# Check exit code: npm run build echo $? # Should be 0
# Check if command exists: which npm
# Check npm scripts: npm run # List available scripts
# Check package.json: cat package.json | grep scripts
# Add missing script: npm pkg set scripts.build="webpack --mode production" ```
Step 4: Check Agent Environment
```bash # Check agent status: # In Jenkins UI: Manage Jenkins -> Nodes
# Or via API: curl -u user:token "http://jenkins/computer/api/json?tree=computer[displayName,offline]"
# Check agent offline: curl -u user:token "http://jenkins/computer/agent-name/api/json" | jq .offline
# Check agent logs: # Manage Jenkins -> Nodes -> agent-name -> Logs
# SSH to agent and test: ssh jenkins-agent
# Check environment: echo $PATH echo $JAVA_HOME echo $NODE_HOME
# Check tools: java -version node --version npm --version git --version
# Check workspace: ls -la /home/jenkins/workspace/myjob/ ```
Step 5: Check Dependencies and Tools
```bash # Check required files: stage('Build') { steps { sh 'npm run build' # Needs package.json } }
# Check package.json exists: ls package.json
# Check node_modules: ls node_modules/
# Install dependencies: npm install
# Check specific tool: stage('Deploy') { steps { sh 'docker push image' # Needs docker } }
# Test docker: docker --version docker ps
# Check credentials: # Jenkins credentials for docker login: # Manage Jenkins -> Credentials
# Use credentials in pipeline: stage('Deploy') { steps { withCredentials([usernamePassword(credentialsId: 'docker-creds', usernameVariable: 'USER', passwordVariable: 'PASS')]) { sh 'docker login -u $USER -p $PASS' } } } ```
Step 6: Check Stage Timeout
```groovy # Check timeout configuration: stage('Build') { options { timeout(time: 10, unit: 'MINUTES') } steps { sh 'npm run build' } }
# If build takes longer, stage fails
# Increase timeout: options { timeout(time: 30, unit: 'MINUTES') }
# Or remove timeout for testing: stage('Build') { steps { sh 'npm run build' } }
# Check actual build time: # Previous successful builds - compare duration
# Use retry for flaky stages: stage('Test') { options { retry(3) } steps { sh 'npm test' } } ```
Step 7: Check Error Handling
```groovy # Add error handling to stage: stage('Build') { steps { script { try { sh 'npm run build' } catch (Exception e) { echo "Build failed: ${e.getMessage()}" currentBuild.result = 'FAILURE' throw e } } } }
# Use catchError for non-blocking failure: stage('Build') { steps { catchError(buildResult: 'UNSTABLE', stageResult: 'FAILURE') { sh 'npm run build' # Continue even if fails } } }
# Check post actions: post { always { echo 'Pipeline completed' } failure { mail to: 'admin@example.com', subject: "Pipeline failed: ${currentBuild.fullDisplayName}", body: "Check console output at ${env.BUILD_URL}" } } ```
Step 8: Check Permissions and Credentials
```bash # Check file permissions: stage('Build') { steps { sh './build.sh' # Needs execute permission } }
# Add execute permission: sh 'chmod +x build.sh'
# Or in workspace: ssh jenkins-agent chmod +x /home/jenkins/workspace/job/build.sh
# Check directory permissions: ls -la /home/jenkins/workspace/
# Check Jenkins credentials: # Manage Jenkins -> Credentials -> System -> Global
# Use credentials in pipeline: environment { AWS_ACCESS_KEY_ID = credentials('aws-key-id') AWS_SECRET_ACCESS_KEY = credentials('aws-secret-key') }
# Check credential exists: curl -u user:token "http://jenkins/credentials/store/system/domain/_/api/json?tree=credentials[id]" ```
Step 9: Debug with Pipeline Steps
```groovy # Add debug output: stage('Build') { steps { echo "Current directory: ${pwd()}" echo "Environment: ${env}" sh 'ls -la' sh 'npm run build' } }
# Check environment variables: sh 'printenv | sort'
# Check specific variable: echo "BRANCH_NAME: ${env.BRANCH_NAME}" echo "BUILD_NUMBER: ${env.BUILD_NUMBER}"
# Use script block for debugging: stage('Debug') { steps { script { def workspace = pwd() echo "Workspace: ${workspace}" def files = findFiles(glob: '**/*.json') echo "JSON files: ${files}" } } }
# Add verbose output: sh 'npm run build --verbose' ```
Step 10: Jenkins Pipeline Verification Script
```bash # Create verification script: cat << 'EOF' > /usr/local/bin/check-jenkins-pipeline.sh #!/bin/bash
JOB=$1 BUILD=$2 JENKINS_URL="http://jenkins"
echo "=== Jenkins Status ===" curl -s -u user:token "$JENKINS_URL/api/json?tree=jobs[name,color]" | jq .
echo "" echo "=== Job Info ===" curl -s -u user:token "$JENKINS_URL/job/$JOB/api/json?tree=name,lastBuild[number,result,duration],lastCompletedBuild[number,result]" | jq .
echo "" echo "=== Build Result ===" curl -s -u user:token "$JENKINS_URL/job/$JOB/$BUILD/api/json?tree=result,duration,stages[state,name,error]" | jq .
echo "" echo "=== Console Output (last 50 lines) ===" curl -s -u user:token "$JENKINS_URL/job/$JOB/$BUILD/consoleText" | tail -50
echo "" echo "=== Errors ===" curl -s -u user:token "$JENKINS_URL/job/$JOB/$BUILD/consoleText" | grep -i "error|failed|exception" | head -20
echo "" echo "=== Agent Status ===" curl -s -u user:token "$JENKINS_URL/computer/api/json?tree=computer[displayName,offline,offlineCauseReason]" | jq . EOF
chmod +x /usr/local/bin/check-jenkins-pipeline.sh
# Usage: /usr/local/bin/check-jenkins-pipeline.sh myjob 123
# Replay and fix: # Jenkins UI: Job -> Build Number -> Replay -> Edit -> Run ```
Jenkins Pipeline Checklist
| Check | Command | Expected |
|---|---|---|
| Console output | View in UI | Identify error |
| Command test | SSH agent | Command succeeds |
| Agent status | Nodes page | Online |
| Tools installed | which command | Tool found |
| Dependencies | ls workspace | Files present |
| Jenkinsfile syntax | Replay test | Syntax valid |
Verify the Fix
```bash # After fixing pipeline stage
# 1. Rebuild pipeline # Trigger new build // Stage passes
# 2. Check console curl "http://jenkins/job/job/124/consoleText" // No errors
# 3. Verify all stages # View pipeline visualization // All stages completed
# 4. Check build result curl "http://jenkins/job/job/124/api/json" | jq .result // SUCCESS
# 5. Test on agent ssh agent && npm run build // Command works
# 6. Monitor future builds # Check if issue persists // Consistent success ```
Related Issues
- [Fix Jenkins Build Stuck](/articles/fix-jenkins-build-stuck)
- [Fix GitLab CI Pipeline Stuck](/articles/fix-gitlab-ci-pipeline-stuck)
- [Fix GitHub Actions Workflow Failed](/articles/fix-github-actions-workflow-failed)