unit 6 · Making it real
Galaxy, requirements.yml & pinning
The lockfile instinct, ported
you may want to read 4 · Collections & FQCN , 24 · Roles: structure, defaults vs vars first — but nothing is locked
tl;dr
- ansible-galaxy installs collections and roles; requirements.yml is the manifest a project commits.
- One command restores every dependency: ansible-galaxy install -r requirements.yml.
- Pin versions — unpinned installs grab whatever is latest that day, and machines drift apart.
why it matters Clone a repo, run the playbook, fail on a missing collection — requirements.yml is how real projects turn "install what this needs" into one reproducible command.
Lesson 4 left you with one command: ansible-galaxy collection install community.general. It works, and it’s also a trap: it installs whatever
version is latest today, onto your machine only. Fine for a laptop
experiment; useless as a team workflow. This lesson covers where that
command reaches, how a project declares its needs in one committed file,
and why the version pin saves you.
The command talks to Galaxy — Ansible’s public hub at
galaxy.ansible.com for collections and community roles — via the
ansible-galaxy CLI. Two install verbs cover both kinds of content:
ansible-galaxy collection install community.general # a collection, from lesson 4
ansible-galaxy role install geerlingguy.nginx # a standalone role from the hubThe second verb matters because Galaxy predates collections: thousands of
standalone roles (lesson 24’s unit of reuse) live there under
author.rolename names, and plenty of teams still consume them directly.
The manifest: requirements.yml
A real repo doesn’t document dependencies in a README. It commits a
manifest named requirements.yml:
# requirements.yml
collections:
- name: ansible.windows
version: 3.5.0 # exact pin — every install identical
- name: community.general # unpinned — grabs latest today (avoid)
roles:
- name: geerlingguy.nginx # roles list the same way, version: includedThe shape is what you see: a collections: list and a roles: list,
each entry a dict with name: and — always, in a repo you respect —
version:. One command installs everything the file names:
ansible-galaxy install -r requirements.yml # installs both listsThat command is how a fresh clone becomes runnable. You’ll meet it again
verbatim in lesson 41: the Jenkins pipeline pattern starts this way —
check out the repo, ansible-galaxy install -r requirements.yml, run the
playbook. The CI agent starts empty every time; the manifest makes that a
feature instead of a failure.
In the standard repo layout (lesson 36) you’ll usually find the manifest
split in two — collections/requirements.yml and roles/requirements.yml —
same shape, one kind of content per file.
Pin it
An unpinned entry means “latest at the moment of install.” You installed
in March, the CI agent installs tonight, the new teammate installs in
August: three collection versions, one Git commit, and a bug that
reproduces on only one machine. You already own the instinct that
prevents this — it’s a lockfile. The same reflex that pins a Docker base
image to a real tag instead of :latest applies here: exact version:
pins, upgraded deliberately in a reviewed commit, never as a side effect
of install day.
Pinning also connects this file to the execution-environment world of
lesson 40. There, dependencies get baked into a container image at build
time instead of installed on the control node — but they’re built from
this same manifest. Either way the habit is identical: the moment a
playbook uses a collection outside the bundle from lesson 5, it goes into
requirements.yml with a version — not just into your machine’s
collection path. The next person to clone the repo is counting on it, and
so is the CI runner that deploys it.
self-check — recall, not a test
1 A teammate’s playbook fails with a module-not-found error on ansible.windows.win_service. What do you look for in the repo, and what do you run?
2 Your playbook works, CI fails, a teammate sees a third behavior — all running the same Git commit. What dependency mistake produces this?
3 A repo has both collections/requirements.yml and roles/requirements.yml. Why does running only ansible-galaxy collection install -r leave you broken?
lab (optional — never required)
Write a requirements.yml pinning community.general to an exact version, install with ansible-galaxy install -r, then confirm the version with ansible-galaxy collection list.
needs: The control node from lesson 5.