Chapter 18Lesson 03180–240 min

Database, SSH, Filesystem, Process, and Infrastructure Automation Patterns: Configuration, Design Patterns, and Trade-Offs

Choose deliberately among database versus API assertions, rollback versus cleanup, SSH versus local process execution, connection reuse, resource abstractions, and simulation versus local services.

IsolationParameterizationResource layerTrade-offsCI portability

Learning objectives

  • Choose database versus API assertions based on the contract under test rather than convenience.
  • Choose rollback, explicit cleanup, connection reuse, or per-test isolation based on observable state ownership.
  • Compare SSH remote execution with local Process and simulation without hiding security or portability costs.
  • Keep low-level library keywords behind a small domain infrastructure resource.
  • Reason about parallel workers, CI workspaces, and container networking before sharing external state.

Current compatibility baseline — verified 2026-08-31. Robot Framework 7.4.2 is the stable course baseline. The mandatory database layer uses robotframework-databaselibrary 2.4.1, which requires Python 3.8.1+ and Robot Framework 5.0.1+; the lab uses Python's built-in sqlite3 driver, so no database server is required. SSHLibrary 3.8.0 is still the latest stable PyPI release and 3.8.1rc1 remains prerelease. Its stable Paramiko implementation accepts unknown host keys with AutoAddPolicy; therefore real SSH is optional here and never used as the mandatory production-security pattern. The required path is local/free: SQLite, Robot standard OperatingSystem/Process, synthetic files, and a loopback-equivalent SSH simulation. No public host, production database, paid service, Pabot, CI provider, or container runtime is required.

1. Design frame: minimize the number of mutable states a test owns

A test that opens a database connection, edits three files, starts a daemon, SSHes to a host, and then calls an API may be “end to end,” but it has five independent cleanup contracts. That increases diagnostic ambiguity. Prefer the smallest set of boundaries that can prove the intended behavior.

2. Direct database assertion versus API assertion

Question Direct DB assertion API/service assertion
What is proven? Persistence/storage state Published service behavior
Coupling Schema/driver/query coupling HTTP/API contract coupling
Speed Usually fast locally Usually fast but includes service layer
Setup usefulness Excellent for fixture verification Excellent when API is supported fixture boundary
Risk Bypasses business rules if used as mutation path May hide DB-specific persistence defects
Production pattern Use narrowly for integration/storage invariants Prefer for business behavior when API is the product contract

A useful rule: if the requirement says “the client receives X,” assert through the service. If the requirement says “migration/index/persistence contains X,” a direct database assertion can be appropriate. Do not use DB writes to bypass the exact business behavior you are testing unless the write is explicitly fixture setup outside the behavior under test.

3. Transaction rollback versus explicit cleanup

Rollback is ideal when all mutations stay inside one connection/transaction and the test can guarantee the transaction is never committed by the code under test. Explicit cleanup is needed when state crosses transaction boundaries or is visible to another process/service. The two strategies can coexist, but their ownership must be obvious.

Strategy Best fit Failure mode
Rollback single DB connection, test-only mutations hidden commit makes rollback ineffective
Delete by owned ID API/DB mutation committed by application lost ID causes orphan state
Recreate disposable DB file SQLite lab or isolated worker database shared file path causes races
Snapshot/restore complex controlled fixture with tooling support expensive; easy to restore wrong target

4. SSH remote command versus local Process

If the target is the same machine that runs Robot, use Process for a local program. Adding SSH to localhost adds authentication, host trust, port, daemon, and connection-state failure modes without changing the target. Use SSH only when remote execution is part of the integration boundary.

For a disposable remote fixture, expose a narrow domain keyword such as Read Remote Service State, not arbitrary Execute Command calls in every test. This is where an allowlist can reject package managers, service stop/start, user management, broad deletion, or shell metacharacters.

5. One domain resource versus library keywords everywhere

*** Keywords ***
Inventory Should Contain Ready Item
    [Arguments]    ${name}
    ${rows}=    Get Inventory Row    ${name}
    Length Should Be    ${rows}    1
    Should Be Equal    ${rows}[0][state]    ready

The higher-level keyword owns the data-access pattern and diagnostic message. A test now says what infrastructure condition matters instead of repeating connection aliases, SQL placeholders, and row-shape assumptions. Keep resources cohesive: one giant Common.resource containing every infrastructure operation creates dependency tangles and name collisions.

6. Persistent connection versus per-test isolation

Choice Advantage Cost / risk Use when
Suite-scoped DB connection less setup overhead transaction/session leakage between tests read-heavy, well-reset local fixture
Per-test DB connection stronger isolation more connection cost mutating tests, parallel workers, flaky shared state
Suite-scoped SSH connection fewer handshakes remote shell/session state can leak read-only commands with strict reset
Per-test SSH connection clear ownership connection overhead mutable remote state or stronger isolation

Library scope and connection scope are different. DatabaseLibrary may be GLOBAL as a Robot library while it manages several independently aliased DB connections. SSHLibrary also maintains a global connection cache. Design the connection lifetime explicitly instead of inferring it from import placement.

7. Simulation versus real local service

Simulation is appropriate when the learning goal is Robot architecture, cleanup, and evidence—not protocol conformance. A real local service is appropriate when the behavior under test includes the protocol. The mandatory chapter uses real SQLite/filesystem/process boundaries and simulates SSH because safe SSH host-trust provisioning would otherwise dominate the lesson.

8. Absolute/owned paths versus working-directory folklore

Resolve run-owned paths once from ${OUTPUTDIR} or ${CURDIR} depending on ownership, normalize them, and pass explicit paths to libraries. Do not assume the CI working directory equals your laptop working directory. A child process can also have its own cwd; that state is distinct from Robot's ${EXECDIR}.

9. Parallelism and worker isolation

Pabot arrives later in Chapter 24, but infrastructure design must already be concurrency-safe. A fixed SQLite path such as /tmp/test.db, fixed SSH temp filename, or common process port becomes a shared resource when workers run concurrently. Use worker-specific/run-specific roots and never rely on global mutable test variables to coordinate external state.

Do not solve a collision by adding sleeps. Collisions are ownership/design problems. A wait may help only when the underlying state transition is expected and uniquely owned.

10. “localhost” changes meaning across container boundaries

On a developer machine, 127.0.0.1 refers to that host. Inside a container, it refers to the container itself. A database or SSH service on the host is not automatically at the container's localhost. Treat network namespace, published port, DNS name, and trust material as explicit container/CI configuration. Do not rewrite a failing target to a public hostname just to make the test connect.

11. Worked decision table

Scenario Preferred boundary Why
Verify local migration created one index DatabaseLibrary + disposable DB storage contract is the target
Verify customer status returned by service API resource business/API contract is the target
Run local compiler/helper Process no SSH/session/trust overhead
Check remote non-production host service version domain SSH keyword on pre-trusted host remote host is intentionally part of test
Teach remote-call orchestration without trusted SSH fixture simulation preserves architecture without fake security
Delete generated run directory OperatingSystem behind exact ownership guard filesystem ownership can be proven locally

12. Configuration boundaries

  • Robot core: variables, suites, selection, output directory, lifecycle.
  • External libraries: DatabaseLibrary/SSHLibrary import args and connection APIs.
  • Python environment: database drivers, Paramiko/SCP dependencies, interpreter.
  • SUT/infrastructure: DB schema, SSH daemon, users, host keys, process executables.
  • Editor/RobotCode: developer assistance only; not runtime target configuration.
  • CI/container: workspace, network namespace, service containers, secret injection, artifact retention.

Knowledge check

When is a direct DB assertion better than an API assertion?

Why can a suite-scoped connection make tests order-dependent?

Why is SSH to localhost usually inferior to Process for a local helper?

How should a Pabot worker change this chapter’s design even before Pabot is introduced?

What does “localhost inside a container” mean?

13. Summary and next lesson

Good infrastructure tests choose one boundary for a reason, minimize owned state, and isolate connection/transaction/process/path lifecycles. Lesson 4 deliberately breaks those contracts and diagnoses the evidence without using destructive shortcuts.

Next lesson

Database, SSH, Filesystem, Process, and Infrastructure Automation Patterns: Diagnostics, Failure Modes, and Production Practices

Continue with Database, SSH, Filesystem, Process, and Infrastructure Automation Patterns: Diagnostics, Failure Modes, and Production Practices. It builds directly on the state, evidence, and operating assumptions established here, so carry those constraints forward rather than treating the next page as an isolated topic.

References and version anchors

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.