Repository navigation
Expand file tree
/
Copy pathproblems_v2.html
More file actions
131 lines (117 loc) · 5.67 KB
/
Copy pathproblems_v2.html
File metadata and controls
131 lines (117 loc) · 5.67 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>CodePilot - Practice</title>
<link rel="stylesheet" href="css/style.css">
<style>
.problem-row {
display: grid;
grid-template-columns: 2fr 1fr 1fr auto;
padding: 1rem;
border-bottom: 1px solid var(--border-color);
align-items: center;
}
.problem-row:last-child {
border-bottom: none;
}
.problem-row:hover {
background: rgba(255,255,255,0.02);
}
.problem-header {
font-weight: 700;
color: var(--text-secondary);
border-bottom: 2px solid var(--border-color);
}
</style>
</head>
<body>
<nav>
<a href="index.html" class="logo">CodePilot</a>
<div class="nav-links">
<a href="dashboard_v2.html">Dashboard</a>
<a href="#" onclick="logout()">Logout</a>
</div>
</nav>
<div class="section">
<h1 class="mb-2">Practice Problems</h1>
<h2 style="color: var(--success); margin-bottom: 1rem; margin-top: 2rem;">▶ Easy (10)</h2>
<div class="card" style="padding: 0; margin-bottom: 2rem;">
<div class="problem-row problem-header">
<div>Title</div><div>Difficulty</div><div>Category</div><div>Action</div>
</div>
<div id="easyProblemsList"><div style="padding: 2rem; text-align: center;" class="text-secondary">Loading...</div></div>
</div>
<h2 style="color: var(--warning); margin-bottom: 1rem;">▶ Medium (10)</h2>
<div class="card" style="padding: 0; margin-bottom: 2rem;">
<div class="problem-row problem-header">
<div>Title</div><div>Difficulty</div><div>Category</div><div>Action</div>
</div>
<div id="mediumProblemsList"><div style="padding: 2rem; text-align: center;" class="text-secondary">Loading...</div></div>
</div>
<h2 style="color: var(--danger); margin-bottom: 1rem;">▶ Hard (10)</h2>
<div class="card" style="padding: 0; margin-bottom: 2rem;">
<div class="problem-row problem-header">
<div>Title</div><div>Difficulty</div><div>Category</div><div>Action</div>
</div>
<div id="hardProblemsList"><div style="padding: 2rem; text-align: center;" class="text-secondary">Loading...</div></div>
</div>
</div>
<script src="js/app.js?v=2"></script>
<script>
// Use API_URL from app.js instead of absolute URL
async function loadProblems() {
const renderHTML = (p) => `
<div class="problem-row">
<div style="font-weight: 500;">${p.title}</div>
<div><span class="badge ${p.difficulty.toLowerCase()}">${p.difficulty}</span></div>
<div class="text-secondary">${p.category}</div>
<div><a href="practice_v2.html?id=${p._id}" class="btn-secondary">Solve</a></div>
</div>
`;
function renderAllLists(problems) {
const easy = problems.filter(p => p.difficulty === 'Easy');
const medium = problems.filter(p => p.difficulty === 'Medium');
const hard = problems.filter(p => p.difficulty === 'Hard');
const easyList = document.getElementById('easyProblemsList');
const mediumList = document.getElementById('mediumProblemsList');
const hardList = document.getElementById('hardProblemsList');
if (easyList) easyList.innerHTML = easy.length ? easy.map(renderHTML).join('') : '<p style="padding: 2rem; text-align: center;" class="text-secondary">No problems found.</p>';
if (mediumList) mediumList.innerHTML = medium.length ? medium.map(renderHTML).join('') : '<p style="padding: 2rem; text-align: center;" class="text-secondary">No problems found.</p>';
if (hardList) hardList.innerHTML = hard.length ? hard.map(renderHTML).join('') : '<p style="padding: 2rem; text-align: center;" class="text-secondary">No problems found.</p>';
}
// Step 1: Stale-While-Revalidate - Load from Cache instantly
let hasCache = false;
try {
const cachedData = localStorage.getItem('codepilot_problems_cache');
if (cachedData) {
const parsed = JSON.parse(cachedData);
if (Array.isArray(parsed) && parsed.length > 0) {
renderAllLists(parsed);
hasCache = true;
}
}
} catch (e) {
console.error("Cache read error:", e);
}
// Step 2: Fetch fresh data in the background
try {
const res = await fetch(`${API_URL}/problems`);
if (!res.ok) throw new Error('Failed to fetch');
const problems = await res.json();
renderAllLists(problems);
// Update cache
localStorage.setItem('codepilot_problems_cache', JSON.stringify(problems));
} catch (e) {
console.error("Fresh fetch error:", e);
if (!hasCache) {
const easyList = document.getElementById('easyProblemsList');
if (easyList) easyList.innerHTML = '<p style="padding: 2rem; text-align: center; color: var(--danger);">Failed to load problems.</p>';
}
}
}
loadProblems();
</script>
</body>
</html>