Chapter 09Lesson 01~55 minutes

Package Formats, Repositories, and Dependency Resolution

Build a systems-level model of Linux packages, repositories, metadata, dependency solving, transactions, and package database state before using a distribution-specific tool.

Package architectureDependenciesHands-on lab

Learning objectives

By the end of this lesson

  • Distinguish a package archive, repository, package database, package manager, and dependency solver.
  • Explain how names, versions, architectures, capabilities, dependencies, conflicts, and scripts influence a transaction.
  • Trace a package request from repository metadata through download, verification, unpacking, configuration, and database update.
  • Use read-only commands to identify the package-management stack on an unfamiliar Linux system.
  • Capture package provenance and ownership evidence before changing software.

1. A package is more than a compressed directory

A Linux package normally contains a payload of files plus structured metadata that tells the package system what the software is, which architecture it targets, which version it provides, what it requires, where files belong, and which lifecycle actions must run. Debian-family systems commonly use .deb packages managed at the low level by dpkg. Fedora, Rocky Linux, AlmaLinux, and related systems use RPM packages managed at the low level by rpm.

Payload

Files installed on the system

Executables, libraries, service units, documentation, configuration templates, metadata, and support files.

Control metadata

Transaction instructions

Name, version, architecture, dependencies, conflicts, checksums, ownership, permissions, and maintainer scripts.

Package database

Installed-state ledger

Records which packages and files are installed, their versions, expected metadata, and configuration state.

A package archive is therefore an input to a state transition. Installing it can add users, reload services, update caches, register alternatives, rebuild an initramfs, or trigger other package-maintainer logic. Treat package transactions as controlled system changes, not simple file copies.

2. Separate the package layers

Repository-to-installed-state workflow
flowchart TB
  U["Operator or automation"] --> H["High-level manager: APT or DNF"]
  H --> M["Repository metadata and dependency solver"]
  M --> P["Selected package set and transaction plan"]
  P --> V["Signature and integrity verification"]
  V --> L["Low-level manager: dpkg or rpm"]
  L --> F["Files, scripts, services, and configuration"]
  L --> D["Installed package database"]
  D --> H
  R["Configured repositories"] --> M
LayerResponsibilityExamples
RepositoryPublishes package archives, indexes, signatures, and release metadataDebian archive, Fedora repository
High-level managerQueries sources, solves dependencies, plans transactions, and downloads packagesapt, apt-get, dnf, dnf5
Low-level managerReads package archives and maintains installed statedpkg, rpm
DatabaseTracks installed packages and file ownership/var/lib/dpkg, RPM database

Use the high-level manager for normal installation and removal because it understands repositories and dependency closure. Use low-level tools primarily for inspection, verification, packaging work, and carefully diagnosed recovery.

3. Dependency solving is a constraint problem

A request such as “install package X” expands into constraints. X may require a minimum version of library Y, conflict with package Z, provide a virtual capability, recommend optional components, or be available for several architectures. The solver attempts to select a consistent transaction from enabled repositories and installed state.

01Normalize the request

Resolve the package name, capability, file provider, version selector, architecture, or group.

02Read candidate metadata

Combine configured repository indexes with installed package state and policy.

03Solve constraints

Select versions that satisfy dependencies, conflicts, obsoletes, architecture rules, and pinning or exclusion policy.

04Present a transaction

Show installs, upgrades, removals, downloads, disk changes, and sometimes service effects.

05Verify and apply

Authenticate repository metadata or packages, unpack files, run lifecycle scripts, and commit database state.

Read the proposed removals

A solver can produce a technically consistent plan that is operationally unacceptable. Unexpected removals, downgrades, repository switches, or large dependency expansions are reasons to stop and investigate.

4. Version ordering is distribution-specific

Package versions are structured strings, not ordinary decimal numbers. Debian and RPM ecosystems use different comparison rules and may include epochs, upstream versions, distribution releases, revision components, and architecture qualifiers. Never implement version ordering with lexical string comparison or floating-point conversion.

# Read-only comparisons on systems that provide the relevant tool.
if command -v dpkg >/dev/null 2>&1; then
  dpkg --compare-versions '2:1.4-3' gt '1:9.9-9'
  printf 'dpkg comparison status=%s\n' "$?"
fi

if command -v rpmdev-vercmp >/dev/null 2>&1; then
  rpmdev-vercmp '1:1.4-3' '1:1.4-2'
elif command -v rpm >/dev/null 2>&1; then
  rpm --eval '%{rpmversion}\n'
fi

An epoch can override the apparent upstream version and is generally difficult to remove once introduced. Distribution release fields distinguish multiple package builds of the same upstream version. Always query the package manager for the installed and candidate versions.

5. Ask who owns the file and where the package came from

Operational debugging often begins with a path: an executable, service unit, library, or configuration file. Package tools can map installed files back to packages, list package contents, show versions, and identify repository candidates. This is more reliable than assuming a file was installed manually.

target=${1:-/bin/sh}

printf 'target=%s\n' "$target"
command -v "$target" 2>/dev/null || true

if command -v dpkg-query >/dev/null 2>&1; then
  dpkg-query -S "$target" 2>/dev/null || true
  dpkg-query -W -f='${binary:Package}\t${Version}\t${Architecture}\n' 2>/dev/null | head
fi

if command -v rpm >/dev/null 2>&1; then
  rpm -qf "$target" 2>/dev/null || true
  rpm -qa --qf '%{NAME}\t%{EPOCHNUM}:%{VERSION}-%{RELEASE}\t%{ARCH}\n' | head
fi

A file may be unmanaged, generated at runtime, supplied by a container, mounted from another filesystem, or replaced after package installation. Package ownership is strong evidence, but verify current file metadata and integrity when compromise or drift is possible.

6. Hands-on lab: inventory the package-management stack

This read-only lab records the distribution, available package tools, repository configuration locations, package counts, and ownership of selected commands.

lab="$HOME/devops-academy/linux/chapter09/lesson01"
mkdir -p "$lab"
report="$lab/package-stack.txt"

{
  printf '=== operating system ===\n'
  cat /etc/os-release

  printf '\n=== package tools ===\n'
  for cmd in apt apt-get apt-cache dpkg dpkg-query dnf dnf5 yum rpm; do
    if command -v "$cmd" >/dev/null 2>&1; then
      printf '%-12s %s\n' "$cmd" "$(command -v "$cmd")"
    fi
  done

  printf '\n=== repository configuration ===\n'
  find /etc/apt /etc/yum.repos.d /etc/dnf -maxdepth 2 -type f \
    2>/dev/null | sort || true

  printf '\n=== installed package count ===\n'
  if command -v dpkg-query >/dev/null 2>&1; then
    dpkg-query -W -f='${binary:Package}\n' | wc -l
  elif command -v rpm >/dev/null 2>&1; then
    rpm -qa | wc -l
  fi

  printf '\n=== ownership examples ===\n'
  for path in /bin/sh /usr/bin/env /usr/bin/ssh; do
    [ -e "$path" ] || continue
    printf '%s\n' "$path"
    if command -v dpkg-query >/dev/null 2>&1; then
      dpkg-query -S "$path" 2>/dev/null || true
    elif command -v rpm >/dev/null 2>&1; then
      rpm -qf "$path" 2>/dev/null || true
    fi
  done
} > "$report"

less "$report"

Verification checklist

7. Common mistakes

Installing a local archive with only the low-level tool

This may leave dependencies unresolved. Prefer the distribution's high-level manager when installing local packages.

Assuming newest means compatible

Repository policy and distribution integration matter. A higher upstream version from an unrelated source can break dependency and support assumptions.

Treating metadata refresh as an upgrade

Refreshing repository indexes changes available information; applying upgrades changes installed software.

Ignoring package scripts

Transactions can restart services, create users, and regenerate system artifacts. Review impact and maintenance-window requirements.

8. Knowledge check

Question 1. Why should normal installations use APT or DNF rather than only dpkg or rpm?

Question 2. What does the package database provide that a filesystem listing does not?

Question 3. Why is lexical version comparison unsafe?

9. Summary

Linux software management is a layered state-management system. Repositories publish authenticated metadata and package archives; high-level managers select candidates and solve dependencies; low-level managers apply package transactions and maintain installed state. Before changing software, identify the stack, inspect candidates and provenance, and review the full transaction plan.

Next lesson

APT and dpkg on Debian-Based Systems

Next, you will apply this model to Debian and Ubuntu systems using APT for repository-aware transactions and dpkg for installed-state inspection.

10. Further reading

  • Debian Reference: package management and APT policy.
  • APT User's Guide and Debian apt(8), apt-get(8), and dpkg(1) manual pages.
  • DNF5 documentation and RPM Reference Manual.

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
0x716c4Ab160C4B66F31a28AE2448BfF68fc3a2ef0 Send only Ethereum/ERC-20 compatible assets to this address.