<article class="max-w-4xl mx-auto px-6 py-12">
<header class="mb-12">
<div class="inline-flex items-center gap-2 px-3 py-1 rounded-full bg-success-500/10 text-success-400 text-sm font-medium mb-4">
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M13 10V3L4 14h7v7l9-11h-7z"/>
</svg>
Matches Diesel for type-level filters
</div>
<h1 class="text-4xl font-bold mb-4">Performance</h1>
<p class="text-xl text-muted">
Prax is highly optimized for performance, matching Diesel for type-level operations while providing a developer-friendly Prisma-like API.
</p>
</header>
<div class="space-y-12">
<section>
<h2 class="text-2xl font-semibold mb-6">Key Achievements</h2>
<div class="grid md:grid-cols-4 gap-4">
<div class="p-6 rounded-xl bg-surface border border-border">
<div class="text-3xl font-bold text-success-400 mb-2">5.1ns</div>
<div class="text-sm text-muted">Type-level AND(5)</div>
<div class="text-xs text-success-400 mt-1">Matches Diesel!</div>
</div>
<div class="p-6 rounded-xl bg-surface border border-border">
<div class="text-3xl font-bold text-success-400 mb-2">3.8ns</div>
<div class="text-sm text-muted">IN(10) SQL generation</div>
<div class="text-xs text-success-400 mt-1">5.8x faster with patterns</div>
</div>
<div class="p-6 rounded-xl bg-surface border border-border">
<div class="text-3xl font-bold text-primary-400 mb-2">64B</div>
<div class="text-sm text-muted">Filter enum size</div>
<div class="text-xs text-primary-400 mt-1">Fits in single cache line</div>
</div>
<div class="p-6 rounded-xl bg-surface border border-border">
<div class="text-3xl font-bold text-accent-400 mb-2">30%</div>
<div class="text-sm text-muted">Faster than SQLx</div>
<div class="text-xs text-accent-400 mt-1">Database execution</div>
</div>
</div>
</section>
<section>
<h2 class="text-2xl font-semibold mb-6">Query Building Performance</h2>
<div class="overflow-x-auto">
<table class="w-full text-sm">
<thead>
<tr class="border-b border-border text-left">
<th class="py-3 px-4 font-medium">Operation</th>
<th class="py-3 px-4 font-medium text-primary-400">Prax</th>
<th class="py-3 px-4 font-medium">Diesel</th>
<th class="py-3 px-4 font-medium">SQLx</th>
<th class="py-3 px-4 font-medium">Notes</th>
</tr>
</thead>
<tbody class="divide-y divide-border">
<tr>
<td class="py-3 px-4">Simple SELECT</td>
<td class="py-3 px-4 text-success-400 font-medium">40ns</td>
<td class="py-3 px-4">278ns</td>
<td class="py-3 px-4">5ns</td>
<td class="py-3 px-4 text-muted">7x faster than Diesel</td>
</tr>
<tr>
<td class="py-3 px-4">SELECT + filters</td>
<td class="py-3 px-4 text-success-400 font-medium">105ns</td>
<td class="py-3 px-4">633ns</td>
<td class="py-3 px-4">5ns</td>
<td class="py-3 px-4 text-muted">6x faster than Diesel</td>
</tr>
<tr>
<td class="py-3 px-4">INSERT query</td>
<td class="py-3 px-4 text-success-400 font-medium">81ns</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4">5ns</td>
<td class="py-3 px-4 text-muted">-</td>
</tr>
<tr>
<td class="py-3 px-4">UPDATE query</td>
<td class="py-3 px-4 text-success-400 font-medium">101ns</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4">5ns</td>
<td class="py-3 px-4 text-muted">-</td>
</tr>
</tbody>
</table>
</div>
</section>
<section>
<h2 class="text-2xl font-semibold mb-6">Filter Construction Performance</h2>
<div class="overflow-x-auto">
<table class="w-full text-sm">
<thead>
<tr class="border-b border-border text-left">
<th class="py-3 px-4 font-medium">Operation</th>
<th class="py-3 px-4 font-medium text-primary-400">Prax (TypeLevel)</th>
<th class="py-3 px-4 font-medium text-primary-400">Prax (Runtime)</th>
<th class="py-3 px-4 font-medium">Diesel</th>
<th class="py-3 px-4 font-medium">Notes</th>
</tr>
</thead>
<tbody class="divide-y divide-border">
<tr>
<td class="py-3 px-4">Simple filter</td>
<td class="py-3 px-4 text-success-400 font-medium">2.1ns</td>
<td class="py-3 px-4">7ns</td>
<td class="py-3 px-4">4.7ns</td>
<td class="py-3 px-4 text-muted">DirectSql: 2.1ns</td>
</tr>
<tr>
<td class="py-3 px-4">AND (2 filters)</td>
<td class="py-3 px-4 text-success-400 font-medium">4.3ns</td>
<td class="py-3 px-4">17ns</td>
<td class="py-3 px-4">5ns</td>
<td class="py-3 px-4 text-muted">DirectSql matches Diesel</td>
</tr>
<tr>
<td class="py-3 px-4">AND (5 filters)</td>
<td class="py-3 px-4 text-success-400 font-medium">5.1ns</td>
<td class="py-3 px-4">32ns</td>
<td class="py-3 px-4">5ns</td>
<td class="py-3 px-4 text-muted">TypeLevel = Diesel!</td>
</tr>
<tr>
<td class="py-3 px-4">AND (5) SQL gen</td>
<td class="py-3 px-4 font-medium">17ns</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4 text-muted">DirectSql write</td>
</tr>
<tr>
<td class="py-3 px-4">IN (10 values)</td>
<td class="py-3 px-4 text-success-400 font-medium">3.8ns</td>
<td class="py-3 px-4">21ns</td>
<td class="py-3 px-4">14ns</td>
<td class="py-3 px-4 text-muted">Pre-computed pattern</td>
</tr>
<tr>
<td class="py-3 px-4">IN (32 values)</td>
<td class="py-3 px-4 text-success-400 font-medium">5.0ns</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4 text-muted">Pre-computed pattern</td>
</tr>
<tr>
<td class="py-3 px-4">IN (100 values)</td>
<td class="py-3 px-4 font-medium">158ns</td>
<td class="py-3 px-4">160ns</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4 text-muted">Looped generation</td>
</tr>
</tbody>
</table>
</div>
</section>
<section>
<h2 class="text-2xl font-semibold mb-6">Database Execution (PostgreSQL with Pooling)</h2>
<div class="overflow-x-auto">
<table class="w-full text-sm">
<thead>
<tr class="border-b border-border text-left">
<th class="py-3 px-4 font-medium">Operation</th>
<th class="py-3 px-4 font-medium text-primary-400">Prax</th>
<th class="py-3 px-4 font-medium">SQLx</th>
<th class="py-3 px-4 font-medium">Diesel-Async</th>
<th class="py-3 px-4 font-medium">Winner</th>
</tr>
</thead>
<tbody class="divide-y divide-border">
<tr>
<td class="py-3 px-4">SELECT by ID</td>
<td class="py-3 px-4 text-success-400 font-medium">193µs</td>
<td class="py-3 px-4">276µs</td>
<td class="py-3 px-4">6.18ms*</td>
<td class="py-3 px-4 text-success-400">Prax</td>
</tr>
<tr>
<td class="py-3 px-4">SELECT filtered</td>
<td class="py-3 px-4 text-success-400 font-medium">192µs</td>
<td class="py-3 px-4">269µs</td>
<td class="py-3 px-4">7.40ms*</td>
<td class="py-3 px-4 text-success-400">Prax</td>
</tr>
<tr>
<td class="py-3 px-4">COUNT</td>
<td class="py-3 px-4 text-success-400 font-medium">255µs</td>
<td class="py-3 px-4">320µs</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4 text-success-400">Prax</td>
</tr>
<tr>
<td class="py-3 px-4">SELECT prepared</td>
<td class="py-3 px-4 text-success-400 font-medium">191µs</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4">-</td>
<td class="py-3 px-4 text-success-400">Prax</td>
</tr>
</tbody>
</table>
<p class="text-xs text-muted mt-2">* Diesel-Async establishes a new connection per iteration (~6ms overhead). Prax and SQLx use connection pooling with warmup.</p>
</div>
</section>
<section>
<h2 class="text-2xl font-semibold mb-6">Memory Footprint</h2>
<div class="overflow-x-auto">
<table class="w-full text-sm">
<thead>
<tr class="border-b border-border text-left">
<th class="py-3 px-4 font-medium">Type</th>
<th class="py-3 px-4 font-medium">Size</th>
<th class="py-3 px-4 font-medium">Notes</th>
</tr>
</thead>
<tbody class="divide-y divide-border">
<tr>
<td class="py-3 px-4 font-mono text-sm">Filter</td>
<td class="py-3 px-4 text-success-400 font-medium">64 bytes</td>
<td class="py-3 px-4 text-muted">Fits in single cache line</td>
</tr>
<tr>
<td class="py-3 px-4 font-mono text-sm">ValueList</td>
<td class="py-3 px-4 text-success-400 font-medium">24 bytes</td>
<td class="py-3 px-4 text-muted">91% reduction from SmallVec</td>
</tr>
<tr>
<td class="py-3 px-4 font-mono text-sm">FieldName</td>
<td class="py-3 px-4">24 bytes</td>
<td class="py-3 px-4 text-muted">Cow<'static, str></td>
</tr>
</tbody>
</table>
</div>
</section>
<section>
<h2 class="text-2xl font-semibold mb-6">Optimization Techniques</h2>
<div class="space-y-4">
<div class="p-4 rounded-lg bg-surface border border-border">
<h3 class="font-semibold mb-2">DirectSql Trait (~5ns)</h3>
<p class="text-sm text-muted mb-3">Zero-allocation SQL generation directly from typed filters.</p>
<app-code-block [code]="directSqlExample" language="rust" />
</div>
<div class="p-4 rounded-lg bg-surface border border-border">
<h3 class="font-semibold mb-2">Pre-computed Placeholders</h3>
<p class="text-sm text-muted mb-3">256-entry static lookup table for PostgreSQL placeholders ($1, $2, ...). Pre-computed IN patterns for 1-32 elements.</p>
<app-code-block [code]="placeholderExample" language="rust" />
</div>
<div class="p-4 rounded-lg bg-surface border border-border">
<h3 class="font-semibold mb-2">Execution Plan Cache</h3>
<p class="text-sm text-muted mb-3">Cache query plans with performance hints and automatic execution time tracking.</p>
<app-code-block [code]="planCacheExample" language="rust" />
</div>
<div class="p-4 rounded-lg bg-surface border border-border">
<h3 class="font-semibold mb-2">Zero-Copy Row Deserialization</h3>
<p class="text-sm text-muted mb-3">Borrow string data directly from database rows without allocating.</p>
<app-code-block [code]="zeroCopyExample" language="rust" />
</div>
<div class="p-4 rounded-lg bg-surface border border-border">
<h3 class="font-semibold mb-2">Pipeline Execution</h3>
<p class="text-sm text-muted mb-3">Combine multiple queries into a single database round-trip.</p>
<app-code-block [code]="pipelineExample" language="rust" />
</div>
<div class="p-4 rounded-lg bg-surface border border-border">
<h3 class="font-semibold mb-2">Type-Level Filters (And5, Or5)</h3>
<p class="text-sm text-muted mb-3">Stack-allocated filter composition matching Diesel's zero-cost abstractions.</p>
<app-code-block [code]="typeLevelExample" language="rust" />
</div>
</div>
</section>
<section>
<h2 class="text-2xl font-semibold mb-6">Why Prax is Fast</h2>
<div class="grid md:grid-cols-2 gap-4">
<div class="p-4 rounded-lg bg-surface border border-border">
<div class="flex items-start gap-3">
<div class="w-8 h-8 rounded-lg bg-success-500/10 flex items-center justify-center flex-shrink-0">
<svg class="w-4 h-4 text-success-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 13l4 4L19 7"/>
</svg>
</div>
<div>
<h3 class="font-semibold mb-1">Cache-Friendly Layout</h3>
<p class="text-sm text-muted">Filter enum fits in a single 64-byte cache line.</p>
</div>
</div>
</div>
<div class="p-4 rounded-lg bg-surface border border-border">
<div class="flex items-start gap-3">
<div class="w-8 h-8 rounded-lg bg-success-500/10 flex items-center justify-center flex-shrink-0">
<svg class="w-4 h-4 text-success-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 13l4 4L19 7"/>
</svg>
</div>
<div>
<h3 class="font-semibold mb-1">Zero Allocation Paths</h3>
<p class="text-sm text-muted">Static field names and pre-computed values avoid heap allocation.</p>
</div>
</div>
</div>
<div class="p-4 rounded-lg bg-surface border border-border">
<div class="flex items-start gap-3">
<div class="w-8 h-8 rounded-lg bg-success-500/10 flex items-center justify-center flex-shrink-0">
<svg class="w-4 h-4 text-success-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 13l4 4L19 7"/>
</svg>
</div>
<div>
<h3 class="font-semibold mb-1">Connection Pool Warmup</h3>
<p class="text-sm text-muted">Pre-establish connections and prepare statements at startup.</p>
</div>
</div>
</div>
<div class="p-4 rounded-lg bg-surface border border-border">
<div class="flex items-start gap-3">
<div class="w-8 h-8 rounded-lg bg-success-500/10 flex items-center justify-center flex-shrink-0">
<svg class="w-4 h-4 text-success-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 13l4 4L19 7"/>
</svg>
</div>
<div>
<h3 class="font-semibold mb-1">Prepared Statement Caching</h3>
<p class="text-sm text-muted">All queries use prepare_cached() for per-connection statement reuse.</p>
</div>
</div>
</div>
</div>
</section>
<section>
<h2 class="text-2xl font-semibold mb-6">Prax vs Diesel</h2>
<div class="grid md:grid-cols-2 gap-6">
<div class="p-6 rounded-xl bg-surface border border-success-500/30">
<h3 class="font-semibold text-success-400 mb-4">Where Prax Wins</h3>
<ul class="space-y-2 text-sm">
<li class="flex items-start gap-2">
<span class="text-success-400">✓</span>
<span>6-7x faster SQL string construction</span>
</li>
<li class="flex items-start gap-2">
<span class="text-success-400">✓</span>
<span>TypeLevel filters match Diesel (5.1ns vs 5ns)</span>
</li>
<li class="flex items-start gap-2">
<span class="text-success-400">✓</span>
<span>30% faster database execution vs SQLx</span>
</li>
<li class="flex items-start gap-2">
<span class="text-success-400">✓</span>
<span>Runtime flexibility with Prisma-like API</span>
</li>
<li class="flex items-start gap-2">
<span class="text-success-400">✓</span>
<span>Pre-computed IN patterns (3.8ns for 10 values)</span>
</li>
</ul>
</div>
<div class="p-6 rounded-xl bg-surface border border-primary-500/30">
<h3 class="font-semibold text-primary-400 mb-4">Where They're Equal</h3>
<ul class="space-y-2 text-sm">
<li class="flex items-start gap-2">
<span class="text-primary-400">≈</span>
<span>Type-level AND(5): 5.1ns vs 5ns</span>
</li>
<li class="flex items-start gap-2">
<span class="text-primary-400">≈</span>
<span>DirectSql trait matches zero-cost abstractions</span>
</li>
<li class="flex items-start gap-2">
<span class="text-primary-400">≈</span>
<span>64-byte Filter vs Diesel's type-level size</span>
</li>
</ul>
</div>
</div>
</section>
</div>
</article>