Chapter 07Lesson 01~95 minutes

Build Parameters, Environment Variables, Build Causes, Schedules, Remote Triggers, and Parameterized Automation: Concepts, Architecture, and Mental Model

Treat every Jenkins parameter, environment value, schedule, and remote trigger as control-plane input that must be typed, validated, attributed to a cause, and tied to a specific queue/build identity before it can change anything.

ParametersEnvironmentBuild causesCronRemote APIInput validation

Learning objectives

  • Explain the trigger → cause/parameters → queue/build → environment → validated logic → side effect → evidence chain.
  • Distinguish parameter definitions, parameter values, environment variables, causes, queue items, and build records.
  • Use Jenkins cron hash syntax to spread scheduled load instead of creating avoidable timer herds.
  • Explain why API authentication, CSRF handling, and job-level remote tokens are different security mechanisms.
  • Describe why rerunning a build with the same visible inputs does not guarantee the same external outcome.

1. The problem: build inputs are a control plane

Parameters often look harmless because they arrive as text boxes, check boxes, environment variables, timer entries, or HTTP form fields. Operationally, however, they decide what code runs, which target is touched, whether a destructive branch is taken, and which external side effects are attempted. That makes them control-plane input, not merely convenience values.

A robust Jenkins job therefore answers more than “what value did the user type?” It records who or what caused the build, which parameter definition accepted the value, which queue item and build number resulted, what environment was constructed on the assigned agent, which validation gate ran, and which side effects actually occurred.

Chapter 07 rule: no string, checkbox, timer, webhook field, API payload, branch metadata, or environment value becomes trusted merely because Jenkins made it available to a build. Validate the value for the operation you intend to perform.

2. Causal mental model: from intent to evidence

The same job can start because a human clicked a button, a timer fired, SCM integration notified Jenkins, another job finished, or an authenticated API client posted a request. Jenkins preserves the cause separately from the parameter values. After queueing and agent allocation, parameter values may also appear as environment variables, but that environment is an execution interface—not a proof that the values are safe.

Parameterized automation — control input becomes execution only after validation
flowchart TD
  A[Human, timer, webhook, upstream job, or API client] --> B[Build cause]
  A --> C[Parameter values]
  D[Job parameter definitions + timer configuration] --> C
  B --> E[Queue item + build identity]
  C --> E
  E --> F[Agent environment and workspace]
  F --> G[Validation + authorization-aware job logic]
  G --> H[Bounded side effect or no-op]
  H --> I[Build record, logs, artifacts, external evidence]

Notice the boundary between environment construction and validated job logic. A value can be syntactically available in $TARGET and still be forbidden for the operation. The safest automation fails closed before it derives a path, shell command, API URL, package name, or production target from an untrusted value.

3. Keep the state layers separate

State What it answers Evidence
Parameter definition What inputs does the job advertise and what defaults/types exist? Job configuration or Jenkinsfile revision.
Parameter value What value did this build receive? Build parameters in UI/API; carefully selected non-secret log evidence.
Build cause Why did Jenkins schedule this execution? CauseAction, UI cause text, build JSON API.
Queue item Was work accepted but not yet assigned to an executor? Queue ID, queue API, blockage reason.
Build/run Which numbered execution actually started? Job full name, build number, URL, result.
Environment What key/value interface did the process receive on the agent? Selected variables, not a blind environment dump.
External side effect Did the requested maintenance/deployment change really occur? Target-side ID/state/health, not only Jenkins success.

4. Parameter types constrain UX, not trust

Jenkins supports common parameter types such as strings, choices, booleans, and password-style fields. Declarative Pipeline exposes parameters through the read-only params map and exports parameter values as environment variables when the build starts. Freestyle jobs likewise expose parameter values to build steps as environment variables.

Type Good use Production caution
String Ticket ID, bounded label, version identifier. Validate length/format and never concatenate into shell, path, SQL, URL, or resource names without a safe encoding/allowlist.
Choice Small allowlist such as dev or staging. Still validate in the executing logic because API/plugin behavior and future configuration may change.
Boolean DRY_RUN, optional verification switch. Be explicit about default behavior; absence/false must not accidentally mean “perform destructive work.”
Password-style parameter Rare transitional cases. Do not treat it as a credentials store. Jenkins Credentials or an external secret manager is the correct security boundary for real secrets.

Parameter names themselves should also be controlled. Jenkins security guidance warns that special environment variables such as PATH, LD_PRELOAD, or platform equivalents can alter program execution. Do not let arbitrary user-provided names become environment-variable names.

5. Environment variables are an interface with scope and precedence

Environment values can come from Jenkins itself, the job configuration, parameters, Pipeline environment blocks, tools, plugins, credentials bindings, and the agent operating system. The same-looking key can therefore have different ownership. Before using a value, know where it came from and whether that source is trusted.

printf 'job=%s build=%s url=%s\n' "$JOB_NAME" "$BUILD_NUMBER" "$BUILD_URL"
printf 'target=%s action=%s dry_run=%s\n' "$TARGET" "$ACTION" "$DRY_RUN"

Print only non-secret values you actually need. A full env or printenv dump can expose tokens, usernames, internal URLs, temporary credential-file paths, or plugin-specific data. Evidence collection should be selective.

6. Cause and input answer different questions

A manual build may carry the same parameters as a scheduled or API-triggered build, but its governance meaning is different. Jenkins core models causes such as user actions, timers, SCM triggers, upstream builds, and remote causes. Plugins can add more. Preserve the actual cause Jenkins reports instead of inferring it from a parameter value like TRIGGER=timer.

The build API can expose causes and parameters together. In a disposable lab, query only the fields you need; never use an API view that accidentally serializes secrets merely because it is convenient.

curl --silent --show-error \
  --user "$JENKINS_USER:$JENKINS_API_TOKEN" \
  "$JENKINS_URL/job/ch07-maintenance/lastBuild/api/json?tree=number,url,queueId,actions[causes[*],parameters[name,value]]"

7. Jenkins cron is capacity policy, not just a clock

Jenkins cron uses five fields similar to traditional cron, but adds the H (“hash”) symbol to distribute load. Prefer hashed schedules when exact wall-clock timing is unnecessary. For example, H/15 * * * * runs about every fifteen minutes at a stable hashed offset instead of forcing every job onto minute 0, 15, 30, and 45.

Timer caution: a schedule can fire even when the external system is degraded, a previous run is still active, or prerequisites have changed. Scheduled automation still needs validation, bounded concurrency, idempotency, and target-side verification.

8. Remote API calls need identity, authorization, and CSRF-aware clients

For a parameterized job, Jenkins' Remote API supports an authenticated HTTP POST to .../buildWithParameters with form data. Prefer a dedicated least-privilege user identity and API token over placing a legacy build token in a URL. URL query tokens can leak through shell history, browser history, proxy logs, or monitoring systems.

Jenkins CSRF protection remains enabled. Scripted requests authenticated with an API token are exempt from the crumb requirement; username/password clients generally need the crumb plus session cookie. Do not disable CSRF to “make curl work.”

curl --fail-with-body --silent --show-error --request POST \
  --user "$JENKINS_USER:$JENKINS_API_TOKEN" \
  --data-urlencode 'TARGET=dev' \
  --data-urlencode 'ACTION=inspect' \
  --data-urlencode 'DRY_RUN=true' \
  "$JENKINS_URL/job/ch07-maintenance/buildWithParameters"

A successful HTTP response proves request acceptance, not build completion. Follow the queue/build identity and inspect the resulting build record.

9. Validate before deriving paths, commands, or targets

The safest pattern is an allowlist followed by quoted direct arguments. Avoid eval, string-built shell commands, and ambiguous path concatenation. Validate the semantic target before any side effect.

case "$TARGET" in
  dev|staging) ;;
  *) printf 'Rejected target: %s\n' "$TARGET" >&2; exit 64 ;;
esac
case "$ACTION" in
  inspect|rotate-cache) ;;
  *) printf 'Rejected action: %s\n' "$ACTION" >&2; exit 64 ;;
esac

10. A rerun is a new interaction with the external world

Starting the job again with the same parameters creates another build identity. The source, agent image, dependency mirrors, clock, queue delay, credentials, and external target may all have changed. A Pipeline “Replay” additionally changes execution code for that run; it is not the same as simply rebuilding a Freestyle job.

For operations with side effects, make the operation idempotent when practical and preserve an external idempotency key or target state. “Build #42 succeeded last time” does not authorize build #43 to repeat the side effect blindly.

11. Read-only inspection before changing trigger or parameter configuration

Capture the job full name, current parameter definitions/defaults, timer specification, last build number and cause, queue state, assigned agent, non-secret parameter values, selected environment keys, and any external target IDs. This baseline lets you distinguish configuration drift from a runtime-input problem.

12. DevOps connection: reproducibility requires input provenance

Source revision alone is not enough for parameterized automation. A reproducible Jenkins record ties together controller/runtime baseline, job configuration, cause, parameter set, queue/build identity, agent context, validation result, produced evidence, and external side effects. That chain is what turns “I reran the maintenance job” into an auditable operational event.

Next lesson

Guided Hands-On Workflow and Core Operations

Create a disposable parameterized Freestyle job, inspect manual/timer/API causes, validate targets before a simulated side effect, and capture the evidence chain.

Knowledge check

Why is a choice parameter still validated in the build step?

What does a build cause prove that a parameter cannot?

Why prefer H in many Jenkins cron schedules?

Do API-token-authenticated scripted requests require a CSRF crumb?

What additional fact must be checked after an API call returns successfully?

Official references and version notes

Version and compatibility note

Rechecked on 2026-09-16. Examples target Jenkins 2.568.3 LTS, which is tested with Java 21 and 25; the disposable lab uses Java 21. The chapter intentionally relies on Jenkins core/Freestyle parameter, timer, build-cause, environment, and Remote API behavior so mandatory completion does not depend on a commercial service or a specialized trigger plugin. Exact cause payloads and environment variables can vary by job type and installed plugins, so inspect the controller's own .../api/ output rather than assuming a fixed payload.

Keep the academy open

Support free, practical DevOps education.

Every lesson is designed to remain readable in a browser, downloadable from GitHub, and usable without a paid learning platform. Contributions help expand and maintain the curriculum.

Ethereum / ERC-20
0x716c4Ab160C4B66F31a28AE2448BfF68fc3a2ef0Send only Ethereum/ERC-20 compatible assets to this address.