DEV Community

Cover image for CHAPTER 42 AI MODEL ORCHESTRATION, PROVIDER ABSTRACTION, MODEL ROUTING, PROMPT ARCHITECTURE, TOKEN MANAGEMENT & SECURE INFERENCE
Black Shadow Team ©
Black Shadow Team ©

Posted on

CHAPTER 42 AI MODEL ORCHESTRATION, PROVIDER ABSTRACTION, MODEL ROUTING, PROMPT ARCHITECTURE, TOKEN MANAGEMENT & SECURE INFERENCE

#ai

42.1 Introduction

The document and RAG architecture established in Chapter 41 provides the evidence layer of the AI system.

The next requirement is a reliable inference layer.

A production AI application should not allow every API route to directly call a model provider. That approach creates tight coupling, inconsistent prompts, duplicated error handling, uncontrolled costs, and weak security boundaries.

Instead, the application should introduce an AI Orchestration Layer.

The conceptual architecture is:

Application
     │
     ▼
AI Orchestrator
     │
     ├── Model Router
     ├── Prompt Manager
     ├── Context Manager
     ├── Token Manager
     ├── Safety Policy
     ├── Provider Adapter
     ├── Retry/Fallback Manager
     ├── Usage Meter
     └── Observability
             │
             ▼
       Model Provider(s)
Enter fullscreen mode Exit fullscreen mode

The purpose of this layer is to make model invocation controlled, observable, replaceable, and secure.


42.2 Why Direct Model Calls Are a Problem

A weak architecture might look like:

API Route
   ↓
AI Provider
Enter fullscreen mode Exit fullscreen mode

Then another feature might implement:

Another API Route
   ↓
Different AI Provider
Enter fullscreen mode Exit fullscreen mode

Eventually the application contains dozens of independent model calls.

This creates problems:

  • duplicated authentication logic,
  • duplicated prompts,
  • inconsistent safety controls,
  • inconsistent timeouts,
  • inconsistent retries,
  • difficult provider migration,
  • difficult cost tracking,
  • difficult testing,
  • inconsistent logging.

The preferred architecture is:

Feature
   ↓
AI Orchestrator
   ↓
Provider Adapter
   ↓
Model
Enter fullscreen mode Exit fullscreen mode

Every AI feature therefore passes through a common control layer.


42.3 Provider Abstraction

The application should define a provider-neutral interface.

Conceptually:

AIProvider
 ├── generateText()
 ├── generateStructured()
 ├── generateEmbeddings()
 └── healthCheck()
Enter fullscreen mode Exit fullscreen mode

Individual providers implement the interface.

The application should not need to know the implementation details.

For example:

Provider Adapter
      │
      ├── Cloud Model Adapter
      ├── Local Model Adapter
      └── Backup Model Adapter
Enter fullscreen mode Exit fullscreen mode

This makes the system portable.


42.4 Model Abstraction

Provider and model should be separate concepts.

For example:

Provider
   └── Model
Enter fullscreen mode Exit fullscreen mode

A provider may expose multiple models.

The application should therefore use an internal model identifier such as:

fast-general
quality-general
reasoning
vision
embedding
Enter fullscreen mode Exit fullscreen mode

rather than hard-coding provider-specific names throughout the codebase.

The routing layer can translate internal identifiers into actual configured models.


42.5 Model Capability Registry

The orchestrator should maintain metadata about model capabilities.

Example:

ModelProfile
 ├── modelId
 ├── provider
 ├── capability
 ├── contextLimit
 ├── supportsVision
 ├── supportsStructuredOutput
 ├── supportsTools
 ├── latencyClass
 └── costClass
Enter fullscreen mode Exit fullscreen mode

This allows the router to select an appropriate model based on task requirements.

For example:

Image Question
     ↓
Vision-capable model
Enter fullscreen mode Exit fullscreen mode

while:

Simple Classification
     ↓
Fast low-cost model
Enter fullscreen mode Exit fullscreen mode

and:

Complex Reasoning
     ↓
High-capability model
Enter fullscreen mode Exit fullscreen mode

42.6 Model Routing

Model routing determines which model should process a request.

A basic routing function can consider:

Task
User Plan
Latency Requirement
Context Size
Required Capability
Safety Requirement
Availability
Cost Budget
Enter fullscreen mode Exit fullscreen mode

Conceptually:

Request
  │
  ▼
Task Classification
  │
  ▼
Capability Check
  │
  ▼
Policy Check
  │
  ▼
Model Selection
  │
  ▼
Inference
Enter fullscreen mode Exit fullscreen mode

The router should not select a model merely because it is currently popular or inexpensive.

It should satisfy the application's explicit requirements.


42.7 Task Classes

A practical system can define task classes such as:

CHAT
RAG_QA
SUMMARIZATION
CLASSIFICATION
STRUCTURED_EXTRACTION
VISION_ANALYSIS
CODE_ASSISTANCE
EMBEDDING
AGENT_PLANNING
Enter fullscreen mode Exit fullscreen mode

Each task can have a default model policy.

For example:

RAG_QA
 → quality-general

CLASSIFICATION
 → fast-general

EMBEDDING
 → embedding-model

VISION_ANALYSIS
 → vision-model
Enter fullscreen mode Exit fullscreen mode

The mapping should remain configurable.


42.8 Fallback Routing

External AI services can fail.

Possible causes include:

  • temporary network errors,
  • provider outages,
  • rate limits,
  • capacity errors,
  • invalid requests,
  • timeout,
  • quota exhaustion.

A resilient architecture can use controlled fallback routing.

Example:

Primary Model
      │
      ├── Success → Return
      │
      └── Retryable Failure
              ↓
        Backup Model
              │
              ├── Success → Return
              └── Failure → Safe Error
Enter fullscreen mode Exit fullscreen mode

Fallback should never bypass authorization or safety controls.

Every provider must operate under the same application policy.


42.9 Retry Policy

Not every failure should be retried.

Retryable conditions may include certain:

  • transient network failures,
  • temporary service unavailability,
  • controlled rate-limit responses.

Non-retryable conditions may include:

  • invalid request,
  • invalid authentication configuration,
  • malformed structured output,
  • authorization failure,
  • policy rejection.

Retries should use bounded exponential backoff.

A system should also enforce a maximum retry count.

Otherwise, one failed request could generate unnecessary provider traffic and cost.


42.10 Timeouts

Every model request should have a timeout.

Conceptually:

Request
   ↓
Timeout Boundary
   ↓
Model Provider
Enter fullscreen mode Exit fullscreen mode

Without a timeout, an application worker can remain occupied indefinitely.

The timeout should be appropriate for the operation.

For example:

Simple classification
 → short timeout

Long document summarization
 → longer timeout
Enter fullscreen mode Exit fullscreen mode

The exact values should be configurable.


42.11 Prompt Architecture

Prompts should not be scattered throughout API handlers.

Instead, create a prompt layer.

Conceptually:

PromptRegistry
   ├── ChatPrompt
   ├── RagPrompt
   ├── SummaryPrompt
   ├── ExtractionPrompt
   └── AgentPrompt
Enter fullscreen mode Exit fullscreen mode

Each prompt should have:

  • an identifier,
  • a version,
  • an intended task,
  • required variables,
  • expected output format.

Example:

rag.answer.v3
Enter fullscreen mode Exit fullscreen mode

is more manageable than an anonymous string embedded inside an API route.


42.12 Prompt Versioning

Prompts are part of application behavior.

Changing a prompt can change model output.

Therefore, prompt versions should be tracked.

Example:

rag.answer.v1
rag.answer.v2
rag.answer.v3
Enter fullscreen mode Exit fullscreen mode

The system can then determine:

Which prompt produced this answer?
Enter fullscreen mode Exit fullscreen mode

This is valuable for:

  • debugging,
  • evaluation,
  • regression testing,
  • research,
  • reproducibility.

42.13 Prompt Construction

A RAG request may contain:

System Policy
Task Instructions
User Question
Retrieved Evidence
Output Requirements
Enter fullscreen mode Exit fullscreen mode

The orchestrator should construct these components explicitly.

Conceptually:

SYSTEM
  ↓
TASK
  ↓
USER INPUT
  ↓
RETRIEVED EVIDENCE
  ↓
OUTPUT CONTRACT
Enter fullscreen mode Exit fullscreen mode

The exact implementation depends on the model interface.

The important architectural principle is that different content types retain their roles.


42.14 Instruction Hierarchy

The system must distinguish between trusted instructions and untrusted content.

For example:

Trusted Application Policy
          ↓
Application Task
          ↓
User Request
          ↓
Retrieved Documents
          ↓
External Tool Output
Enter fullscreen mode Exit fullscreen mode

Document content, search results, webpages, uploaded files, and tool outputs should not automatically gain authority simply because they appear inside the model context.

This is particularly important for agentic systems.


42.15 User Input Is Also Data

Although the user controls their own request, the application should not blindly interpolate arbitrary user input into privileged instructions.

User input may contain:

  • accidental formatting,
  • malformed data,
  • prompt-like language,
  • very large text,
  • unsupported instructions.

The application should therefore separate:

Application Instructions
Enter fullscreen mode Exit fullscreen mode

from:

User Content
Enter fullscreen mode Exit fullscreen mode

rather than concatenating everything into one indistinguishable string.


42.16 Structured Output

Whenever an AI operation has a machine-readable result, structured output should be preferred.

Instead of asking for:

"Return the answer somehow."
Enter fullscreen mode Exit fullscreen mode

the application should define an expected structure.

For example:

{
  "summary": "string",
  "confidence": 0.0,
  "sources": []
}
Enter fullscreen mode Exit fullscreen mode

The application can then validate the result before using it.

This is especially important for:

  • database updates,
  • workflow decisions,
  • tool calls,
  • document extraction,
  • automated actions.

42.17 Output Validation

Model output must be considered untrusted until validated.

A structured response should pass through:

Model Output
     ↓
Parser
     ↓
Schema Validator
     ↓
Business Rules
     ↓
Application
Enter fullscreen mode Exit fullscreen mode

If validation fails:

Validation Failure
       ↓
Repair / Retry
       ↓
Second Validation
       ↓
Safe Failure
Enter fullscreen mode Exit fullscreen mode

The system should never assume that a model will always obey an output schema perfectly.


42.18 Token Management

Token usage affects:

  • latency,
  • cost,
  • context capacity,
  • model reliability.

The orchestrator should calculate or estimate:

Input Tokens
Output Tokens
Total Tokens
Enter fullscreen mode Exit fullscreen mode

for every inference operation where the provider exposes appropriate usage data.

A usage record can contain:

requestId
userId
projectId
model
inputTokens
outputTokens
totalTokens
duration
status
Enter fullscreen mode Exit fullscreen mode

42.19 Context Budget

A request may contain:

Conversation History
+
User Question
+
Retrieved Documents
+
System Instructions
Enter fullscreen mode Exit fullscreen mode

All of these consume context.

Therefore, the application should maintain a context budget.

Conceptually:

Maximum Context
 ├── System Policy
 ├── Conversation
 ├── Retrieved Evidence
 └── Output Reserve
Enter fullscreen mode Exit fullscreen mode

If the input exceeds the budget, the context manager should reduce it systematically.

Possible strategies include:

  • remove redundant history,
  • summarize older conversation,
  • retrieve fewer chunks,
  • compress evidence,
  • prioritize relevant sources.

42.20 Context Prioritization

Not every piece of information has equal importance.

A priority system can be:

Priority 1:
Security / system requirements

Priority 2:
Current user request

Priority 3:
Relevant retrieved evidence

Priority 4:
Recent conversation

Priority 5:
Older optional context
Enter fullscreen mode Exit fullscreen mode

The exact ordering depends on application design, but it should be deterministic and testable.


42.21 Conversation Management

Long conversations can become expensive.

Instead of sending the entire conversation on every request, the system can maintain:

Recent Messages
+
Conversation Summary
+
Relevant Retrieved History
Enter fullscreen mode Exit fullscreen mode

For example:

Conversation
 ├── Summary
 ├── Recent 10 messages
 └── Relevant historical messages
Enter fullscreen mode Exit fullscreen mode

This reduces unnecessary context consumption.


42.22 Model Context and RAG Context

Conversation context and document context should remain distinguishable.

Conceptually:

Conversation Context
        +
Document Evidence
        +
Current Request
Enter fullscreen mode Exit fullscreen mode

The model can then understand which information came from where.

This also improves citation generation.


42.23 AI Request Lifecycle

Every AI request should pass through a controlled lifecycle:

1. Receive Request
2. Authenticate User
3. Authorize Operation
4. Validate Input
5. Apply Rate Limits
6. Determine Task Type
7. Select Model
8. Retrieve Context
9. Build Prompt
10. Apply Token Budget
11. Call Provider
12. Validate Output
13. Record Usage
14. Record Audit Event
15. Return Response
Enter fullscreen mode Exit fullscreen mode

This creates a consistent security boundary.


42.24 AI Request Object

Internally, the system can normalize requests into a common structure:

AIRequest
 ├── requestId
 ├── userId
 ├── projectId
 ├── task
 ├── input
 ├── context
 ├── modelPolicy
 ├── outputSchema
 └── metadata
Enter fullscreen mode Exit fullscreen mode

This allows the orchestrator to process different AI features consistently.


42.25 AI Response Object

Likewise:

AIResponse
 ├── requestId
 ├── content
 ├── structuredData
 ├── model
 ├── usage
 ├── citations
 ├── finishReason
 └── metadata
Enter fullscreen mode Exit fullscreen mode

This provides a stable contract for the frontend and backend.


42.26 Usage Accounting

AI operations should be connected to the usage system established earlier.

A request can record:

User
Project
Task
Model
Input Tokens
Output Tokens
Duration
Status
Enter fullscreen mode Exit fullscreen mode

This enables:

  • quotas,
  • billing,
  • analytics,
  • abuse detection,
  • capacity planning.

Usage records should not contain unnecessary sensitive prompt content.


42.27 Rate Limiting

AI endpoints require stronger controls than ordinary read APIs because inference can be expensive.

Rate limits can operate at multiple levels:

IP
User
Project
API Key
Task
Model
Enter fullscreen mode Exit fullscreen mode

For example:

User Limit
      ↓
Project Limit
      ↓
Model Limit
      ↓
Global Capacity Limit
Enter fullscreen mode Exit fullscreen mode

The system should return a controlled response when a limit is exceeded.


42.28 Budget Controls

A project may have a monthly AI budget.

The orchestrator can check:

Current Usage
+
Estimated Request Cost
≤
Allowed Budget
Enter fullscreen mode Exit fullscreen mode

before starting expensive operations.

For exact cost accounting, the implementation should use provider-reported usage and configured pricing data where applicable.


42.29 Safety Policy Layer

Safety controls should not depend entirely on the model.

The application can have a policy layer that determines whether a requested operation is permitted.

Conceptually:

Request
  ↓
Application Policy
  ↓
Model Policy
  ↓
Provider
Enter fullscreen mode Exit fullscreen mode

The policy layer can enforce application-specific restrictions such as:

  • user permissions,
  • project permissions,
  • feature availability,
  • content handling requirements,
  • tool permissions,
  • data access restrictions.

42.30 Tool Permissions

When the AI system eventually gains access to tools, model output must not automatically execute arbitrary actions.

Instead:

Model Request
      ↓
Tool Authorization
      ↓
Parameter Validation
      ↓
Approval Policy
      ↓
Tool Execution
Enter fullscreen mode Exit fullscreen mode

For sensitive operations, human approval can be required.

This creates a crucial separation:

Model proposes
Enter fullscreen mode Exit fullscreen mode

versus:

Application authorizes
Enter fullscreen mode Exit fullscreen mode

42.31 Agentic Inference

A future agent system may perform multiple inference steps:

Goal
 ↓
Plan
 ↓
Retrieve
 ↓
Reason
 ↓
Tool Proposal
 ↓
Verification
 ↓
Action
Enter fullscreen mode Exit fullscreen mode

Each step should be separately observable.

The model should not receive unrestricted authority over the entire application.

Instead, the orchestrator should provide bounded capabilities.


42.32 Model Independence

One major benefit of orchestration is model independence.

The application can evolve from:

One Model
Enter fullscreen mode Exit fullscreen mode

to:

Multiple Models
Enter fullscreen mode Exit fullscreen mode

without rewriting every feature.

The architecture becomes:

Feature
  ↓
Task
  ↓
Model Policy
  ↓
Router
  ↓
Selected Model
Enter fullscreen mode Exit fullscreen mode

This is particularly valuable as model capabilities and pricing change over time.


42.33 Local and Remote Models

The abstraction layer can support both remote and locally hosted models.

Conceptually:

AI Orchestrator
       │
       ├── Remote Provider
       │
       └── Local Provider
Enter fullscreen mode Exit fullscreen mode

This can support different deployment strategies.

For sensitive workloads, an organization may choose a locally hosted model.

For high-capability workloads, it may use a remote model.

The application architecture should remain consistent.


42.34 Provider Health Monitoring

The router should maintain basic provider health information.

Possible states:

HEALTHY
DEGRADED
RATE_LIMITED
UNAVAILABLE
DISABLED
Enter fullscreen mode Exit fullscreen mode

A provider that repeatedly fails can temporarily be removed from normal routing.

This prevents every request from repeatedly encountering the same failure.


42.35 Circuit Breaker Concept

A circuit breaker can protect the application from an unhealthy dependency.

Conceptually:

Normal
  ↓
Repeated Failures
  ↓
Open Circuit
  ↓
Stop Requests Temporarily
  ↓
Health Check
  ↓
Recovery
  ↓
Normal
Enter fullscreen mode Exit fullscreen mode

This should be carefully implemented so that a provider outage does not cascade into application-wide resource exhaustion.


42.36 Caching

Some AI operations may be safely cacheable.

Examples could include deterministic operations where the same input and configuration produce reusable results.

A cache key might include:

task
model
promptVersion
inputHash
contextHash
configurationVersion
Enter fullscreen mode Exit fullscreen mode

Sensitive data should not be placed into shared caches without appropriate isolation.

Caching should never bypass authorization.


42.37 Determinism and Reproducibility

Model outputs can vary.

For research and testing, the system should record relevant configuration.

For example:

model
promptVersion
temperature
maxOutputTokens
retrievalVersion
embeddingVersion
applicationVersion
Enter fullscreen mode Exit fullscreen mode

Not every provider exposes identical controls, so the architecture should record what is actually available.

This makes experiments easier to reproduce.


42.38 AI Audit Trail

The system should maintain an AI operation record.

A conceptual audit entry:

AI Audit Event
 ├── requestId
 ├── userId
 ├── projectId
 ├── task
 ├── model
 ├── promptVersion
 ├── retrievalVersion
 ├── status
 ├── duration
 └── timestamp
Enter fullscreen mode Exit fullscreen mode

The audit record should avoid storing full sensitive prompts or outputs unless explicitly required and appropriately protected.


42.39 Error Classification

AI failures should be categorized.

Example:

INPUT_VALIDATION_ERROR
AUTHORIZATION_ERROR
RATE_LIMIT_ERROR
PROVIDER_TIMEOUT
PROVIDER_UNAVAILABLE
MODEL_OUTPUT_INVALID
CONTEXT_LIMIT_ERROR
POLICY_REJECTION
INTERNAL_ERROR
Enter fullscreen mode Exit fullscreen mode

This allows the frontend to provide meaningful responses without exposing internal implementation details.


42.40 Secure Error Messages

The system should not expose:

  • provider credentials,
  • internal stack traces,
  • private configuration,
  • database details,
  • internal network information.

A user-facing response should be safe.

Internally:

Detailed diagnostic
Enter fullscreen mode Exit fullscreen mode

Externally:

Controlled error
Enter fullscreen mode Exit fullscreen mode

This follows the same security boundary established for the API layer.


42.41 AI Service Architecture

The resulting backend architecture can now be:

src/
├── app/
│   └── api/
├── services/
│   ├── ai/
│   │   ├── orchestrator
│   │   ├── router
│   │   ├── prompts
│   │   ├── context
│   │   ├── token-manager
│   │   ├── safety
│   │   ├── usage
│   │   └── providers/
│   ├── documents/
│   ├── retrieval/
│   └── storage/
├── repositories/
└── lib/
Enter fullscreen mode Exit fullscreen mode

This keeps model-specific implementation away from business-facing API routes.


42.42 Example AI Request Flow

A RAG question might follow:

User
 ↓
POST /api/ai/ask
 ↓
Authenticate
 ↓
Authorize Project
 ↓
Validate Question
 ↓
Check Usage Limit
 ↓
Retrieve Authorized Evidence
 ↓
Select RAG Model
 ↓
Build Versioned Prompt
 ↓
Apply Context Budget
 ↓
Call Provider
 ↓
Validate Response
 ↓
Attach Citations
 ↓
Record Usage
 ↓
Audit
 ↓
Return Answer
Enter fullscreen mode Exit fullscreen mode

This flow integrates the architecture established in previous chapters.


42.43 Testing Strategy

The orchestration layer requires multiple levels of testing.

Unit Tests

Test:

  • model routing,
  • token budgeting,
  • prompt construction,
  • output validation,
  • retry decisions.

Integration Tests

Test:

  • provider adapters,
  • database usage recording,
  • retrieval integration,
  • authorization.

Failure Tests

Simulate:

  • timeout,
  • provider unavailable,
  • malformed output,
  • rate limit,
  • context overflow.

Security Tests

Test:

  • unauthorized project access,
  • cross-user retrieval,
  • untrusted document instructions,
  • tool authorization,
  • sensitive error leakage.

42.44 Evaluation Matrix

A useful evaluation matrix is:

Task
Model
Prompt Version
Retrieval Version
Expected Quality
Actual Quality
Latency
Token Usage
Failure Rate
Enter fullscreen mode Exit fullscreen mode

This enables systematic comparison.

For example:

RAG-QA
Model A
Prompt v3
Retriever v2
Accuracy: ...
Latency: ...
Enter fullscreen mode Exit fullscreen mode

The exact metrics should be determined by the research objective.


42.45 Operational Dashboard

The system can expose metrics such as:

AI Requests / Minute
Success Rate
Failure Rate
Average Latency
P95 Latency
Input Tokens
Output Tokens
Provider Errors
Fallback Rate
Retrieval Latency
Model Distribution
Enter fullscreen mode Exit fullscreen mode

Sensitive user content should not be displayed in operational dashboards.


42.46 Configuration Management

AI configuration should be environment-controlled.

Examples include:

AI_DEFAULT_MODEL
AI_TIMEOUT_MS
AI_MAX_RETRIES
AI_MAX_CONTEXT_TOKENS
AI_MAX_OUTPUT_TOKENS
AI_DEFAULT_TEMPERATURE
AI_PROVIDER_MODE
Enter fullscreen mode Exit fullscreen mode

Secrets should remain outside source control.

Configuration should be validated when the application starts.


42.47 No Secrets in Prompts or Logs

API keys, passwords, session tokens, and private credentials must never be intentionally inserted into model prompts.

Similarly, logs should avoid storing credentials or unnecessary sensitive content.

The AI layer should assume that model providers and logging systems are separate trust boundaries.


42.48 Data Minimization

Before sending information to a model, the application should ask:

Does the model actually need this data?

If not, it should be omitted.

For example:

Full User Profile
Enter fullscreen mode Exit fullscreen mode

may not be necessary for:

Simple Document Summarization
Enter fullscreen mode Exit fullscreen mode

Reducing unnecessary context improves:

  • privacy,
  • latency,
  • cost,
  • security.

42.49 The AI Orchestrator as a Security Boundary

The orchestrator should become the central checkpoint for AI operations.

                    AI REQUEST
                        │
                        ▼
                ┌──────────────┐
                │ Orchestrator │
                └──────────────┘
                  │    │    │
          ┌───────┘    │    └────────┐
          ▼            ▼             ▼
     Authorization   Routing      Safety
          │            │             │
          └────────────┼─────────────┘
                       ▼
                    Context
                       │
                       ▼
                     Model
                       │
                       ▼
                   Validation
                       │
                       ▼
                  Application
Enter fullscreen mode Exit fullscreen mode

This architecture makes AI behavior significantly easier to control.


42.50 Complete AI Architecture

Combining previous chapters produces the following architecture:

                         USER
                           │
                           ▼
                        API
                           │
                           ▼
                Authentication/AuthZ
                           │
                           ▼
                    AI Orchestrator
                           │
        ┌──────────────────┼──────────────────┐
        ▼                  ▼                  ▼
   Model Router      Context Manager      Safety Policy
        │                  │                  │
        ▼                  ▼                  │
   Provider Adapter   RAG Retrieval           │
        │                  │                  │
        └──────────────┬───┴──────────────────┘
                       ▼
                    Prompt
                       │
                       ▼
                 Token Manager
                       │
                       ▼
                 Selected Model
                       │
                       ▼
                Output Validation
                       │
             ┌─────────┴─────────┐
             ▼                   ▼
          Usage                Audit
             │                   │
             └─────────┬─────────┘
                       ▼
                    Response
Enter fullscreen mode Exit fullscreen mode

42.51 Architectural Principles

Principle 1 — Centralize AI access

Features should call the orchestrator rather than providers directly.

Principle 2 — Keep providers replaceable

Provider-specific details belong inside adapters.

Principle 3 — Separate model selection from application logic

Use task and capability policies.

Principle 4 — Treat prompts as versioned software artifacts

Prompt changes should be traceable.

Principle 5 — Control context

Never send unnecessary information to the model.

Principle 6 — Validate model output

Model-generated data is not automatically trusted.

Principle 7 — Enforce authorization before retrieval

The model must never become an access-control mechanism.

Principle 8 — Keep tools behind authorization

Model proposals are not automatically authorized actions.

Principle 9 — Record usage and operational metadata

AI behavior must be measurable.

Principle 10 — Design for failure

Provider outages, timeouts, rate limits, and malformed outputs are expected conditions.


42.52 Chapter Summary

The system now contains a dedicated AI inference architecture.

The major components are:

AI Orchestrator
Model Router
Provider Adapters
Prompt Registry
Context Manager
Token Manager
Safety Policy
Output Validator
Usage Meter
Audit Layer
Observability
Enter fullscreen mode Exit fullscreen mode

The resulting lifecycle is:

Request → Authenticate → Authorize → Validate → Route → Retrieve → Build Context → Construct Prompt → Infer → Validate → Meter → Audit → Respond

This architecture prevents AI providers from becoming deeply embedded throughout the application.

It also establishes the foundation for the next stage of the project: agent architecture, tool calling, planning, execution boundaries, approvals, task state, and safe autonomous workflows.

END OF CHAPTER 42

Implementation snippet — provider abstraction
export type GenerateInput = {
messages: Array<{
role: "system" | "user" | "assistant";
content: string;
}>;
maxOutputTokens?: number;
};

export type GenerateResult = {
text: string;
model: string;
usage?: {
inputTokens?: number;
outputTokens?: number;
totalTokens?: number;
};
};

export interface AIProvider {
generate(input: GenerateInput): Promise;
}
Implementation snippet — simple model router
type TaskType =
| "CHAT"
| "RAG_QA"
| "SUMMARIZATION"
| "CLASSIFICATION"
| "STRUCTURED_EXTRACTION"
| "VISION_ANALYSIS";

type ModelPolicy = {
task: TaskType;
preferredModel: string;
fallbackModel?: string;
};

const policies: ModelPolicy[] = [
{
task: "CHAT",
preferredModel: "fast-general",
fallbackModel: "quality-general",
},
{
task: "RAG_QA",
preferredModel: "quality-general",
fallbackModel: "fast-general",
},
{
task: "CLASSIFICATION",
preferredModel: "fast-general",
},
];

export function routeModel(task: TaskType): ModelPolicy {
const policy = policies.find((item) => item.task === task);

if (!policy) {
throw new Error(No model policy configured for task: ${task});
}

return policy;
}
Implementation snippet — orchestrator skeleton
export async function runAIRequest(input: {
userId: string;
projectId: string;
task: TaskType;
messages: GenerateInput["messages"];
}) {
// Authorization should happen before this function is allowed to run.

const policy = routeModel(input.task);

const provider = providerRegistry.get(policy.preferredModel);

try {
return await provider.generate({
messages: input.messages,
maxOutputTokens: 2000,
});
} catch (error) {
if (!policy.fallbackModel) {
throw error;
}

const fallback = providerRegistry.get(policy.fallbackModel);

return fallback.generate({
  messages: input.messages,
  maxOutputTokens: 2000,
});
Enter fullscreen mode Exit fullscreen mode

}
}

Top comments (0)