0mij commited on
Commit
4c5551c
·
verified ·
1 Parent(s): 21bf5b9

Update index.html

Browse files
Files changed (1) hide show
  1. index.html +1163 -19
index.html CHANGED
@@ -1,19 +1,1163 @@
1
- <!doctype html>
2
- <html>
3
- <head>
4
- <meta charset="utf-8" />
5
- <meta name="viewport" content="width=device-width" />
6
- <title>My static Space</title>
7
- <link rel="stylesheet" href="style.css" />
8
- </head>
9
- <body>
10
- <div class="card">
11
- <h1>Welcome to your static Space!</h1>
12
- <p>You can modify this app directly by editing <i>index.html</i> in the Files and versions tab.</p>
13
- <p>
14
- Also don't forget to check the
15
- <a href="https://huggingface.co/docs/hub/spaces" target="_blank">Spaces documentation</a>.
16
- </p>
17
- </div>
18
- </body>
19
- </html>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
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>CodeSignal Interview Prompt Generator</title>
7
+ <link rel="preconnect" href="https://fonts.googleapis.com">
8
+ <link href="https://fonts.googleapis.com/css2?family=Syne:wght@400;600;700;800&family=JetBrains+Mono:wght@400;500;700&display=swap" rel="stylesheet">
9
+ <style>
10
+ :root {
11
+ --bg: #0a0c10;
12
+ --surface: #111318;
13
+ --surface2: #191d24;
14
+ --border: #252b36;
15
+ --accent: #f97316;
16
+ --accent2: #fb923c;
17
+ --green: #22c55e;
18
+ --blue: #38bdf8;
19
+ --purple: #a78bfa;
20
+ --red: #f87171;
21
+ --text: #e2e8f0;
22
+ --muted: #64748b;
23
+ --heading: #f8fafc;
24
+ }
25
+
26
+ *, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }
27
+
28
+ body {
29
+ background: var(--bg);
30
+ color: var(--text);
31
+ font-family: 'Syne', sans-serif;
32
+ min-height: 100vh;
33
+ overflow-x: hidden;
34
+ }
35
+
36
+ /* GRID BACKGROUND */
37
+ body::before {
38
+ content: '';
39
+ position: fixed;
40
+ inset: 0;
41
+ background-image:
42
+ linear-gradient(rgba(249,115,22,0.03) 1px, transparent 1px),
43
+ linear-gradient(90deg, rgba(249,115,22,0.03) 1px, transparent 1px);
44
+ background-size: 48px 48px;
45
+ pointer-events: none;
46
+ z-index: 0;
47
+ }
48
+
49
+ /* NOISE OVERLAY */
50
+ body::after {
51
+ content: '';
52
+ position: fixed;
53
+ inset: 0;
54
+ background-image: url("data:image/svg+xml,%3Csvg viewBox='0 0 256 256' xmlns='http://www.w3.org/2000/svg'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='4' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)' opacity='0.03'/%3E%3C/svg%3E");
55
+ pointer-events: none;
56
+ z-index: 0;
57
+ opacity: 0.4;
58
+ }
59
+
60
+ .container {
61
+ position: relative;
62
+ z-index: 1;
63
+ max-width: 1100px;
64
+ margin: 0 auto;
65
+ padding: 0 24px 80px;
66
+ }
67
+
68
+ /* HEADER */
69
+ header {
70
+ padding: 48px 0 40px;
71
+ border-bottom: 1px solid var(--border);
72
+ margin-bottom: 48px;
73
+ display: flex;
74
+ align-items: flex-end;
75
+ justify-content: space-between;
76
+ gap: 24px;
77
+ }
78
+
79
+ .brand {
80
+ display: flex;
81
+ flex-direction: column;
82
+ gap: 6px;
83
+ }
84
+
85
+ .brand-tag {
86
+ font-family: 'JetBrains Mono', monospace;
87
+ font-size: 11px;
88
+ color: var(--accent);
89
+ letter-spacing: 0.2em;
90
+ text-transform: uppercase;
91
+ }
92
+
93
+ h1 {
94
+ font-size: clamp(28px, 5vw, 44px);
95
+ font-weight: 800;
96
+ color: var(--heading);
97
+ line-height: 1.1;
98
+ letter-spacing: -0.02em;
99
+ }
100
+
101
+ h1 span {
102
+ color: var(--accent);
103
+ }
104
+
105
+ .header-meta {
106
+ font-family: 'JetBrains Mono', monospace;
107
+ font-size: 12px;
108
+ color: var(--muted);
109
+ text-align: right;
110
+ line-height: 1.8;
111
+ }
112
+
113
+ /* MAIN LAYOUT */
114
+ .layout {
115
+ display: grid;
116
+ grid-template-columns: 340px 1fr;
117
+ gap: 32px;
118
+ align-items: start;
119
+ }
120
+
121
+ @media (max-width: 768px) {
122
+ .layout { grid-template-columns: 1fr; }
123
+ header { flex-direction: column; align-items: flex-start; }
124
+ .header-meta { text-align: left; }
125
+ }
126
+
127
+ /* SIDEBAR / CONFIG PANEL */
128
+ .panel {
129
+ background: var(--surface);
130
+ border: 1px solid var(--border);
131
+ border-radius: 12px;
132
+ padding: 28px;
133
+ position: sticky;
134
+ top: 24px;
135
+ }
136
+
137
+ .panel-title {
138
+ font-family: 'JetBrains Mono', monospace;
139
+ font-size: 11px;
140
+ color: var(--accent);
141
+ letter-spacing: 0.18em;
142
+ text-transform: uppercase;
143
+ margin-bottom: 24px;
144
+ display: flex;
145
+ align-items: center;
146
+ gap: 8px;
147
+ }
148
+
149
+ .panel-title::before {
150
+ content: '//';
151
+ opacity: 0.5;
152
+ }
153
+
154
+ .field {
155
+ margin-bottom: 20px;
156
+ }
157
+
158
+ label {
159
+ display: block;
160
+ font-size: 12px;
161
+ font-weight: 600;
162
+ color: var(--muted);
163
+ letter-spacing: 0.08em;
164
+ text-transform: uppercase;
165
+ margin-bottom: 8px;
166
+ }
167
+
168
+ input, select, textarea {
169
+ width: 100%;
170
+ background: var(--surface2);
171
+ border: 1px solid var(--border);
172
+ border-radius: 8px;
173
+ color: var(--text);
174
+ font-family: 'JetBrains Mono', monospace;
175
+ font-size: 13px;
176
+ padding: 11px 14px;
177
+ outline: none;
178
+ transition: border-color 0.2s, box-shadow 0.2s;
179
+ appearance: none;
180
+ }
181
+
182
+ input::placeholder, textarea::placeholder { color: var(--muted); }
183
+
184
+ input:focus, select:focus, textarea:focus {
185
+ border-color: var(--accent);
186
+ box-shadow: 0 0 0 3px rgba(249,115,22,0.12);
187
+ }
188
+
189
+ select {
190
+ cursor: pointer;
191
+ background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='12' viewBox='0 0 24 24' fill='none' stroke='%2364748b' stroke-width='2'%3E%3Cpolyline points='6 9 12 15 18 9'/%3E%3C/svg%3E");
192
+ background-repeat: no-repeat;
193
+ background-position: right 12px center;
194
+ padding-right: 36px;
195
+ }
196
+
197
+ textarea { resize: vertical; min-height: 80px; line-height: 1.5; }
198
+
199
+ .api-key-wrap {
200
+ position: relative;
201
+ }
202
+
203
+ .api-key-wrap input { padding-right: 44px; }
204
+
205
+ .toggle-vis {
206
+ position: absolute;
207
+ right: 12px;
208
+ top: 50%;
209
+ transform: translateY(-50%);
210
+ background: none;
211
+ border: none;
212
+ cursor: pointer;
213
+ color: var(--muted);
214
+ padding: 4px;
215
+ display: flex;
216
+ align-items: center;
217
+ transition: color 0.2s;
218
+ }
219
+
220
+ .toggle-vis:hover { color: var(--text); }
221
+
222
+ /* GENERATE BUTTON */
223
+ .btn-generate {
224
+ width: 100%;
225
+ background: var(--accent);
226
+ color: #fff;
227
+ border: none;
228
+ border-radius: 8px;
229
+ font-family: 'Syne', sans-serif;
230
+ font-weight: 700;
231
+ font-size: 14px;
232
+ letter-spacing: 0.05em;
233
+ text-transform: uppercase;
234
+ padding: 14px;
235
+ cursor: pointer;
236
+ position: relative;
237
+ overflow: hidden;
238
+ transition: background 0.2s, transform 0.1s;
239
+ margin-top: 8px;
240
+ }
241
+
242
+ .btn-generate:hover { background: var(--accent2); }
243
+ .btn-generate:active { transform: scale(0.98); }
244
+ .btn-generate:disabled { opacity: 0.5; cursor: not-allowed; transform: none; }
245
+
246
+ .btn-generate .spinner {
247
+ display: none;
248
+ width: 16px;
249
+ height: 16px;
250
+ border: 2px solid rgba(255,255,255,0.3);
251
+ border-top-color: white;
252
+ border-radius: 50%;
253
+ animation: spin 0.7s linear infinite;
254
+ margin-right: 8px;
255
+ }
256
+
257
+ .btn-generate.loading .spinner { display: inline-block; }
258
+ .btn-generate.loading .btn-text::before { content: 'Generating'; }
259
+ .btn-generate:not(.loading) .btn-text::before { content: '⚡ Generate Prompt'; }
260
+
261
+ @keyframes spin { to { transform: rotate(360deg); } }
262
+
263
+ .btn-generate-inner {
264
+ display: flex;
265
+ align-items: center;
266
+ justify-content: center;
267
+ }
268
+
269
+ /* DIVIDER */
270
+ .divider {
271
+ border: none;
272
+ border-top: 1px solid var(--border);
273
+ margin: 20px 0;
274
+ }
275
+
276
+ .systems-presets {
277
+ display: flex;
278
+ flex-wrap: wrap;
279
+ gap: 6px;
280
+ margin-top: -8px;
281
+ }
282
+
283
+ .preset-chip {
284
+ font-family: 'JetBrains Mono', monospace;
285
+ font-size: 10px;
286
+ padding: 4px 10px;
287
+ border-radius: 20px;
288
+ border: 1px solid var(--border);
289
+ background: transparent;
290
+ color: var(--muted);
291
+ cursor: pointer;
292
+ transition: all 0.15s;
293
+ white-space: nowrap;
294
+ }
295
+
296
+ .preset-chip:hover {
297
+ border-color: var(--accent);
298
+ color: var(--accent);
299
+ background: rgba(249,115,22,0.06);
300
+ }
301
+
302
+ /* OUTPUT AREA */
303
+ .output-area {
304
+ min-height: 500px;
305
+ }
306
+
307
+ .output-header {
308
+ display: flex;
309
+ align-items: center;
310
+ justify-content: space-between;
311
+ margin-bottom: 24px;
312
+ }
313
+
314
+ .output-title {
315
+ font-size: 18px;
316
+ font-weight: 700;
317
+ color: var(--heading);
318
+ }
319
+
320
+ .output-actions {
321
+ display: flex;
322
+ gap: 8px;
323
+ }
324
+
325
+ .btn-sm {
326
+ font-family: 'JetBrains Mono', monospace;
327
+ font-size: 11px;
328
+ padding: 7px 14px;
329
+ border-radius: 6px;
330
+ border: 1px solid var(--border);
331
+ background: var(--surface);
332
+ color: var(--muted);
333
+ cursor: pointer;
334
+ transition: all 0.15s;
335
+ letter-spacing: 0.05em;
336
+ }
337
+
338
+ .btn-sm:hover { border-color: var(--accent); color: var(--accent); }
339
+
340
+ /* PLACEHOLDER */
341
+ .placeholder {
342
+ display: flex;
343
+ flex-direction: column;
344
+ align-items: center;
345
+ justify-content: center;
346
+ min-height: 420px;
347
+ border: 1px dashed var(--border);
348
+ border-radius: 12px;
349
+ gap: 16px;
350
+ }
351
+
352
+ .placeholder-icon {
353
+ font-size: 48px;
354
+ opacity: 0.3;
355
+ }
356
+
357
+ .placeholder p {
358
+ font-family: 'JetBrains Mono', monospace;
359
+ font-size: 13px;
360
+ color: var(--muted);
361
+ text-align: center;
362
+ line-height: 1.6;
363
+ }
364
+
365
+ /* LEVEL TABS */
366
+ .level-tabs {
367
+ display: flex;
368
+ gap: 0;
369
+ margin-bottom: 24px;
370
+ border-bottom: 1px solid var(--border);
371
+ }
372
+
373
+ .level-tab {
374
+ font-family: 'JetBrains Mono', monospace;
375
+ font-size: 12px;
376
+ font-weight: 700;
377
+ padding: 10px 20px;
378
+ border: none;
379
+ background: transparent;
380
+ color: var(--muted);
381
+ cursor: pointer;
382
+ border-bottom: 2px solid transparent;
383
+ margin-bottom: -1px;
384
+ transition: all 0.15s;
385
+ letter-spacing: 0.05em;
386
+ }
387
+
388
+ .level-tab:hover { color: var(--text); }
389
+
390
+ .level-tab.active {
391
+ color: var(--accent);
392
+ border-bottom-color: var(--accent);
393
+ }
394
+
395
+ .level-tab .level-badge {
396
+ display: inline-flex;
397
+ align-items: center;
398
+ justify-content: center;
399
+ width: 18px;
400
+ height: 18px;
401
+ border-radius: 4px;
402
+ font-size: 10px;
403
+ margin-right: 6px;
404
+ }
405
+
406
+ .level-tab[data-level="1"] .level-badge { background: rgba(34,197,94,0.15); color: var(--green); }
407
+ .level-tab[data-level="2"] .level-badge { background: rgba(56,189,248,0.15); color: var(--blue); }
408
+ .level-tab[data-level="3"] .level-badge { background: rgba(167,139,250,0.15); color: var(--purple); }
409
+ .level-tab[data-level="4"] .level-badge { background: rgba(249,115,22,0.15); color: var(--accent); }
410
+
411
+ /* LEVEL CONTENT PANELS */
412
+ .level-panel { display: none; }
413
+ .level-panel.active { display: block; animation: fadeUp 0.3s ease; }
414
+
415
+ @keyframes fadeUp {
416
+ from { opacity: 0; transform: translateY(8px); }
417
+ to { opacity: 1; transform: translateY(0); }
418
+ }
419
+
420
+ .level-card {
421
+ background: var(--surface);
422
+ border: 1px solid var(--border);
423
+ border-radius: 12px;
424
+ overflow: hidden;
425
+ }
426
+
427
+ .level-card-header {
428
+ padding: 20px 24px;
429
+ border-bottom: 1px solid var(--border);
430
+ display: flex;
431
+ align-items: center;
432
+ gap: 12px;
433
+ }
434
+
435
+ .level-dot {
436
+ width: 10px;
437
+ height: 10px;
438
+ border-radius: 50%;
439
+ }
440
+
441
+ [data-level="1"] .level-dot { background: var(--green); box-shadow: 0 0 8px var(--green); }
442
+ [data-level="2"] .level-dot { background: var(--blue); box-shadow: 0 0 8px var(--blue); }
443
+ [data-level="3"] .level-dot { background: var(--purple); box-shadow: 0 0 8px var(--purple); }
444
+ [data-level="4"] .level-dot { background: var(--accent); box-shadow: 0 0 8px var(--accent); }
445
+
446
+ .level-card-title {
447
+ font-size: 15px;
448
+ font-weight: 700;
449
+ color: var(--heading);
450
+ }
451
+
452
+ .level-card-subtitle {
453
+ font-family: 'JetBrains Mono', monospace;
454
+ font-size: 11px;
455
+ color: var(--muted);
456
+ margin-left: auto;
457
+ }
458
+
459
+ .level-card-body {
460
+ padding: 24px;
461
+ }
462
+
463
+ /* CONTENT SECTIONS */
464
+ .section {
465
+ margin-bottom: 24px;
466
+ }
467
+
468
+ .section:last-child { margin-bottom: 0; }
469
+
470
+ .section-label {
471
+ font-family: 'JetBrains Mono', monospace;
472
+ font-size: 10px;
473
+ letter-spacing: 0.15em;
474
+ text-transform: uppercase;
475
+ color: var(--muted);
476
+ margin-bottom: 10px;
477
+ display: flex;
478
+ align-items: center;
479
+ gap: 8px;
480
+ }
481
+
482
+ .section-label::after {
483
+ content: '';
484
+ flex: 1;
485
+ height: 1px;
486
+ background: var(--border);
487
+ }
488
+
489
+ .section p, .section li {
490
+ font-size: 14px;
491
+ line-height: 1.75;
492
+ color: var(--text);
493
+ }
494
+
495
+ .section ul {
496
+ list-style: none;
497
+ padding: 0;
498
+ display: flex;
499
+ flex-direction: column;
500
+ gap: 6px;
501
+ }
502
+
503
+ .section ul li::before {
504
+ content: '→';
505
+ color: var(--accent);
506
+ margin-right: 10px;
507
+ font-family: 'JetBrains Mono', monospace;
508
+ }
509
+
510
+ /* CODE BLOCKS */
511
+ pre, .code-block {
512
+ background: #060810;
513
+ border: 1px solid var(--border);
514
+ border-radius: 8px;
515
+ padding: 16px 18px;
516
+ overflow-x: auto;
517
+ font-family: 'JetBrains Mono', monospace;
518
+ font-size: 13px;
519
+ line-height: 1.65;
520
+ color: #c9d1d9;
521
+ position: relative;
522
+ }
523
+
524
+ .code-block-header {
525
+ display: flex;
526
+ align-items: center;
527
+ justify-content: space-between;
528
+ margin-bottom: 10px;
529
+ }
530
+
531
+ .code-lang {
532
+ font-family: 'JetBrains Mono', monospace;
533
+ font-size: 10px;
534
+ letter-spacing: 0.1em;
535
+ text-transform: uppercase;
536
+ color: var(--accent);
537
+ background: rgba(249,115,22,0.1);
538
+ padding: 2px 8px;
539
+ border-radius: 4px;
540
+ }
541
+
542
+ .copy-btn {
543
+ font-family: 'JetBrains Mono', monospace;
544
+ font-size: 10px;
545
+ padding: 3px 10px;
546
+ border-radius: 4px;
547
+ border: 1px solid var(--border);
548
+ background: var(--surface2);
549
+ color: var(--muted);
550
+ cursor: pointer;
551
+ transition: all 0.15s;
552
+ }
553
+
554
+ .copy-btn:hover { color: var(--green); border-color: var(--green); }
555
+ .copy-btn.copied { color: var(--green); border-color: var(--green); }
556
+
557
+ /* KEYWORD HIGHLIGHTING */
558
+ .kw-method { color: #38bdf8; }
559
+ .kw-type { color: #a78bfa; }
560
+ .kw-string { color: #86efac; }
561
+ .kw-comment { color: #475569; font-style: italic; }
562
+ .kw-num { color: #fb923c; }
563
+
564
+ /* SYSTEM INFO BANNER */
565
+ .system-banner {
566
+ background: linear-gradient(135deg, rgba(249,115,22,0.08), rgba(167,139,250,0.06));
567
+ border: 1px solid rgba(249,115,22,0.2);
568
+ border-radius: 10px;
569
+ padding: 16px 20px;
570
+ margin-bottom: 24px;
571
+ display: flex;
572
+ align-items: center;
573
+ gap: 14px;
574
+ }
575
+
576
+ .system-banner-icon {
577
+ font-size: 24px;
578
+ }
579
+
580
+ .system-banner-name {
581
+ font-size: 18px;
582
+ font-weight: 800;
583
+ color: var(--heading);
584
+ }
585
+
586
+ .system-banner-desc {
587
+ font-size: 13px;
588
+ color: var(--muted);
589
+ margin-top: 2px;
590
+ }
591
+
592
+ .difficulty-pills {
593
+ margin-left: auto;
594
+ display: flex;
595
+ gap: 6px;
596
+ }
597
+
598
+ .pill {
599
+ font-family: 'JetBrains Mono', monospace;
600
+ font-size: 10px;
601
+ padding: 3px 10px;
602
+ border-radius: 20px;
603
+ font-weight: 700;
604
+ }
605
+
606
+ .pill-easy { background: rgba(34,197,94,0.15); color: var(--green); }
607
+ .pill-med { background: rgba(56,189,248,0.15); color: var(--blue); }
608
+ .pill-hard { background: rgba(167,139,250,0.15); color: var(--purple); }
609
+ .pill-expert { background: rgba(249,115,22,0.15); color: var(--accent); }
610
+
611
+ /* ERROR */
612
+ .error-box {
613
+ background: rgba(248,113,113,0.08);
614
+ border: 1px solid rgba(248,113,113,0.25);
615
+ border-radius: 8px;
616
+ padding: 14px 18px;
617
+ font-family: 'JetBrains Mono', monospace;
618
+ font-size: 12px;
619
+ color: var(--red);
620
+ margin-bottom: 16px;
621
+ }
622
+
623
+ /* STREAM CURSOR */
624
+ .cursor {
625
+ display: inline-block;
626
+ width: 2px;
627
+ height: 1em;
628
+ background: var(--accent);
629
+ margin-left: 2px;
630
+ animation: blink 1s step-end infinite;
631
+ vertical-align: text-bottom;
632
+ }
633
+
634
+ @keyframes blink { 0%,100%{opacity:1} 50%{opacity:0} }
635
+
636
+ /* RAW VIEW */
637
+ .raw-view {
638
+ display: none;
639
+ background: #060810;
640
+ border: 1px solid var(--border);
641
+ border-radius: 12px;
642
+ padding: 24px;
643
+ font-family: 'JetBrains Mono', monospace;
644
+ font-size: 12px;
645
+ line-height: 1.7;
646
+ color: #c9d1d9;
647
+ white-space: pre-wrap;
648
+ word-break: break-word;
649
+ max-height: 600px;
650
+ overflow-y: auto;
651
+ }
652
+
653
+ .raw-view.visible { display: block; }
654
+
655
+ /* FOOTER */
656
+ footer {
657
+ margin-top: 60px;
658
+ border-top: 1px solid var(--border);
659
+ padding-top: 24px;
660
+ display: flex;
661
+ align-items: center;
662
+ justify-content: space-between;
663
+ font-family: 'JetBrains Mono', monospace;
664
+ font-size: 11px;
665
+ color: var(--muted);
666
+ }
667
+
668
+ footer a { color: var(--accent); text-decoration: none; }
669
+ </style>
670
+ </head>
671
+ <body>
672
+ <div class="container">
673
+ <header>
674
+ <div class="brand">
675
+ <div class="brand-tag">// codesignal · oop systems design</div>
676
+ <h1>CodeSignal<br><span>Prompt</span> Generator</h1>
677
+ </div>
678
+ <div class="header-meta">
679
+ Powered by GPT-4o<br>
680
+ OOP System Design<br>
681
+ 4-Level Interview Format
682
+ </div>
683
+ </header>
684
+
685
+ <div class="layout">
686
+ <!-- SIDEBAR -->
687
+ <aside>
688
+ <div class="panel">
689
+ <div class="panel-title">Configuration</div>
690
+
691
+ <div class="field">
692
+ <label>System Name</label>
693
+ <input type="text" id="systemName" placeholder="e.g. LRU Cache" />
694
+ </div>
695
+
696
+ <div class="field">
697
+ <label>Quick Presets</label>
698
+ <div class="systems-presets">
699
+ <button class="preset-chip" onclick="setPreset('Time-Based Key-Value Store')">KV Store</button>
700
+ <button class="preset-chip" onclick="setPreset('In-Memory Database')">In-Memory DB</button>
701
+ <button class="preset-chip" onclick="setPreset('LRU / LFU Cache')">LRU/LFU Cache</button>
702
+ <button class="preset-chip" onclick="setPreset('C-Like Memory Allocator')">Allocator</button>
703
+ <button class="preset-chip" onclick="setPreset('Type Inference Engine')">Type Inference</button>
704
+ <button class="preset-chip" onclick="setPreset('Circuit Breaker')">Circuit Breaker</button>
705
+ <button class="preset-chip" onclick="setPreset('API Gateway with Rate Limiting')">API Gateway</button>
706
+ <button class="preset-chip" onclick="setPreset('Thread Pool / Task Scheduler')">Thread Pool</button>
707
+ <button class="preset-chip" onclick="setPreset('Transaction / Credit System')">Transaction</button>
708
+ <button class="preset-chip" onclick="setPreset('Employee Management System')">Employee Mgmt</button>
709
+ </div>
710
+ </div>
711
+
712
+ <div class="field">
713
+ <label>Brief Description <span style="color:var(--muted);font-weight:400">(optional)</span></label>
714
+ <textarea id="systemDesc" placeholder="Any extra context or constraints for this system..."></textarea>
715
+ </div>
716
+
717
+ <hr class="divider">
718
+
719
+ <div class="field">
720
+ <label>OpenAI API Key</label>
721
+ <div class="api-key-wrap">
722
+ <input type="password" id="apiKey" placeholder="sk-..." autocomplete="off" />
723
+ <button class="toggle-vis" onclick="toggleKey()" title="Show/hide key">
724
+ <svg id="eyeIcon" xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
725
+ <path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"/><circle cx="12" cy="12" r="3"/>
726
+ </svg>
727
+ </button>
728
+ </div>
729
+ </div>
730
+
731
+ <div class="field">
732
+ <label>Model</label>
733
+ <select id="modelSelect">
734
+ <option value="gpt-4o">gpt-4o (recommended)</option>
735
+ <option value="gpt-4o-mini">gpt-4o-mini (faster)</option>
736
+ <option value="gpt-4-turbo">gpt-4-turbo</option>
737
+ <option value="gpt-4">gpt-4</option>
738
+ </select>
739
+ </div>
740
+
741
+ <button class="btn-generate" id="generateBtn" onclick="generate()">
742
+ <div class="btn-generate-inner">
743
+ <span class="spinner"></span>
744
+ <span class="btn-text"></span>
745
+ </div>
746
+ </button>
747
+ </div>
748
+ </aside>
749
+
750
+ <!-- OUTPUT -->
751
+ <main class="output-area">
752
+ <div class="output-header">
753
+ <div class="output-title">Generated Prompt</div>
754
+ <div class="output-actions" id="outputActions" style="display:none">
755
+ <button class="btn-sm" onclick="toggleRaw()">⊞ Raw</button>
756
+ <button class="btn-sm" onclick="copyAll()">⎘ Copy All</button>
757
+ </div>
758
+ </div>
759
+
760
+ <div id="errorBox" class="error-box" style="display:none"></div>
761
+
762
+ <div id="placeholder" class="placeholder">
763
+ <div class="placeholder-icon">⚙</div>
764
+ <p>Enter a system name and your OpenAI key,<br>then click Generate to build your interview prompt.</p>
765
+ </div>
766
+
767
+ <!-- STRUCTURED OUTPUT -->
768
+ <div id="structuredOutput" style="display:none">
769
+ <div class="system-banner" id="systemBanner">
770
+ <div class="system-banner-icon" id="bannerIcon">🏗️</div>
771
+ <div>
772
+ <div class="system-banner-name" id="bannerName"></div>
773
+ <div class="system-banner-desc" id="bannerDesc"></div>
774
+ </div>
775
+ <div class="difficulty-pills">
776
+ <span class="pill pill-easy">L1 Easy</span>
777
+ <span class="pill pill-med">L2 Medium</span>
778
+ <span class="pill pill-hard">L3 Hard</span>
779
+ <span class="pill pill-expert">L4 Expert</span>
780
+ </div>
781
+ </div>
782
+
783
+ <div class="level-tabs">
784
+ <button class="level-tab active" data-level="1" onclick="switchLevel(1)">
785
+ <span class="level-badge">1</span>Foundation
786
+ </button>
787
+ <button class="level-tab" data-level="2" onclick="switchLevel(2)">
788
+ <span class="level-badge">2</span>Extended
789
+ </button>
790
+ <button class="level-tab" data-level="3" onclick="switchLevel(3)">
791
+ <span class="level-badge">3</span>Concurrent
792
+ </button>
793
+ <button class="level-tab" data-level="4" onclick="switchLevel(4)">
794
+ <span class="level-badge">4</span>Production
795
+ </button>
796
+ </div>
797
+
798
+ <div id="lvl1" class="level-panel active" data-level="1"></div>
799
+ <div id="lvl2" class="level-panel" data-level="2"></div>
800
+ <div id="lvl3" class="level-panel" data-level="3"></div>
801
+ <div id="lvl4" class="level-panel" data-level="4"></div>
802
+ </div>
803
+
804
+ <!-- RAW OUTPUT -->
805
+ <div id="rawOutput" class="raw-view"></div>
806
+ </main>
807
+ </div>
808
+
809
+ <footer>
810
+ <span>CodeSignal-style Interview Prompt Generator</span>
811
+ <span>4-Level OOP Systems Design · <a href="https://platform.openai.com/docs" target="_blank">OpenAI Docs ↗</a></span>
812
+ </footer>
813
+ </div>
814
+
815
+ <script>
816
+ const LEVEL_DESCRIPTIONS = ['Foundation', 'Extended APIs', 'Concurrency', 'Production-Ready'];
817
+ const LEVEL_ICONS = ['🟢', '🔵', '🟣', '🟠'];
818
+ const SYSTEM_ICONS = {
819
+ 'cache': '🗃️', 'store': '📦', 'database': '🗄️', 'memory': '💾',
820
+ 'allocator': '⚙️', 'type': '🔍', 'circuit': '⚡', 'gateway': '🚦',
821
+ 'thread': '🧵', 'task': '📋', 'transaction': '💳', 'credit': '💰',
822
+ 'employee': '👥', 'default': '🏗️'
823
+ };
824
+
825
+ let rawText = '';
826
+ let showingRaw = false;
827
+ let levels = { 1: '', 2: '', 3: '', 4: '' };
828
+
829
+ function setPreset(name) {
830
+ document.getElementById('systemName').value = name;
831
+ }
832
+
833
+ function toggleKey() {
834
+ const inp = document.getElementById('apiKey');
835
+ inp.type = inp.type === 'password' ? 'text' : 'password';
836
+ }
837
+
838
+ function getSystemIcon(name) {
839
+ const lower = name.toLowerCase();
840
+ for (const [k, v] of Object.entries(SYSTEM_ICONS)) {
841
+ if (lower.includes(k)) return v;
842
+ }
843
+ return SYSTEM_ICONS.default;
844
+ }
845
+
846
+ function switchLevel(num) {
847
+ document.querySelectorAll('.level-tab').forEach(t => t.classList.toggle('active', parseInt(t.dataset.level) === num));
848
+ document.querySelectorAll('.level-panel').forEach(p => p.classList.toggle('active', p.id === `lvl${num}`));
849
+ }
850
+
851
+ function toggleRaw() {
852
+ showingRaw = !showingRaw;
853
+ document.getElementById('rawOutput').classList.toggle('visible', showingRaw);
854
+ document.getElementById('structuredOutput').style.display = showingRaw ? 'none' : 'block';
855
+ document.querySelector('[onclick="toggleRaw()"]').textContent = showingRaw ? '⊞ Structured' : '⊞ Raw';
856
+ }
857
+
858
+ async function copyAll() {
859
+ try {
860
+ await navigator.clipboard.writeText(rawText);
861
+ const btn = document.querySelector('[onclick="copyAll()"]');
862
+ btn.textContent = '✓ Copied!';
863
+ setTimeout(() => btn.textContent = '⎘ Copy All', 2000);
864
+ } catch (e) {}
865
+ }
866
+
867
+ function copyCode(btn, text) {
868
+ navigator.clipboard.writeText(text).then(() => {
869
+ btn.textContent = '✓ Copied';
870
+ btn.classList.add('copied');
871
+ setTimeout(() => { btn.textContent = 'Copy'; btn.classList.remove('copied'); }, 2000);
872
+ });
873
+ }
874
+
875
+ function buildLevelCard(levelNum, content) {
876
+ const descriptions = ['Basic Functionality & Core Classes', 'Constraints & Additional APIs', 'Concurrency & Performance', 'Extensibility & Production Requirements'];
877
+ const colors = ['var(--green)', 'var(--blue)', 'var(--purple)', 'var(--accent)'];
878
+
879
+ const card = document.createElement('div');
880
+ card.className = 'level-card';
881
+ card.dataset.level = levelNum;
882
+
883
+ const sections = parseContent(content);
884
+
885
+ card.innerHTML = `
886
+ <div class="level-card-header" data-level="${levelNum}">
887
+ <div class="level-dot"></div>
888
+ <div class="level-card-title">Level ${levelNum} — ${descriptions[levelNum - 1]}</div>
889
+ <div class="level-card-subtitle">${LEVEL_ICONS[levelNum - 1]} ${LEVEL_DESCRIPTIONS[levelNum - 1]}</div>
890
+ </div>
891
+ <div class="level-card-body">
892
+ ${sections}
893
+ </div>`;
894
+
895
+ return card;
896
+ }
897
+
898
+ function parseContent(text) {
899
+ // Detect code blocks
900
+ const parts = text.split(/(```[\s\S]*?```)/g);
901
+ let out = '';
902
+
903
+ for (const part of parts) {
904
+ if (part.startsWith('```')) {
905
+ const lines = part.split('\n');
906
+ const lang = lines[0].replace('```', '').trim() || 'code';
907
+ const code = lines.slice(1, -1).join('\n');
908
+ const id = Math.random().toString(36).substr(2, 8);
909
+ out += `
910
+ <div class="section">
911
+ <div class="code-block-header">
912
+ <span class="code-lang">${lang}</span>
913
+ <button class="copy-btn" onclick="copyCode(this, ${JSON.stringify(code)})">Copy</button>
914
+ </div>
915
+ <pre>${escapeHtml(code)}</pre>
916
+ </div>`;
917
+ } else {
918
+ out += convertMarkdown(part);
919
+ }
920
+ }
921
+ return out;
922
+ }
923
+
924
+ function convertMarkdown(text) {
925
+ const lines = text.split('\n');
926
+ let out = '';
927
+ let inList = false;
928
+ let listItems = [];
929
+
930
+ const flushList = () => {
931
+ if (listItems.length) {
932
+ out += `<div class="section"><ul>${listItems.map(li => `<li>${li}</li>`).join('')}</ul></div>`;
933
+ listItems = [];
934
+ }
935
+ inList = false;
936
+ };
937
+
938
+ for (let i = 0; i < lines.length; i++) {
939
+ const line = lines[i];
940
+ const trimmed = line.trim();
941
+
942
+ if (!trimmed) {
943
+ if (inList) flushList();
944
+ continue;
945
+ }
946
+
947
+ // Section labels (##, ###, ####)
948
+ if (/^#{2,4}\s/.test(trimmed)) {
949
+ if (inList) flushList();
950
+ const label = trimmed.replace(/^#{2,4}\s/, '');
951
+ out += `<div class="section"><div class="section-label">${label}</div></div>`;
952
+ continue;
953
+ }
954
+
955
+ // Bullet points
956
+ if (/^[-*]\s/.test(trimmed)) {
957
+ inList = true;
958
+ const item = trimmed.replace(/^[-*]\s/, '').replace(/`([^`]+)`/g, '<code style="font-family:JetBrains Mono,monospace;background:#060810;padding:1px 5px;border-radius:3px;font-size:12px;color:#38bdf8">$1</code>').replace(/\*\*([^*]+)\*\*/g, '<strong>$1</strong>');
959
+ listItems.push(item);
960
+ continue;
961
+ }
962
+
963
+ if (inList) flushList();
964
+
965
+ // Bold **text**
966
+ const processed = trimmed
967
+ .replace(/`([^`]+)`/g, '<code style="font-family:JetBrains Mono,monospace;background:#060810;padding:1px 5px;border-radius:3px;font-size:12px;color:#38bdf8">$1</code>')
968
+ .replace(/\*\*([^*]+)\*\*/g, '<strong style="color:var(--heading)">$1</strong>');
969
+
970
+ out += `<div class="section"><p>${processed}</p></div>`;
971
+ }
972
+
973
+ if (inList) flushList();
974
+ return out;
975
+ }
976
+
977
+ function escapeHtml(s) {
978
+ return s.replace(/&/g,'&amp;').replace(/</g,'&lt;').replace(/>/g,'&gt;');
979
+ }
980
+
981
+ function parseLevels(text) {
982
+ const result = { 1: '', 2: '', 3: '', 4: '' };
983
+
984
+ // Try to split on Level N headers
985
+ const levelRegex = /(?:^|\n)(?:#{1,4}\s*)?Level\s*(\d)[\s\S]*?(?=\n(?:#{1,4}\s*)?Level\s*\d|$)/gi;
986
+ let match;
987
+ while ((match = levelRegex.exec(text)) !== null) {
988
+ const num = parseInt(match[1]);
989
+ if (num >= 1 && num <= 4) {
990
+ result[num] = match[0].trim();
991
+ }
992
+ }
993
+
994
+ // If nothing found, try to split by "---" or lines starting with ## Level
995
+ if (!result[1]) {
996
+ const chunks = text.split(/\n#{1,3}\s*Level/i);
997
+ for (let i = 1; i < chunks.length && i <= 4; i++) {
998
+ result[i] = ('Level' + chunks[i]).trim();
999
+ }
1000
+ }
1001
+
1002
+ // Fallback: split evenly
1003
+ if (!result[1]) {
1004
+ const quarterLen = Math.floor(text.length / 4);
1005
+ for (let i = 1; i <= 4; i++) {
1006
+ result[i] = text.slice((i - 1) * quarterLen, i * quarterLen);
1007
+ }
1008
+ }
1009
+
1010
+ return result;
1011
+ }
1012
+
1013
+ async function generate() {
1014
+ const systemName = document.getElementById('systemName').value.trim();
1015
+ const apiKey = document.getElementById('apiKey').value.trim();
1016
+ const desc = document.getElementById('systemDesc').value.trim();
1017
+ const model = document.getElementById('modelSelect').value;
1018
+
1019
+ const errorBox = document.getElementById('errorBox');
1020
+ errorBox.style.display = 'none';
1021
+
1022
+ if (!systemName) {
1023
+ errorBox.textContent = '⚠ Please enter a system name.';
1024
+ errorBox.style.display = 'block';
1025
+ return;
1026
+ }
1027
+ if (!apiKey || !apiKey.startsWith('sk-')) {
1028
+ errorBox.textContent = '⚠ Please enter a valid OpenAI API key starting with sk-';
1029
+ errorBox.style.display = 'block';
1030
+ return;
1031
+ }
1032
+
1033
+ const btn = document.getElementById('generateBtn');
1034
+ btn.disabled = true;
1035
+ btn.classList.add('loading');
1036
+ document.getElementById('placeholder').style.display = 'none';
1037
+ document.getElementById('structuredOutput').style.display = 'none';
1038
+ document.getElementById('rawOutput').classList.remove('visible');
1039
+ document.getElementById('outputActions').style.display = 'none';
1040
+ rawText = '';
1041
+ showingRaw = false;
1042
+
1043
+ const prompt = buildPrompt(systemName, desc);
1044
+
1045
+ try {
1046
+ const response = await fetch('https://api.openai.com/v1/chat/completions', {
1047
+ method: 'POST',
1048
+ headers: {
1049
+ 'Content-Type': 'application/json',
1050
+ 'Authorization': `Bearer ${apiKey}`
1051
+ },
1052
+ body: JSON.stringify({
1053
+ model,
1054
+ messages: [{ role: 'user', content: prompt }],
1055
+ stream: true,
1056
+ temperature: 0.7,
1057
+ max_tokens: 4096
1058
+ })
1059
+ });
1060
+
1061
+ if (!response.ok) {
1062
+ const err = await response.json();
1063
+ throw new Error(err.error?.message || `HTTP ${response.status}`);
1064
+ }
1065
+
1066
+ // Show streaming raw view first
1067
+ document.getElementById('rawOutput').classList.add('visible');
1068
+ document.getElementById('rawOutput').textContent = '';
1069
+ showingRaw = true;
1070
+
1071
+ const reader = response.body.getReader();
1072
+ const decoder = new TextDecoder();
1073
+
1074
+ while (true) {
1075
+ const { done, value } = await reader.read();
1076
+ if (done) break;
1077
+ const chunk = decoder.decode(value);
1078
+ const lines = chunk.split('\n').filter(l => l.startsWith('data: ') && l !== 'data: [DONE]');
1079
+ for (const line of lines) {
1080
+ try {
1081
+ const data = JSON.parse(line.slice(6));
1082
+ const delta = data.choices?.[0]?.delta?.content || '';
1083
+ rawText += delta;
1084
+ document.getElementById('rawOutput').textContent = rawText;
1085
+ } catch {}
1086
+ }
1087
+ }
1088
+
1089
+ // Parse and render structured output
1090
+ renderStructured(systemName, desc);
1091
+
1092
+ } catch (e) {
1093
+ errorBox.textContent = `⚠ Error: ${e.message}`;
1094
+ errorBox.style.display = 'block';
1095
+ document.getElementById('rawOutput').classList.remove('visible');
1096
+ document.getElementById('placeholder').style.display = 'flex';
1097
+ } finally {
1098
+ btn.disabled = false;
1099
+ btn.classList.remove('loading');
1100
+ }
1101
+ }
1102
+
1103
+ function renderStructured(systemName, desc) {
1104
+ // Switch to structured view
1105
+ document.getElementById('rawOutput').classList.remove('visible');
1106
+ showingRaw = false;
1107
+
1108
+ // Setup banner
1109
+ document.getElementById('bannerIcon').textContent = getSystemIcon(systemName);
1110
+ document.getElementById('bannerName').textContent = systemName;
1111
+ document.getElementById('bannerDesc').textContent = desc || 'CodeSignal-style 4-level OOP interview prompt';
1112
+
1113
+ // Parse levels
1114
+ const parsedLevels = parseLevels(rawText);
1115
+
1116
+ for (let i = 1; i <= 4; i++) {
1117
+ const container = document.getElementById(`lvl${i}`);
1118
+ container.innerHTML = '';
1119
+ const card = buildLevelCard(i, parsedLevels[i]);
1120
+ container.appendChild(card);
1121
+ }
1122
+
1123
+ switchLevel(1);
1124
+
1125
+ document.getElementById('structuredOutput').style.display = 'block';
1126
+ document.getElementById('outputActions').style.display = 'flex';
1127
+ document.getElementById('rawOutput').textContent = rawText;
1128
+
1129
+ // Update raw ref
1130
+ document.querySelector('[onclick="toggleRaw()"]').textContent = '⊞ Raw';
1131
+ }
1132
+
1133
+ function buildPrompt(systemName, description) {
1134
+ const descPart = description ? `\nAdditional context for this system: ${description}\n` : '';
1135
+ return `You are an interview question designer.
1136
+ For the system listed below, generate a **CodeSignal-style 4-level coding prompt** that incrementally builds an object-oriented system.
1137
+
1138
+ ### System
1139
+ - ${systemName}
1140
+ ${descPart}
1141
+ ### Requirements
1142
+ - Generate **4 levels**, where:
1143
+ - **Level 1**: Basic functionality and core classes (single-threaded, minimal features)
1144
+ - **Level 2**: Adds constraints, edge cases, or additional APIs
1145
+ - **Level 3**: Introduces concurrency, performance constraints, or correctness guarantees
1146
+ - **Level 4**: Extensibility or production-like requirements (pluggability, configuration, failure handling)
1147
+ - Each level must include:
1148
+ - A clear problem statement
1149
+ - Required public methods and their signatures (use code blocks with \`\`\`python or \`\`\`java)
1150
+ - Explicit constraints and assumptions
1151
+ - Example inputs/outputs or representative test cases (in code blocks)
1152
+ - Keep the scope realistic for a **45–60 minute interview**.
1153
+ - Focus on **class design, APIs, and invariants**, not UI or persistence.
1154
+ - Do **not** include the solution—only the prompt.
1155
+
1156
+ ### Output Format
1157
+ - Use clear section headers for each level: ## Level 1, ## Level 2, ## Level 3, ## Level 4
1158
+ - Under each level use subsections: ### Problem Statement, ### API, ### Constraints, ### Examples
1159
+ - Keep descriptions concise and interview-realistic.`;
1160
+ }
1161
+ </script>
1162
+ </body>
1163
+ </html>