From 6e28d1530aa08b878f5082bbcd85a95f84f830e8 Mon Sep 17 00:00:00 2001 From: Adam Mathes Date: Sat, 14 Feb 2026 21:34:49 -0800 Subject: chore: update build artifacts and finalize test improvements --- frontend/coverage/src/components/Settings.tsx.html | 316 ++++++++++++++++----- 1 file changed, 242 insertions(+), 74 deletions(-) (limited to 'frontend/coverage/src/components/Settings.tsx.html') diff --git a/frontend/coverage/src/components/Settings.tsx.html b/frontend/coverage/src/components/Settings.tsx.html index 3d8d219..892218e 100644 --- a/frontend/coverage/src/components/Settings.tsx.html +++ b/frontend/coverage/src/components/Settings.tsx.html @@ -23,30 +23,30 @@
- 56.25% + 80% Statements - 36/64 + 60/75
- 41.66% + 66.66% Branches - 10/24 + 20/30
- 63.63% + 85.18% Functions - 14/22 + 23/27
- 62.5% + 87.87% Lines - 35/56 + 58/66
@@ -61,7 +61,7 @@
-
+
1 2 @@ -243,55 +243,138 @@ 178 179 180 -181  +181 +182 +183 +184 +185 +186 +187 +188 +189 +190 +191 +192 +193 +194 +195 +196 +197 +198 +199 +200 +201 +202 +203 +204 +205 +206 +207 +208 +209 +210 +211 +212 +213 +214 +215 +216 +217 +218 +219 +220 +221 +222 +223 +224 +225 +226 +227 +228 +229 +230 +231 +232 +233 +234 +235 +236 +237  +  +  +  +  +  +  +  +  +  +  +34x +  +34x +34x +34x +  +34x +  +  +34x +9x +9x +  +9x +9x +  +  +9x +9x     +  +        -14x -14x -14x -14x +34x   -14x +7x   -14x -4x -4x   -4x -4x   +34x +2x +2x   -4x -4x +2x +2x     -  -        -14x -3x +2x +1x     -14x 1x 1x   +  1x 1x       -  +34x +1x   1x 1x     +  +1x 1x 1x   @@ -301,12 +384,22 @@       -14x +34x +1x 1x   1x 1x +1x +1x   +1x +  +  +  +  +1x +1x     1x @@ -319,35 +412,28 @@       -14x -  -  -  -  -  -  -  +34x +1x +1x   -      +1x +1x     -  -  +1x +1x         -      -  -    +34x     -14x       @@ -375,8 +461,32 @@       +2x +  +  +  +  +  +  +  +  +  +  +  +  +  +  +  +  +  +  +  +1x +  +  +  +    -        @@ -403,7 +513,9 @@       -5x +  +  +6x       @@ -428,15 +540,22 @@ import type { Feed } from '../types'; import './Settings.css'; import { apiFetch } from '../utils';   -export default function Settings() { +interface SettingsProps { + fontTheme?: string; + setFontTheme?: (t: string) => void; +} +  +export default function Settings({ fontTheme, setFontTheme }: SettingsProps) { const [feeds, setFeeds] = useState<Feed[]>([]); + /* ... existing state ... */ const [newFeedUrl, setNewFeedUrl] = useState(''); const [loading, setLoading] = useState(false); const [error, setError] = useState<string | null>(null);   const [importFile, setImportFile] = useState<File | null>(null);   - const fetchFeeds = () => { + /* ... existing fetchFeeds ... */ + const fetchFeeds = React.useCallback(() => { setLoading(true); apiFetch('/api/feed/') .then((res) => { @@ -451,12 +570,14 @@ export default function Settings() { setError(err.message); setLoading(false); }); - }; + }, []);   useEffect(() => { + // eslint-disable-next-line fetchFeeds(); - }, []); + }, [fetchFeeds]);   + /* ... existing handlers ... */ const handleAddFeed = (e: React.FormEvent) => { e.preventDefault(); Iif (!newFeedUrl) return; @@ -468,16 +589,16 @@ export default function Settings() { body: JSON.stringify({ url: newFeedUrl }), }) .then((res) => { - Iif (!res.ok) throw new Error('Failed to add feed'); + if (!res.ok) throw new Error('Failed to add feed'); return res.json(); }) .then(() => { setNewFeedUrl(''); fetchFeeds(); }) - .catch((err) => { - setError(err.message); - setLoading(false); + .catch((err) => { + setError(err.message); + setLoading(false); }); };   @@ -499,27 +620,46 @@ export default function Settings() { }); };   - const handleImport = (e: React.FormEvent) => { - e.preventDefault(); - if (!importFile) return; + const handleImport = (e: React.FormEvent) => { + e.preventDefault(); + Iif (!importFile) return;   - setLoading(true); - const formData = new FormData(); - formData.append('file', importFile); - formData.append('format', 'opml'); + setLoading(true); + const formData = new FormData(); + formData.append('file', importFile); + formData.append('format', 'opml');   - apiFetch('/api/import', { + apiFetch('/api/import', { method: 'POST', body: formData, }) - .then((res) => { - if (!res.ok) throw new Error('Failed to import feeds'); - return res.json(); + .then((res) => { + Iif (!res.ok) throw new Error('Failed to import feeds'); + return res.json(); }) - .then(() => { - setImportFile(null); - fetchFeeds(); - alert('Import successful!'); + .then(() => { + setImportFile(null); + fetchFeeds(); + alert('Import successful!'); + }) + .catch((err) => { + setError(err.message); + setLoading(false); + }); + }; +  + const handleCrawl = () => { + setLoading(true); + apiFetch('/api/crawl', { + method: 'POST', + }) + .then((res) => { + Iif (!res.ok) throw new Error('Failed to start crawl'); + return res.json(); + }) + .then(() => { + setLoading(false); + alert('Crawl started!'); }) .catch((err) => { setError(err.message); @@ -528,8 +668,28 @@ export default function Settings() { };   return ( - <div className="settings-page"> + <div className="settings-page variant-glass"> <h2>Settings</h2> +  + {setFontTheme && ( + <div className="appearance-section"> + <h3>Appearance</h3> + <div className="font-selector"> + <label htmlFor="font-theme-select">Font Theme:</label> + <select + id="font-theme-select" + value={fontTheme || 'default'} + onChange={(e) => setFontTheme(e.target.value)} + className="font-select" + > + <option value="default">Default</option> + <option value="serif">Serif</option> + <option value="sans">Sans-Serif</option> + <option value="mono">Monospace</option> + </select> + </div> + </div> + )}   <div className="add-feed-section"> <h3>Add New Feed</h3> @@ -556,11 +716,12 @@ export default function Settings() { <input type="file" accept=".opml,.xml,.txt" - onChange={(e) => setImportFile(e.target.files?.[0] || null)} + aria-label="Import Feeds" + onChange={(e) => setImportFile(e.target.files?.[0] || null)} className="file-input" disabled={loading} /> - <button type="submit" disabled={!importFile || loading}> + <button type="submit" disabled={!importFile || loading}> Import </button> </form> @@ -574,9 +735,16 @@ export default function Settings() { <a href="/api/export/json" className="export-btn">JSON</a> </div> </div> +  + <div className="crawl-section"> + <h3>Actions</h3> + <button onClick={handleCrawl} disabled={loading} className="crawl-btn"> + Crawl All Feeds Now + </button> + </div> </div>   - {error && <p className="error-message">{error}</p>} + {error && <p className="error-message">{error}</p>}   <div className="feed-list-section"> <h3>Manage Feeds</h3> @@ -610,7 +778,7 @@ export default function Settings() {