Chapter 14 — Software engineering
Lesson map
Lesson 14 published. Map, example, EX040.
flowchart TD
N0["Learning outcomes"]
N1["14.1 Version control and review"]
N2["14.2 Continuous integration"]
N3["14.3 Dependencies"]
N4["14.4 Traceability"]
N5["14.5 Configuration"]
N6["Practice note — Release notes"]
N7["Synthesis"]
N0 --> N1 --> N2 --> N3 --> N4 --> N5 --> N6 --> N7
N7 --> EX["Worked example"]
EX --> Q["Exercise EX040"]
Logical drawing
flowchart LR
N0["Learning outcomes"]
N1["14.1 Version control and review"]
N2["14.2 Continuous integration"]
N3["14.3 Dependencies"]
N4["14.4 Traceability"]
N5["14.5 Configuration"]
N6["Practice note — Release notes"]
N7["Synthesis"]
N0 --> N1 --> N2 --> N3 --> N4 --> N5 --> N6 --> N7 --> Q["EX040"]
[Learning outcomes]
|
v
[14.1 Version control and review]
|
v
[14.2 Continuous integration]
|
v
[14.3 Dependencies]
|
v
[14.4 Traceability]
|
v
[14.5 Configuration]
|
v
[Practice note — Release notes]
|
v
[Synthesis]
|
v
[Worked example] --> [Exercise EX040]
Learning outcomes
You will (1) apply version control, code review and continuous integration to a CTI platform; (2) manage dependencies with supply-chain care; (3) write change records that link to requirements; (4) separate configuration from code.
14.1 Version control and review
Every change to Lantern goes through a branch, an automated test run and a second engineer's review. Parser changes need a reviewer who understands the partner format.
Review is more than reading code. The reviewer runs the tests, checks that the change matches what was asked and asks what happens with bad input. For parser changes, a sample of real partner records under the agreement is run through both versions. Kofi has seen reviews catch a field being read from the wrong position, which tests on clean synthetic data had passed.
14.2 Continuous integration
CI runs unit tests, property tests and a replay of a synthetic feed through the whole pipeline, comparing outputs with a known-good snapshot. A difference fails the build until explained.
The replay is what made the change in the worked example visible: the snapshot showed exactly how many indicators would stay in blocking: 1,240 more once the decay floor dropped from 30 to 20. A failing replay is not always a bug. Sometimes the change is intended, and the engineer updates the snapshot with a note explaining why.
14.3 Dependencies
Third-party libraries can carry vulnerabilities or be compromised. Pin versions, review updates, and prefer the standard library for small tasks. ATT&CK T1195 Supply Chain Compromise reminds defenders that their own tooling is a target.
Kofi's rule is that each new library needs a reason the standard library cannot meet, a named owner and a check of its maintainers and recent history. Updates arrive in a weekly batch, read before merging, and the build fails if a dependency is fetched without a fixed version and hash. Lantern holds partner data and influences firewalls, which makes a compromised library in its build an attractive route for an attacker.
14.4 Traceability
Each change cites the requirement or defect it addresses. When an auditor asks why the TLP gate allows AMBER to "org", the history links to the requirement and the TLP 2.0 definition.
Kofi links each commit to a ticket, and each ticket to a requirement number in the requirements document. An auditor can follow the chain from code back to the reason for it in a few clicks. Changes without a linked reason are not merged. This also helps when removing code: if the requirement has been withdrawn, the link shows which parts can go.
14.5 Configuration
Partner endpoints, credentials references and thresholds live in configuration, not code. Secrets live in a vault; configuration stores only references.
Separating them means the same tested code can run in test and production with different settings, and changing a threshold does not need a new build. Configuration changes still go through review, because a wrong threshold can do as much harm as a bug. Kofi keeps a short description beside each setting saying what it controls and who may change it. A credential is never pasted into configuration, even temporarily; the vault reference is the only thing stored.
Practice note — Release notes
Each Lantern release ships with notes written for analysts: what behaviour changed, which thresholds moved and how to report problems. Analysts who understand a change are less likely to mistake new behaviour for an incident, and they report regressions faster.
Worked example
A pull request lowers the decay floor from 30 to 20. CI's replay shows 1,240 more indicators would remain in automated blocking. The reviewer asks for the requirement; none exists. The change is rejected until the SOC lead agrees and a requirement is written.
Synthetic case. The pull request and counts are invented.
Errors and limits
Tests on synthetic data cannot prove behaviour on all partner data; keep sampling real formats under agreement. Speed pressure is the usual enemy of review.
Exercises
- EX040 — Replay value. What does the synthetic-feed replay in CI catch that unit tests may miss? Rubric: 3 = end-to-end behaviour changes across stages; 2 = integration bugs vaguely; 1 = vague; 0 = none.
- EX041 — Rejected change. Why was the decay-floor change rejected? Rubric: 3 = no requirement/owner agreement; large behavioural impact; 2 = one; 1 = tests failed; 0 = none.
- EX042 — Secret location. Where do partner credentials live, and what does configuration hold? Rubric: 3 = vault; config holds references; 2 = vault only; 1 = in code; 0 = none.
Synthesis
Review, replay, pin, trace and keep secrets out of code.
Continue studying — chapter 14 of 50
← Chapter 13 (draft) · Course chapter index · Chapter 15 (draft) →