| |
| from fastapi import FastAPI |
| from fastapi.responses import HTMLResponse |
| import uvicorn |
|
|
| app = FastAPI() |
|
|
| HTML = """ |
| <!DOCTYPE html> |
| <html lang="en"> |
| <head> |
| <meta charset="UTF-8"> |
| <title>SALT:// Neo War Terminal</title> |
| <script src="https://cdn.tailwindcss.com"></script> |
| <script src="https://cdn.jsdelivr.net/npm/ethers@6.7.0/dist/ethers.min.js"></script> |
| <style> |
| body { |
| background: linear-gradient(145deg, #0a0a0f, #050509); |
| font-family: monospace; |
| color: #eee; |
| } |
| #terminal { |
| background: #0c0c14; |
| border-radius: 18px; |
| padding: 24px; |
| margin: 50px auto; |
| max-width: 960px; |
| height: 560px; |
| overflow-y: auto; |
| box-shadow: |
| inset 6px 6px 12px #000, |
| inset -6px -6px 12px #1c1c28, |
| 0 0 12px rgba(249,115,22,0.5); |
| } |
| .line { margin: 6px 0; } |
| .prompt { color: #f97316; text-shadow: 0 0 10px #f97316; } |
| input { |
| background: transparent; |
| border: none; |
| outline: none; |
| color: #fff; |
| width: 80%; |
| } |
| </style> |
| </head> |
| <body> |
| <div id="terminal"> |
| <div class="line">⚡ Ignition engaged...</div> |
| <div class="line">Welcome to <span class="prompt">SALT:// Neo War Terminal 🧂</span></div> |
| <div class="line">Type <span class="prompt">help</span> to deploy cognition.</div> |
| <div class="line"><span class="prompt">SALT://></span> <input id="input" autofocus></div> |
| </div> |
| |
| <script> |
| const term = document.getElementById('terminal'); |
| const input = document.getElementById('input'); |
| let wallet = null; |
| |
| const HF_MODEL = "gpt2"; |
| const HF_API = `https://api-inference.huggingface.co/models/${HF_MODEL}`; |
| |
| function writeLine(text) { |
| const line = document.createElement('div'); |
| line.className = "line"; |
| line.innerHTML = text; |
| term.insertBefore(line, term.lastElementChild); |
| term.scrollTop = term.scrollHeight; |
| return line; |
| } |
| |
| async function streamText(el, text, speed=20) { |
| for (let i=0; i<text.length; i++) { |
| el.innerHTML += text[i]; |
| term.scrollTop = term.scrollHeight; |
| await new Promise(r=>setTimeout(r,speed)); |
| } |
| } |
| |
| async function queryLLM(prompt) { |
| const res = await fetch(HF_API, { |
| method: "POST", |
| headers: { "Content-Type": "application/json" }, |
| body: JSON.stringify({ inputs: prompt }) |
| }); |
| const data = await res.json(); |
| if (Array.isArray(data) && data[0].generated_text) return data[0].generated_text; |
| return JSON.stringify(data); |
| } |
| |
| // Local wallet ops |
| async function walletNew() { |
| wallet = ethers.Wallet.createRandom(); |
| localStorage.setItem("salt_wallet", wallet.privateKey); |
| writeLine(`[wallet] New ignition key forged: ${wallet.address}`); |
| } |
| async function walletLoad() { |
| const pk = localStorage.getItem("salt_wallet"); |
| if (pk) { |
| wallet = new ethers.Wallet(pk); |
| writeLine(`[wallet] Reloaded ignition key: ${wallet.address}`); |
| } else { |
| writeLine("[wallet] No local ignition key found. Run 'wallet new'"); |
| } |
| } |
| async function walletAddress() { |
| if (!wallet) return writeLine("[wallet] No wallet loaded"); |
| writeLine(`[wallet] Address: ${wallet.address}`); |
| } |
| async function walletSign(msg) { |
| if (!wallet) return writeLine("[wallet] No wallet loaded"); |
| const sig = await wallet.signMessage(msg); |
| writeLine(`[wallet] Signature: ${sig}`); |
| } |
| async function walletExport() { |
| if (!wallet) return writeLine("[wallet] No wallet loaded"); |
| const blob = new Blob([JSON.stringify({ privateKey: wallet.privateKey, address: wallet.address }, null, 2)], {type:"application/json"}); |
| const url = URL.createObjectURL(blob); |
| const a = document.createElement("a"); |
| a.href = url; |
| a.download = "wallet.json"; |
| a.click(); |
| URL.revokeObjectURL(url); |
| writeLine("[wallet] Exported ignition key as wallet.json"); |
| } |
| |
| async function handleCommand(cmd) { |
| const parts = cmd.trim().split(" "); |
| const base = parts[0]; |
| const args = parts.slice(1); |
| |
| if (base === "help") { |
| writeLine("Commands: help, llm <text>, clear, wallet <new|load|address|sign|export>"); |
| } else if (base === "llm") { |
| const thinking = writeLine(`<span class="prompt">[LLM]</span> `); |
| const out = await queryLLM(args.join(" ")); |
| await streamText(thinking, out, 20); |
| } else if (base === "wallet") { |
| if (args[0] === "new") await walletNew(); |
| else if (args[0] === "load") await walletLoad(); |
| else if (args[0] === "address") await walletAddress(); |
| else if (args[0] === "sign") await walletSign(args.slice(1).join(" ")); |
| else if (args[0] === "export") await walletExport(); |
| else writeLine("[wallet] Usage: wallet <new|load|address|sign|export>"); |
| } else if (base === "clear") { |
| [...term.querySelectorAll(".line")].forEach(l => l.remove()); |
| writeLine("⚡ Ignition reset..."); |
| writeLine("Welcome back to <span class='prompt'>SALT:// Neo War Terminal 🧂</span>"); |
| } else { |
| writeLine(`<span class="prompt">Unknown:</span> ${cmd}`); |
| } |
| } |
| |
| input.addEventListener("keydown", async (e) => { |
| if (e.key === "Enter") { |
| const cmd = input.value; |
| writeLine(`<span class="prompt">SALT://></span> ${cmd}`); |
| input.value = ""; |
| await handleCommand(cmd); |
| } |
| }); |
| |
| // Auto-load wallet |
| walletLoad(); |
| </script> |
| </body> |
| </html> |
| """ |
|
|
| @app.get("/", response_class=HTMLResponse) |
| async def root(): |
| return HTML |
|
|
| if __name__ == "__main__": |
| uvicorn.run("app:app", host="0.0.0.0", port=7860) |