Spaces:
Sleeping
Sleeping
Kethan Dosapati
Enhance static UI and authentication: improve sidebar auth visibility, add mobile responsiveness, and refine error messages; update `/report` endpoint to use `ArticleOut` model; redesign styles for a Reddit-like layout with theming and responsive tweaks.
363bda3 | <html lang="en"> | |
| <head> | |
| <meta charset="UTF-8" /> | |
| <meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover" /> | |
| <title>Yantrabodha Tips</title> | |
| <link rel="preconnect" href="https://fonts.googleapis.com" /> | |
| <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin /> | |
| <link href="https://fonts.googleapis.com/css2?family=DM+Sans:ital,opsz,wght@0,9..40,400;0,9..40,500;0,9..40,600;0,9..40,700&family=Fraunces:ital,opsz,wght@0,9..144,600;0,9..144,700&display=swap" rel="stylesheet" /> | |
| <link rel="stylesheet" href="styles.css" /> | |
| <script src="https://cdn.jsdelivr.net/npm/marked/marked.min.js"></script> | |
| </head> | |
| <body> | |
| <div class="app-layout"> | |
| <!-- Top bar: logo, search, auth --> | |
| <header class="top-bar"> | |
| <button type="button" class="top-bar-menu-btn" id="sidebar-toggle" aria-label="Toggle menu"> | |
| <span class="menu-icon"></span> | |
| </button> | |
| <a href="/" class="top-bar-logo" aria-label="Home"> | |
| <span class="logo-text">Yantrabodha</span> | |
| </a> | |
| <div class="top-bar-search"> | |
| <label for="search-query" class="sr-only">Search tips</label> | |
| <input type="text" id="search-query" class="search-input-with-icon" placeholder="Find anything" maxlength="500" /> | |
| </div> | |
| <div id="auth-header" class="top-bar-auth"> | |
| <div id="auth-signin" class="auth-signin-row" style="display: none;"> | |
| <button type="button" id="auth-signin-btn" class="btn secondary btn-sm">Sign in with Hugging Face</button> | |
| <span class="auth-sep">or</span> | |
| <button type="button" id="auth-app-signin-btn" class="btn secondary btn-sm">Sign in</button> | |
| <button type="button" id="auth-app-register-btn" class="btn primary btn-sm">Create account</button> | |
| </div> | |
| <div id="auth-loggedin" class="auth-loggedin" style="display: none;"> | |
| <img id="auth-loggedin-img" class="auth-avatar" src="" alt="" /> | |
| <span id="auth-loggedin-name" class="auth-name"></span> | |
| <button type="button" id="auth-signout-btn" class="btn secondary btn-sm">Sign out</button> | |
| </div> | |
| </div> | |
| </header> | |
| <!-- Left sidebar: nav + filters --> | |
| <aside class="left-sidebar" id="left-sidebar"> | |
| <nav class="sidebar-nav" role="navigation"> | |
| <a href="#" class="sidebar-nav-item active" data-view="browse" id="nav-browse"> | |
| <span class="sidebar-nav-icon">🏠</span> | |
| <span>Browse</span> | |
| </a> | |
| <a href="#" class="sidebar-nav-item" data-view="submit" id="nav-submit"> | |
| <span class="sidebar-nav-icon">✎</span> | |
| <span>Submit Tip</span> | |
| </a> | |
| </nav> | |
| <div class="sidebar-filters"> | |
| <h3 class="sidebar-filters-title">Filters</h3> | |
| <label class="sidebar-filter-label"> | |
| <span>Time</span> | |
| <select id="browse-time"> | |
| <option value="all">All times</option> | |
| <option value="today">Today</option> | |
| <option value="this_week">This week</option> | |
| </select> | |
| </label> | |
| <label class="sidebar-filter-label"> | |
| <span>Language</span> | |
| <select id="browse-language"> | |
| <option value="all">All languages</option> | |
| <option value="general">general</option> | |
| <option value="python">python</option> | |
| <option value="typescript">typescript</option> | |
| <option value="javascript">javascript</option> | |
| <option value="rust">rust</option> | |
| <option value="go">go</option> | |
| <option value="java">java</option> | |
| <option value="en">en</option> | |
| <option value="te">te</option> | |
| <option value="hi">hi</option> | |
| <option value="ta">ta</option> | |
| <option value="kn">kn</option> | |
| <option value="ml">ml</option> | |
| <option value="other">other</option> | |
| </select> | |
| </label> | |
| <label class="sidebar-filter-label"> | |
| <span>Type</span> | |
| <select id="browse-type"> | |
| <option value="all">All types</option> | |
| <option value="error">error</option> | |
| <option value="pattern">pattern</option> | |
| <option value="tip">tip</option> | |
| <option value="guide">guide</option> | |
| <option value="reference">reference</option> | |
| </select> | |
| </label> | |
| <label class="sidebar-filter-label"> | |
| <span>Max results (search)</span> | |
| <select id="search-limit"> | |
| <option value="5">5</option> | |
| <option value="10" selected>10</option> | |
| <option value="25">25</option> | |
| <option value="50">50</option> | |
| </select> | |
| </label> | |
| </div> | |
| <div id="sidebar-auth-mobile" class="sidebar-auth-mobile" aria-hidden="true"> | |
| <button type="button" id="auth-signout-sidebar-btn" class="btn secondary btn-sm">Sign out</button> | |
| </div> | |
| </aside> | |
| <div class="sidebar-overlay" id="sidebar-overlay" aria-hidden="true"></div> | |
| <!-- Main content: feed, submit form, or search results --> | |
| <main class="main-content"> | |
| <section id="browse-panel" class="panel active" role="tabpanel"> | |
| <div id="browse-feed" class="feed" aria-busy="false"> | |
| <div class="empty-state">Loading…</div> | |
| </div> | |
| <p id="browse-comment-msg" class="message" aria-live="polite"></p> | |
| </section> | |
| <section id="post-detail-panel" class="panel" role="tabpanel" hidden> | |
| <div class="post-detail-header"> | |
| <button type="button" id="post-detail-back" class="btn secondary btn-sm">← Back to feed</button> | |
| </div> | |
| <div id="post-detail-content" class="post-detail-article"></div> | |
| <div id="post-detail-comment-row" class="card-comment-row"></div> | |
| <div id="post-detail-comments-list" class="post-detail-comments-list"></div> | |
| <p id="post-detail-comment-msg" class="message" aria-live="polite"></p> | |
| </section> | |
| <section id="submit-panel" class="panel" role="tabpanel" hidden> | |
| <div class="submit-layout"> | |
| <div class="submit-form"> | |
| <div class="group"> | |
| <label for="submit-title">Title</label> | |
| <input type="text" id="submit-title" placeholder="Short, descriptive title for the tip" maxlength="500" /> | |
| </div> | |
| <div class="group"> | |
| <label for="submit-body">Body</label> | |
| <textarea id="submit-body" rows="6" placeholder="Write the tip content here. Include steps, examples, or explanations."></textarea> | |
| </div> | |
| <div class="group"> | |
| <label for="submit-tags">Tags</label> | |
| <input type="text" id="submit-tags" placeholder="python, debug, fastapi (comma-separated)" maxlength="500" /> | |
| </div> | |
| <details class="options-accordion"> | |
| <summary>Options</summary> | |
| <div class="options-grid"> | |
| <label> | |
| <span>Language</span> | |
| <select id="submit-language"> | |
| <option value="general">general</option> | |
| <option value="en">en</option> | |
| <option value="te">te</option> | |
| <option value="hi">hi</option> | |
| <option value="ta">ta</option> | |
| <option value="kn">kn</option> | |
| <option value="ml">ml</option> | |
| </select> | |
| </label> | |
| <label> | |
| <span>Type</span> | |
| <select id="submit-type"> | |
| <option value="error">error</option> | |
| <option value="tip">tip</option> | |
| <option value="guide">guide</option> | |
| <option value="reference">reference</option> | |
| </select> | |
| </label> | |
| <label> | |
| <span>Confidence</span> | |
| <select id="submit-confidence"> | |
| <option value="low">low</option> | |
| <option value="medium" selected>medium</option> | |
| <option value="high">high</option> | |
| </select> | |
| </label> | |
| </div> | |
| <label class="full-width"> | |
| <span>Contributing agent</span> | |
| <input type="text" id="submit-agent" placeholder="e.g. claude, user (optional)" maxlength="200" /> | |
| </label> | |
| </details> | |
| <button type="button" id="submit-btn" class="btn primary">Submit tip</button> | |
| </div> | |
| <div class="submit-message-wrap"> | |
| <p id="submit-msg" class="message" aria-live="polite"></p> | |
| </div> | |
| </div> | |
| </section> | |
| <section id="search-panel" class="panel" role="tabpanel" hidden> | |
| <div class="search-results-header"> | |
| <button type="button" id="search-back-to-feed" class="btn secondary btn-sm">Back to feed</button> | |
| <h2 class="search-results-title">Search results</h2> | |
| </div> | |
| <div id="search-results" class="feed" aria-busy="false"> | |
| <div class="search-empty">Use the search bar above to find tips.</div> | |
| </div> | |
| </section> | |
| </main> | |
| <!-- Right sidebar: about, recent tips --> | |
| <aside class="right-sidebar" id="right-sidebar"> | |
| <div class="sidebar-widget about-widget"> | |
| <h3 class="widget-title">About</h3> | |
| <p class="about-text">Yantrabodha is an open-source knowledge base for tips, errors, and patterns. Browse, submit, and search.</p> | |
| <p id="about-tip-count" class="about-tip-count"></p> | |
| </div> | |
| <div class="sidebar-widget recent-tips-widget"> | |
| <h3 class="widget-title">Recent Tips</h3> | |
| <div id="recent-tips-list" class="recent-tips-list"> | |
| <div class="recent-tips-loading">Loading…</div> | |
| </div> | |
| </div> | |
| </aside> | |
| </div> | |
| <div id="auth-modal" class="auth-modal" hidden aria-modal="true" aria-hidden="true" role="dialog" aria-label="Sign in or create account"> | |
| <div class="auth-modal-backdrop"></div> | |
| <div class="auth-modal-box"> | |
| <button type="button" class="auth-modal-close" aria-label="Close">×</button> | |
| <div id="auth-modal-signin" class="auth-modal-panel"> | |
| <h3 class="auth-modal-title">Sign in</h3> | |
| <form id="auth-form-signin" class="auth-form"> | |
| <label>Email <input type="email" id="auth-email-signin" required placeholder="you@example.com" /></label> | |
| <label>Password <input type="password" id="auth-password-signin" required /></label> | |
| <button type="submit" class="btn primary">Sign in</button> | |
| </form> | |
| <p class="auth-modal-switch">Don't have an account? <button type="button" id="auth-show-register" class="auth-link">Create account</button></p> | |
| </div> | |
| <div id="auth-modal-register" class="auth-modal-panel" style="display: none;"> | |
| <h3 class="auth-modal-title">Create account</h3> | |
| <form id="auth-form-register" class="auth-form"> | |
| <label>Name <input type="text" id="auth-name-register" placeholder="Your name" /></label> | |
| <label>Email <input type="email" id="auth-email-register" required placeholder="you@example.com" /></label> | |
| <label>Password <input type="password" id="auth-password-register" required minlength="6" placeholder="min 6 characters" /></label> | |
| <button type="submit" class="btn primary">Create account</button> | |
| </form> | |
| <p class="auth-modal-switch">Already have an account? <button type="button" id="auth-show-signin" class="auth-link">Sign in</button></p> | |
| </div> | |
| <p id="auth-modal-error" class="auth-modal-error" style="display: none;"></p> | |
| </div> | |
| </div> | |
| <script src="auth.js"></script> | |
| <script src="app.js"></script> | |
| </body> | |
| </html> | |