π E8-UQB Integration Architecture¶
MVP Scope: Simple database lookups for pre-filling E8 questions from existing policy/insurance answers Post-MVP: ML-based confidence scoring, intelligent inference, predictive analytics
Executive Summary¶
The Essential Eight (E8) assessment framework integrates with the Unified Question Bank (UQB) to deliver a board-friendly compliance experience while leveraging our "answer once, use everywhere" philosophy. This integration enables 85% pre-completion through simple database lookups (not ML inference) that match E8 questions to existing answers from policies, insurance questionnaires, and other assessments.
MVP Implementation: Pre-fill uses direct field mappings (e.g., "MFA required" in password policy β E8 MFA question). Confidence is binary: either we have a mapped answer (100% confidence) or we don't (0% confidence).
Integration Overview¶
Core Principles¶
- E8 as Board Initiative: Present E8 as a distinct feature while leveraging UQB infrastructure
- Role-Based Delegation: Automatically route ~35 technical questions to IT, ~5 governance questions to board
- Triple Crossover (MVP): Pre-fill from policies (45%), insurance (30%), and other assessments (10%) using simple field lookups
- Two-Phase Process: Discovery (IT) β Decision (Board)
MVP Pre-Fill Approach¶
The "intelligent" crossover is actually simple database joins:
-- Example: Pre-fill E8 MFA question from password policy
SELECT policy_fields.value as prefill_value,
'password-authentication-policy' as source
FROM policy_fields
WHERE policy_fields.org_id = $1
AND policy_fields.field_name = 'mfa_admin_required'
AND policy_fields.policy_type = 'password-authentication-policy';
No ML inference, no AI, just structured data lookups.
Architecture Diagram¶
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β E8 Assessment Module β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β βββββββββββββββ ββββββββββββββββ ββββββββββββββββββββ β
β β E8 UI β β E8 Question β β E8 Maturity β β
β β Component β β Router β β Calculator β β
β ββββββββ¬βββββββ ββββββββ¬ββββββββ ββββββββββ¬ββββββββββ β
β β β β β
β ββββββββΌββββββββββββββββββΌβββββββββββββββββββββΌβββββββββ β
β β E8 Service Layer β β
β β β’ Pre-fill Engine β’ Role Mapper β’ Board Presenter β β
β ββββββββββββββββββββββββ¬ββββββββββββββββββββββββββββββββ β
βββββββββββββββββββββββββββΌββββββββββββββββββββββββββββββββββββ
β
βββββββΌββββββ
β UQB β
β Core β
βββββββββββββ
Data Model Extensions¶
E8Question Interface¶
interface E8Question extends UnifiedQuestion {
// E8-specific metadata
e8Id: string // E8_STRATEGY_NNN format
boardTranslation: string // Plain English version
quickWin: boolean // Can be completed quickly
estimatedTime: string // e.g., "30 seconds"
// Role routing
primaryRole: UserRole
delegationPath: string[] // Delegation hierarchy
// E8 mappings
e8Strategy: E8Strategy // One of 8 strategies
controlMappings: string[] // ACSC control IDs
maturityImpact: {
ML0: string[] // Answers that indicate ML0
ML1: string[] // Answers that indicate ML1
ML2: string[] // Answers that indicate ML2
ML3?: string[] // Answers that indicate ML3
}
// Crossover sources
crossoverSources: CrossoverSource[]
}
interface CrossoverSource {
type: 'policy' | 'insurance' | 'assessment'
id: string // Source identifier
field?: string // Specific field in source
confidence: number // 0-1 confidence score
}
enum E8Strategy {
APPLICATION_CONTROL = 'application_control',
PATCH_APPLICATIONS = 'patch_applications',
OFFICE_MACROS = 'office_macros',
USER_HARDENING = 'user_hardening',
ADMIN_PRIVILEGES = 'admin_privileges',
PATCH_OS = 'patch_os',
MFA = 'mfa',
REGULAR_BACKUPS = 'regular_backups',
}
Role-Based Routing¶
interface RoutedQuestions {
assigned: E8Question[] // Questions for current user
delegated: DelegatedQuestion[] // Questions delegated to others
completed: CompletedQuestion[] // Pre-filled questions
visibility: E8Question[] // Questions user can see but not answer
}
interface DelegatedQuestion extends E8Question {
delegatedTo: string // Role or specific user
reason: string // Why delegated
dueDate?: Date // When needed by
}
interface CompletedQuestion extends E8Question {
preFilledValue: any // The pre-filled answer
preFilledFrom: string // Source description
confidence: number // Confidence in pre-fill
lastUpdated: Date // When source was updated
requiresVerification: boolean // Needs human review
}
Integration Components¶
1. E8 Pre-Fill Engine¶
Leverages UQB to pre-fill E8 questions from existing data:
class E8PreFillEngine {
constructor(
private uqb: UnifiedQuestionBank,
private policyService: PolicyService,
private insuranceService: InsuranceService
) {}
async preFillAssessment(orgId: string): Promise<PreFillResult> {
const e8Questions = await this.loadE8Questions()
const results: PreFilledQuestion[] = []
for (const question of e8Questions) {
// Try each crossover source in order of confidence
const sources = question.crossoverSources.sort(
(a, b) => b.confidence - a.confidence
)
for (const source of sources) {
const value = await this.extractFromSource(source, orgId)
if (value !== undefined) {
results.push({
questionId: question.id,
value,
source,
confidence: source.confidence,
})
break // Use first available source
}
}
}
return {
total: e8Questions.length,
preFilled: results.length,
percentage: (results.length / e8Questions.length) * 100,
bySource: this.groupBySourceType(results),
estimatedTimeSaved: this.calculateTimeSaved(results),
}
}
private async extractFromSource(
source: CrossoverSource,
orgId: string
): Promise<any> {
switch (source.type) {
case 'policy':
return this.policyService.getFieldValue(orgId, source.id, source.field)
case 'insurance':
return this.insuranceService.getAnswer(orgId, source.id)
case 'assessment':
return this.uqb.getAnswer(orgId, source.id)
default:
return undefined
}
}
}
2. Role-Based Question Router¶
Routes questions based on user role and delegation model:
class E8QuestionRouter {
private delegationRules = {
board: {
delegates: ['executive', 'it_manager'],
keepQuestions: (q: E8Question) =>
q.primaryRole === 'board' ||
q.e8Strategy === E8Strategy.REGULAR_BACKUPS, // Board cares about recovery
},
executive: {
delegates: ['it_manager', 'admin'],
keepQuestions: (q: E8Question) =>
q.primaryRole === 'executive' || q.importance === 'critical',
},
it_manager: {
delegates: ['admin', 'staff'],
keepQuestions: (q: E8Question) =>
q.domain === 'security' || q.domain === 'technical',
},
}
routeQuestions(
questions: E8Question[],
userRole: UserRole,
preFilled: Set<string>
): RoutedQuestions {
const result: RoutedQuestions = {
assigned: [],
delegated: [],
completed: [],
visibility: [],
}
for (const question of questions) {
// Already answered via pre-fill
if (preFilled.has(question.id)) {
result.completed.push(question)
continue
}
// Check delegation rules
const rules = this.delegationRules[userRole]
if (rules.keepQuestions(question)) {
result.assigned.push(question)
} else if (this.canDelegate(userRole, question.primaryRole)) {
result.delegated.push({
...question,
delegatedTo: question.primaryRole,
reason: this.getDelegationReason(userRole, question),
})
} else {
result.visibility.push(question)
}
}
return result
}
}
3. Board Experience Presenter¶
Creates the simplified board view:
class E8BoardPresenter {
async presentToBoard(
orgId: string,
assessmentId: string
): Promise<BoardE8View> {
const assessment = await this.getAssessment(assessmentId)
const maturity = await this.calculateMaturity(assessment)
return {
// The one number that matters
currentLevel: maturity.overall,
// Visual representation
maturityRadar: {
strategies: maturity.byStrategy,
benchmark: await this.getIndustryBenchmark(orgId),
minimum: this.getRegulatedMinimum(orgId),
},
// Clear decision options
targetOptions: [
{
level: 1,
label: 'Basic Protection',
description: 'Stops opportunistic attacks',
suitable: 'Small businesses without sensitive data',
investment: { cost: '$50k', time: '6 months' },
},
{
level: 2,
label: 'Industry Standard',
description: 'Expected by boards and insurers',
suitable: 'Most businesses with customer data',
investment: { cost: '$150k', time: '9 months' },
recommended: true,
},
{
level: 3,
label: 'Advanced Protection',
description: 'Nation-state level defense',
suitable: 'Critical infrastructure, major banks',
investment: { cost: '$300k', time: '18 months' },
},
],
// Work completed summary
delegationSummary: {
totalQuestions: 40,
answeredByIT: 35,
answeredByManagement: 3,
remainingForBoard: 2,
percentComplete: 95,
},
// Clear next steps
boardActions: [
'Review current maturity level',
'Compare to industry benchmark',
'Select target maturity level',
'Approve budget and timeline',
],
}
}
}
Implementation Flow¶
Phase 1: Discovery (IT/Management)¶
async function runE8Discovery(orgId: string): Promise<DiscoveryResult> {
// 1. Load E8 questions into UQB format
const e8Questions = await loadE8Questions()
// 2. Pre-fill from existing sources
const preFillResult = await preFillEngine.preFillAssessment(orgId)
// 3. Route remaining questions
const unanswered = e8Questions.filter(
(q) => !preFillResult.preFilled.find((p) => p.questionId === q.id)
)
const routed = await router.routeQuestions(unanswered, 'it_manager')
// 4. IT completes technical questions
const answers = await collectAnswers(routed.assigned)
// 5. Calculate current maturity
const maturity = await calculator.calculateMaturity({
preFilled: preFillResult.preFilled,
answered: answers,
})
return {
currentLevel: maturity.overall,
strategies: maturity.byStrategy,
completion: {
preFilled: preFillResult.percentage,
answeredByIT: routed.assigned.length,
total: 40,
},
readyForBoard: true,
}
}
Phase 2: Board Decision¶
async function presentE8ToBoard(
orgId: string,
discoveryResult: DiscoveryResult
): Promise<BoardDecision> {
// 1. Create board-friendly view
const boardView = await presenter.presentToBoard(orgId, discoveryResult)
// 2. Board reviews and decides
const decision = await boardInterface.collectDecision({
current: boardView.currentLevel,
options: boardView.targetOptions,
recommendation: getRecommendation(orgId, boardView),
})
// 3. Create implementation plan
if (decision.approved) {
await createE8Plan({
target: decision.targetLevel,
timeline: decision.timeline,
budget: decision.budget,
owner: decision.delegatedTo,
milestones: generateMilestones(decision),
})
}
return decision
}
Success Metrics¶
Technical Metrics¶
- Pre-fill accuracy: > 85%
- Question routing accuracy: > 95%
- Time to complete assessment: < 25 minutes
- Board decision time: < 5 minutes
Business Metrics¶
- Board satisfaction: "Finally understand our cyber position"
- IT efficiency: 75% reduction in assessment time
- Compliance coverage: Maps to multiple frameworks
- Implementation success: 80% achieve target within timeline
Audit Export Architecture (MVP)¶
Overview¶
Instead of building a full 152-control management UI, we provide an export function that generates audit-ready reports from our 40-question assessment.
Key Design Decision: Serve the 5% use case (external audits) without gold-plating the 95% use case (board decisions).
Control Reference Data¶
Store all 152 ACSC controls as read-only reference data:
interface ACSCControlReference {
id: string // ML2-RA-04
strategy: E8Strategy // admin_privileges
maturityLevel: 'ML1' | 'ML2' | 'ML3'
description: string // Full ACSC requirement text
questionMapping: string // E8_AP_003 (which question covers this)
displayOrder: number
}
This data is populated once from official ACSC documentation, never modified by users.
Question-Level Evidence & Exceptions¶
Extend question model to support evidence and exceptions:
interface E8QuestionAnswer {
id: string
assessmentId: string
questionId: string
selectedOption: string
// Evidence fields (NEW)
evidence: {
files: AttachedFile[] // Policy docs, screenshots, configs
notes: string // Free-text explanation
lastUpdated: Date
updatedBy: string
}
// Exception fields (NEW)
exception: {
isException: boolean
justification: string // Why this exception exists
compensatingControls: string // What we do instead
riskAcceptance: string // Who approved the risk
reviewDate: Date // When to re-assess
boardApprovalDate: Date // Governance trail
}
}
Evidence and exceptions are collected at the question level, then flow to all controls covered by that question.
Export Generation Logic¶
async function generateAuditExport(assessmentId: string): Promise<ExportData> {
// 1. Load assessment with all question answers
const assessment = await db.e8_assessments.findById(assessmentId)
const answers = await db.e8_question_answers.findByAssessment(assessmentId)
// 2. Load all 152 ACSC controls from reference data
const allControls = await db.e8_control_reference.findAll()
// 3. Map each control to its source question
const controlRows = allControls.map((control) => {
const sourceAnswer = answers.find(
(a) => a.questionId === control.questionMapping
)
return {
control_id: control.id,
control_description: control.description,
strategy: control.strategy,
maturity_level: control.maturityLevel,
status: inferControlStatus(control, sourceAnswer),
source_question_id: control.questionMapping,
source_question_text: getQuestionText(control.questionMapping),
evidence_summary: formatEvidence(sourceAnswer?.evidence),
exception_justification: sourceAnswer?.exception?.justification,
last_assessed: assessment.completedAt,
}
})
// 4. Generate Excel/CSV
return {
filename: `${org.name}-e8-audit-report-${date}.xlsx`,
format: 'excel',
data: controlRows,
metadata: {
organizationName: org.name,
assessmentDate: assessment.completedAt,
overallMaturity: calculateOverallML(answers),
totalControls: 152,
implementedControls: controlRows.filter((c) => c.status === 'implemented')
.length,
},
}
}
function inferControlStatus(
control: ACSCControlReference,
answer: E8QuestionAnswer
): ControlStatus {
// Exception takes precedence
if (answer?.exception?.isException) {
return 'documented_exception'
}
// Check if answer indicates this control is implemented
const maturityMapping = getMaturityMapping(control.questionMapping)
const controlImplemented = maturityMapping[control.maturityLevel]?.includes(
answer?.selectedOption
)
if (controlImplemented) {
return 'implemented'
} else if (answer?.selectedOption?.includes('Partially')) {
return 'partially_implemented'
} else {
return 'not_implemented'
}
}
Export Output Format¶
Excel/CSV Structure:
| Column | Description | Example |
|---|---|---|
| control_id | ACSC control ID | ML2-RA-04 |
| control_description | Full requirement text | "Privileged access disabled after 45 days..." |
| strategy | One of 8 strategies | Admin Privileges |
| maturity_level | ML1, ML2, or ML3 | ML2 |
| status | Implementation status | implemented |
| source_question_id | Covering question | E8_AP_003 |
| source_question_text | Question asked | "Are admin accounts auto-disabled?" |
| evidence_summary | Files + notes | "password-policy.pdf; Quarterly reviews" |
| exception_justification | If exception, why | "Legacy systems require manual review" |
| last_assessed | Assessment date | 2025-10-13 |
Progressive Disclosure¶
Three Levels of Detail (no control-level UI, just export):
-
Board View (Primary UI)
-
8 strategy-level summaries
- Overall maturity level
- Target vs current gaps
-
2-3 minute experience
-
Management View (Assessment UI)
-
40 questions with answers
- Evidence upload per question
- Exception documentation per question
-
Delegation and routing
-
Audit Export (Generated Artifact)
- 152 controls with status
- Evidence per control (inherited from questions)
- Exception justifications
- Audit-ready Excel/CSV
Integration with UQB¶
The audit export leverages UQB's "answer once, use everywhere" philosophy:
// Question answered once
E8_MFA_001: "Is MFA mandatory for admin accounts?"
Answer: "Yes"
Evidence: "password-auth-policy.pdf"
// Flows to multiple controls in export
ML1-MF-01: "MFA for online services" β implemented (from E8_MFA_001)
ML2-MF-01: "MFA for privileged users" β implemented (from E8_MFA_001)
ML2-MF-07: "MFA uses something you have + know" β implemented (from E8_MFA_001)
This maintains the UQB principle while serving audit needs without UI complexity.
Post-MVP Future Enhancements¶
Phase 2: Continuous Monitoring (After MVP + 20 customers)¶
- Real-time maturity tracking
- Automated evidence collection
- Alert on maturity degradation
- Quarterly board updates
Trigger: Customer demand + stable MVP platform
Phase 3: Control Management UI (Only if customers demand)¶
- Full 152-control management interface
- Per-control evidence workflows
- Real-time control status tracking
- Control implementation workflows
- Integration with vulnerability scanners
Trigger: >50% customers using export monthly + >3 customers requesting in-platform control management
Don't build if: Export satisfies audit needs and customers prefer simple board interface
Phase 4: Predictive Analytics (Year 2+)¶
- ML-based maturity predictions
- Cost optimization recommendations
- Peer benchmarking insights
- Risk-adjusted target recommendations
Trigger: Sufficient data (100+ assessments) + ML infrastructure budget
Related Documentation¶
- E8 Audit Export - Full export feature specification
- Essential Eight MVP - Updated with export approach
- Decision Log - Why export vs full control UI
Conclusion¶
The E8-UQB integration transforms a complex 152-control framework into a streamlined board decision while maintaining technical rigor. By leveraging the UQB's "answer once, use everywhere" philosophy, we deliver immediate value through pre-filling while positioning E8 as a distinct board initiative.
The audit export bridges board simplicity with audit compliance, serving the 5% use case (external audits) without gold-plating the 95% use case (board governance). This pragmatic approach validates demand for full control management before committing significant development resources.