gabriel / musehub public
_ci.scss
1,686 lines 44.4 KB
Raw
sha256:9590cee1e0ccd6c76528f005b95d634d80f5019f0dcb7c371e149adc31d1fb65 refactor: enforce gRPC framing on all MWP wire traffic Sonnet 4.6 minor ⚠ breaking 156 days ago
1 /* ── MuseHub CI: Actions runs list and run detail pages ──────────────────── */
2
3 /* ── Status colour tokens ── */
4 :root {
5 --ci-success: #3fb950;
6 --ci-failure: #f85149;
7 --ci-running: #4f8ef7; /* Muse brand blue — active/in-progress */
8 --ci-pending: #8b949e;
9 --ci-cancelled: #6e7681;
10 --ci-skipped: #6e7681;
11 }
12
13 /* ─────────────────────────────────────────────────────────────────────────── */
14 /* CI icon helpers */
15 /* ─────────────────────────────────────────────────────────────────────────── */
16 .ci-icon { flex-shrink: 0; }
17 .ci-icon--success { stroke: var(--ci-success); }
18 .ci-icon--failure { stroke: var(--ci-failure); }
19 .ci-icon--running { stroke: var(--ci-running); }
20 .ci-icon--pending { stroke: var(--ci-pending); }
21 .ci-icon--cancelled { stroke: var(--ci-cancelled); }
22 .ci-icon--skipped { stroke: var(--ci-skipped); }
23
24 @keyframes ci-spin {
25 to { transform: rotate(360deg); }
26 }
27 .ci-spin { animation: ci-spin 1.2s linear infinite; }
28
29 /* ─────────────────────────────────────────────────────────────────────────── */
30 /* Actions runs list page (.cir-*) */
31 /* */
32 /* Visual language: gradient hero + status-accented cards. */
33 /* Follows the same design system as the MCP and Releases pages. */
34 /* ─────────────────────────────────────────────────────────────────────────── */
35
36 // ── Hero ──────────────────────────────────────────────────────────────────────
37 .cir-hero {
38 position: relative;
39 background: linear-gradient(135deg, #0d1117 0%, #0f1923 50%, #0d1117 100%);
40 border-bottom: 1px solid var(--border-default);
41 overflow: hidden;
42 // Bleed to page edges (container has horizontal padding)
43 margin: 0 calc(-1 * var(--space-4));
44 padding: 0 var(--space-4);
45 }
46
47 .cir-hero-glow {
48 position: absolute;
49 inset: 0;
50 pointer-events: none;
51 background:
52 radial-gradient(ellipse 60% 90% at 85% 30%, rgba(79,142,247,0.09) 0%, transparent 65%),
53 radial-gradient(ellipse 40% 60% at 10% 80%, rgba(167,139,250,0.06) 0%, transparent 60%);
54 }
55
56 .cir-hero-inner {
57 position: relative;
58 display: flex;
59 align-items: center;
60 justify-content: space-between;
61 gap: var(--space-6);
62 padding: var(--space-8) 0 var(--space-6);
63 flex-wrap: wrap;
64 }
65
66 .cir-hero-left { flex: 1; min-width: 0; }
67
68 .cir-hero-eyebrow {
69 display: inline-flex;
70 align-items: center;
71 gap: 7px;
72 font-size: 11px;
73 font-weight: 700;
74 text-transform: uppercase;
75 letter-spacing: 0.09em;
76 color: var(--ci-running);
77 margin-bottom: var(--space-2);
78 }
79
80 // Pulsing dot shown when any run is active
81 .cir-live-dot {
82 width: 6px;
83 height: 6px;
84 border-radius: 50%;
85 background: var(--ci-running);
86 box-shadow: 0 0 8px var(--ci-running);
87 animation: cir-pulse 2s ease-in-out infinite;
88 }
89 .cir-live-dot--idle {
90 background: var(--text-disabled);
91 box-shadow: none;
92 animation: none;
93 }
94 @keyframes cir-pulse {
95 0%, 100% { opacity: 1; transform: scale(1); }
96 50% { opacity: 0.5; transform: scale(0.8); }
97 }
98
99 .cir-hero-title {
100 font-size: clamp(24px, 3.5vw, 36px);
101 font-weight: 800;
102 letter-spacing: -0.02em;
103 line-height: 1.1;
104 margin: 0 0 var(--space-2);
105 color: var(--text-primary);
106
107 .gradient-text {
108 background: var(--gradient-accent);
109 -webkit-background-clip: text;
110 -webkit-text-fill-color: transparent;
111 background-clip: text;
112 }
113 }
114
115 .cir-hero-sub {
116 font-size: 13px;
117 color: var(--text-muted);
118 margin: 0;
119 display: flex;
120 align-items: center;
121 gap: 6px;
122 }
123
124 .cir-hero-repo {
125 font-family: var(--font-mono);
126 font-size: 13px;
127 color: var(--color-accent-link);
128 text-decoration: none;
129 &:hover { text-decoration: underline; }
130 }
131
132 // Stat pills (right side of hero)
133 .cir-stats {
134 display: flex;
135 gap: var(--space-3);
136 flex-wrap: wrap;
137 flex-shrink: 0;
138 }
139
140 .cir-stat {
141 display: flex;
142 flex-direction: column;
143 align-items: center;
144 gap: 3px;
145 padding: var(--space-3) var(--space-4);
146 background: rgba(255, 255, 255, 0.03);
147 border: 1px solid var(--border-subtle);
148 border-radius: var(--radius-base);
149 min-width: 72px;
150 text-align: center;
151 transition: border-color var(--transition-fast);
152
153 &:hover { border-color: var(--border-muted); }
154
155 &--success { border-top: 2px solid var(--ci-success); }
156 &--failure { border-top: 2px solid var(--ci-failure); }
157 &--running { border-top: 2px solid var(--ci-running); }
158 }
159
160 .cir-stat-num {
161 font-family: var(--font-mono);
162 font-size: 20px;
163 font-weight: 700;
164 line-height: 1;
165 color: var(--text-primary);
166 }
167
168 .cir-stat-label {
169 font-size: 10px;
170 font-weight: 600;
171 text-transform: uppercase;
172 letter-spacing: 0.06em;
173 color: var(--text-muted);
174 }
175
176 // ── Filter strip ──────────────────────────────────────────────────────────────
177 .cir-filter-strip {
178 display: flex;
179 align-items: center;
180 gap: var(--space-3);
181 flex-wrap: wrap;
182 padding: var(--space-4) 0;
183 border-bottom: 1px solid var(--border-subtle);
184 }
185
186 .cir-filter-group {
187 display: flex;
188 align-items: center;
189 gap: var(--space-2);
190 }
191
192 .cir-filter-label {
193 font-size: 12px;
194 font-weight: 500;
195 color: var(--text-muted);
196 white-space: nowrap;
197 }
198
199 .cir-filter-select {
200 font-family: var(--font-sans);
201 font-size: 13px;
202 background: var(--bg-overlay);
203 border: 1px solid var(--border-default);
204 border-radius: var(--radius-base);
205 color: var(--text-primary);
206 padding: 5px 28px 5px 10px;
207 appearance: none;
208 background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='10' height='6' viewBox='0 0 10 6'%3E%3Cpath fill='%238b949e' d='M0 0l5 6 5-6z'/%3E%3C/svg%3E");
209 background-repeat: no-repeat;
210 background-position: right 9px center;
211 cursor: pointer;
212 transition: border-color var(--transition-fast), background var(--transition-fast);
213
214 &:hover { border-color: var(--border-muted); }
215 &:focus { outline: 2px solid rgba(79,142,247,0.5); outline-offset: 1px; border-color: var(--color-accent); }
216 }
217
218 .cir-filter-branch-pill {
219 display: inline-flex;
220 align-items: center;
221 gap: 6px;
222 font-family: var(--font-mono);
223 font-size: 12px;
224 color: var(--color-accent-link);
225 background: rgba(88, 166, 255, 0.08);
226 border: 1px solid rgba(88, 166, 255, 0.2);
227 border-radius: var(--radius-full);
228 padding: 3px 10px 3px 8px;
229 }
230
231 .cir-filter-branch-clear {
232 display: inline-flex;
233 align-items: center;
234 justify-content: center;
235 width: 14px;
236 height: 14px;
237 border-radius: 50%;
238 background: rgba(88, 166, 255, 0.15);
239 color: var(--color-accent-link);
240 text-decoration: none;
241 font-size: 11px;
242 line-height: 1;
243 font-weight: 700;
244 &:hover { background: rgba(88, 166, 255, 0.3); }
245 }
246
247 .cir-filter-spacer { flex: 1; }
248
249 .cir-filter-count {
250 font-size: 12px;
251 color: var(--text-muted);
252 white-space: nowrap;
253 }
254
255 // ── Run list ──────────────────────────────────────────────────────────────────
256 .cir-run-list {
257 display: flex;
258 flex-direction: column;
259 gap: var(--space-2);
260 padding: var(--space-4) 0;
261 }
262
263 .cir-run {
264 display: grid;
265 grid-template-columns: 36px 1fr auto;
266 align-items: center;
267 gap: var(--space-4);
268 padding: var(--space-4) var(--space-4);
269 background: var(--bg-surface);
270 border: 1px solid var(--border-subtle);
271 border-radius: var(--radius-lg);
272 text-decoration: none;
273 color: inherit;
274 transition:
275 background var(--transition-fast),
276 border-color var(--transition-fast),
277 box-shadow var(--transition-fast);
278 border-left: 3px solid transparent;
279 position: relative;
280 overflow: hidden;
281
282 &:hover {
283 background: var(--bg-overlay);
284 border-color: var(--border-default);
285 box-shadow: var(--shadow-sm);
286 }
287
288 // Status accent — left border + subtle background tint on hover
289 &--success {
290 border-left-color: var(--ci-success);
291 &:hover { background: rgba(63, 185, 80, 0.04); }
292 }
293 &--failure {
294 border-left-color: var(--ci-failure);
295 &:hover { background: rgba(248, 81, 73, 0.04); }
296 }
297 &--running,
298 &--queued {
299 border-left-color: var(--ci-running);
300 &:hover { background: rgba(79, 142, 247, 0.04); }
301 }
302 &--pending {
303 border-left-color: var(--border-default);
304 }
305 &--cancelled {
306 border-left-color: var(--ci-cancelled);
307 opacity: 0.75;
308 &:hover { opacity: 1; }
309 }
310 }
311
312 // Status icon circle
313 .cir-run-icon {
314 display: flex;
315 align-items: center;
316 justify-content: center;
317 width: 36px;
318 height: 36px;
319 border-radius: 50%;
320 flex-shrink: 0;
321
322 .cir-run--success & { background: rgba(63, 185, 80, 0.12); }
323 .cir-run--failure & { background: rgba(248, 81, 73, 0.12); }
324 .cir-run--running &,
325 .cir-run--queued & { background: rgba(79, 142, 247, 0.12); }
326 .cir-run--pending & { background: rgba(139, 148, 158, 0.10);}
327 .cir-run--cancelled & { background: rgba(110, 118, 129, 0.10);}
328 }
329
330 // Main content column
331 .cir-run-body {
332 min-width: 0;
333 display: flex;
334 flex-direction: column;
335 gap: 4px;
336 }
337
338 .cir-run-name {
339 font-size: 14px;
340 font-weight: 600;
341 color: var(--text-primary);
342 white-space: nowrap;
343 overflow: hidden;
344 text-overflow: ellipsis;
345 line-height: 1.3;
346 }
347
348 .cir-run-meta {
349 display: flex;
350 align-items: center;
351 flex-wrap: wrap;
352 gap: 5px;
353 font-size: 12px;
354 color: var(--text-muted);
355 line-height: 1.4;
356 }
357
358 .cir-run-sep {
359 opacity: 0.3;
360 font-size: 10px;
361 }
362
363 // Trigger badge
364 .cir-trigger {
365 display: inline-flex;
366 align-items: center;
367 gap: 4px;
368 font-size: 11px;
369 font-weight: 600;
370 padding: 2px 7px;
371 border-radius: var(--radius-full);
372
373 &--push {
374 background: rgba(79, 142, 247, 0.12);
375 color: var(--color-accent-link);
376 border: 1px solid rgba(79, 142, 247, 0.2);
377 }
378 &--proposal {
379 background: rgba(188, 140, 255, 0.12);
380 color: var(--color-purple);
381 border: 1px solid rgba(188, 140, 255, 0.2);
382 }
383 &--manual {
384 background: rgba(139, 148, 158, 0.1);
385 color: var(--text-muted);
386 border: 1px solid var(--border-subtle);
387 }
388 }
389
390 .cir-run-branch {
391 font-family: var(--font-mono);
392 font-size: 11px;
393 color: var(--text-secondary);
394 max-width: 200px;
395 overflow: hidden;
396 text-overflow: ellipsis;
397 white-space: nowrap;
398 }
399
400 .cir-run-commit {
401 font-family: var(--font-mono);
402 font-size: 11px;
403 color: var(--color-accent-link);
404 }
405
406 .cir-run-actor {
407 font-size: 12px;
408 color: var(--text-muted);
409 }
410
411 // Right column: status pill + time
412 .cir-run-aside {
413 display: flex;
414 flex-direction: column;
415 align-items: flex-end;
416 gap: 6px;
417 flex-shrink: 0;
418 min-width: 100px;
419 }
420
421 .cir-status-pill {
422 display: inline-flex;
423 align-items: center;
424 gap: 5px;
425 font-size: 11px;
426 font-weight: 600;
427 padding: 3px 9px;
428 border-radius: var(--radius-full);
429 white-space: nowrap;
430
431 &--success { background: rgba(63,185,80,0.12); color: var(--ci-success); border: 1px solid rgba(63,185,80,0.25); }
432 &--failure { background: rgba(248,81,73,0.12); color: var(--ci-failure); border: 1px solid rgba(248,81,73,0.25); }
433 &--running,
434 &--queued { background: rgba(79,142,247,0.12); color: var(--ci-running); border: 1px solid rgba(79,142,247,0.25); }
435 &--pending { background: rgba(139,148,158,0.1); color: var(--text-muted); border: 1px solid var(--border-subtle); }
436 &--cancelled { background: rgba(110,118,129,0.1); color: var(--ci-cancelled); border: 1px solid var(--border-subtle); }
437 }
438
439 // Animated dot inside a running pill
440 .cir-running-dot {
441 width: 6px;
442 height: 6px;
443 border-radius: 50%;
444 background: currentColor;
445 animation: cir-pulse 1.5s ease-in-out infinite;
446 }
447
448 .cir-run-time {
449 font-size: 11px;
450 color: var(--text-disabled);
451 white-space: nowrap;
452 }
453
454 // ── Pagination ────────────────────────────────────────────────────────────────
455 .cir-pagination {
456 display: flex;
457 align-items: center;
458 justify-content: center;
459 gap: var(--space-3);
460 padding: var(--space-4) 0 var(--space-2);
461 }
462
463 .cir-page-btn {
464 display: inline-flex;
465 align-items: center;
466 gap: 6px;
467 font-size: 13px;
468 font-weight: 500;
469 color: var(--text-secondary);
470 background: var(--bg-surface);
471 border: 1px solid var(--border-default);
472 border-radius: var(--radius-base);
473 padding: 6px 14px;
474 text-decoration: none;
475 transition: background var(--transition-fast), color var(--transition-fast), border-color var(--transition-fast);
476
477 &:hover {
478 background: var(--bg-overlay);
479 border-color: var(--border-muted);
480 color: var(--text-primary);
481 }
482 }
483
484 .cir-page-info {
485 font-size: 12px;
486 color: var(--text-muted);
487 }
488
489 // ── Empty state ───────────────────────────────────────────────────────────────
490 .cir-empty {
491 display: flex;
492 flex-direction: column;
493 align-items: center;
494 gap: var(--space-4);
495 padding: 80px var(--space-4);
496 text-align: center;
497 }
498
499 .cir-empty-icon {
500 width: 56px;
501 height: 56px;
502 border-radius: 50%;
503 background: rgba(79, 142, 247, 0.08);
504 border: 1px solid rgba(79, 142, 247, 0.15);
505 display: flex;
506 align-items: center;
507 justify-content: center;
508 svg { stroke: var(--color-accent); }
509 }
510
511 .cir-empty-title {
512 font-size: 16px;
513 font-weight: 600;
514 color: var(--text-primary);
515 margin: 0;
516 }
517
518 .cir-empty-body {
519 font-size: 13px;
520 color: var(--text-muted);
521 margin: 0;
522 max-width: 380px;
523 line-height: 1.6;
524 code {
525 font-family: var(--font-mono);
526 font-size: 12px;
527 background: var(--bg-overlay);
528 border: 1px solid var(--border-subtle);
529 border-radius: var(--radius-sm);
530 padding: 1px 5px;
531 color: var(--color-accent-link);
532 }
533 }
534
535 // ── Page wrapper ──────────────────────────────────────────────────────────────
536 .cir-page {
537 display: flex;
538 flex-direction: column;
539 }
540
541 /* ─────────────────────────────────────────────────────────────────────────── */
542 /* LEGACY list-page classes (replaced by .cir-* above — kept as empty tombstones
543 so old server-rendered HTML doesn't break while the template is being updated)
544 /* ─────────────────────────────────────────────────────────────────────────── */
545 .ci-runs-page {}
546 .ci-runs-header {}
547 .ci-runs-title {}
548 .ci-runs-subtitle {}
549 .ci-filter-bar {}
550 .ci-filter-group {}
551 .ci-filter-label {}
552 .ci-filter-select {}
553 .ci-filter-active {}
554 .ci-filter-clear {}
555 .ci-run-list {}
556 .ci-run-row {}
557 .ci-run-status-icon {}
558 .ci-run-main {}
559 .ci-run-name {}
560 .ci-run-meta {}
561 .ci-run-sep {}
562 .ci-run-trigger {}
563 .ci-run-commit {}
564 .ci-run-right {}
565 .ci-run-status {
566 font-size: 0.75rem;
567 font-weight: 600;
568 border-radius: 20px;
569 padding: 0.15rem 0.5rem;
570
571 &--success { background: rgba(63,185,80,0.15); color: var(--ci-success); }
572 &--failure { background: rgba(248,81,73,0.15); color: var(--ci-failure); }
573 &--running { background: rgba(210,153,34,0.15); color: var(--ci-running); }
574 &--queued { background: rgba(210,153,34,0.1); color: var(--ci-running); }
575 &--pending { background: rgba(139,148,158,0.15); color: var(--ci-pending); }
576 &--cancelled { background: rgba(110,118,129,0.15); color: var(--ci-cancelled); }
577 }
578
579 .ci-run-time {
580 font-size: 0.75rem;
581 color: var(--text-muted);
582 }
583
584 /* Pagination */
585 .ci-pagination {
586 display: flex;
587 align-items: center;
588 justify-content: center;
589 gap: 1rem;
590 margin-top: 1.25rem;
591 font-size: 0.875rem;
592 }
593
594 .ci-page-btn {
595 color: var(--accent);
596 text-decoration: none;
597 padding: 0.375rem 0.75rem;
598 border: 1px solid var(--border-default);
599 border-radius: 6px;
600 transition: background 0.12s ease;
601
602 &:hover { background: var(--bg-hover); }
603 }
604
605 .ci-page-info {
606 color: var(--text-secondary);
607 }
608
609 /* Empty state */
610 .ci-runs-empty {
611 display: flex;
612 flex-direction: column;
613 align-items: center;
614 justify-content: center;
615 gap: 0.75rem;
616 padding: 4rem 2rem;
617 text-align: center;
618 color: var(--text-secondary);
619 border: 1px solid var(--border-default);
620 border-radius: 8px;
621
622 svg { opacity: 0.3; }
623
624 p { margin: 0; }
625 }
626
627 .ci-runs-empty-hint {
628 font-size: 0.875rem;
629
630 code {
631 background: var(--bg-overlay);
632 border-radius: 4px;
633 padding: 0.1rem 0.3rem;
634 font-family: var(--font-mono);
635 font-size: 0.8125rem;
636 }
637 }
638
639 /* ─────────────────────────────────────────────────────────────────────────── */
640 /* CI Run detail — two-pane layout (.cird-*) */
641 /* */
642 /* All class names use the "cird-" prefix to avoid collisions with the */
643 /* older .ci-* classes used by the runs list. */
644 /* Tokens used here are confirmed to exist in _tokens.scss. */
645 /* ─────────────────────────────────────────────────────────────────────────── */
646
647 /* Outer wrapper — no extra padding needed (page-container strips it) */
648 .cird {
649 display: flex;
650 flex-direction: column;
651 min-height: 0;
652 background: var(--bg-base);
653 }
654
655 /* ── Top bar ──────────────────────────────────────────────────────────────── */
656 .cird-topbar {
657 display: flex;
658 align-items: center;
659 gap: var(--space-4);
660 padding: var(--space-4) var(--space-5);
661 background: var(--bg-surface);
662 border-bottom: 1px solid var(--border-default);
663 position: sticky;
664 top: 0;
665 z-index: var(--z-raised);
666 flex-wrap: wrap;
667 }
668
669 .cird-back {
670 display: flex;
671 align-items: center;
672 gap: var(--space-1);
673 font-size: 12px;
674 color: var(--text-muted);
675 text-decoration: none;
676 white-space: nowrap;
677 flex-shrink: 0;
678 &:hover { color: var(--text-primary); }
679 }
680
681 .cird-topbar-main {
682 display: flex;
683 align-items: center;
684 gap: var(--space-2);
685 flex-shrink: 0;
686 }
687
688 .cird-run-icon { display: flex; align-items: center; flex-shrink: 0; }
689
690 .cird-icon {
691 display: block;
692 &--success { stroke: var(--ci-success); }
693 &--failure { stroke: var(--ci-failure); }
694 &--running { stroke: var(--ci-running); }
695 &--pending { stroke: var(--ci-pending); }
696 &--cancelled{ stroke: var(--ci-cancelled); }
697 }
698
699 .cird-title {
700 font-size: 15px;
701 font-weight: 600;
702 color: var(--text-primary);
703 margin: 0;
704 white-space: nowrap;
705 }
706
707 .cird-topbar-meta {
708 display: flex;
709 align-items: center;
710 gap: var(--space-2);
711 flex: 1;
712 flex-wrap: wrap;
713 font-size: 12px;
714 color: var(--text-muted);
715 }
716
717 .cird-trigger-badge {
718 font-size: 10px;
719 font-weight: 600;
720 padding: 2px 7px;
721 border-radius: var(--radius-full);
722 white-space: nowrap;
723 &--push { background: rgba(88,166,255,.15); color: #58a6ff; }
724 &--proposal { background: rgba(188,140,255,.15); color: #bc8cff; }
725 &--manual { background: rgba(210,153,34,.15); color: #e3b341; }
726 }
727
728 .cird-meta-link {
729 color: var(--color-accent-link);
730 text-decoration: none;
731 &:hover { text-decoration: underline; }
732 }
733 .cird-commit { font-family: var(--font-mono); font-size: 11px; }
734 .cird-sep { color: var(--border-muted); }
735
736 .cird-topbar-end {
737 display: flex;
738 align-items: center;
739 gap: var(--space-3);
740 flex-shrink: 0;
741 }
742
743 .cird-status-pill {
744 font-size: 11px;
745 font-weight: 700;
746 padding: 3px 10px;
747 border-radius: var(--radius-full);
748 &--success { background: rgba(63,185,80,.15); color: var(--ci-success); }
749 &--failure { background: rgba(248,81,73,.15); color: var(--ci-failure); }
750 &--running,
751 &--queued,
752 &--pending { background: rgba(210,153,34,.15); color: var(--ci-running); }
753 &--cancelled { background: rgba(110,118,129,.15); color: var(--ci-cancelled); }
754 }
755
756 .cird-total-dur {
757 font-size: 12px;
758 font-family: var(--font-mono);
759 color: var(--text-muted);
760 }
761
762 /* ── Two-pane body ────────────────────────────────────────────────────────── */
763 .cird-body {
764 display: flex;
765 flex: 1;
766 min-height: calc(100vh - 110px);
767 align-items: stretch;
768 }
769
770 /* ── Left sidebar ─────────────────────────────────────────────────────────── */
771 .cird-sidebar {
772 width: 220px;
773 flex-shrink: 0;
774 border-right: 1px solid var(--border-default);
775 background: var(--bg-surface);
776 padding: var(--space-3) 0;
777 position: sticky;
778 top: 56px; /* below the sticky top bar */
779 height: calc(100vh - 56px);
780 overflow-y: auto;
781 display: flex;
782 flex-direction: column;
783 gap: 2px;
784 }
785
786 .cird-sidebar-title {
787 font-size: 11px;
788 font-weight: 600;
789 color: var(--text-muted);
790 text-transform: uppercase;
791 letter-spacing: 0.06em;
792 padding: 0 var(--space-4) var(--space-2);
793 }
794
795 .cird-job-btn {
796 display: flex;
797 align-items: center;
798 gap: var(--space-2);
799 padding: 8px var(--space-4);
800 margin: 0 var(--space-2);
801 border-radius: var(--radius-base);
802 border: none;
803 background: transparent;
804 cursor: pointer;
805 width: calc(100% - 16px);
806 text-align: left;
807 font-size: 13px;
808 font-family: var(--font-sans);
809 color: var(--text-secondary);
810 transition: background var(--transition-fast), color var(--transition-fast);
811
812 &:hover { background: var(--bg-hover); color: var(--text-primary); }
813
814 &--active {
815 background: var(--bg-hover);
816 color: var(--text-primary);
817 font-weight: 500;
818 /* GitHub-style: blue left border on the active job */
819 box-shadow: inset 3px 0 0 var(--color-accent);
820 }
821
822 /* Icon colour per status */
823 &--success .cird-job-btn-icon svg { stroke: var(--ci-success); }
824 &--failure .cird-job-btn-icon svg { stroke: var(--ci-failure); }
825 &--running .cird-job-btn-icon svg,
826 &--queued .cird-job-btn-icon svg { stroke: var(--ci-running); }
827 &--skipped .cird-job-btn-icon svg { stroke: var(--ci-skipped); }
828 &--pending .cird-job-btn-icon svg { stroke: var(--ci-pending); }
829 &--cancelled .cird-job-btn-icon svg{ stroke: var(--ci-cancelled); }
830 }
831
832 .cird-job-btn-icon { flex-shrink: 0; display: flex; align-items: center; }
833 .cird-job-btn-name { flex: 1; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; font-size: 13px; }
834 .cird-job-btn-dur {
835 font-size: 11px;
836 font-family: var(--font-mono);
837 color: var(--text-muted);
838 flex-shrink: 0;
839 }
840
841 .cird-live-pulse {
842 font-size: 10px;
843 color: var(--ci-running);
844 animation: ci-pulse 1.5s ease-in-out infinite;
845 }
846 @keyframes ci-pulse { 0%, 100% { opacity: 1; } 50% { opacity: 0.3; } }
847
848 /* ── Main pane ────────────────────────────────────────────────────────────── */
849 .cird-main {
850 flex: 1;
851 min-width: 0;
852 background: var(--bg-base);
853 }
854
855 .cird-job-panel { display: block; }
856 .cird-job-panel[hidden] { display: none; }
857
858 /* Job header strip */
859 .cird-job-header {
860 display: flex;
861 align-items: center;
862 justify-content: space-between;
863 padding: var(--space-4) var(--space-5);
864 background: var(--bg-surface);
865 border-bottom: 1px solid var(--border-default);
866 }
867
868 .cird-job-header-left {
869 display: flex;
870 align-items: center;
871 gap: var(--space-3);
872 }
873
874 .cird-job-header-name { font-weight: 600; font-size: 14px; color: var(--text-primary); }
875
876 .cird-job-image, .cird-job-needs {
877 font-size: 11px;
878 font-family: var(--font-mono);
879 color: var(--text-muted);
880 background: var(--bg-overlay);
881 padding: 2px 6px;
882 border-radius: var(--radius-sm);
883 }
884
885 .cird-job-header-dur {
886 font-size: 12px;
887 font-family: var(--font-mono);
888 color: var(--text-muted);
889 }
890 .cird-live { color: var(--ci-running); }
891
892 /* ── Step list ────────────────────────────────────────────────────────────── */
893 .cird-step-list {
894 display: flex;
895 flex-direction: column;
896 }
897
898 .cird-step {
899 border-bottom: 1px solid var(--border-subtle);
900 &:last-child { border-bottom: none; }
901
902 /* Left accent bar per status */
903 &--failure { border-left: 3px solid var(--ci-failure); }
904 &--running,
905 &--queued { border-left: 3px solid var(--ci-running); }
906 &--success { border-left: 3px solid transparent; }
907 }
908
909 /* Step row button — full width, hover highlights entire row */
910 .cird-step-row {
911 display: flex;
912 align-items: center;
913 gap: var(--space-2);
914 padding: 10px var(--space-5);
915 background: none;
916 border: none;
917 width: 100%;
918 cursor: pointer;
919 text-align: left;
920 color: var(--text-secondary);
921 font-size: 13px;
922 font-family: var(--font-sans);
923 transition: background var(--transition-fast);
924
925 &:hover { background: var(--bg-hover); color: var(--text-primary); }
926 &[aria-expanded="true"] { background: var(--bg-overlay); }
927 }
928
929 /* Expand chevron — rotates when row is open */
930 .cird-step-expand {
931 flex-shrink: 0;
932 stroke: var(--text-muted);
933 transition: transform var(--transition-base);
934 }
935 .cird-step--open .cird-step-expand { transform: rotate(90deg); }
936
937 /* Status icon in the step row */
938 .cird-step-status-icon {
939 flex-shrink: 0;
940 display: flex;
941 align-items: center;
942 .si-success { stroke: var(--ci-success); }
943 .si-failure { stroke: var(--ci-failure); }
944 .si-running { stroke: var(--ci-running); }
945 .si-skipped { stroke: var(--ci-skipped); }
946 .si-pending { stroke: var(--ci-pending); }
947 .si-cancelled { stroke: var(--ci-cancelled); }
948 }
949
950 .cird-step-name {
951 flex: 1;
952 font-family: var(--font-mono);
953 font-size: 12px;
954 overflow: hidden;
955 text-overflow: ellipsis;
956 white-space: nowrap;
957 }
958
959 .cird-step-row-end {
960 display: flex;
961 align-items: center;
962 gap: var(--space-2);
963 flex-shrink: 0;
964 margin-left: var(--space-2);
965 }
966
967 .cird-step-exit {
968 font-size: 11px;
969 font-family: var(--font-mono);
970 color: var(--ci-failure);
971 background: rgba(248,81,73,.12);
972 padding: 1px 6px;
973 border-radius: var(--radius-sm);
974 }
975
976 .cird-step-dur {
977 font-size: 12px;
978 font-family: var(--font-mono);
979 color: var(--text-muted);
980 min-width: 32px;
981 text-align: right;
982 }
983
984 /* ── Log panel ────────────────────────────────────────────────────────────── */
985 .cird-log-panel {
986 background: #0d1117;
987 border-top: 1px solid var(--border-subtle);
988 }
989 .cird-log-panel[hidden] { display: none; }
990
991 .cird-log-cmd {
992 display: flex;
993 align-items: baseline;
994 gap: var(--space-2);
995 padding: var(--space-2) var(--space-5);
996 background: rgba(255,255,255,.03);
997 border-bottom: 1px solid rgba(255,255,255,.05);
998 font-family: var(--font-mono);
999 font-size: 12px;
1000 color: #b1bac4;
1001 }
1002 .cird-log-prompt { color: #3fb950; font-weight: 700; margin-right: 4px; }
1003
1004 .cird-log-toolbar {
1005 display: flex;
1006 justify-content: flex-end;
1007 padding: var(--space-1) var(--space-4);
1008 background: rgba(255,255,255,.02);
1009 }
1010
1011 .cird-log-copy {
1012 display: flex;
1013 align-items: center;
1014 gap: 4px;
1015 font-size: 11px;
1016 color: var(--text-muted);
1017 background: none;
1018 border: 1px solid var(--border-default);
1019 border-radius: var(--radius-sm);
1020 padding: 3px 8px;
1021 cursor: pointer;
1022 font-family: var(--font-sans);
1023 transition: color var(--transition-fast), border-color var(--transition-fast);
1024 &:hover { color: var(--text-primary); border-color: var(--border-muted); }
1025 }
1026
1027 .cird-log-pre {
1028 margin: 0;
1029 padding: var(--space-3) var(--space-5);
1030 font-family: var(--font-mono);
1031 font-size: 12px;
1032 line-height: 1.65;
1033 color: #e6edf3;
1034 white-space: pre-wrap;
1035 word-break: break-all;
1036 max-height: 600px;
1037 overflow-y: auto;
1038 }
1039
1040 /* ── Empty state ──────────────────────────────────────────────────────────── */
1041 .cird-empty {
1042 display: flex;
1043 flex-direction: column;
1044 align-items: center;
1045 gap: var(--space-3);
1046 padding: 80px var(--space-4);
1047 color: var(--text-muted);
1048 text-align: center;
1049 svg { stroke: var(--text-muted); opacity: .35; }
1050 p { margin: 0; font-size: 14px; }
1051 }
1052
1053 /* ── Responsive ───────────────────────────────────────────────────────────── */
1054 @media (max-width: 768px) {
1055 .cird-body { flex-direction: column; }
1056 .cird-sidebar {
1057 width: 100%;
1058 position: static;
1059 height: auto;
1060 border-right: none;
1061 border-bottom: 1px solid var(--border-default);
1062 }
1063 }
1064
1065 /* ─────────────────────────────────────────────────────────────────────────── */
1066 /* OLD ci-detail-* classes removed — replaced by .cird-* above */
1067 /* ── Proposal-detail CI run list ─────────────────────────────────────────── */
1068 .proposal-ci-row {
1069 display: flex;
1070 align-items: center;
1071 gap: var(--space-2);
1072 padding: 7px 0;
1073 border-bottom: 1px solid var(--border-subtle);
1074 font-size: 12px;
1075 &:last-child { border-bottom: none; }
1076 }
1077 .proposal-ci-name { flex: 1; font-weight: 500; color: var(--text-primary); }
1078 .proposal-ci-dur { font-family: var(--font-mono); font-size: 11px; color: var(--text-muted); }
1079 .proposal-ci-link {
1080 font-size: 11px;
1081 color: var(--color-accent);
1082 text-decoration: none;
1083 &:hover { text-decoration: underline; }
1084 }
1085 .proposal-ci-dot {
1086 width: 8px;
1087 height: 8px;
1088 border-radius: 50%;
1089 flex-shrink: 0;
1090 &.proposal-ci-dot--success { background: var(--ci-success); }
1091 &.proposal-ci-dot--failure { background: var(--ci-failure); }
1092 &.proposal-ci-dot--running,
1093 &.proposal-ci-dot--queued { background: var(--ci-running); }
1094 &.proposal-ci-dot--skipped { background: var(--text-muted); }
1095 }
1096 .proposal-ci-pill {
1097 display: inline-flex;
1098 align-items: center;
1099 font-size: 10px;
1100 font-weight: 600;
1101 padding: 3px 8px;
1102 border-radius: 4px;
1103 &.proposal-ci-pill--success { background: rgba(63,185,80, 0.12); color: var(--ci-success); border: 1px solid rgba(63,185,80, 0.3); }
1104 &.proposal-ci-pill--failure { background: rgba(248,81,73, 0.12); color: var(--ci-failure); border: 1px solid rgba(248,81,73, 0.3); }
1105 &.proposal-ci-pill--running,
1106 &.proposal-ci-pill--queued { background: rgba(47,129,247, 0.12); color: var(--ci-running); border: 1px solid rgba(47,129,247, 0.3); }
1107 }
1108 .proposal-ci-state {
1109 font-size: 10px;
1110 font-weight: 600;
1111 font-family: var(--font-mono);
1112 &.proposal-ci-state--success { color: var(--ci-success); }
1113 &.proposal-ci-state--failure { color: var(--ci-failure); }
1114 &.proposal-ci-state--running,
1115 &.proposal-ci-state--queued { color: var(--ci-running); }
1116 }
1117 .proposal-ci-val {
1118 &.proposal-ci-val--success { color: var(--ci-success); }
1119 &.proposal-ci-val--failure { color: var(--ci-failure); }
1120 &.proposal-ci-val--running,
1121 &.proposal-ci-val--queued { color: var(--ci-running); }
1122 }
1123
1124 // ─────────────────────────────────────────────────────────────────────────────
1125 // Selective CI badge + gate warning (CI runs list, .cir-* namespace)
1126 // ─────────────────────────────────────────────────────────────────────────────
1127
1128 .cir-selective-badge {
1129 display: inline-flex;
1130 align-items: center;
1131 gap: 4px;
1132 font-size: 10px;
1133 font-weight: 600;
1134 font-family: var(--font-mono);
1135 padding: 2px 7px;
1136 border-radius: 4px;
1137 background: rgba(79, 142, 247, 0.10);
1138 color: var(--color-accent);
1139 border: 1px solid rgba(79, 142, 247, 0.25);
1140 white-space: nowrap;
1141 svg { opacity: 0.8; flex-shrink: 0; }
1142 }
1143
1144 .cir-gate-warn {
1145 display: inline-flex;
1146 align-items: center;
1147 gap: 4px;
1148 font-size: 10px;
1149 font-weight: 600;
1150 padding: 2px 7px;
1151 border-radius: 4px;
1152 background: rgba(210, 153, 34, 0.12);
1153 color: var(--color-warning);
1154 border: 1px solid rgba(210, 153, 34, 0.30);
1155 white-space: nowrap;
1156 svg { opacity: 0.9; flex-shrink: 0; }
1157 }
1158
1159 .cir-gates-link {
1160 display: inline-flex;
1161 align-items: center;
1162 gap: 5px;
1163 font-size: 12px;
1164 color: var(--text-muted);
1165 text-decoration: none;
1166 padding: 4px 8px;
1167 border-radius: 5px;
1168 border: 1px solid var(--border-subtle);
1169 background: transparent;
1170 transition: color 0.15s, border-color 0.15s;
1171 svg { opacity: 0.6; flex-shrink: 0; }
1172 &:hover {
1173 color: var(--text-primary);
1174 border-color: var(--border-default);
1175 }
1176 }
1177
1178 // ─────────────────────────────────────────────────────────────────────────────
1179 // Gate results band (CI run detail, .cird-gate-* namespace)
1180 // ─────────────────────────────────────────────────────────────────────────────
1181
1182 .cird-gate-band {
1183 display: flex;
1184 align-items: center;
1185 gap: 8px;
1186 flex-wrap: wrap;
1187 padding: 10px 24px;
1188 border-bottom: 1px solid var(--border-subtle);
1189 background: var(--bg-surface);
1190 }
1191
1192 .cird-gate-band-label {
1193 display: inline-flex;
1194 align-items: center;
1195 gap: 5px;
1196 font-size: 11px;
1197 font-weight: 600;
1198 color: var(--text-muted);
1199 text-transform: uppercase;
1200 letter-spacing: 0.06em;
1201 margin-right: 4px;
1202 svg { opacity: 0.5; }
1203 }
1204
1205 .cird-gate-chip {
1206 display: inline-flex;
1207 align-items: center;
1208 gap: 4px;
1209 font-size: 11px;
1210 font-weight: 600;
1211 padding: 3px 9px;
1212 border-radius: 4px;
1213
1214 &.cird-gate-chip--pass {
1215 background: rgba(63, 185, 80, 0.10);
1216 color: var(--ci-success);
1217 border: 1px solid rgba(63, 185, 80, 0.25);
1218 }
1219 &.cird-gate-chip--fail {
1220 background: rgba(248, 81, 73, 0.12);
1221 color: var(--ci-failure);
1222 border: 1px solid rgba(248, 81, 73, 0.30);
1223 }
1224 &.cird-gate-chip--skip {
1225 background: rgba(139, 148, 158, 0.10);
1226 color: var(--text-muted);
1227 border: 1px solid var(--border-subtle);
1228 }
1229 &.cird-gate-chip--error {
1230 background: rgba(210, 153, 34, 0.10);
1231 color: var(--color-warning);
1232 border: 1px solid rgba(210, 153, 34, 0.25);
1233 }
1234 }
1235
1236 .cird-gate-band-config {
1237 margin-left: auto;
1238 font-size: 11px;
1239 color: var(--text-muted);
1240 text-decoration: none;
1241 &:hover { color: var(--color-accent-link); text-decoration: underline; }
1242 }
1243
1244 // ─────────────────────────────────────────────────────────────────────────────
1245 // Symbol → Test Mapping panel (CI run detail, .cird-tm-* namespace)
1246 // ─────────────────────────────────────────────────────────────────────────────
1247
1248 .cird-tm {
1249 margin: 0;
1250 border-top: 1px solid var(--border-subtle);
1251 background: var(--bg-base);
1252
1253 &[open] .cird-tm-chevron { transform: rotate(90deg); }
1254 }
1255
1256 .cird-tm-summary {
1257 display: flex;
1258 align-items: center;
1259 gap: 8px;
1260 padding: 12px 24px;
1261 cursor: pointer;
1262 font-size: 13px;
1263 font-weight: 600;
1264 color: var(--text-secondary);
1265 user-select: none;
1266 list-style: none;
1267 background: var(--bg-surface);
1268 border-bottom: 1px solid var(--border-subtle);
1269
1270 &::-webkit-details-marker { display: none; }
1271 &:hover { background: var(--bg-overlay); }
1272 }
1273
1274 .cird-tm-chevron {
1275 flex-shrink: 0;
1276 opacity: 0.5;
1277 transition: transform 0.15s ease;
1278 }
1279
1280 .cird-tm-stat {
1281 margin-left: 6px;
1282 font-size: 11px;
1283 font-weight: 400;
1284 color: var(--text-muted);
1285 }
1286
1287 .cird-tm-body {
1288 padding: 16px 24px;
1289 display: flex;
1290 flex-direction: column;
1291 gap: 20px;
1292 }
1293
1294 .cird-tm-coverage {
1295 display: flex;
1296 align-items: center;
1297 gap: 10px;
1298 }
1299
1300 .cird-tm-coverage-label {
1301 font-size: 11px;
1302 font-weight: 600;
1303 color: var(--text-muted);
1304 text-transform: uppercase;
1305 letter-spacing: 0.06em;
1306 white-space: nowrap;
1307 }
1308
1309 .cird-tm-bar {
1310 flex: 1;
1311 height: 6px;
1312 border-radius: 3px;
1313 background: var(--bg-overlay);
1314 overflow: hidden;
1315 }
1316
1317 .cird-tm-bar-fill {
1318 height: 100%;
1319 border-radius: 3px;
1320 background: linear-gradient(90deg, var(--color-accent) 0%, var(--ci-success) 100%);
1321 transition: width 0.4s ease;
1322 }
1323
1324 .cird-tm-coverage-pct {
1325 font-size: 13px;
1326 font-weight: 700;
1327 color: var(--text-primary);
1328 min-width: 36px;
1329 text-align: right;
1330 }
1331
1332 .cird-tm-coverage-frac {
1333 font-size: 11px;
1334 color: var(--text-muted);
1335 font-family: var(--font-mono);
1336 }
1337
1338 .cird-tm-section {
1339 display: flex;
1340 flex-direction: column;
1341 gap: 8px;
1342
1343 &.cird-tm-section--warn .cird-tm-section-title {
1344 color: var(--color-warning);
1345 svg { vertical-align: middle; }
1346 }
1347 }
1348
1349 .cird-tm-section-title {
1350 font-size: 11px;
1351 font-weight: 600;
1352 text-transform: uppercase;
1353 letter-spacing: 0.06em;
1354 color: var(--text-muted);
1355 display: flex;
1356 align-items: center;
1357 gap: 5px;
1358 }
1359
1360 .cird-tm-test-list {
1361 display: flex;
1362 flex-direction: column;
1363 gap: 4px;
1364 }
1365
1366 .cird-tm-test {
1367 display: flex;
1368 align-items: baseline;
1369 gap: 8px;
1370 font-size: 12px;
1371 padding: 4px 0;
1372 border-bottom: 1px solid var(--border-subtle);
1373 &:last-child { border-bottom: none; }
1374 }
1375
1376 .cird-tm-confidence {
1377 font-family: var(--font-mono);
1378 font-size: 10px;
1379 letter-spacing: -1px;
1380 flex-shrink: 0;
1381 &.cird-tm-confidence--high { color: var(--ci-success); }
1382 &.cird-tm-confidence--med { color: var(--color-warning); }
1383 &.cird-tm-confidence--low { color: var(--text-muted); }
1384 }
1385
1386 .cird-tm-test-id {
1387 font-family: var(--font-mono);
1388 font-size: 11px;
1389 color: var(--text-primary);
1390 flex: 1;
1391 min-width: 0;
1392 overflow: hidden;
1393 text-overflow: ellipsis;
1394 white-space: nowrap;
1395 }
1396
1397 .cird-tm-test-via {
1398 font-size: 10px;
1399 color: var(--text-muted);
1400 font-family: var(--font-mono);
1401 white-space: nowrap;
1402 flex-shrink: 0;
1403 }
1404
1405 .cird-tm-test-reason {
1406 font-size: 10px;
1407 color: var(--text-muted);
1408 white-space: nowrap;
1409 flex-shrink: 0;
1410 }
1411
1412 .cird-tm-addr-list {
1413 display: flex;
1414 flex-wrap: wrap;
1415 gap: 6px;
1416 }
1417
1418 .cird-tm-addr {
1419 font-family: var(--font-mono);
1420 font-size: 11px;
1421 padding: 2px 8px;
1422 border-radius: 4px;
1423
1424 &.cird-tm-addr--uncovered {
1425 background: rgba(248, 81, 73, 0.08);
1426 color: var(--ci-failure);
1427 border: 1px solid rgba(248, 81, 73, 0.20);
1428 }
1429 }
1430
1431 // ─────────────────────────────────────────────────────────────────────────────
1432 // CI Gates configuration page (.cig-* namespace)
1433 // ─────────────────────────────────────────────────────────────────────────────
1434
1435 .cig-page {
1436 max-width: 860px;
1437 margin: 0 auto;
1438 padding: var(--space-6) var(--space-4);
1439 }
1440
1441 .cig-hero {
1442 position: relative;
1443 overflow: hidden;
1444 border-radius: 10px;
1445 border: 1px solid var(--border-subtle);
1446 background: var(--bg-surface);
1447 margin-bottom: var(--space-6);
1448 }
1449
1450 .cig-hero-glow {
1451 position: absolute;
1452 inset: 0;
1453 background: radial-gradient(ellipse at 80% 50%, rgba(79, 142, 247, 0.06) 0%, transparent 60%);
1454 pointer-events: none;
1455 }
1456
1457 .cig-hero-inner {
1458 position: relative;
1459 display: flex;
1460 align-items: flex-start;
1461 justify-content: space-between;
1462 gap: var(--space-4);
1463 padding: var(--space-6);
1464 }
1465
1466 .cig-hero-eyebrow {
1467 display: flex;
1468 align-items: center;
1469 gap: 6px;
1470 font-size: 11px;
1471 font-weight: 600;
1472 text-transform: uppercase;
1473 letter-spacing: 0.08em;
1474 color: var(--text-muted);
1475 margin-bottom: var(--space-2);
1476 svg { opacity: 0.5; }
1477 }
1478
1479 .cig-hero-title {
1480 font-size: 22px;
1481 font-weight: 700;
1482 margin: 0 0 var(--space-2) 0;
1483 }
1484
1485 .cig-hero-sub {
1486 font-size: 13px;
1487 color: var(--text-muted);
1488 margin: 0;
1489 max-width: 440px;
1490 }
1491
1492 .cig-hero-actions {
1493 flex-shrink: 0;
1494 }
1495
1496 .cig-save-banner {
1497 display: flex;
1498 align-items: center;
1499 gap: 8px;
1500 padding: 10px 16px;
1501 border-radius: 7px;
1502 background: rgba(63, 185, 80, 0.10);
1503 border: 1px solid rgba(63, 185, 80, 0.28);
1504 color: var(--ci-success);
1505 font-size: 13px;
1506 font-weight: 500;
1507 margin-bottom: var(--space-4);
1508 }
1509
1510 .cig-form {
1511 display: flex;
1512 flex-direction: column;
1513 gap: var(--space-4);
1514 }
1515
1516 .cig-table {
1517 border: 1px solid var(--border-subtle);
1518 border-radius: 8px;
1519 overflow: hidden;
1520 }
1521
1522 .cig-table-head {
1523 display: grid;
1524 grid-template-columns: 220px 110px 1fr;
1525 background: var(--bg-overlay);
1526 border-bottom: 1px solid var(--border-subtle);
1527 }
1528
1529 .cig-col {
1530 padding: 10px 16px;
1531 font-size: 11px;
1532 font-weight: 600;
1533 text-transform: uppercase;
1534 letter-spacing: 0.07em;
1535 color: var(--text-muted);
1536 }
1537
1538 .cig-row {
1539 display: grid;
1540 grid-template-columns: 220px 110px 1fr;
1541 align-items: center;
1542 border-bottom: 1px solid var(--border-subtle);
1543 background: var(--bg-base);
1544 transition: background 0.15s;
1545 &:last-child { border-bottom: none; }
1546 &.cig-row--on { background: rgba(79, 142, 247, 0.03); }
1547
1548 .cig-col {
1549 padding: 14px 16px;
1550 font-size: 13px;
1551 font-weight: 400;
1552 text-transform: none;
1553 letter-spacing: 0;
1554 color: var(--text-primary);
1555 }
1556 }
1557
1558 .cig-gate-name {
1559 font-weight: 600;
1560 font-size: 13px;
1561 margin-bottom: 3px;
1562 }
1563
1564 .cig-gate-desc {
1565 font-size: 11px;
1566 color: var(--text-muted);
1567 line-height: 1.4;
1568 }
1569
1570 .cig-toggle {
1571 display: inline-flex;
1572 align-items: center;
1573 gap: 8px;
1574 cursor: pointer;
1575 }
1576
1577 .cig-toggle-input {
1578 position: absolute;
1579 opacity: 0;
1580 pointer-events: none;
1581 }
1582
1583 .cig-toggle-track {
1584 position: relative;
1585 width: 34px;
1586 height: 18px;
1587 border-radius: 9px;
1588 background: var(--bg-overlay);
1589 border: 1px solid var(--border-default);
1590 transition: background 0.2s, border-color 0.2s;
1591 flex-shrink: 0;
1592
1593 .cig-toggle-input:checked + & {
1594 background: var(--color-accent);
1595 border-color: var(--color-accent);
1596 }
1597 }
1598
1599 .cig-toggle-thumb {
1600 position: absolute;
1601 top: 2px;
1602 left: 2px;
1603 width: 12px;
1604 height: 12px;
1605 border-radius: 50%;
1606 background: var(--text-muted);
1607 transition: transform 0.2s, background 0.2s;
1608
1609 .cig-toggle-input:checked ~ .cig-toggle-track & {
1610 transform: translateX(16px);
1611 background: #fff;
1612 }
1613 }
1614
1615 .cig-toggle-label {
1616 font-size: 11px;
1617 font-weight: 700;
1618 font-family: var(--font-mono);
1619 color: var(--text-muted);
1620 min-width: 24px;
1621
1622 .cig-toggle-input:checked ~ & {
1623 color: var(--color-accent);
1624 }
1625 }
1626
1627 .cig-config-note {
1628 font-size: 12px;
1629 color: var(--text-muted);
1630 }
1631
1632 .cig-field {
1633 display: flex;
1634 align-items: center;
1635 gap: 8px;
1636 cursor: default;
1637 }
1638
1639 .cig-field-label {
1640 font-size: 12px;
1641 color: var(--text-secondary);
1642 white-space: nowrap;
1643 }
1644
1645 .cig-field-input {
1646 width: 72px;
1647 padding: 4px 8px;
1648 background: var(--bg-overlay);
1649 border: 1px solid var(--border-default);
1650 border-radius: 5px;
1651 color: var(--text-primary);
1652 font-size: 12px;
1653 font-family: var(--font-mono);
1654 &:focus {
1655 outline: none;
1656 border-color: var(--color-accent);
1657 box-shadow: 0 0 0 2px rgba(79, 142, 247, 0.15);
1658 }
1659 &:disabled {
1660 opacity: 0.45;
1661 cursor: not-allowed;
1662 }
1663 }
1664
1665 .cig-field-hint {
1666 font-size: 11px;
1667 color: var(--text-muted);
1668 }
1669
1670 .cig-form-footer {
1671 display: flex;
1672 align-items: center;
1673 gap: 12px;
1674 }
1675
1676 .cig-form-note {
1677 font-size: 12px;
1678 color: var(--text-muted);
1679 }
1680
1681 .cig-read-only-note {
1682 font-size: 12px;
1683 color: var(--text-muted);
1684 padding: 10px 0;
1685 text-align: center;
1686 }
File History 1 commit
sha256:9590cee1e0ccd6c76528f005b95d634d80f5019f0dcb7c371e149adc31d1fb65 refactor: enforce gRPC framing on all MWP wire traffic Sonnet 4.6 minor ⚠ 156 days ago