<!-- CANARY: REQ=REQ-GQL-024; FEATURE="Conformance Flagger"; ASPECT=ImplDefinedCollationAndNullOrdering; STATUS=TESTED; OWNER=engine; UPDATED=2025-09-21 --> <h3 id="overview" class="position-relative d-flex align-items-center group"> <span>Overview</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="overview" aria-haspopup="dialog" aria-label="Share link: Overview"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3><div id="headingShareModal" class="heading-share-modal" role="dialog" aria-modal="true" aria-labelledby="headingShareTitle" hidden> <div class="hsm-dialog" role="document"> <div class="hsm-header"> <h2 id="headingShareTitle" class="h6 mb-0 fw-bold">Share this section</h2> <button type="button" class="hsm-close" aria-label="Close"> <i class="fa-solid fa-xmark"></i> </button> </div> <div class="hsm-body"> <label for="headingShareInput" class="form-label small text-muted mb-1 text-uppercase fw-bold" style="font-size: 0.7rem; letter-spacing: 0.5px;">Permalink</label> <div class="input-group mb-4 hsm-url-group"> <input id="headingShareInput" type="text" class="form-control font-monospace" readonly aria-readonly="true" style="font-size: 0.85rem;" /> <button class="btn btn-primary hsm-copy" type="button" aria-label="Copy" title="Copy"> <i class="fa-duotone fa-clipboard" aria-hidden="true"></i> </button> </div> <div class="small fw-bold mb-2 text-muted text-uppercase" style="font-size: 0.7rem; letter-spacing: 0.5px;">Share via</div> <div class="hsm-share-grid"> <a id="share-twitter" class="btn btn-outline-secondary w-100" target="_blank" rel="noopener noreferrer"> <i class="fa-brands fa-twitter me-2"></i>Twitter </a> <a id="share-linkedin" class="btn btn-outline-secondary w-100" target="_blank" rel="noopener noreferrer"> <i class="fa-brands fa-linkedin me-2"></i>LinkedIn </a> <a id="share-facebook" class="btn btn-outline-secondary w-100" target="_blank" rel="noopener noreferrer"> <i class="fa-brands fa-facebook me-2"></i>Facebook </a> </div> </div> </div> </div> <style> .heading-share-modal { position: fixed; inset: 0; display: flex; justify-content: center; align-items: center; background: rgba(0, 0, 0, 0.6); z-index: 1050; padding: 1rem; backdrop-filter: blur(4px); -webkit-backdrop-filter: blur(4px); } .heading-share-modal[hidden] { display: none !important; } .hsm-dialog { max-width: 420px; width: 100%; background: var(--bs-body-bg, #fff); color: var(--bs-body-color, #212529); border: 1px solid var(--bs-border-color, rgba(0,0,0,0.1)); border-radius: 1rem; box-shadow: 0 25px 50px -12px rgba(0, 0, 0, 0.25); overflow: hidden; animation: hsm-fade-in 0.2s ease-out; } @keyframes hsm-fade-in { from { opacity: 0; transform: scale(0.95); } to { opacity: 1; transform: scale(1); } } [data-bs-theme="dark"] .hsm-dialog { background: #1e293b; border-color: rgba(255,255,255,0.1); color: #f8f9fa; } .hsm-header { display: flex; justify-content: space-between; align-items: center; padding: 1rem 1.5rem; border-bottom: 1px solid var(--bs-border-color, rgba(0,0,0,0.1)); background: rgba(0,0,0,0.02); } [data-bs-theme="dark"] .hsm-header { background: rgba(255,255,255,0.02); border-color: rgba(255,255,255,0.1); } .hsm-close { background: transparent; border: none; color: inherit; opacity: 0.5; padding: 0.25rem 0.5rem; border-radius: 0.25rem; font-size: 1.2rem; line-height: 1; transition: opacity 0.2s; } .hsm-close:hover { opacity: 1; } .hsm-body { padding: 1.5rem; } .hsm-url-group { display: flex !important; align-items: stretch; } .hsm-url-group .form-control { flex: 1; min-width: 0; margin: 0; background: var(--bs-secondary-bg, #f8f9fa); border-color: var(--bs-border-color, #dee2e6); border-top-right-radius: 0; border-bottom-right-radius: 0; height: 42px; } .hsm-url-group .btn { flex: 0 0 auto; margin: 0; margin-left: -1px; border-top-left-radius: 0; border-bottom-left-radius: 0; height: 42px; display: flex; align-items: center; justify-content: center; padding: 0 1.25rem; z-index: 2; } [data-bs-theme="dark"] .hsm-url-group .form-control { background: #0f172a; border-color: #334155; color: #e2e8f0; } .hsm-share-grid { display: flex; flex-direction: column; gap: 0.5rem; } .hsm-share-grid .btn { display: flex; align-items: center; justify-content: center; font-size: 0.9rem; padding: 0.6rem; border-color: var(--bs-border-color); width: 100%; } [data-bs-theme="dark"] .hsm-share-grid .btn { color: #e2e8f0; border-color: #475569; } [data-bs-theme="dark"] .hsm-share-grid .btn:hover { background: #334155; border-color: #cbd5e1; } </style> <script> (function(){ const modal = document.getElementById('headingShareModal'); if(!modal) return; const input = modal.querySelector('#headingShareInput'); const copyBtn = modal.querySelector('.hsm-copy'); const twitter = modal.querySelector('#share-twitter'); const linkedin = modal.querySelector('#share-linkedin'); const facebook = modal.querySelector('#share-facebook'); const closeBtn = modal.querySelector('.hsm-close'); let lastFocus=null; let trapBound=false; function buildUrl(id){ return window.location.origin + window.location.pathname + '#' + id; } function isOpen(){ return !modal.hasAttribute('hidden'); } function hydrate(id){ const url=buildUrl(id); input.value=url; const enc=encodeURIComponent(url); const text=encodeURIComponent(document.title); if(twitter) twitter.href=`https://twitter.com/intent/tweet?url=${enc}&text=${text}`; if(linkedin) linkedin.href=`https://www.linkedin.com/sharing/share-offsite/?url=${enc}`; if(facebook) facebook.href=`https://www.facebook.com/sharer/sharer.php?u=${enc}`; } function openModal(id){ lastFocus=document.activeElement; hydrate(id); if(!isOpen()){ modal.removeAttribute('hidden'); } requestAnimationFrame(()=>{ input.focus(); }); trapFocus(); } function closeModal(){ if(!isOpen()) return; modal.setAttribute('hidden',''); if(lastFocus && typeof lastFocus.focus==='function') lastFocus.focus(); } function copyCurrent(){ try{ navigator.clipboard.writeText(input.value).then(()=>feedback(true),()=>fallback()); } catch(e){ fallback(); } } function fallback(){ input.select(); try{ document.execCommand('copy'); feedback(true);}catch(e){ feedback(false);} } function feedback(ok){ if(!copyBtn) return; const icon=copyBtn.querySelector('i'); if(!icon) return; const prev=copyBtn.getAttribute('data-prev')||icon.className; if(!copyBtn.getAttribute('data-prev')) copyBtn.setAttribute('data-prev',prev); icon.className= ok ? 'fa-duotone fa-clipboard-check':'fa-duotone fa-circle-exclamation'; setTimeout(()=>{ icon.className=prev; },1800); } function handleShareClick(e){ e.preventDefault(); const btn=e.currentTarget; const id=btn.getAttribute('data-share-target'); if(id) openModal(id); } function bindShareButtons(){ document.querySelectorAll('.h-share').forEach(btn=>{ if(!btn.dataset.hShareBound){ btn.addEventListener('click', handleShareClick); btn.dataset.hShareBound='1'; } }); } bindShareButtons(); if(document.readyState==='loading'){ document.addEventListener('DOMContentLoaded', bindShareButtons); } else { requestAnimationFrame(bindShareButtons); } document.addEventListener('click', function(e){ const shareBtn=e.target.closest && e.target.closest('.h-share'); if(shareBtn && !shareBtn.dataset.hShareBound){ handleShareClick.call(shareBtn, e); } }, true); document.addEventListener('click', e=>{ if(e.target===modal) closeModal(); if(e.target.closest && e.target.closest('.hsm-close')){ e.preventDefault(); closeModal(); } if(copyBtn && (e.target===copyBtn || (e.target.closest && e.target.closest('.hsm-copy')))) { e.preventDefault(); copyCurrent(); } }); document.addEventListener('keydown', e=>{ if(e.key==='Escape' && isOpen()) closeModal(); }); function trapFocus(){ if(trapBound) return; trapBound=true; modal.addEventListener('keydown', f=>{ if(f.key==='Tab' && isOpen()){ const focusable=[...modal.querySelectorAll('a[href],button,input,textarea,select,[tabindex]:not([tabindex="-1"])')].filter(el=>!el.hasAttribute('disabled')); if(!focusable.length) return; const first=focusable[0]; const last=focusable[focusable.length-1]; if(f.shiftKey && document.activeElement===first){ f.preventDefault(); last.focus(); } else if(!f.shiftKey && document.activeElement===last){ f.preventDefault(); first.focus(); } } }); } if(closeBtn) closeBtn.addEventListener('click', e=>{ e.preventDefault(); closeModal(); }); })(); </script><p>This guide teaches you how to analyze and optimize query performance in Geode using EXPLAIN, PROFILE, indexes, and the cost-based optimizer. You&rsquo;ll learn to diagnose slow queries, understand execution plans, and apply optimization strategies.</p> <p><strong>Performance Tuning Process:</strong></p> <ol> <li><strong>Measure</strong> - Use PROFILE to identify slow queries</li> <li><strong>Analyze</strong> - Use EXPLAIN to understand execution plans</li> <li><strong>Optimize</strong> - Apply indexes, rewrite queries, tune configuration</li> <li><strong>Verify</strong> - Re-measure to confirm improvements</li> </ol> <p><strong>Quick Links:</strong></p> <ul> <li><a href="https://geodedb.com/docs/query/performance-tuning/#using-explain" >Using EXPLAIN</a> </li> <li><a href="https://geodedb.com/docs/query/performance-tuning/#using-profile" >Using PROFILE</a> </li> <li><a href="https://geodedb.com/docs/query/performance-tuning/#index-optimization" >Index Optimization</a> </li> <li><a href="https://geodedb.com/docs/query/performance-tuning/#query-rewriting-patterns" >Query Rewriting Patterns</a> </li> <li><a href="https://geodedb.com/docs/query/performance-tuning/#common-performance-issues" >Common Performance Issues</a> </li> </ul> <hr> <h3 id="using-explain" class="position-relative d-flex align-items-center group"> <span>Using EXPLAIN</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="using-explain" aria-haspopup="dialog" aria-label="Share link: Using EXPLAIN"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3><p><strong>EXPLAIN</strong> shows the query execution plan <strong>without</strong> running the query. Use it to understand how Geode will execute your query before committing resources.</p> <h4 id="basic-explain-syntax" class="position-relative d-flex align-items-center group"> <span>Basic EXPLAIN Syntax</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="basic-explain-syntax" aria-haspopup="dialog" aria-label="Share link: Basic EXPLAIN Syntax"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">EXPLAIN</span><span class="w"> </span><span class="err">&lt;</span><span class="py">statement</span><span class="err">&gt;</span><span class="w"> </span></span></span></code></pre></div> <h4 id="understanding-execution-plans" class="position-relative d-flex align-items-center group"> <span>Understanding Execution Plans</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="understanding-execution-plans" aria-haspopup="dialog" aria-label="Share link: Understanding Execution Plans"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p>EXPLAIN output shows <strong>logical operators</strong> Geode will use:</p> <table> <thead> <tr> <th>Operator</th> <th>Description</th> <th>Performance Impact</th> </tr> </thead> <tbody> <tr> <td><code>NodeScan</code></td> <td>Scans all nodes (or by label)</td> <td>O(n) - can be slow for large graphs</td> </tr> <tr> <td><code>IndexSeek</code></td> <td>Uses index for direct lookup</td> <td>O(log n) - fast</td> </tr> <tr> <td><code>IndexScan</code></td> <td>Scans index range</td> <td>O(k log n) - moderate</td> </tr> <tr> <td><code>ExpandRelationships</code></td> <td>Traverses relationships</td> <td>O(degree) per node</td> </tr> <tr> <td><code>Filter</code></td> <td>Applies WHERE predicates</td> <td>O(n) on input rows</td> </tr> <tr> <td><code>Project</code></td> <td>Selects/transforms columns</td> <td>O(n) - lightweight</td> </tr> <tr> <td><code>Sort</code></td> <td>Orders results (ORDER BY)</td> <td>O(n log n) - expensive</td> </tr> <tr> <td><code>Limit</code></td> <td>Restricts output rows</td> <td>O(1) - cheap</td> </tr> <tr> <td><code>Aggregate</code></td> <td>Groups and aggregates</td> <td>O(n) - moderate</td> </tr> </tbody> </table> <h4 id="explain-examples" class="position-relative d-flex align-items-center group"> <span>EXPLAIN Examples</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="explain-examples" aria-haspopup="dialog" aria-label="Share link: EXPLAIN Examples"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>Example 1: Simple Node Scan</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">EXPLAIN</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Output:</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-fallback" data-lang="fallback"><span class="line"><span class="cl">| plan | </span></span><span class="line"><span class="cl">|-------------------| </span></span><span class="line"><span class="cl">| EXPLAIN | </span></span><span class="line"><span class="cl">| MATCH | </span></span><span class="line"><span class="cl">| NodeScan | ← Scans all Person nodes </span></span><span class="line"><span class="cl">| RETURN | </span></span><span class="line"><span class="cl">| Project | ← Selects name property </span></span></code></pre></div><p><strong>Analysis</strong>: Full node scan - acceptable for small graphs, slow for large.</p> <hr> <p><strong>Example 2: Filtered Query</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">EXPLAIN</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">25</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Output:</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-fallback" data-lang="fallback"><span class="line"><span class="cl">| plan | </span></span><span class="line"><span class="cl">|-------------------| </span></span><span class="line"><span class="cl">| EXPLAIN | </span></span><span class="line"><span class="cl">| MATCH | </span></span><span class="line"><span class="cl">| NodeScan | ← Scans all Person nodes </span></span><span class="line"><span class="cl">| Filter | ← Filters age &gt; 25 </span></span><span class="line"><span class="cl">| RETURN | </span></span><span class="line"><span class="cl">| Project | </span></span></code></pre></div><p><strong>Analysis</strong>: Scans all nodes, then filters. <strong>Optimization needed</strong> if large dataset.</p> <hr> <p><strong>Example 3: Relationship Traversal</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">EXPLAIN</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">WORKS_FOR</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">c</span><span class="p">:</span><span class="nc">Company</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">c</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Output:</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-fallback" data-lang="fallback"><span class="line"><span class="cl">| plan | </span></span><span class="line"><span class="cl">|-------------------------| </span></span><span class="line"><span class="cl">| EXPLAIN | </span></span><span class="line"><span class="cl">| MATCH | </span></span><span class="line"><span class="cl">| NodeScan | ← Start with Person nodes </span></span><span class="line"><span class="cl">| ExpandRelationships | ← Traverse WORKS_FOR edges </span></span><span class="line"><span class="cl">| RETURN | </span></span><span class="line"><span class="cl">| Project | </span></span></code></pre></div><p><strong>Analysis</strong>: Scans all Persons, expands relationships. Consider index on Company if filtering by company properties.</p> <hr> <p><strong>Example 4: Complex Query with Aggregation</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">EXPLAIN</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">WORKS_FOR</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">c</span><span class="p">:</span><span class="nc">Company</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">25</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">c</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">count</span><span class="p">(</span><span class="py">p</span><span class="p">)</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">employee_count</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">employee_count</span><span class="w"> </span><span class="py">DESC</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">LIMIT</span><span class="w"> </span><span class="py">10</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Output:</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-fallback" data-lang="fallback"><span class="line"><span class="cl">| plan | </span></span><span class="line"><span class="cl">|-------------------------| </span></span><span class="line"><span class="cl">| EXPLAIN | </span></span><span class="line"><span class="cl">| MATCH | </span></span><span class="line"><span class="cl">| NodeScan | </span></span><span class="line"><span class="cl">| ExpandRelationships | </span></span><span class="line"><span class="cl">| Filter | </span></span><span class="line"><span class="cl">| RETURN | </span></span><span class="line"><span class="cl">| Aggregate | ← Group by company, count employees </span></span><span class="line"><span class="cl">| Sort | ← Sort by count (expensive!) </span></span><span class="line"><span class="cl">| Limit | </span></span><span class="line"><span class="cl">| Project | </span></span></code></pre></div><p><strong>Analysis</strong>: Full scan → filter → aggregate → <strong>sort</strong> (expensive). Optimize filter with index.</p> <hr> <h4 id="reading-explain-output" class="position-relative d-flex align-items-center group"> <span>Reading EXPLAIN Output</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="reading-explain-output" aria-haspopup="dialog" aria-label="Share link: Reading EXPLAIN Output"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>🚩 Red Flags (Slow Patterns)</strong>:</p> <ul> <li><code>NodeScan</code> without subsequent <code>Filter</code> on large graphs</li> <li><code>Sort</code> on large result sets</li> <li>Multiple <code>ExpandRelationships</code> without indexes</li> <li><code>Aggregate</code> on unindexed properties</li> </ul> <p><strong>✅ Good Patterns (Fast)</strong>:</p> <ul> <li><code>IndexSeek</code> for direct lookups</li> <li><code>Filter</code> early in the plan (before expensive operations)</li> <li><code>Limit</code> without <code>Sort</code> for large datasets</li> <li>Index-backed <code>Aggregate</code> operations</li> </ul> <hr> <h3 id="using-profile" class="position-relative d-flex align-items-center group"> <span>Using PROFILE</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="using-profile" aria-haspopup="dialog" aria-label="Share link: Using PROFILE"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3><p><strong>PROFILE</strong> executes the query and returns <strong>real execution metrics</strong>. Use it to measure actual performance.</p> <h4 id="basic-profile-syntax" class="position-relative d-flex align-items-center group"> <span>Basic PROFILE Syntax</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="basic-profile-syntax" aria-haspopup="dialog" aria-label="Share link: Basic PROFILE Syntax"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">PROFILE</span><span class="w"> </span><span class="err">&lt;</span><span class="py">statement</span><span class="err">&gt;</span><span class="w"> </span></span></span></code></pre></div> <h4 id="profile-metrics" class="position-relative d-flex align-items-center group"> <span>PROFILE Metrics</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="profile-metrics" aria-haspopup="dialog" aria-label="Share link: PROFILE Metrics"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><table> <thead> <tr> <th>Metric</th> <th>Description</th> </tr> </thead> <tbody> <tr> <td><code>rows_returned</code></td> <td>Number of rows returned</td> </tr> <tr> <td><code>columns</code></td> <td>Number of columns in result</td> </tr> <tr> <td><code>execution_time_ms</code></td> <td>Execution time in milliseconds</td> </tr> </tbody> </table> <h4 id="profile-examples" class="position-relative d-flex align-items-center group"> <span>PROFILE Examples</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="profile-examples" aria-haspopup="dialog" aria-label="Share link: PROFILE Examples"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>Example 1: Measure Simple Query</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">PROFILE</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Output:</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-fallback" data-lang="fallback"><span class="line"><span class="cl">| metric | value | </span></span><span class="line"><span class="cl">|---------------------|-------| </span></span><span class="line"><span class="cl">| rows_returned | 42 | </span></span><span class="line"><span class="cl">| columns | 1 | </span></span><span class="line"><span class="cl">| execution_time_ms | 1 | </span></span></code></pre></div><p><strong>Analysis</strong>: Returned 42 rows in 1ms - acceptable.</p> <hr> <p><strong>Example 2: Measure Query with Filter</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">PROFILE</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">30</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Output:</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-fallback" data-lang="fallback"><span class="line"><span class="cl">| metric | value | </span></span><span class="line"><span class="cl">|---------------------|-------| </span></span><span class="line"><span class="cl">| rows_returned | 15 | </span></span><span class="line"><span class="cl">| columns | 2 | </span></span><span class="line"><span class="cl">| execution_time_ms | 2 | </span></span></code></pre></div><p><strong>Analysis</strong>: 15 results in 2ms - good. If time is higher, add index on <code>age</code>.</p> <hr> <p><strong>Example 3: Before/After Optimization</strong></p> <p><strong>Before (no index):</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">PROFILE</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">email</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="err">&#39;</span><span class="p">[</span><span class="py">email</span><span class="w"> </span><span class="py">protected</span><span class="p">]</span><span class="err">&#39;</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Output:</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-fallback" data-lang="fallback"><span class="line"><span class="cl">| metric | value | </span></span><span class="line"><span class="cl">|---------------------|-------| </span></span><span class="line"><span class="cl">| rows_returned | 1 | </span></span><span class="line"><span class="cl">| execution_time_ms | 50 | ← Slow: full scan </span></span></code></pre></div><p><strong>Create Index:</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">person_email</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Person</span><span class="p">(</span><span class="py">email</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>After (with index):</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">PROFILE</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">email</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="err">&#39;</span><span class="p">[</span><span class="py">email</span><span class="w"> </span><span class="py">protected</span><span class="p">]</span><span class="err">&#39;</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Output:</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-fallback" data-lang="fallback"><span class="line"><span class="cl">| metric | value | </span></span><span class="line"><span class="cl">|---------------------|-------| </span></span><span class="line"><span class="cl">| rows_returned | 1 | </span></span><span class="line"><span class="cl">| execution_time_ms | 2 | ← Fast: index seek! </span></span></code></pre></div><p><strong>Result</strong>: Significant speedup with index.</p> <hr> <h4 id="performance-measurement-workflow" class="position-relative d-flex align-items-center group"> <span>Performance Measurement Workflow</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="performance-measurement-workflow" aria-haspopup="dialog" aria-label="Share link: Performance Measurement Workflow"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>Step 1: Establish Baseline</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">PROFILE</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">KNOWS</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">friend</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">30</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">count</span><span class="p">(</span><span class="py">friend</span><span class="p">)</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">friend_count</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">friend_count</span><span class="w"> </span><span class="py">DESC</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Step 2: Analyze with EXPLAIN</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">EXPLAIN</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">KNOWS</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">friend</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">30</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">count</span><span class="p">(</span><span class="py">friend</span><span class="p">)</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">friend_count</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">friend_count</span><span class="w"> </span><span class="py">DESC</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Step 3: Apply Optimization</strong> (add index, rewrite query)</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">person_age</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Person</span><span class="p">(</span><span class="py">age</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Step 4: Re-measure with PROFILE</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">PROFILE</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">KNOWS</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">friend</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">30</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">count</span><span class="p">(</span><span class="py">friend</span><span class="p">)</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">friend_count</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">friend_count</span><span class="w"> </span><span class="py">DESC</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Step 5: Compare Results</strong></p> <ul> <li>Before: execution_time_ms = 150</li> <li>After: execution_time_ms = 20</li> <li><strong>Speedup: 7.5x</strong> ✅</li> </ul> <hr> <h3 id="index-optimization" class="position-relative d-flex align-items-center group"> <span>Index Optimization</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="index-optimization" aria-haspopup="dialog" aria-label="Share link: Index Optimization"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3> <h4 id="index-types-in-geode" class="position-relative d-flex align-items-center group"> <span>Index Types in Geode</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="index-types-in-geode" aria-haspopup="dialog" aria-label="Share link: Index Types in Geode"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><table> <thead> <tr> <th>Index Type</th> <th>Use Case</th> <th>Creation Syntax</th> </tr> </thead> <tbody> <tr> <td><strong>B-tree</strong> (default)</td> <td>Exact matches, range queries, sorting</td> <td><code>CREATE INDEX name ON Label(property)</code></td> </tr> <tr> <td><strong>Hash</strong></td> <td>Exact lookups only (faster than B-tree)</td> <td><code>CREATE INDEX name ON Label(property) USING hash</code></td> </tr> <tr> <td><strong>Fulltext</strong></td> <td>Text search, CONTAINS queries</td> <td><code>CREATE FULLTEXT INDEX name ON Label(property)</code></td> </tr> <tr> <td><strong>Spatial</strong></td> <td>Geographic queries (distance, bounding box)</td> <td><code>CREATE SPATIAL INDEX name ON Label(property)</code></td> </tr> <tr> <td><strong>Vector</strong></td> <td>Similarity search (embeddings, recommendations)</td> <td><code>CREATE VECTOR INDEX name ON Label(property)</code></td> </tr> </tbody> </table> <h4 id="creating-indexes" class="position-relative d-flex align-items-center group"> <span>Creating Indexes</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="creating-indexes" aria-haspopup="dialog" aria-label="Share link: Creating Indexes"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>B-tree Index (Default)</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">For</span><span class="w"> </span><span class="py">exact</span><span class="w"> </span><span class="py">matches</span><span class="w"> </span><span class="py">and</span><span class="w"> </span><span class="py">range</span><span class="w"> </span><span class="py">queries</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">person_age</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Person</span><span class="p">(</span><span class="py">age</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">product_price</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Product</span><span class="p">(</span><span class="py">price</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Use</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">queries</span><span class="w"> </span><span class="py">like</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">30</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">prod</span><span class="p">:</span><span class="nc">Product</span><span class="p">)</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">prod</span><span class="err">.</span><span class="py">price</span><span class="w"> </span><span class="err">&lt;</span><span class="w"> </span><span class="py">100</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">prod</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Hash Index</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">For</span><span class="w"> </span><span class="py">exact</span><span class="w"> </span><span class="py">lookups</span><span class="w"> </span><span class="kd">on</span><span class="py">ly</span><span class="w"> </span><span class="p">(</span><span class="py">faster</span><span class="w"> </span><span class="py">than</span><span class="w"> </span><span class="py">B</span><span class="err">-</span><span class="py">tree</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">equality</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">person_email</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Person</span><span class="p">(</span><span class="py">email</span><span class="p">)</span><span class="w"> </span><span class="py">USING</span><span class="w"> </span><span class="py">hash</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Use</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">queries</span><span class="w"> </span><span class="py">like</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="w"> </span><span class="p">{</span><span class="py">email</span><span class="p">:</span><span class="w"> </span><span class="err">&#39;</span><span class="p">[</span><span class="nc">email</span><span class="w"> </span><span class="py">protected</span><span class="p">]</span><span class="err">&#39;</span><span class="p">})</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">email</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="err">&#39;</span><span class="p">[</span><span class="py">email</span><span class="w"> </span><span class="py">protected</span><span class="p">]</span><span class="err">&#39;</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Fulltext Index (BM25-Optimized)</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">For</span><span class="w"> </span><span class="py">text</span><span class="w"> </span><span class="py">search</span><span class="w"> </span><span class="py">with</span><span class="w"> </span><span class="py">relevance</span><span class="w"> </span><span class="py">ranking</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">FULLTEXT</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">article_content</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Article</span><span class="p">(</span><span class="py">content</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">FULLTEXT</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">doc_abstract</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Document</span><span class="p">(</span><span class="py">abstract</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Use</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">queries</span><span class="w"> </span><span class="py">like</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">a</span><span class="p">:</span><span class="nc">Article</span><span class="p">)</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">a</span><span class="err">.</span><span class="py">content</span><span class="w"> </span><span class="py">CONTAINS</span><span class="w"> </span><span class="err">&#39;</span><span class="py">graph</span><span class="w"> </span><span class="py">database</span><span class="err">&#39;</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">a</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">d</span><span class="p">:</span><span class="nc">Document</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">d</span><span class="err">.</span><span class="py">abstract</span><span class="w"> </span><span class="py">CONTAINS</span><span class="w"> </span><span class="err">&#39;</span><span class="py">machine</span><span class="w"> </span><span class="py">learning</span><span class="err">&#39;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">d</span><span class="err">.</span><span class="py">title</span><span class="p">,</span><span class="w"> </span><span class="py">bm25_score</span><span class="p">(</span><span class="py">d</span><span class="err">.</span><span class="py">abstract</span><span class="p">,</span><span class="w"> </span><span class="err">&#39;</span><span class="py">machine</span><span class="w"> </span><span class="py">learning</span><span class="err">&#39;</span><span class="p">)</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">relevance</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">relevance</span><span class="w"> </span><span class="py">DESC</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Spatial Index</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">For</span><span class="w"> </span><span class="py">geographic</span><span class="w"> </span><span class="py">queries</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">SPATIAL</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">location_coords</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Location</span><span class="p">(</span><span class="py">coordinates</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Use</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">queries</span><span class="w"> </span><span class="py">like</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">loc</span><span class="p">:</span><span class="nc">Location</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">distance</span><span class="p">(</span><span class="py">loc</span><span class="err">.</span><span class="py">coordinates</span><span class="p">,</span><span class="w"> </span><span class="py">point</span><span class="p">(</span><span class="py">37</span><span class="mf">.7749</span><span class="p">,</span><span class="w"> </span><span class="err">-</span><span class="py">122</span><span class="mf">.4194</span><span class="p">))</span><span class="w"> </span><span class="err">&lt;</span><span class="w"> </span><span class="py">10000</span><span class="w"> </span><span class="err">--</span><span class="w"> </span><span class="py">10km</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">loc</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">distance</span><span class="p">(</span><span class="py">loc</span><span class="err">.</span><span class="py">coordinates</span><span class="p">,</span><span class="w"> </span><span class="py">point</span><span class="p">(</span><span class="py">37</span><span class="mf">.7749</span><span class="p">,</span><span class="w"> </span><span class="err">-</span><span class="py">122</span><span class="mf">.4194</span><span class="p">))</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">dist</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">dist</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Vector Index (HNSW)</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">For</span><span class="w"> </span><span class="py">similarity</span><span class="w"> </span><span class="py">search</span><span class="w"> </span><span class="p">(</span><span class="py">embeddings</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">VECTOR</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">doc_embedding</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Document</span><span class="p">(</span><span class="py">embedding</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Use</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">queries</span><span class="w"> </span><span class="py">like</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">doc</span><span class="p">:</span><span class="nc">Document</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">vector_cosine</span><span class="p">(</span><span class="py">doc</span><span class="err">.</span><span class="py">embedding</span><span class="p">,</span><span class="w"> </span><span class="nv">$query_embedding</span><span class="p">)</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">0</span><span class="mf">.7</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">doc</span><span class="err">.</span><span class="py">title</span><span class="p">,</span><span class="w"> </span><span class="py">vector_cosine</span><span class="p">(</span><span class="py">doc</span><span class="err">.</span><span class="py">embedding</span><span class="p">,</span><span class="w"> </span><span class="nv">$query_embedding</span><span class="p">)</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">similarity</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">similarity</span><span class="w"> </span><span class="py">DESC</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">LIMIT</span><span class="w"> </span><span class="py">10</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div> <h4 id="when-to-create-indexes" class="position-relative d-flex align-items-center group"> <span>When to Create Indexes</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="when-to-create-indexes" aria-haspopup="dialog" aria-label="Share link: When to Create Indexes"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>✅ Create Indexes For:</strong></p> <ol> <li> <p><strong>Frequently filtered properties</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Queries</span><span class="w"> </span><span class="py">like</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">status</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="err">&#39;</span><span class="py">active</span><span class="err">&#39;</span><span class="w"> </span><span class="py">are</span><span class="w"> </span><span class="py">common</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">user_status</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">User</span><span class="p">(</span><span class="py">status</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div></li> <li> <p><strong>Properties used in ORDER BY</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Queries</span><span class="w"> </span><span class="py">like</span><span class="w"> </span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">created_at</span><span class="w"> </span><span class="py">DESC</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">post_created</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Post</span><span class="p">(</span><span class="py">created_at</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div></li> <li> <p><strong>Properties in JOIN conditions</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Foreign</span><span class="err">-</span><span class="py">key</span><span class="err">-</span><span class="py">like</span><span class="w"> </span><span class="py">lookups</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">order_customer_id</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Order</span><span class="p">(</span><span class="py">customer_id</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div></li> <li> <p><strong>Unique identifiers</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Email</span><span class="p">,</span><span class="w"> </span><span class="py">username</span><span class="p">,</span><span class="w"> </span><span class="py">SKU</span><span class="p">,</span><span class="w"> </span><span class="py">etc</span><span class="err">.</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">user_email</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">User</span><span class="p">(</span><span class="py">email</span><span class="p">)</span><span class="w"> </span><span class="py">USING</span><span class="w"> </span><span class="py">hash</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">product_sku</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Product</span><span class="p">(</span><span class="py">sku</span><span class="p">)</span><span class="w"> </span><span class="py">USING</span><span class="w"> </span><span class="py">hash</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div></li> </ol> <p><strong>❌ Don&rsquo;t Create Indexes For:</strong></p> <ol> <li><strong>Rarely queried properties</strong> - Index overhead not worth it</li> <li><strong>High-cardinality properties with rare lookups</strong> - E.g., free-text descriptions</li> <li><strong>Properties that change frequently</strong> - Index maintenance overhead</li> <li><strong>Small datasets</strong> - Full scans are fast enough (&lt;1000 nodes)</li> </ol> <h4 id="viewing-indexes" class="position-relative d-flex align-items-center group"> <span>Viewing Indexes</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="viewing-indexes" aria-haspopup="dialog" aria-label="Share link: Viewing Indexes"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Show</span><span class="w"> </span><span class="py">all</span><span class="w"> </span><span class="py">indexes</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">SHOW</span><span class="w"> </span><span class="py">INDEXES</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Output</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="p">|</span><span class="w"> </span><span class="nc">index_name</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">label</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">property</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="kd">type</span><span class="w"> </span><span class="p">|</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="p">|</span><span class="err">------------------</span><span class="p">|</span><span class="err">---------</span><span class="p">|</span><span class="err">-------------</span><span class="p">|</span><span class="err">-----------</span><span class="p">|</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="p">|</span><span class="w"> </span><span class="nc">person_email</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">Person</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">email</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">hash</span><span class="w"> </span><span class="p">|</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="p">|</span><span class="w"> </span><span class="py">person_age</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">Person</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">age</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">btree</span><span class="w"> </span><span class="p">|</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="p">|</span><span class="w"> </span><span class="py">article_content</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">Article</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">content</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">fulltext</span><span class="w"> </span><span class="p">|</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="p">|</span><span class="w"> </span><span class="py">doc_embedding</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">Document</span><span class="p">|</span><span class="w"> </span><span class="py">embedding</span><span class="w"> </span><span class="p">|</span><span class="w"> </span><span class="py">vector</span><span class="w"> </span><span class="p">|</span><span class="w"> </span></span></span></code></pre></div> <h4 id="dropping-indexes" class="position-relative d-flex align-items-center group"> <span>Dropping Indexes</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="dropping-indexes" aria-haspopup="dialog" aria-label="Share link: Dropping Indexes"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Drop</span><span class="w"> </span><span class="py">unused</span><span class="w"> </span><span class="py">or</span><span class="w"> </span><span class="py">redundant</span><span class="w"> </span><span class="py">indexes</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">DROP</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">person_age</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">DROP</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">article_content</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><hr> <h3 id="bm25-full-text-search-optimization" class="position-relative d-flex align-items-center group"> <span>BM25 Full-Text Search Optimization</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="bm25-full-text-search-optimization" aria-haspopup="dialog" aria-label="Share link: BM25 Full-Text Search Optimization"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3><p>Geode&rsquo;s <strong>cost-based optimizer</strong> automatically uses <strong>BM25 relevance ranking</strong> for fulltext searches, providing enterprise-grade search quality.</p> <h4 id="bm25-scoring-formula" class="position-relative d-flex align-items-center group"> <span>BM25 Scoring Formula</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="bm25-scoring-formula" aria-haspopup="dialog" aria-label="Share link: BM25 Scoring Formula"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><div class="highlight"><pre tabindex="0" class="chroma"><code class="language-fallback" data-lang="fallback"><span class="line"><span class="cl">score(q,d) = Σ IDF(qi) × f(qi,d) × (k1 + 1) / (f(qi,d) + k1 × (1 - b + b × |d| / avgdl)) </span></span></code></pre></div><p><strong>Where:</strong></p> <ul> <li><code>IDF(qi)</code> = Inverse document frequency (rare terms score higher)</li> <li><code>f(qi,d)</code> = Term frequency in document</li> <li><code>|d|</code> = Document length in words</li> <li><code>avgdl</code> = Average document length in collection</li> <li><code>k1 = 1.2</code> = Term frequency saturation parameter</li> <li><code>b = 0.75</code> = Length normalization parameter</li> </ul> <h4 id="bm25-optimization-examples" class="position-relative d-flex align-items-center group"> <span>BM25 Optimization Examples</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="bm25-optimization-examples" aria-haspopup="dialog" aria-label="Share link: BM25 Optimization Examples"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>Example 1: Simple Text Search</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Create</span><span class="w"> </span><span class="py">fulltext</span><span class="w"> </span><span class="py">index</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">FULLTEXT</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">article_content</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Article</span><span class="p">(</span><span class="py">content</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Query</span><span class="w"> </span><span class="py">automatically</span><span class="w"> </span><span class="py">uses</span><span class="w"> </span><span class="py">BM25</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">a</span><span class="p">:</span><span class="nc">Article</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">a</span><span class="err">.</span><span class="py">content</span><span class="w"> </span><span class="py">CONTAINS</span><span class="w"> </span><span class="err">&#39;</span><span class="py">machine</span><span class="w"> </span><span class="py">learning</span><span class="w"> </span><span class="py">algorithms</span><span class="err">&#39;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">a</span><span class="err">.</span><span class="py">title</span><span class="p">,</span><span class="w"> </span><span class="py">a</span><span class="err">.</span><span class="py">author</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">a</span><span class="err">.</span><span class="py">relevance_score</span><span class="w"> </span><span class="py">DESC</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Optimizer Behavior:</strong></p> <ul> <li><strong>Base cost</strong>: 25.0 (vs 20.0 for standard fulltext)</li> <li><strong>Query complexity</strong>: 1.0 + (3 terms - 1) × 0.3 = 1.6x multiplier</li> <li><strong>Corpus scaling</strong>: Logarithmic with document count</li> <li><strong>Result</strong>: Relevance-ranked results, 40-60% better quality</li> </ul> <hr> <p><strong>Example 2: Multi-Term Search with Ranking</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">doc</span><span class="p">:</span><span class="nc">Document</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">doc</span><span class="err">.</span><span class="py">abstract</span><span class="w"> </span><span class="py">CONTAINS</span><span class="w"> </span><span class="err">&#39;</span><span class="py">artificial</span><span class="w"> </span><span class="py">intelligence</span><span class="err">&#39;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span><span class="py">AND</span><span class="w"> </span><span class="py">doc</span><span class="err">.</span><span class="py">keywords</span><span class="w"> </span><span class="py">CONTAINS</span><span class="w"> </span><span class="err">&#39;</span><span class="py">neural</span><span class="w"> </span><span class="py">networks</span><span class="err">&#39;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">doc</span><span class="err">.</span><span class="py">title</span><span class="p">,</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span><span class="py">bm25_score</span><span class="p">(</span><span class="py">doc</span><span class="err">.</span><span class="py">abstract</span><span class="p">,</span><span class="w"> </span><span class="err">&#39;</span><span class="py">artificial</span><span class="w"> </span><span class="py">intelligence</span><span class="w"> </span><span class="py">neural</span><span class="w"> </span><span class="py">networks</span><span class="err">&#39;</span><span class="p">)</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">relevance</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">relevance</span><span class="w"> </span><span class="py">DESC</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">LIMIT</span><span class="w"> </span><span class="py">10</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Performance:</strong></p> <ul> <li>BM25 considers document length and term frequency</li> <li>Shorter documents with exact matches score higher</li> <li>Longer documents are penalized unless terms are frequent</li> <li><strong>Typical speedup over naive text search: 2-5x</strong> with better results</li> </ul> <hr> <p><strong>Example 3: Corpus-Aware Optimization</strong></p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Technical</span><span class="w"> </span><span class="py">documentation</span><span class="w"> </span><span class="p">(</span><span class="py">high</span><span class="w"> </span><span class="py">vocabulary</span><span class="w"> </span><span class="py">density</span><span class="p">,</span><span class="w"> </span><span class="py">long</span><span class="w"> </span><span class="py">docs</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">tech_doc</span><span class="p">:</span><span class="nc">TechnicalDocument</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">tech_doc</span><span class="err">.</span><span class="py">content</span><span class="w"> </span><span class="py">CONTAINS</span><span class="w"> </span><span class="err">&#39;</span><span class="py">distributed</span><span class="w"> </span><span class="py">systems</span><span class="w"> </span><span class="py">architecture</span><span class="err">&#39;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">tech_doc</span><span class="err">.</span><span class="py">title</span><span class="p">,</span><span class="w"> </span><span class="py">tech_doc</span><span class="err">.</span><span class="py">complexity_score</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Optimizer</span><span class="w"> </span><span class="py">adjusts</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="err">-</span><span class="w"> </span><span class="nc">Vocabulary</span><span class="w"> </span><span class="py">density</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">100</span><span class="w"> </span><span class="err">→</span><span class="w"> </span><span class="py">1</span><span class="mf">.2</span><span class="py">x</span><span class="w"> </span><span class="py">cost</span><span class="w"> </span><span class="py">multiplier</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="err">-</span><span class="w"> </span><span class="py">Average</span><span class="w"> </span><span class="py">document</span><span class="w"> </span><span class="py">length</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">1000</span><span class="w"> </span><span class="py">words</span><span class="w"> </span><span class="err">→</span><span class="w"> </span><span class="py">length</span><span class="w"> </span><span class="py">normalization</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="err">-</span><span class="w"> </span><span class="py">Result</span><span class="p">:</span><span class="w"> </span><span class="nc">Accurate</span><span class="w"> </span><span class="py">cost</span><span class="w"> </span><span class="py">estimation</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">complex</span><span class="w"> </span><span class="py">corpus</span><span class="w"> </span></span></span></code></pre></div><div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Social</span><span class="w"> </span><span class="py">media</span><span class="w"> </span><span class="py">posts</span><span class="w"> </span><span class="p">(</span><span class="py">low</span><span class="w"> </span><span class="py">vocabulary</span><span class="p">,</span><span class="w"> </span><span class="py">short</span><span class="w"> </span><span class="py">docs</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">post</span><span class="p">:</span><span class="nc">SocialPost</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">post</span><span class="err">.</span><span class="py">text</span><span class="w"> </span><span class="py">CONTAINS</span><span class="w"> </span><span class="err">&#39;</span><span class="py">climate</span><span class="w"> </span><span class="py">change</span><span class="err">&#39;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">post</span><span class="err">.</span><span class="py">text</span><span class="p">,</span><span class="w"> </span><span class="py">post</span><span class="err">.</span><span class="py">engagement_score</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">post</span><span class="err">.</span><span class="py">timestamp</span><span class="w"> </span><span class="py">DESC</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Optimizer</span><span class="w"> </span><span class="py">adjusts</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="err">-</span><span class="w"> </span><span class="nc">Vocabulary</span><span class="w"> </span><span class="py">density</span><span class="w"> </span><span class="err">&lt;</span><span class="w"> </span><span class="py">20</span><span class="w"> </span><span class="err">→</span><span class="w"> </span><span class="py">0</span><span class="mf">.9</span><span class="py">x</span><span class="w"> </span><span class="py">cost</span><span class="w"> </span><span class="py">multiplier</span><span class="w"> </span><span class="p">(</span><span class="py">simpler</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="err">-</span><span class="w"> </span><span class="py">Average</span><span class="w"> </span><span class="py">document</span><span class="w"> </span><span class="py">length</span><span class="w"> </span><span class="err">&lt;</span><span class="w"> </span><span class="py">200</span><span class="w"> </span><span class="py">words</span><span class="w"> </span><span class="err">→</span><span class="w"> </span><span class="py">reduced</span><span class="w"> </span><span class="py">length</span><span class="w"> </span><span class="py">penalty</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="err">-</span><span class="w"> </span><span class="py">Result</span><span class="p">:</span><span class="w"> </span><span class="nc">Faster</span><span class="w"> </span><span class="py">execution</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">short</span><span class="err">-</span><span class="py">form</span><span class="w"> </span><span class="py">content</span><span class="w"> </span></span></span></code></pre></div> <h4 id="bm25-vs-standard-fulltext-comparison" class="position-relative d-flex align-items-center group"> <span>BM25 vs Standard Fulltext Comparison</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="bm25-vs-standard-fulltext-comparison" aria-haspopup="dialog" aria-label="Share link: BM25 vs Standard Fulltext Comparison"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><table> <thead> <tr> <th>Metric</th> <th>Standard Fulltext</th> <th>BM25 Enhanced</th> <th>Benefit</th> </tr> </thead> <tbody> <tr> <td>Base cost</td> <td>20.0</td> <td>25.0</td> <td>25% overhead for ranking</td> </tr> <tr> <td>Query complexity</td> <td>20% per term</td> <td>30% per term</td> <td>Better multi-term accuracy</td> </tr> <tr> <td>Corpus scaling</td> <td>Linear</td> <td>Logarithmic</td> <td>Better large-scale performance</td> </tr> <tr> <td>Search quality</td> <td>Term matching</td> <td>Relevance ranking</td> <td><strong>40-60% better results</strong></td> </tr> <tr> <td>Cost accuracy</td> <td>Heuristic</td> <td>Statistics-based</td> <td><strong>25-35% more accurate</strong></td> </tr> </tbody> </table> <hr> <h3 id="query-rewriting-patterns" class="position-relative d-flex align-items-center group"> <span>Query Rewriting Patterns</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="query-rewriting-patterns" aria-haspopup="dialog" aria-label="Share link: Query Rewriting Patterns"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3> <h4 id="pattern-1-push-filters-early" class="position-relative d-flex align-items-center group"> <span>Pattern 1: Push Filters Early</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="pattern-1-push-filters-early" aria-haspopup="dialog" aria-label="Share link: Pattern 1: Push Filters Early"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>❌ Bad (Filter Late)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">KNOWS</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">friend</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">30</span><span class="w"> </span><span class="py">AND</span><span class="w"> </span><span class="py">friend</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">25</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">friend</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>✅ Good (Filter Early)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="w"> </span><span class="p">{</span><span class="py">age</span><span class="p">:</span><span class="w"> </span><span class="nc">30</span><span class="p">})</span><span class="w"> </span><span class="err">--</span><span class="w"> </span><span class="py">Filter</span><span class="w"> </span><span class="py">immediately</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">KNOWS</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">friend</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">friend</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="err">&gt;</span><span class="w"> </span><span class="py">25</span><span class="w"> </span><span class="err">--</span><span class="w"> </span><span class="py">Filter</span><span class="w"> </span><span class="kd">on</span><span class="w"> </span><span class="py">expansion</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">friend</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Why</strong>: Reduces nodes to expand from, fewer relationship traversals.</p> <hr> <h4 id="pattern-2-avoid-cartesian-products" class="position-relative d-flex align-items-center group"> <span>Pattern 2: Avoid Cartesian Products</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="pattern-2-avoid-cartesian-products" aria-haspopup="dialog" aria-label="Share link: Pattern 2: Avoid Cartesian Products"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>❌ Bad (Cartesian Product)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">c</span><span class="p">:</span><span class="nc">Company</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">company_id</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="py">c</span><span class="err">.</span><span class="py">id</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">c</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">If</span><span class="w"> </span><span class="py">1000</span><span class="w"> </span><span class="py">people</span><span class="w"> </span><span class="err">×</span><span class="w"> </span><span class="py">100</span><span class="w"> </span><span class="py">companies</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="py">100</span><span class="p">,</span><span class="py">000</span><span class="w"> </span><span class="py">intermediate</span><span class="w"> </span><span class="py">rows</span><span class="p">!</span><span class="w"> </span></span></span></code></pre></div><p><strong>✅ Good (Connected Pattern)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">WORKS_AT</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">c</span><span class="p">:</span><span class="nc">Company</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">c</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Direct</span><span class="w"> </span><span class="py">relationship</span><span class="w"> </span><span class="py">traversal</span><span class="w"> </span></span></span></code></pre></div><p><strong>Why</strong>: Explicit relationships prevent combinatorial explosion.</p> <hr> <h4 id="pattern-3-use-limits-early" class="position-relative d-flex align-items-center group"> <span>Pattern 3: Use Limits Early</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="pattern-3-use-limits-early" aria-haspopup="dialog" aria-label="Share link: Pattern 3: Use Limits Early"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>❌ Bad (Limit After Sort)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="py">DESC</span><span class="err">;</span><span class="w"> </span><span class="err">--</span><span class="w"> </span><span class="py">Sorts</span><span class="w"> </span><span class="py">ALL</span><span class="w"> </span><span class="py">people</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Then</span><span class="w"> </span><span class="py">application</span><span class="w"> </span><span class="py">takes</span><span class="w"> </span><span class="kd">on</span><span class="py">ly</span><span class="w"> </span><span class="py">first</span><span class="w"> </span><span class="py">10</span><span class="w"> </span></span></span></code></pre></div><p><strong>✅ Good (Limit in Query)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">age</span><span class="w"> </span><span class="py">DESC</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">LIMIT</span><span class="w"> </span><span class="py">10</span><span class="err">;</span><span class="w"> </span><span class="err">--</span><span class="w"> </span><span class="py">Database</span><span class="w"> </span><span class="py">returns</span><span class="w"> </span><span class="kd">on</span><span class="py">ly</span><span class="w"> </span><span class="py">10</span><span class="w"> </span></span></span></code></pre></div><p><strong>Why</strong>: Database can use top-K optimization, avoid sorting/returning all rows.</p> <hr> <h4 id="pattern-4-denormalize-for-read-performance" class="position-relative d-flex align-items-center group"> <span>Pattern 4: Denormalize for Read Performance</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="pattern-4-denormalize-for-read-performance" aria-haspopup="dialog" aria-label="Share link: Pattern 4: Denormalize for Read Performance"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>❌ Bad (Join on Every Query)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">order</span><span class="p">:</span><span class="nc">Order</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">CONTAINS</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(:</span><span class="nc">LineItem</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">OF_PRODUCT</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">product</span><span class="p">:</span><span class="nc">Product</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">order</span><span class="err">.</span><span class="py">id</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="py">12345</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">sum</span><span class="p">(</span><span class="py">product</span><span class="err">.</span><span class="py">price</span><span class="p">)</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">total</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Complex</span><span class="w"> </span><span class="py">join</span><span class="w"> </span><span class="py">every</span><span class="w"> </span><span class="py">time</span><span class="w"> </span></span></span></code></pre></div><p><strong>✅ Good (Precompute Total)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Store</span><span class="w"> </span><span class="py">total</span><span class="w"> </span><span class="kd">on</span><span class="w"> </span><span class="py">Order</span><span class="w"> </span><span class="py">when</span><span class="w"> </span><span class="py">creating</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">order</span><span class="p">:</span><span class="nc">Order</span><span class="w"> </span><span class="p">{</span><span class="py">id</span><span class="p">:</span><span class="w"> </span><span class="nc">12345</span><span class="p">})</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">order</span><span class="err">.</span><span class="py">total</span><span class="err">;</span><span class="w"> </span><span class="err">--</span><span class="w"> </span><span class="py">Single</span><span class="w"> </span><span class="py">property</span><span class="w"> </span><span class="py">lookup</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Update</span><span class="w"> </span><span class="py">total</span><span class="w"> </span><span class="py">when</span><span class="w"> </span><span class="py">items</span><span class="w"> </span><span class="py">change</span><span class="w"> </span><span class="p">(</span><span class="py">trade</span><span class="w"> </span><span class="py">write</span><span class="w"> </span><span class="py">speed</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">read</span><span class="w"> </span><span class="py">speed</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">order</span><span class="p">:</span><span class="nc">Order</span><span class="w"> </span><span class="p">{</span><span class="py">id</span><span class="p">:</span><span class="w"> </span><span class="nc">12345</span><span class="p">})</span><span class="err">-</span><span class="p">[:</span><span class="nc">CONTAINS</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">li</span><span class="p">:</span><span class="nc">LineItem</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">SET</span><span class="w"> </span><span class="py">order</span><span class="err">.</span><span class="py">total</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="py">sum</span><span class="p">(</span><span class="py">li</span><span class="err">.</span><span class="py">subtotal</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Why</strong>: Read-heavy workloads benefit from denormalization.</p> <hr> <h4 id="pattern-5-use-optional-match-sparingly" class="position-relative d-flex align-items-center group"> <span>Pattern 5: Use OPTIONAL MATCH Sparingly</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="pattern-5-use-optional-match-sparingly" aria-haspopup="dialog" aria-label="Share link: Pattern 5: Use OPTIONAL MATCH Sparingly"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>❌ Bad (Multiple OPTIONAL)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">OPTIONAL</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">WORKS_AT</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">c</span><span class="p">:</span><span class="nc">Company</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">OPTIONAL</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">LIVES_IN</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">city</span><span class="p">:</span><span class="nc">City</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">OPTIONAL</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">STUDIED_AT</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">school</span><span class="p">:</span><span class="nc">School</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="p">,</span><span class="w"> </span><span class="py">c</span><span class="p">,</span><span class="w"> </span><span class="py">city</span><span class="p">,</span><span class="w"> </span><span class="py">school</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Many</span><span class="w"> </span><span class="py">optional</span><span class="w"> </span><span class="py">branches</span><span class="w"> </span><span class="py">slow</span><span class="w"> </span><span class="py">execution</span><span class="w"> </span></span></span></code></pre></div><p><strong>✅ Good (Filter Required First)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">If</span><span class="w"> </span><span class="py">most</span><span class="w"> </span><span class="py">people</span><span class="w"> </span><span class="py">work</span><span class="w"> </span><span class="py">somewhere</span><span class="p">,</span><span class="w"> </span><span class="py">make</span><span class="w"> </span><span class="py">it</span><span class="w"> </span><span class="py">required</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">WORKS_AT</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">c</span><span class="p">:</span><span class="nc">Company</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">OPTIONAL</span><span class="w"> </span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">LIVES_IN</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">city</span><span class="p">:</span><span class="nc">City</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="p">,</span><span class="w"> </span><span class="py">c</span><span class="p">,</span><span class="w"> </span><span class="py">city</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Why</strong>: Required MATCH is faster than OPTIONAL.</p> <hr> <h3 id="common-performance-issues" class="position-relative d-flex align-items-center group"> <span>Common Performance Issues</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="common-performance-issues" aria-haspopup="dialog" aria-label="Share link: Common Performance Issues"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3> <h4 id="issue-1-full-node-scans" class="position-relative d-flex align-items-center group"> <span>Issue 1: Full Node Scans</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="issue-1-full-node-scans" aria-haspopup="dialog" aria-label="Share link: Issue 1: Full Node Scans"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>Symptom</strong>: Queries slow on large graphs, EXPLAIN shows <code>NodeScan</code>.</p> <p><strong>Example</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span><span class="py">WHERE</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">email</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="err">&#39;</span><span class="p">[</span><span class="py">email</span><span class="w"> </span><span class="py">protected</span><span class="p">]</span><span class="err">&#39;</span><span class="w"> </span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">EXPLAIN</span><span class="w"> </span><span class="py">shows</span><span class="p">:</span><span class="w"> </span><span class="nc">NodeScan</span><span class="w"> </span><span class="err">→</span><span class="w"> </span><span class="py">Filter</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution</strong>: Create index on filtered property.</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">person_email</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Person</span><span class="p">(</span><span class="py">email</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Now</span><span class="w"> </span><span class="py">EXPLAIN</span><span class="w"> </span><span class="py">shows</span><span class="p">:</span><span class="w"> </span><span class="nc">IndexSeek</span><span class="w"> </span></span></span></code></pre></div><p><strong>Impact</strong>: Significant improvement on large datasets.</p> <hr> <h4 id="issue-2-expensive-sorts" class="position-relative d-flex align-items-center group"> <span>Issue 2: Expensive Sorts</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="issue-2-expensive-sorts" aria-haspopup="dialog" aria-label="Share link: Issue 2: Expensive Sorts"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>Symptom</strong>: Queries with ORDER BY are slow, high memory usage.</p> <p><strong>Example</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">created_at</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">created_at</span><span class="w"> </span><span class="py">DESC</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Sorts</span><span class="w"> </span><span class="py">ALL</span><span class="w"> </span><span class="py">people</span><span class="w"> </span><span class="py">in</span><span class="w"> </span><span class="py">memory</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution 1</strong>: Create index on sort property.</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">person_created</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Person</span><span class="p">(</span><span class="py">created_at</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Index</span><span class="w"> </span><span class="py">provides</span><span class="w"> </span><span class="py">sorted</span><span class="w"> </span><span class="py">iteration</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution 2</strong>: Add LIMIT if you don&rsquo;t need all results.</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">name</span><span class="p">,</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">created_at</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">p</span><span class="err">.</span><span class="py">created_at</span><span class="w"> </span><span class="py">DESC</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">LIMIT</span><span class="w"> </span><span class="py">100</span><span class="err">;</span><span class="w"> </span><span class="err">--</span><span class="w"> </span><span class="py">Only</span><span class="w"> </span><span class="py">sort</span><span class="w"> </span><span class="py">top</span><span class="w"> </span><span class="py">100</span><span class="w"> </span></span></span></code></pre></div><p><strong>Impact</strong>: <strong>5-50x speedup</strong> depending on dataset size.</p> <hr> <h4 id="issue-3-supernode-expansion" class="position-relative d-flex align-items-center group"> <span>Issue 3: Supernode Expansion</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="issue-3-supernode-expansion" aria-haspopup="dialog" aria-label="Share link: Issue 3: Supernode Expansion"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>Symptom</strong>: Queries traversing high-degree nodes are slow.</p> <p><strong>Example</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="s">&#34;Popular&#34;</span><span class="w"> </span><span class="py">node</span><span class="w"> </span><span class="py">with</span><span class="w"> </span><span class="py">1</span><span class="p">,</span><span class="py">000</span><span class="p">,</span><span class="py">000</span><span class="w"> </span><span class="py">followers</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">celebrity</span><span class="p">:</span><span class="nc">Person</span><span class="w"> </span><span class="p">{</span><span class="py">name</span><span class="p">:</span><span class="w"> </span><span class="s">&#34;Celebrity&#34;</span><span class="p">})</span><span class="err">-</span><span class="p">[:</span><span class="nc">FOLLOWED_BY</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="nc">follower</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">follower</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Expands</span><span class="w"> </span><span class="py">1M</span><span class="w"> </span><span class="py">relationships</span><span class="p">!</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution 1</strong>: Add LIMIT and pagination.</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">celebrity</span><span class="p">:</span><span class="nc">Person</span><span class="w"> </span><span class="p">{</span><span class="py">name</span><span class="p">:</span><span class="w"> </span><span class="s">&#34;Celebrity&#34;</span><span class="p">})</span><span class="err">-</span><span class="p">[:</span><span class="nc">FOLLOWED_BY</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="nc">follower</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">follower</span><span class="err">.</span><span class="py">name</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">ORDER</span><span class="w"> </span><span class="py">BY</span><span class="w"> </span><span class="py">follower</span><span class="err">.</span><span class="py">id</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">SKIP</span><span class="w"> </span><span class="py">1000</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">LIMIT</span><span class="w"> </span><span class="py">100</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution 2</strong>: Denormalize with cached counts.</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">celebrity</span><span class="p">:</span><span class="nc">Person</span><span class="w"> </span><span class="p">{</span><span class="py">name</span><span class="p">:</span><span class="w"> </span><span class="s">&#34;Celebrity&#34;</span><span class="p">})</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">RETURN</span><span class="w"> </span><span class="py">celebrity</span><span class="err">.</span><span class="py">follower_count</span><span class="err">;</span><span class="w"> </span><span class="err">--</span><span class="w"> </span><span class="py">Precomputed</span><span class="w"> </span><span class="py">property</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution 3</strong>: Partition relationships.</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Instead</span><span class="w"> </span><span class="py">of</span><span class="w"> </span><span class="kd">on</span><span class="py">e</span><span class="w"> </span><span class="py">celebrity</span><span class="w"> </span><span class="py">node</span><span class="w"> </span><span class="py">with</span><span class="w"> </span><span class="py">1M</span><span class="w"> </span><span class="py">edges</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="nc">Create</span><span class="w"> </span><span class="py">follower</span><span class="w"> </span><span class="py">buckets</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="p">(</span><span class="py">celebrity</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">HAS_FOLLOWER_BUCKET</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">bucket</span><span class="p">:</span><span class="nc">FollowerBucket</span><span class="w"> </span><span class="p">{</span><span class="py">range</span><span class="p">:</span><span class="w"> </span><span class="s">&#34;A-F&#34;</span><span class="p">})</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="p">(</span><span class="nc">bucket</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">CONTAINS_FOLLOWER</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">follower</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span></code></pre></div><p><strong>Impact</strong>: <strong>Avoid O(n) expansion</strong> on supernodes.</p> <hr> <h4 id="issue-4-inefficient-aggregations" class="position-relative d-flex align-items-center group"> <span>Issue 4: Inefficient Aggregations</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="issue-4-inefficient-aggregations" aria-haspopup="dialog" aria-label="Share link: Issue 4: Inefficient Aggregations"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>Symptom</strong>: COUNT, SUM, AVG queries are slow.</p> <p><strong>Example</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">count</span><span class="p">(</span><span class="py">p</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Scans</span><span class="w"> </span><span class="py">all</span><span class="w"> </span><span class="py">Person</span><span class="w"> </span><span class="py">nodes</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution 1</strong>: Maintain counts in metadata node.</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">stats</span><span class="p">:</span><span class="nc">Statistics</span><span class="w"> </span><span class="p">{</span><span class="kd">type</span><span class="p">:</span><span class="w"> </span><span class="s">&#34;Person&#34;</span><span class="p">})</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">RETURN</span><span class="w"> </span><span class="nc">stats</span><span class="err">.</span><span class="py">total_count</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Update</span><span class="w"> </span><span class="kd">on</span><span class="w"> </span><span class="py">create</span><span class="err">/</span><span class="py">delete</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">stats</span><span class="p">:</span><span class="nc">Statistics</span><span class="w"> </span><span class="p">{</span><span class="kd">type</span><span class="p">:</span><span class="w"> </span><span class="s">&#34;Person&#34;</span><span class="p">})</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">SET</span><span class="w"> </span><span class="nc">stats</span><span class="err">.</span><span class="py">total_count</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="py">stats</span><span class="err">.</span><span class="py">total_count</span><span class="w"> </span><span class="err">+</span><span class="w"> </span><span class="py">1</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution 2</strong>: Use index-backed aggregation (if supported).</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">person_label</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Person</span><span class="p">(</span><span class="py">label</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Future</span><span class="p">:</span><span class="w"> </span><span class="nc">Optimizer</span><span class="w"> </span><span class="py">uses</span><span class="w"> </span><span class="py">index</span><span class="w"> </span><span class="py">stats</span><span class="w"> </span><span class="py">for</span><span class="w"> </span><span class="py">count</span><span class="w"> </span></span></span></code></pre></div><p><strong>Impact</strong>: <strong>Constant time vs O(n)</strong> for large datasets.</p> <hr> <h4 id="issue-5-unindexed-joins" class="position-relative d-flex align-items-center group"> <span>Issue 5: Unindexed JOINs</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="issue-5-unindexed-joins" aria-haspopup="dialog" aria-label="Share link: Issue 5: Unindexed JOINs"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p><strong>Symptom</strong>: Queries joining on properties without indexes are slow.</p> <p><strong>Example</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">order</span><span class="p">:</span><span class="nc">Order</span><span class="p">),</span><span class="w"> </span><span class="p">(</span><span class="py">customer</span><span class="p">:</span><span class="nc">Customer</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">WHERE</span><span class="w"> </span><span class="py">order</span><span class="err">.</span><span class="py">customer_id</span><span class="w"> </span><span class="p">=</span><span class="w"> </span><span class="py">customer</span><span class="err">.</span><span class="py">id</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">order</span><span class="err">.</span><span class="py">id</span><span class="p">,</span><span class="w"> </span><span class="py">customer</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Cartesian</span><span class="w"> </span><span class="py">product</span><span class="p">:</span><span class="w"> </span><span class="nc">orders</span><span class="w"> </span><span class="err">×</span><span class="w"> </span><span class="py">customers</span><span class="p">!</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution 1</strong>: Use explicit relationships.</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">order</span><span class="p">:</span><span class="nc">Order</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">PLACED_BY</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">customer</span><span class="p">:</span><span class="nc">Customer</span><span class="p">)</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">RETURN</span><span class="w"> </span><span class="py">order</span><span class="err">.</span><span class="py">id</span><span class="p">,</span><span class="w"> </span><span class="py">customer</span><span class="err">.</span><span class="py">name</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Solution 2</strong>: If relationships don&rsquo;t exist, create indexes.</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">order_customer_id</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Order</span><span class="p">(</span><span class="py">customer_id</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="py">CREATE</span><span class="w"> </span><span class="py">INDEX</span><span class="w"> </span><span class="py">customer_id</span><span class="w"> </span><span class="py">ON</span><span class="w"> </span><span class="py">Customer</span><span class="p">(</span><span class="py">id</span><span class="p">)</span><span class="err">;</span><span class="w"> </span></span></span></code></pre></div><p><strong>Impact</strong>: Avoids expensive Cartesian products.</p> <hr> <h3 id="performance-checklist" class="position-relative d-flex align-items-center group"> <span>Performance Checklist</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="performance-checklist" aria-haspopup="dialog" aria-label="Share link: Performance Checklist"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3> <h4 id="before-query-execution" class="position-relative d-flex align-items-center group"> <span>Before Query Execution</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="before-query-execution" aria-haspopup="dialog" aria-label="Share link: Before Query Execution"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><ul> <li><input disabled="" type="checkbox"> <strong>Use EXPLAIN</strong> to review execution plan</li> <li><input disabled="" type="checkbox"> <strong>Check for NodeScan</strong> - add indexes if needed</li> <li><input disabled="" type="checkbox"> <strong>Verify index usage</strong> - IndexSeek is ideal</li> <li><input disabled="" type="checkbox"> <strong>Look for expensive sorts</strong> - consider index on ORDER BY property</li> <li><input disabled="" type="checkbox"> <strong>Identify Cartesian products</strong> - use relationships instead</li> </ul> <h4 id="after-query-execution" class="position-relative d-flex align-items-center group"> <span>After Query Execution</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="after-query-execution" aria-haspopup="dialog" aria-label="Share link: After Query Execution"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><ul> <li><input disabled="" type="checkbox"> <strong>Use PROFILE</strong> to measure actual performance</li> <li><input disabled="" type="checkbox"> <strong>Compare execution_time_ms</strong> to expectations</li> <li><input disabled="" type="checkbox"> <strong>Check rows_returned</strong> - is it what you expected?</li> <li><input disabled="" type="checkbox"> <strong>Verify index hit</strong> - did optimizer use your index?</li> <li><input disabled="" type="checkbox"> <strong>Re-measure after optimization</strong> - confirm improvement</li> </ul> <h4 id="index-strategy" class="position-relative d-flex align-items-center group"> <span>Index Strategy</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="index-strategy" aria-haspopup="dialog" aria-label="Share link: Index Strategy"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><ul> <li><input disabled="" type="checkbox"> <strong>Index frequently filtered properties</strong></li> <li><input disabled="" type="checkbox"> <strong>Index ORDER BY properties</strong></li> <li><input disabled="" type="checkbox"> <strong>Use hash indexes for exact lookups</strong></li> <li><input disabled="" type="checkbox"> <strong>Use fulltext indexes for text search</strong></li> <li><input disabled="" type="checkbox"> <strong>Use vector indexes for similarity search</strong></li> <li><input disabled="" type="checkbox"> <strong>Don&rsquo;t over-index</strong> - each index adds write overhead</li> </ul> <hr> <h3 id="advanced-optimization-techniques" class="position-relative d-flex align-items-center group"> <span>Advanced Optimization Techniques</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="advanced-optimization-techniques" aria-haspopup="dialog" aria-label="Share link: Advanced Optimization Techniques"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3> <h4 id="materialized-views" class="position-relative d-flex align-items-center group"> <span>Materialized Views</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="materialized-views" aria-haspopup="dialog" aria-label="Share link: Materialized Views"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p>For expensive aggregations run frequently, precompute results:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-gql" data-lang="gql"><span class="line"><span class="cl"><span class="err">--</span><span class="w"> </span><span class="py">Instead</span><span class="w"> </span><span class="py">of</span><span class="w"> </span><span class="py">computing</span><span class="w"> </span><span class="kd">on</span><span class="w"> </span><span class="py">every</span><span class="w"> </span><span class="kd">query</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">MATCH</span><span class="w"> </span><span class="p">(</span><span class="nc">p</span><span class="p">:</span><span class="nc">Person</span><span class="p">)</span><span class="err">-</span><span class="p">[:</span><span class="nc">WORKS_FOR</span><span class="p">]</span><span class="err">-&gt;</span><span class="p">(</span><span class="py">c</span><span class="p">:</span><span class="nc">Company</span><span class="w"> </span><span class="p">{</span><span class="py">name</span><span class="p">:</span><span class="w"> </span><span class="s">&#34;Acme&#34;</span><span class="p">})</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">RETURN</span><span class="w"> </span><span class="py">count</span><span class="p">(</span><span class="py">p</span><span class="p">)</span><span class="w"> </span><span class="py">AS</span><span class="w"> </span><span class="py">employee_count</span><span class="err">;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="err">--</span><span class="w"> </span><span class="py">Maintain</span><span class="w"> </span><span class="py">a</span><span class="w"> </span><span class="py">cached</span><span class="w"> </span><span class="py">value</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">MATCH</span><span class="w"> </span><span class="p">(</span><span class="py">c</span><span class="p">:</span><span class="nc">Company</span><span class="w"> </span><span class="p">{</span><span class="py">name</span><span class="p">:</span><span class="w"> </span><span class="s">&#34;Acme&#34;</span><span class="p">})</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nc">RETURN</span><span class="w"> </span><span class="py">c</span><span class="err">.</span><span class="py">employee_count</span><span class="err">;</span><span class="w"> </span><span class="err">--</span><span class="w"> </span><span class="py">Updated</span><span class="w"> </span><span class="kd">on</span><span class="w"> </span><span class="py">hire</span><span class="err">/</span><span class="py">termination</span><span class="w"> </span></span></span></code></pre></div> <h4 id="query-result-caching" class="position-relative d-flex align-items-center group"> <span>Query Result Caching</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="query-result-caching" aria-haspopup="dialog" aria-label="Share link: Query Result Caching"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p>Cache frequent query results at application level:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-python" data-lang="python"><span class="line"><span class="cl"><span class="kn">from</span> <span class="nn">functools</span> <span class="kn">import</span> <span class="n">lru_cache</span> </span></span><span class="line"><span class="cl"> </span></span><span class="line"><span class="cl"><span class="nd">@lru_cache</span><span class="p">(</span><span class="n">maxsize</span><span class="o">=</span><span class="mi">128</span><span class="p">)</span> </span></span><span class="line"><span class="cl"><span class="k">def</span> <span class="nf">get_company_employees</span><span class="p">(</span><span class="n">company_name</span><span class="p">):</span> </span></span><span class="line"><span class="cl"> <span class="k">return</span> <span class="n">db</span><span class="o">.</span><span class="n">query</span><span class="p">(</span> </span></span><span class="line"><span class="cl"> <span class="s2">&#34;MATCH (p:Person)-[:WORKS_FOR]-&gt;(c:Company {name: $name}) RETURN p&#34;</span><span class="p">,</span> </span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s2">&#34;name&#34;</span><span class="p">:</span> <span class="n">company_name</span><span class="p">}</span> </span></span><span class="line"><span class="cl"> <span class="p">)</span> </span></span></code></pre></div> <h4 id="batch-operations" class="position-relative d-flex align-items-center group"> <span>Batch Operations</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="batch-operations" aria-haspopup="dialog" aria-label="Share link: Batch Operations"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><p>Instead of N queries, use one batched query:</p> <p><strong>❌ Bad (N+1 Query Problem)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-python" data-lang="python"><span class="line"><span class="cl"><span class="k">for</span> <span class="n">order_id</span> <span class="ow">in</span> <span class="n">order_ids</span><span class="p">:</span> <span class="c1"># 1000 orders</span> </span></span><span class="line"><span class="cl"> <span class="n">result</span> <span class="o">=</span> <span class="n">db</span><span class="o">.</span><span class="n">query</span><span class="p">(</span><span class="s2">&#34;MATCH (o:Order {id: $id}) RETURN o&#34;</span><span class="p">,</span> <span class="p">{</span><span class="s2">&#34;id&#34;</span><span class="p">:</span> <span class="n">order_id</span><span class="p">})</span> </span></span><span class="line"><span class="cl"> <span class="c1"># 1000 individual queries!</span> </span></span></code></pre></div><p><strong>✅ Good (Batch Query)</strong>:</p> <div class="highlight"><pre tabindex="0" class="chroma"><code class="language-python" data-lang="python"><span class="line"><span class="cl"><span class="n">result</span> <span class="o">=</span> <span class="n">db</span><span class="o">.</span><span class="n">query</span><span class="p">(</span> </span></span><span class="line"><span class="cl"> <span class="s2">&#34;MATCH (o:Order) WHERE o.id IN $ids RETURN o&#34;</span><span class="p">,</span> </span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s2">&#34;ids&#34;</span><span class="p">:</span> <span class="n">order_ids</span><span class="p">}</span> </span></span><span class="line"><span class="cl"><span class="p">)</span> </span></span><span class="line"><span class="cl"><span class="c1"># Single query</span> </span></span></code></pre></div><hr> <h3 id="monitoring-query-performance" class="position-relative d-flex align-items-center group"> <span>Monitoring Query Performance</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="monitoring-query-performance" aria-haspopup="dialog" aria-label="Share link: Monitoring Query Performance"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3> <h4 id="enable-query-logging" class="position-relative d-flex align-items-center group"> <span>Enable Query Logging</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="enable-query-logging" aria-haspopup="dialog" aria-label="Share link: Enable Query Logging"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><div class="highlight"><pre tabindex="0" class="chroma"><code class="language-yaml" data-lang="yaml"><span class="line"><span class="cl"><span class="c"># geode.yaml</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="nt">logging</span><span class="p">:</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span><span class="nt">level</span><span class="p">:</span><span class="w"> </span><span class="s1">&#39;info&#39;</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span><span class="nt">slow_query_threshold_ms</span><span class="p">:</span><span class="w"> </span><span class="m">1000</span><span class="w"> </span><span class="c"># Log queries &gt; 1s</span><span class="w"> </span></span></span></code></pre></div> <h4 id="prometheus-metrics" class="position-relative d-flex align-items-center group"> <span>Prometheus Metrics</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="prometheus-metrics" aria-haspopup="dialog" aria-label="Share link: Prometheus Metrics"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><div class="highlight"><pre tabindex="0" class="chroma"><code class="language-bash" data-lang="bash"><span class="line"><span class="cl"><span class="c1"># Query duration histogram</span> </span></span><span class="line"><span class="cl">geode_query_duration_seconds_bucket<span class="o">{</span><span class="nv">le</span><span class="o">=</span><span class="s2">&#34;0.1&#34;</span><span class="o">}</span> </span></span><span class="line"><span class="cl">geode_query_duration_seconds_bucket<span class="o">{</span><span class="nv">le</span><span class="o">=</span><span class="s2">&#34;1.0&#34;</span><span class="o">}</span> </span></span><span class="line"><span class="cl">geode_query_duration_seconds_bucket<span class="o">{</span><span class="nv">le</span><span class="o">=</span><span class="s2">&#34;10.0&#34;</span><span class="o">}</span> </span></span><span class="line"><span class="cl"> </span></span><span class="line"><span class="cl"><span class="c1"># Query rate</span> </span></span><span class="line"><span class="cl">rate<span class="o">(</span>geode_queries_total<span class="o">[</span>5m<span class="o">])</span> </span></span><span class="line"><span class="cl"> </span></span><span class="line"><span class="cl"><span class="c1"># 95th percentile latency</span> </span></span><span class="line"><span class="cl">histogram_quantile<span class="o">(</span>0.95, rate<span class="o">(</span>geode_query_duration_seconds_bucket<span class="o">[</span>5m<span class="o">]))</span> </span></span></code></pre></div> <h4 id="grafana-dashboard-queries" class="position-relative d-flex align-items-center group"> <span>Grafana Dashboard Queries</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="grafana-dashboard-queries" aria-haspopup="dialog" aria-label="Share link: Grafana Dashboard Queries"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h4><div class="highlight"><pre tabindex="0" class="chroma"><code class="language-promql" data-lang="promql"><span class="line"><span class="cl"><span class="c1"># Top 5 slowest query types</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="k">topk</span><span class="o">(</span><span class="mi">5</span><span class="p">,</span><span class="w"> </span><span class="k">avg</span><span class="o">(</span><span class="kr">rate</span><span class="o">(</span><span class="nv">geode_query_duration_seconds_sum</span><span class="p">[</span><span class="s">5m</span><span class="p">]</span><span class="o">))</span><span class="w"> </span><span class="k">by</span><span class="w"> </span><span class="o">(</span><span class="nv">query_type</span><span class="o">))</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="c1"># Query throughput</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="k">sum</span><span class="o">(</span><span class="kr">rate</span><span class="o">(</span><span class="nv">geode_queries_total</span><span class="p">[</span><span class="s">5m</span><span class="p">]</span><span class="o">))</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="c1"># Error rate</span><span class="w"> </span></span></span><span class="line"><span class="cl"><span class="w"></span><span class="kr">rate</span><span class="o">(</span><span class="nv">geode_query_errors_total</span><span class="p">[</span><span class="s">5m</span><span class="p">]</span><span class="o">)</span><span class="w"> </span><span class="o">/</span><span class="w"> </span><span class="kr">rate</span><span class="o">(</span><span class="nv">geode_queries_total</span><span class="p">[</span><span class="s">5m</span><span class="p">]</span><span class="o">)</span><span class="w"> </span></span></span></code></pre></div><hr> <h3 id="next-steps" class="position-relative d-flex align-items-center group"> <span>Next Steps</span> <button type="button" class="h-share btn btn-link p-0 text-decoration-none link-secondary opacity-50 hover-opacity-100 transition-all ms-1" data-share-target="next-steps" aria-haspopup="dialog" aria-label="Share link: Next Steps"> <i class="fa-sharp-duotone fa-solid fa-share-nodes" aria-hidden="true" style="font-size: 0.8em;"></i> <span class="visually-hidden">Share link</span> </button> </h3><ul> <li><a href="/docs/query/indexing-and-optimization/" >Indexing Guide</a> - Complete index reference</li> <li><a href="/docs/model/data-model-and-types/" >Data Model</a> - Type system and schema design</li> <li><a href="/docs/guides/troubleshooting/" >Troubleshooting</a> - Diagnose performance issues</li> <li><a href="/docs/configuration/server-configuration/" >Configuration</a> - Tune server performance</li> <li><a href="/docs/ops/observability/" >Monitoring</a> - Set up performance monitoring</li> </ul>