Skip to content

Prompt engineering in practice

Duration: 12 min Prerequisites: chapter 10 (you’ve seen the 3 tabs), demo 4 running and a project already generated (e.g. banking).

An agent is its system prompt + its tools. Editing the prompt amounts to editing the behaviour, without touching the code. This chapter illustrates that property at runtime, using demo 4.


KindContentWho writes itWhen
System promptThe general role of the agent: “you are a Java dev, you use these tools, here are the hard rules.”The developer who built the agentOnce, at design time
User promptThe specific task: “build a tiny bank with 3 classes.”The userAt every call

For the 3 agents of demo 4:

AgentSystem promptUser prompt
GenerateSYSTEM_PROMPT (line 654+ of agent.py)Chosen in the sidebar (banking, tictactoe, …)
VerifyVERIFY_SYSTEM_PROMPT (line 827+)Auto-generated by build_verifier_bootstrap()
TestsTEST_SYSTEM_PROMPT (line 996+)Auto-generated by build_test_bootstrap()
Concrete examples: the same user prompt under three different system prompts

The user prompt is identical in all three cases: “Write a function that adds two numbers.”

Only the system prompt changes — and with it, the model’s entire behaviour.

System prompt (excerpt)Output for the same user prompt
”You are a Java developer. Always use camelCase, always include a Javadoc comment, never use the keyword var.”
/**
* Returns the sum of two integers.
*/
public int addNumbers(int a, int b) {
return a + b;
}
“You are a Python developer. Always use snake_case, add type hints, never raise an exception silently.”
def add_numbers(a: int, b: int) -> int:
return a + b
”You are a pirate who answers every coding question in pirate slang and never writes more than three lines of code.”
Arr matey, here be yer treasure:
def add(a, b): return a + b
Ahoy, ye sum be ready!

This is the core property of an agent: the system prompt is the role, the user prompt is the task. Changing the system prompt at runtime, without recompiling any code, changes the agent’s identity and conventions. This is exactly what the editable expanders of demo 4 expose, and what the rest of this chapter exercises live.


This sequence takes about 3 minutes to run and makes the property concrete with no additional theory.

  1. Launch demo 4: cd ollama-demo-4-trio-agents-java ; .\start.ps1.
  2. Sidebar: pick Banking system.
  3. Tab 1: click Run agent. Wait for completion (~30s to 2 min depending on machine).
  4. Tab 2 (Verify) should show 3 or 4 files to check. If the Bank class has a private field, the preview banner will say so.

Step 2 — Run the “with rule” version

Section titled “Step 2 — Run the “with rule” version”
  1. Tab 2, open the expander “System prompt (the agent’s role — editable for live demo)”.

  2. You see the full VERIFY_SYSTEM_PROMPT, including this line:

    4. EVERY field declared with ‘private’ is rewritten as ‘public’, so a future test agent can read the state directly. This is a hard project convention.

  3. Click Run code review.

  4. Observe: the agent calls read_file on the offending file, then write_file with a version where private was replaced by public. The Fixes written: 1 counter shows up at the bottom.

  5. If you reopen the Workspace source files expander, you see the diff: private ArrayList<Account> accounts;public ArrayList<Account> accounts;.

  1. Regenerate the project (tab 1, Run agent) to start from a workspace with private to fix.
  2. Tab 2, system-prompt expander: delete the entire rule 4 (the 3 lines that mention private).
  3. Click Run code review.
  4. Observe: this time, the agent touches nothing. Fixes written: 0, message “All good”. The private is still there in the source.
  1. Click Reset to default in the expander to reload the rule.
  2. Rerun Run code review.
  3. The private is fixed again.

What this sequence demonstrates: the behaviour of the agent has been changed without recompiling a single line of Python. Three lines of prompt were edited, and nothing else.


An AI agent is not a classical program. In a classical program:

change behaviour = change code = recompile

In an agent:

change behaviour = change prompt = rerun

This property is what makes:

  • you can prototype a behaviour in 30 seconds;
  • you can test two variants side-by-side without rebuilding;
  • you can give prompt control to the user (that’s what ChatGPT does with Custom Instructions).

It’s also why prompt engineering is a real job: a bad prompt = an unusable agent, a good prompt = a working tool.


NO : "It would be nice if you could use public fields..."
YES : "EVERY field MUST be declared public. No private."

LLMs trained to follow instructions respond better to explicit orders.

Don’t describe, show. The TEST_SYSTEM_PROMPT (lines 999-1018 of agent.py) includes a full mini CalculatorTest.java with imports, class, two @Tests. Five times more effective than prose description.

HARD RULES (must follow):
1. ...
2. ...
3. ...
CONVENTIONS (try to follow):
- ...
- ...

The model treats the first list as constraints; the second as preferences.

Our SYSTEM_PROMPT ends with:

If compile_java reports an error, call read_file then write_file with a fixed COMPLETE version that keeps imports and other classes intact, then call compile_java again.

Without this line, the model often gives up on the first error.

When compile_java returns 'Compilation successful.', stop and write
one short sentence in plain English (no code, no JSON).

Otherwise the model can keep calling tools “just in case”, up to MAX_STEPS.


Once this initial sequence has been completed, ask students to modify other parts of the prompt:

ModificationExpected behaviour
Remove all coding rulesThe model writes “standard” Java with private + getters/setters, tests fail to compile.
Add “Use French names for classes”Compte, Banque, Transaction instead of Account, Bank, etc.
Add “Use the Builder pattern”The model structures classes differently, sometimes well, sometimes not.
Add “Always add a toString() method”All classes get toString (and the model mentions it in its messages).

  • An agent = system prompt + tools + loop. Change the prompt, change the behaviour.
  • Demo 4 exposes the 3 system prompts in editable expanders, which allows the effect of a prompt change to be observed at runtime.
  • A good system prompt: imperative, with a full example, hard rules listed, explicit error handling, clear stop condition.
  • That’s why prompt engineering is a real job — not “chatting with a chatbot”.