🇫🇷 Version française

[!IMPORTANT] Every fixture, rulebook, and calculator output in this lab is synthetic and non-binding. Nothing here represents an actual Desjardins product, rate, or policy, and no regulator or insurer has reviewed or endorsed this material.

Overview

Item Value
Duration 30 minutes
Level Intermediate
Prerequisites Lab 06

Learning Objectives

By the end of this lab, you will be able to:

  • Run the agent’s CLI end to end against a fixture, with no Azure or hosted Foundry call
  • Confirm the applicant-facing message never includes an amount, a rulebook table, or a reviewer-only field
  • Act as the human reviewer against the same ApprovalRepository, before meeting the reviewer interface in Lab 13
  • Confirm an invalid case reference produces a bounded rejection message instead of a raised exception

Exercises

Exercise 7.1: Run the CLI Against a Known Fixture

python src/quote-preparation-agent/main.py CASE-SYN-001

Expected result: a JSON object with en-CA and fr-CA keys, each holding a bilingual sentence telling the applicant their request was submitted for employee review. No dollar amount, rulebook field, or reviewer identifier appears anywhere in the output.

Before the JSON, two log lines on stderr show the agent calling both MCP tools from Labs 04 and 05:

get_application('CASE-SYN-001') -> found
get_rulebook('RULEBOOK-SYN-ON') -> found

[!TIP] If you get ModuleNotFoundError: No module named 'langgraph', the terminal is not using the workshop virtual environment. Run ./.venv/Scripts/Activate.ps1 from the repository root (see Lab 00), then retry.

Exercise 7.2 (Hands-on): Confirm the Workflow State Directly

The CLI only prints the applicant message. Call run_case directly to inspect the full state, including workflow_state.

python -c "
import sys
sys.path.insert(0, 'src/quote-preparation-agent')
from main import run_case

final_state = run_case('CASE-SYN-001')
print('workflow_state:', final_state['workflow_state'])
print('draft_case_id:', final_state['draft_case_id'])
print('applicant_message:', final_state['applicant_message'])
"

Expected result: workflow_state is PENDING_REVIEW. The case was created and submitted for review, but nothing in the agent’s own code approved or rejected it.

Exercise 7.3 (Hands-on): Act as the Human Reviewer

A reviewer acts here directly against ApprovalRepository, one layer below any user interface. Share one repository instance between the agent run and your reviewer step so they operate on the same case.

Lab 13 performs this same transition through the reviewer application, against a persistent case store and a verified Entra identity. Doing it in Python first makes the later lab easier to read, because you will already know which call the button is making.

python -c "
import sys
sys.path.insert(0, 'src/quote-preparation-agent')
sys.path.insert(0, 'apps/workshop')
from main import run_case
from approval_repository import ApprovalRepository

repo = ApprovalRepository()
final_state = run_case('CASE-SYN-001', repository=repo, preparer_id='AGENT-INTAKE')
print('after agent run:', final_state['workflow_state'])

record = repo.approve(final_state['draft_case_id'], reviewer_id='EMP-REVIEWER-01')
print('after human review:', record.state)
"

Expected result: the state moves from PENDING_REVIEW to APPROVED, and the reviewer ID (EMP-REVIEWER-01) differs from the preparer ID (AGENT-INTAKE) used by the agent.

Exercise 7.4: Run Against an Invalid Case Reference

python src/quote-preparation-agent/main.py "NOT-A-VALID-CASE-ID"

Expected result: a bilingual message stating the request could not be processed because the case reference was invalid, with no exception raised and no case created in the approval repository.

Validation Checklist

  • Exercise 7.1 prints a bilingual message with no dollar amount
  • Exercise 7.2 confirms workflow_state is PENDING_REVIEW immediately after the agent runs
  • Exercise 7.3 approves the case as a distinct reviewer, moving it to APPROVED
  • Exercise 7.4 returns the bounded rejection message for an invalid case reference

Knowledge Check

  • Why does the agent stop at PENDING_REVIEW instead of deciding the case itself?
  • What would happen in Exercise 7.3 if you called repo.approve with reviewer_id='AGENT-INTAKE' instead of a distinct reviewer?

Next Steps

Continue to Lab 08: Evaluation Suite.


This site uses Just the Docs, a documentation theme for Jekyll.