CoolFace
Apppublic

hugging2021/local-gemma4-rag

sourceHugging Faceupdated 6mo agoView on Hugging Face
1likes
index_dev.html146 linesDownload Raw Back to root
1<!DOCTYPE html>2<html lang="en">3<head>4    <meta charset="UTF-8">5    <meta name="viewport" content="width=device-width, initial-scale=1.0">6    <title>Gemma 4 | Private Local RAG</title>7    <link rel="preconnect" href="https://fonts.googleapis.com">8    <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>9    <link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;800&display=swap" rel="stylesheet">10    <link rel="stylesheet" href="style.css">11    <!-- Essential Libraries -->12    <script src="https://cdn.jsdelivr.net/npm/marked/marked.min.js"></script>13    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/styles/github-dark.min.css">14    <script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/highlight.min.js"></script>15    <script src="https://cdnjs.cloudflare.com/ajax/libs/pdf.js/3.4.120/pdf.min.js"></script>16    <script>17        // Set worker for pdf.js18        pdfjsLib.GlobalWorkerOptions.workerSrc = 'https://cdnjs.cloudflare.com/ajax/libs/pdf.js/3.4.120/pdf.worker.min.js';19        20        // Configure marked with highlight.js21        window.marked.setOptions({22            highlight: function(code, lang) {23                if (lang && hljs.getLanguage(lang)) {24                    return hljs.highlight(code, { language: lang }).value;25                }26                return hljs.highlightAuto(code).value;27            },28            gfm: true,29            breaks: true30        });31    </script>32</head>33<body>34    <div class="container">35        <header>36            <div class="header-content">37                <h1>Gemma 4 RAG</h1>38                <p class="subtitle">Secure, local-first document chat powered by WebGPU & Orama</p>39            </div>40            <div id="sync-indicator" title="Synchronized with GitHub & HF">41                <svg width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M12 22s8-4 8-10V5l-8-3-8 3v7c0 6 8 10 8 10z"></path></svg>42            </div>43        </header>44 45        <main id="app">46            <!-- Setup & Initialization -->47            <div id="setup-container" class="card glass">48                <div class="status-box">49                    <h2 id="status-text">Initialize AI Engine</h2>50                    <p class="status-label">Ready to load ~1.6GB of optimized models to your GPU</p>51                </div>52                53                <div class="status-grid">54                    <div class="status-item" id="status-embedding">55                        <div class="status-label">Embedding (MiniLM-L6)</div>56                        <div class="progress-bar-container">57                            <div id="progress-embedding" class="progress-fill"></div>58                        </div>59                    </div>60                    <div class="status-item" id="status-llm">61                        <div class="status-label">Gemma 4 (Q4_K_M)</div>62                        <div class="progress-bar-container">63                            <div id="progress-llm" class="progress-fill"></div>64                        </div>65                    </div>66                </div>67 68                <div class="model-selector-container">69                    <label for="model-select" class="status-label">Select Model Variant:</label>70                    <select id="model-select" class="glass-select">71                        <option value="onnx-community/gemma-4-E2B-it-ONNX">Gemma 4 E2B (2B - Fast, Recommended)</option>72                        <option value="onnx-community/gemma-4-E4B-it-ONNX">Gemma 4 E4B (4B - High Quality, needs 6GB+ VRAM)</option>73                    </select>74                    <p class="hint" style="margin-top: 0.5rem; text-align: center;">4B variant requires significant GPU memory (~4GB download).</p>75                </div>76 77                <button id="init-btn" class="primary-btn">Initialize WebGPU AI</button>78                <p id="error-message" class="error-text" style="display: none;"></p>79            </div>80 81            <!-- Chat & Upload Interface (Initially Hidden) -->82            <div id="chat-container" class="hidden">83                <!-- Sidebar: Indexed Documents -->84                <aside id="sidebar" class="card glass">85                    <h3>Indexed Documents</h3>86                    <div id="docs-list-container">87                        <ul id="docs-list">88                            <p class="hint">No documents indexed yet.</p>89                        </ul>90                    </div>91                </aside>92 93                <div class="chat-main">94                    <!-- Upload Section -->95                    <div class="card glass" id="upload-card">96                        <div class="upload-btn-wrapper">97                            <div class="upload-btn-placeholder">98                                <svg width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4"></path><polyline points="17 8 12 3 7 8"></polyline><line x1="12" y1="3" x2="12" y2="15"></line></svg>99                                <p id="upload-status">Drop files here or click to index documents</p>100                                <p class="hint">Supports TXT, MD, PDF (local parsing)</p>101                            </div>102                            <input type="file" id="file-input" multiple accept=".txt,.md,.pdf,.js" />103                        </div>104                    </div>105 106                    <!-- Chat History -->107                    <div class="card glass chat-card">108                        <div class="chat-header">109                            <h3>Conversation</h3>110                            <button id="clear-chat-btn" title="Clear conversation history">🗑️ Clear Chat</button>111                        </div>112                        <div id="chat-history">113                            <div class="message ai">114                                <div class="avatar">G4</div>115                                <div class="content">116                                    Hello! I am initialized and ready. Upload some documents to start our private conversation.117                                </div>118                            </div>119                        </div>120                        121                        <div class="input-area">122                            <input type="text" id="user-input" placeholder="Ask a question about your documents..." autocomplete="off">123                            <button id="send-btn">124                                <svg width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><line x1="22" y1="2" x2="11" y2="13"></line><polygon points="22 2 15 22 11 13 2 9 22 2"></polygon></svg>125                            </button>126                        </div>127                    </div>128                </div>129            </div>130        </main>131 132        <footer>133            <div class="footer-content">134                <p>Created by <strong>Norberto Martín Afonso</strong> &bull; Follow on 135                    <a href="https://x.com/NorbertoMartnAf" target="_blank" class="social-link">X (@NorbertoMartnAf)</a> & 136                    <a href="https://github.com/nmarafo" target="_blank" class="social-link">GitHub (nmarafo)</a>137                </p>138                <p class="tech-stack">Powered by <strong>Transformers.js v4</strong> & <strong>Orama v2</strong> &bull; Local & Private</p>139            </div>140        </footer>141    </div>142 143    <!-- Scripts -->144    <script type="module" src="main.js"></script>145</body>146</html>