Ravindra BagaleCourses & study guides मराठी

Chapter 24: Jenkins with GitHub, GitLab and Bitbucket

24.6 Branch indexing and orphaned items

Why: the problem

Think of Myntra before a big sale. The app repo has 300 branches. Half of them were merged and deleted months ago. But Jenkins still shows 300 child jobs, many red, many from people who left. The disk on the Jenkins server is 92 percent full of old workspaces and logs. A new person cannot find the real jobs. This happens because of two things. Branch indexing is how Jenkins finds branches. Orphaned items are child jobs whose branch is gone. If you never set an orphaned item strategy, Jenkins keeps them forever. In this lesson you will read the indexing log, set rules to remove dead child jobs, limit which branches get jobs, and free disk space safely.

What we will build

You will make five short-lived feature branches in menu-api, scan, then delete three of them on the host. You will read the indexing log, see the orphaned jobs, and set Orphaned Item Strategy to keep at most 2 days and 5 items. You will add a branch name filter so only main, develop, release/ and feature/ get jobs. You will add a buildDiscarder so each child keeps only 20 builds, and you will measure the disk before and after.

What: every term in plain English

  • Branch indexing — The scan where Jenkins lists branches, PRs and tags and checks each for a Jenkinsfile.
  • Indexing log — The console of the scan. It says why each branch was added or skipped.
  • Orphaned item — A child job whose branch, PR or tag no longer exists on the host.
  • Orphaned Item Strategy — A Multibranch setting: how many days and how many orphaned jobs to keep.
  • Disabled item — An orphaned job shown in grey. It is not deleted until the strategy rule says so.
  • Branch filter — A rule with wildcards that lists which branch names get jobs.
  • buildDiscarder — A Jenkinsfile option that deletes old builds of a job.
  • JENKINS_HOME — The folder where Jenkins keeps jobs, builds and logs, often /var/jenkins_home.
Make five lab branches Scan and count jobs Delete three branches on the host Scan again and read the log Set the orphaned strategy Add a branch filter Scan and check disk
Indexing finds branches; the orphaned strategy cleans dead ones

How: step by step

  1. Make five lab branches

    for b in a b c d e; do git push gl main:refs/heads/feature/tmp-$b; done
    

    What it does: Five new branches on GitLab, same code as main.

    Output

    * [new branch]      main -> feature/tmp-a
    ...
     * [new branch]      main -> feature/tmp-e
    
  2. Scan and count jobs

    Scan Multibranch Pipeline Now, then count jobs in the folder
    

    What it does: Jenkins makes five more child jobs.

    Output

    9 child jobs
    
  3. Delete three branches on the host

    for b in a b c; do git push gl --delete feature/tmp-$b; done
    

    What it does: These three are now orphans in Jenkins.

    Output

    - [deleted]         feature/tmp-a
     - [deleted]         feature/tmp-b
     - [deleted]         feature/tmp-c
    
  4. Scan again and read the log

    menu-api-mb > Scan Multibranch Pipeline Log
    

    What it does: Shows the orphans found.

    Output

    Will not remove feature/tmp-a because it is new
    3 orphaned items found
    
  5. Set the orphaned strategy

    Configure > Orphaned Item Strategy > Discard old items > Days to keep: 2 > Max # to keep: 5
    

    What it does: Jenkins removes old orphans on the next scan.

    Output

    (saved)
    
  6. Add a branch filter

    Behaviours > Add > Filter by name (with wildcards) > Include: main develop release/* feature/* > Exclude: feature/tmp-*
    

    What it does: Only real branches get jobs.

    Output

    (saved)
    
  7. Scan and check disk

    Scan Now; then du -sh /var/jenkins_home/jobs/menu-api-mb
    

    What it does: The folder is smaller.

    Output

    Removing orphaned item feature/tmp-a
    ...
    18M /var/jenkins_home/jobs/menu-api-mb
    

Example 1: Read the indexing log line by line

Stack. Multibranch indexing

Goal. Read the indexing log line by line.

Scan Multibranch Pipeline Log

Started by timer
[Sun Oct 25 10:30:00 IST 2026] Starting branch indexing...
Checking branches...
  Checking branch main
      'Jenkinsfile' found
    Met criteria
No changes detected: main (still at 9b77d10)
  Checking branch feature/no-ci
      'Jenkinsfile' not found
    Does not meet criteria
  Checking branch feature/tmp-d
    Met criteria
Changes detected: feature/tmp-d (null -> 9b77d10)
Scheduled build for branch: feature/tmp-d
Processed 4 branches
Evaluating orphaned items in menu-api-mb
Will remove feature/tmp-a
Will remove feature/tmp-b
Will remove feature/tmp-c
Finished: SUCCESS

What each line does

  • Started by timer — The periodic scan ran. "Started by GitLab push" would mean a webhook.
  • 'Jenkinsfile' found / Met criteria — The branch will have a child job.
  • No changes detected — Same commit as last time, so no new build.
  • 'Jenkinsfile' not found / Does not meet criteria — No child job. This is why a branch is missing.
  • Changes detected (null -> 9b77d10) — A new branch. Jenkins schedules its first build.
  • Will remove feature/tmp-a — The orphaned strategy will delete this child job.

Green output

Removed orphaned item: feature/tmp-a
Removed orphaned item: feature/tmp-b
Removed orphaned item: feature/tmp-c

Expected result. You can explain every line. When a branch has no job, you search this log for its name first.

Example 2: Keep each child small with buildDiscarder and a clean workspace

Stack. Workspace Cleanup plugin

Goal. Keep each child small with buildDiscarder and a clean workspace.

Jenkinsfile

pipeline {
  agent any
  options {
    buildDiscarder(logRotator(numToKeepStr: env.BRANCH_NAME == 'main' ? '50' : '10',
                              artifactNumToKeepStr: '5'))
    disableConcurrentBuilds()
    timeout(time: 20, unit: 'MINUTES')
  }
  stages {
    stage('Test') { steps { sh 'npm ci || npm install'; sh 'npm test' } }
  }
  post {
    cleanup { cleanWs() }
  }
}

What each line does

  • numToKeepStr: env.BRANCH_NAME == 'main' ? '50' : '10' — Keep 50 builds on main for history, only 10 on other branches.
  • artifactNumToKeepStr: '5' — Keep files of only the last 5 builds. Files are what fill the disk.
  • disableConcurrentBuilds() — One build per branch at a time.
  • timeout(time: 20, unit: 'MINUTES') — Kill a stuck build so it does not hold an agent all night.
  • cleanup { cleanWs() } — Delete the workspace after the build. Needs the Workspace Cleanup plugin.

Green output

[Pipeline] cleanWs
[WS-CLEANUP] Deleting project workspace...
[WS-CLEANUP] done
Finished: SUCCESS

$ ls /var/jenkins_home/jobs/menu-api-mb/branches/feature-badge-color/builds | wc -l
10

Expected result. Old builds go away by themselves. The workspace folder is empty after each build.

Example 3: Find the biggest jobs on disk and clean them safely

Stack. Linux, Jenkins on EC2

Goal. Find the biggest jobs on disk and clean them safely.

disk-report.sh

#!/usr/bin/env bash
set -euo pipefail
JH=/var/jenkins_home
echo "== disk"
df -h "$JH" | tail -1
echo "== top 5 job folders"
du -sh "$JH"/jobs/* 2>/dev/null | sort -rh | head -5
echo "== workspaces older than 7 days"
find "$JH"/workspace -mindepth 1 -maxdepth 1 -type d -mtime +7 | wc -l

What each line does

  • df -h "$JH" — How full the disk is.
  • du -sh ... | sort -rh | head -5 — The five biggest job folders.
  • find ... -mtime +7 — Workspaces not touched for 7 days. Safe to remove; Jenkins makes them again.
  • Do not delete builds folders by hand — Jenkins keeps an index. Use buildDiscarder or the UI, then restart is not needed.
  • 2>/dev/null — Hides errors for folders you cannot read.

Green output

== disk
/dev/nvme1n1  50G  46G  4.0G  92% /var/jenkins_home
== top 5 job folders
21G /var/jenkins_home/jobs/shop-app-mb
6.1G    /var/jenkins_home/jobs/menu-api-mb
...
== workspaces older than 7 days
212

Expected result. You know which job to fix first. After adding the strategy and discarder to shop-app-mb, the disk drops from 92 to 61 percent.

Verify: did it work?

  1. Count orphaned (disabled) child jobs

    curl -s -u ravi:$JENKINS_TOKEN "http://localhost:8080/job/menu-api-mb/api/json?tree=jobs[name,color]" | jq "[.jobs[] | select(.color==\"disabled\")] | length"
    

    What it does: Should go to 0 after the strategy runs.

    Output

    0
    
  2. Check builds kept on a branch

    ls /var/jenkins_home/jobs/menu-api-mb/branches/main/builds | grep -c "^[0-9]"
    

    What it does: Should be 50 or less on main.

    Output

    50
    

When it is red 1

Deleted branch still shows as a grey job for days

Cause. Orphaned Item Strategy is not set, or Days to keep is large.

Fix, step by step

  1. Set Discard old items with small numbers.
  2. Run a scan; removal happens during indexing.

When it is red 2

Branch exists on the host but no job appears

Cause. No Jenkinsfile on that branch, or the name filter excludes it.

Fix, step by step

  1. Search the indexing log for the branch.
  2. Check Include and Exclude in Filter by name.

When it is red 3

java.io.IOException: No space left on device

Cause. The Jenkins disk is full, usually from builds, artifacts and workspaces.

Fix, step by step

  1. Run disk-report.sh.
  2. Add buildDiscarder and orphaned strategy.
  3. Move artifacts to S3 or Nexus.
  4. Grow the EBS volume if still needed.

Cleanup

  1. Delete the last lab branches

    for b in d e; do git push gl --delete feature/tmp-$b; done
    

    What it does: Leaves only real branches.

    Output

    - [deleted]         feature/tmp-d
     - [deleted]         feature/tmp-e
    
  2. Rescan

    Scan Multibranch Pipeline Now
    

    What it does: Removes their jobs if the rule allows.

    Output

    Removed orphaned item: feature/tmp-d
    

Ravindra Bagale's Tip

Juni branch geli tar tichi job pan javi. Orphaned strategy set kara. Lakshat theva!

Practice tasks

Easy Read one scan log

Why: Logs answer most "where is my job" questions.

What to do: Explain every line of one indexing log.

How:
  1. Open the scan log.
  2. Write one line per message.

Check: You can say why each branch has or has no job.

Medium Set the cleanup rules

Why: Without rules the disk fills up.

What to do: Add an orphaned strategy and buildDiscarder to one job.

How:
  1. Days 2, max 5.
  2. Keep 10 builds on branches.

Check: Old jobs and builds disappear on the next scan.

Hard Write a disk report

Why: On-call people need numbers fast.

What to do: Run disk-report.sh weekly and save results.

How:
  1. Add it as a small Jenkins job on a timer.

Check: You have two weeks of numbers.

Easy Say branch indexing and orphaned items in two lines

Why: If you can say it simply, you understand it. Juniors and interviewers both want the short version first.

What to do: Write two short lines about branch indexing and orphaned items for a fresher who knows only Linux and Git basics.

How:
  1. Write the problem it solves.
  2. Write the one Jenkinsfile step or command you use for it.
  3. Read it aloud to a friend.

Check: A fresher understands it without asking a question.

Easy Start a fresh lab Jenkins

Why: Practice needs a throwaway Jenkins. If you break it, you delete it and start again.

What to do: Run Jenkins LTS in Docker with a named volume.

How:
  1. docker volume create jenkins_home
  2. docker run -d --name jenkins -p 8080:8080 -v jenkins_home:/var/jenkins_home jenkins/jenkins:lts-jdk17
  3. docker logs jenkins 2>&1 | grep -A2 "initialAdminPassword"

Check: The Jenkins login page opens on localhost:8080.

Medium Do it on the second setup

Why: A release idea must work on a VM, on Docker and on Kubernetes. Only the deploy step should change.

What to do: Repeat this lesson on a different target than the one you used first.

How:
  1. If you used Docker, use kind or minikube now.
  2. Change only the deploy commands.
  3. Keep the same Jenkinsfile stages.

Check: Same result, and the stage names did not change.

Medium Break it on purpose

Why: You must know the red output by face. In a real outage there is no time to read slowly.

What to do: Cause one error from the "When it is red" part of this lesson and fix it.

How:
  1. Follow the error section.
  2. Copy the exact message into your notes.
  3. Write the fix in one line.

Check: You fixed it using only the steps, without searching the web.

Medium Write a release runbook page

Why: At 2 a.m. nobody remembers flags. A short page saves the on-call person.

What to do: Write a one-page runbook for this lesson.

How:
  1. Title, when to use, exact commands, how to check, how to undo.

Check: A teammate can follow it alone.

Hard Explain it like an interview

Why: Interviewers want real stories, not definitions.

What to do: Record a 60 second answer about this lesson.

How:
  1. Say the problem, the Jenkinsfile step, and one error you hit.

Check: Your answer has a real command and a real error message.

Hard Draw the flow top to bottom

Why: A drawing shows the order of work and who is waiting on whom.

What to do: Draw this lesson as boxes from top to bottom.

How:
  1. Start at git push, go through the stages, end at the check in production.

Check: Each box matches a real step you ran.

Homework: try at home

Try at home

At home, make five branches, scan, delete three and watch the orphaned jobs. Set an orphaned strategy and a buildDiscarder and write the disk size before and after.

Recap

  • Branch indexing scans the host and makes or skips child jobs.
  • The indexing log tells you why a branch has no job.
  • Set an Orphaned Item Strategy so dead child jobs go away.
  • Use name filters to stop junk branches.
  • Use buildDiscarder and cleanWs to keep the disk small.

FAQ

Will the strategy delete my main job?

No. Only orphans, whose branch is gone.

Can I see orphaned jobs before they go?

Yes. They are shown disabled until removed.

Why not set days to 0?

A branch deleted by mistake would lose its history at once. Keep a day or two.

Does a webhook also run indexing?

Yes. A push event triggers a light scan for that branch.

Should I store artifacts in Jenkins for months?

No. Push them to S3, Nexus or a registry.

Interview questions

  1. What is branch indexing?

    The Multibranch scan that finds branches, PRs and tags and checks for a Jenkinsfile.

  2. A branch has no job. How do you debug?

    Read the indexing log for it, check the Jenkinsfile exists, and check name filters.

  3. How do you stop Jenkins disk filling up?

    buildDiscarder, artifact limits, cleanWs, orphaned item strategy, and external artifact storage.

  4. What is the Orphaned Item Strategy?

    Rules for how long and how many orphaned child jobs to keep before deleting.

  5. Why use a branch name filter?

    To build only real branches and save agents and disk.

Quick quiz

Q1. What is an orphaned item?

A child job whose branch, PR or tag is gone.

Q2. Where do you see why a branch has no job?

In the indexing log.

Q3. Which option keeps only some builds?

buildDiscarder with logRotator.

Q4. When are orphaned items removed?

During a scan, by the Orphaned Item Strategy.

Q5. Is it safe to delete old workspaces?

Yes. Jenkins makes them again on the next build.

Samajla ka?