github-issue-tower-defence-management 1.101.3 → 1.101.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (22) hide show
  1. package/CHANGELOG.md +14 -0
  2. package/bin/adapter/entry-points/console/ui-dist/assets/index-D4zghbcI.css +1 -0
  3. package/bin/adapter/entry-points/console/ui-dist/assets/index-DX0mapkS.js +101 -0
  4. package/bin/adapter/entry-points/console/ui-dist/index.html +2 -2
  5. package/bin/adapter/repositories/issue/ApiV3CheerioRestIssueRepository.js +37 -5
  6. package/bin/adapter/repositories/issue/ApiV3CheerioRestIssueRepository.js.map +1 -1
  7. package/package.json +1 -1
  8. package/src/adapter/entry-points/console/ui/src/features/console/components/detail/ConsoleItemDetail.tsx +145 -139
  9. package/src/adapter/entry-points/console/ui/src/features/console/pages/ConsoleItemDetailContainer.tsx +4 -1
  10. package/src/adapter/entry-points/console/ui/src/features/console/pages/ConsolePage.test.tsx +97 -0
  11. package/src/adapter/entry-points/console/ui/src/features/console/pages/ConsolePage.tsx +39 -0
  12. package/src/adapter/entry-points/console/ui/src/index.css +16 -6
  13. package/src/adapter/entry-points/console/ui-dist/assets/index-D4zghbcI.css +1 -0
  14. package/src/adapter/entry-points/console/ui-dist/assets/index-DX0mapkS.js +101 -0
  15. package/src/adapter/entry-points/console/ui-dist/index.html +2 -2
  16. package/src/adapter/repositories/issue/ApiV3CheerioRestIssueRepository.test.ts +241 -0
  17. package/src/adapter/repositories/issue/ApiV3CheerioRestIssueRepository.ts +55 -7
  18. package/types/adapter/repositories/issue/ApiV3CheerioRestIssueRepository.d.ts.map +1 -1
  19. package/bin/adapter/entry-points/console/ui-dist/assets/index-DP5DGKUj.js +0 -101
  20. package/bin/adapter/entry-points/console/ui-dist/assets/index-ES6SLB1Y.css +0 -1
  21. package/src/adapter/entry-points/console/ui-dist/assets/index-DP5DGKUj.js +0 -101
  22. package/src/adapter/entry-points/console/ui-dist/assets/index-ES6SLB1Y.css +0 -1
@@ -391,6 +391,103 @@ describe('ConsolePage swipe navigation', () => {
391
391
  });
392
392
  });
393
393
 
394
+ describe('ConsolePage detail scroll reset', () => {
395
+ beforeEach(() => {
396
+ localStorage.clear();
397
+ window.history.replaceState({}, '', '/projects/umino/prs?k=token');
398
+ const fetchMock = jest.fn(async (url: string) => {
399
+ const listMatch = url.match(/\/projects\/[^/]+\/([^/]+)\/list\.json/);
400
+ if (listMatch !== null) {
401
+ return {
402
+ ok: true,
403
+ status: 200,
404
+ json: async () =>
405
+ listMatch[1] === 'prs'
406
+ ? twoItemPrPayload()
407
+ : { ...twoItemPrPayload(), items: [] },
408
+ };
409
+ }
410
+ return { ok: true, status: 200, json: async () => ({ body: '# body' }) };
411
+ });
412
+ global.fetch = fetchMock as unknown as typeof fetch;
413
+ });
414
+
415
+ it('resets the detail scroll container to the top when navigating to the next item', async () => {
416
+ const { container, getByText, findByText } = render(<ConsolePage />);
417
+ await waitFor(() => {
418
+ expect(getByText('Add serveConsole subcommand')).toBeInTheDocument();
419
+ });
420
+ fireEvent.click(getByText('Add serveConsole subcommand'));
421
+ expect(await findByText('Approve')).toBeInTheDocument();
422
+
423
+ const scrollContainer = container.querySelector('.console-detail');
424
+ expect(scrollContainer).not.toBeNull();
425
+ (scrollContainer as HTMLElement).scrollTop = 240;
426
+ expect((scrollContainer as HTMLElement).scrollTop).toBe(240);
427
+
428
+ const detailScreen = container.querySelector('.console-detail-screen');
429
+ swipeDetailScreen(
430
+ detailScreen as HTMLElement,
431
+ { clientX: 240, clientY: 100 },
432
+ { clientX: 40, clientY: 110 },
433
+ );
434
+
435
+ await waitFor(() => {
436
+ expect(window.location.hash).toBe('#item/PVTI_2');
437
+ });
438
+ await waitFor(() => {
439
+ expect((scrollContainer as HTMLElement).scrollTop).toBe(0);
440
+ });
441
+ });
442
+ });
443
+
444
+ describe('ConsolePage next item prefetch', () => {
445
+ beforeEach(() => {
446
+ localStorage.clear();
447
+ window.history.replaceState({}, '', '/projects/umino/prs?k=token');
448
+ });
449
+
450
+ it('warms the next pending item resources while the current item is open', async () => {
451
+ const fetchMock = jest.fn(async (url: string) => {
452
+ const listMatch = url.match(/\/projects\/[^/]+\/([^/]+)\/list\.json/);
453
+ if (listMatch !== null) {
454
+ return {
455
+ ok: true,
456
+ status: 200,
457
+ json: async () =>
458
+ listMatch[1] === 'prs'
459
+ ? twoItemPrPayload()
460
+ : { ...twoItemPrPayload(), items: [] },
461
+ };
462
+ }
463
+ return { ok: true, status: 200, json: async () => ({ body: '# body' }) };
464
+ });
465
+ global.fetch = fetchMock as unknown as typeof fetch;
466
+
467
+ const { getByText, findByText, queryByText } = render(<ConsolePage />);
468
+ await waitFor(() => {
469
+ expect(getByText('Add serveConsole subcommand')).toBeInTheDocument();
470
+ });
471
+ fireEvent.click(getByText('Add serveConsole subcommand'));
472
+ expect(await findByText('Approve')).toBeInTheDocument();
473
+ expect(window.location.hash).toBe('#item/PVTI_1');
474
+ expect(queryByText('Add server-side console API handlers')).toBeNull();
475
+
476
+ const nextItemUrlFragment = encodeURIComponent(
477
+ 'https://github.com/o/r/pull/852',
478
+ );
479
+ await waitFor(() => {
480
+ const calledNextItemBody = fetchMock.mock.calls.some(
481
+ ([url]) =>
482
+ typeof url === 'string' &&
483
+ url.includes('/api/itembody') &&
484
+ url.includes(nextItemUrlFragment),
485
+ );
486
+ expect(calledNextItemBody).toBe(true);
487
+ });
488
+ });
489
+ });
490
+
394
491
  describe('ConsolePage auto-advance', () => {
395
492
  beforeEach(() => {
396
493
  localStorage.clear();
@@ -191,6 +191,44 @@ export const ConsolePage = () => {
191
191
  );
192
192
 
193
193
  const detailScreenRef = useConsoleSwipeNavigation(handleSwipe);
194
+ const detailScrollElementRef = useRef<HTMLElement | null>(null);
195
+
196
+ useEffect(() => {
197
+ if (selectedItemKey === null) {
198
+ return;
199
+ }
200
+ const element = detailScrollElementRef.current;
201
+ if (element !== null) {
202
+ element.scrollTop = 0;
203
+ }
204
+ }, [selectedItemKey]);
205
+
206
+ const nextPendingItem = useMemo<ConsoleListItem | null>(() => {
207
+ if (selectedItemKey === null) {
208
+ return null;
209
+ }
210
+ const nextKey = nextPendingKeyBrowse(orderedPendingKeys, selectedItemKey);
211
+ if (nextKey === null) {
212
+ return null;
213
+ }
214
+ return (
215
+ pendingItems.find((item) => overlayKeyForItem(item) === nextKey) ?? null
216
+ );
217
+ }, [selectedItemKey, orderedPendingKeys, pendingItems]);
218
+
219
+ useEffect(() => {
220
+ if (nextPendingItem === null) {
221
+ return;
222
+ }
223
+ const key = `${nextPendingItem.repo}#${nextPendingItem.number}`;
224
+ const url = nextPendingItem.url;
225
+ void caches.body.load(key, url);
226
+ void caches.state.load(key, url);
227
+ if (nextPendingItem.isPr) {
228
+ void caches.files.load(key, url);
229
+ void caches.commits.load(key, url);
230
+ }
231
+ }, [nextPendingItem, caches]);
194
232
 
195
233
  return (
196
234
  <main className="console-app">
@@ -235,6 +273,7 @@ export const ConsolePage = () => {
235
273
  overlayStatus={overlayStatusForSelected}
236
274
  now={now}
237
275
  onQueueAction={handleQueueAction}
276
+ scrollRef={detailScrollElementRef}
238
277
  />
239
278
  </div>
240
279
  )}
@@ -33,8 +33,10 @@ body {
33
33
  .console-app {
34
34
  max-width: 920px;
35
35
  margin: 0 auto;
36
+ height: 100dvh;
36
37
  display: flex;
37
38
  flex-direction: column;
39
+ min-height: 0;
38
40
  }
39
41
 
40
42
  .console-tabbar {
@@ -114,6 +116,10 @@ body {
114
116
  list-style: none;
115
117
  margin: 0;
116
118
  padding: 12px 18px 18px;
119
+ flex: 1;
120
+ min-height: 0;
121
+ overflow-y: auto;
122
+ -webkit-overflow-scrolling: touch;
117
123
  }
118
124
 
119
125
  .console-list-group {
@@ -258,6 +264,10 @@ body {
258
264
  }
259
265
 
260
266
  .console-detail {
267
+ flex: 1;
268
+ min-height: 0;
269
+ overflow-y: auto;
270
+ -webkit-overflow-scrolling: touch;
261
271
  display: flex;
262
272
  flex-direction: column;
263
273
  gap: 12px;
@@ -463,14 +473,11 @@ body {
463
473
  }
464
474
 
465
475
  .console-actionbar {
466
- position: fixed;
467
- bottom: 0;
468
- left: 0;
469
- right: 0;
470
- z-index: 100;
476
+ flex-shrink: 0;
471
477
  background: #161b22;
472
478
  border-top: 2px solid #30363d;
473
479
  padding: 10px 16px;
480
+ padding-bottom: calc(10px + env(safe-area-inset-bottom));
474
481
  }
475
482
 
476
483
  .console-operation-bar {
@@ -561,7 +568,10 @@ body {
561
568
  }
562
569
 
563
570
  .console-detail-screen {
564
- padding-bottom: 140px;
571
+ flex: 1;
572
+ min-height: 0;
573
+ display: flex;
574
+ flex-direction: column;
565
575
  }
566
576
 
567
577
  .console-panel-open-link {
@@ -0,0 +1 @@
1
+ /*! tailwindcss v4.3.0 | MIT License | https://tailwindcss.com */@layer properties{@supports (((-webkit-hyphens:none)) and (not (margin-trim:inline))) or ((-moz-orient:inline) and (not (color:rgb(from red r g b)))){*,:before,:after,::backdrop{--tw-border-style:solid;--tw-font-weight:initial;--tw-outline-style:solid;--tw-shadow:0 0 #0000;--tw-shadow-color:initial;--tw-shadow-alpha:100%;--tw-inset-shadow:0 0 #0000;--tw-inset-shadow-color:initial;--tw-inset-shadow-alpha:100%;--tw-ring-color:initial;--tw-ring-shadow:0 0 #0000;--tw-inset-ring-color:initial;--tw-inset-ring-shadow:0 0 #0000;--tw-ring-inset:initial;--tw-ring-offset-width:0px;--tw-ring-offset-color:#fff;--tw-ring-offset-shadow:0 0 #0000}}}@layer theme{:root,:host{--font-sans:ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji";--font-mono:ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace;--spacing:.25rem;--text-xs:.75rem;--text-xs--line-height:calc(1 / .75);--text-sm:.875rem;--text-sm--line-height:calc(1.25 / .875);--font-weight-medium:500;--font-weight-semibold:600;--radius-md:.375rem;--default-transition-duration:.15s;--default-transition-timing-function:cubic-bezier(.4, 0, .2, 1);--default-font-family:var(--font-sans);--default-mono-font-family:var(--font-mono);--color-input:#e5e5e5;--color-ring:#0a0a0a;--color-background:#fff;--color-foreground:#0a0a0a;--color-primary:#171717;--color-primary-foreground:#fafafa;--color-secondary:#f5f5f5;--color-secondary-foreground:#171717;--color-accent:#f5f5f5;--color-accent-foreground:#171717}}@layer base{*,:after,:before,::backdrop{box-sizing:border-box;border:0 solid;margin:0;padding:0}::file-selector-button{box-sizing:border-box;border:0 solid;margin:0;padding:0}html,:host{-webkit-text-size-adjust:100%;-moz-tab-size:4;tab-size:4;line-height:1.5;font-family:var(--default-font-family,ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji");font-feature-settings:var(--default-font-feature-settings,normal);font-variation-settings:var(--default-font-variation-settings,normal);-webkit-tap-highlight-color:transparent}hr{height:0;color:inherit;border-top-width:1px}abbr:where([title]){-webkit-text-decoration:underline dotted;text-decoration:underline dotted}h1,h2,h3,h4,h5,h6{font-size:inherit;font-weight:inherit}a{color:inherit;-webkit-text-decoration:inherit;text-decoration:inherit}b,strong{font-weight:bolder}code,kbd,samp,pre{font-family:var(--default-mono-font-family,ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace);font-feature-settings:var(--default-mono-font-feature-settings,normal);font-variation-settings:var(--default-mono-font-variation-settings,normal);font-size:1em}small{font-size:80%}sub,sup{vertical-align:baseline;font-size:75%;line-height:0;position:relative}sub{bottom:-.25em}sup{top:-.5em}table{text-indent:0;border-color:inherit;border-collapse:collapse}:-moz-focusring{outline:auto}progress{vertical-align:baseline}summary{display:list-item}ol,ul,menu{list-style:none}img,svg,video,canvas,audio,iframe,embed,object{vertical-align:middle;display:block}img,video{max-width:100%;height:auto}button,input,select,optgroup,textarea{font:inherit;font-feature-settings:inherit;font-variation-settings:inherit;letter-spacing:inherit;color:inherit;opacity:1;background-color:#0000;border-radius:0}::file-selector-button{font:inherit;font-feature-settings:inherit;font-variation-settings:inherit;letter-spacing:inherit;color:inherit;opacity:1;background-color:#0000;border-radius:0}:where(select:is([multiple],[size])) optgroup{font-weight:bolder}:where(select:is([multiple],[size])) optgroup option{padding-inline-start:20px}::file-selector-button{margin-inline-end:4px}::placeholder{opacity:1}@supports (not ((-webkit-appearance:-apple-pay-button))) or (contain-intrinsic-size:1px){::placeholder{color:currentColor}@supports (color:color-mix(in lab,red,red)){::placeholder{color:color-mix(in oklab,currentcolor 50%,transparent)}}}textarea{resize:vertical}::-webkit-search-decoration{-webkit-appearance:none}::-webkit-date-and-time-value{min-height:1lh;text-align:inherit}::-webkit-datetime-edit{display:inline-flex}::-webkit-datetime-edit-fields-wrapper{padding:0}::-webkit-datetime-edit{padding-block:0}::-webkit-datetime-edit-year-field{padding-block:0}::-webkit-datetime-edit-month-field{padding-block:0}::-webkit-datetime-edit-day-field{padding-block:0}::-webkit-datetime-edit-hour-field{padding-block:0}::-webkit-datetime-edit-minute-field{padding-block:0}::-webkit-datetime-edit-second-field{padding-block:0}::-webkit-datetime-edit-millisecond-field{padding-block:0}::-webkit-datetime-edit-meridiem-field{padding-block:0}::-webkit-calendar-picker-indicator{line-height:1}:-moz-ui-invalid{box-shadow:none}button,input:where([type=button],[type=reset],[type=submit]){-webkit-appearance:button;-moz-appearance:button;appearance:button}::file-selector-button{-webkit-appearance:button;-moz-appearance:button;appearance:button}::-webkit-inner-spin-button{height:auto}::-webkit-outer-spin-button{height:auto}[hidden]:where(:not([hidden=until-found])){display:none!important}}@layer components;@layer utilities{.visible{visibility:visible}.relative{position:relative}.static{position:static}.container{width:100%}@media(min-width:40rem){.container{max-width:40rem}}@media(min-width:48rem){.container{max-width:48rem}}@media(min-width:64rem){.container{max-width:64rem}}@media(min-width:80rem){.container{max-width:80rem}}@media(min-width:96rem){.container{max-width:96rem}}.hidden{display:none}.inline-flex{display:inline-flex}.h-8{height:calc(var(--spacing) * 8)}.h-9{height:calc(var(--spacing) * 9)}.h-10{height:calc(var(--spacing) * 10)}.items-center{align-items:center}.justify-center{justify-content:center}.gap-2{gap:calc(var(--spacing) * 2)}.rounded-md{border-radius:var(--radius-md)}.border{border-style:var(--tw-border-style);border-width:1px}.border-input{border-color:var(--color-input)}.border-transparent{border-color:#0000}.bg-background{background-color:var(--color-background)}.bg-primary{background-color:var(--color-primary)}.bg-secondary{background-color:var(--color-secondary)}.px-2\.5{padding-inline:calc(var(--spacing) * 2.5)}.px-3{padding-inline:calc(var(--spacing) * 3)}.px-4{padding-inline:calc(var(--spacing) * 4)}.px-8{padding-inline:calc(var(--spacing) * 8)}.py-0\.5{padding-block:calc(var(--spacing) * .5)}.py-2{padding-block:calc(var(--spacing) * 2)}.text-sm{font-size:var(--text-sm);line-height:var(--tw-leading,var(--text-sm--line-height))}.text-xs{font-size:var(--text-xs);line-height:var(--tw-leading,var(--text-xs--line-height))}.font-medium{--tw-font-weight:var(--font-weight-medium);font-weight:var(--font-weight-medium)}.font-semibold{--tw-font-weight:var(--font-weight-semibold);font-weight:var(--font-weight-semibold)}.whitespace-nowrap{white-space:nowrap}.text-foreground{color:var(--color-foreground)}.text-primary-foreground{color:var(--color-primary-foreground)}.text-secondary-foreground{color:var(--color-secondary-foreground)}.lowercase{text-transform:lowercase}.outline{outline-style:var(--tw-outline-style);outline-width:1px}.transition-colors{transition-property:color,background-color,border-color,outline-color,text-decoration-color,fill,stroke,--tw-gradient-from,--tw-gradient-via,--tw-gradient-to;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}@media(hover:hover){.hover\:bg-accent:hover{background-color:var(--color-accent)}.hover\:bg-primary\/90:hover{background-color:#171717e6}@supports (color:color-mix(in lab,red,red)){.hover\:bg-primary\/90:hover{background-color:color-mix(in oklab,var(--color-primary) 90%,transparent)}}.hover\:bg-secondary\/80:hover{background-color:#f5f5f5cc}@supports (color:color-mix(in lab,red,red)){.hover\:bg-secondary\/80:hover{background-color:color-mix(in oklab,var(--color-secondary) 80%,transparent)}}.hover\:text-accent-foreground:hover{color:var(--color-accent-foreground)}}.focus-visible\:ring-2:focus-visible{--tw-ring-shadow:var(--tw-ring-inset,) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color,currentcolor);box-shadow:var(--tw-inset-shadow),var(--tw-inset-ring-shadow),var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow)}.focus-visible\:ring-ring:focus-visible{--tw-ring-color:var(--color-ring)}.focus-visible\:outline-none:focus-visible{--tw-outline-style:none;outline-style:none}.disabled\:pointer-events-none:disabled{pointer-events:none}.disabled\:opacity-50:disabled{opacity:.5}}body{color:#e6edf3;background-color:#0d1117;margin:0;font-family:ui-sans-serif,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica,Arial,sans-serif}.console-app{flex-direction:column;max-width:920px;height:100dvh;min-height:0;margin:0 auto;display:flex}.console-tabbar{-webkit-overflow-scrolling:touch;background:#161b22;border-bottom:2px solid #30363d;flex-wrap:nowrap;align-items:stretch;gap:0;min-height:42px;padding:0 8px;display:flex;overflow-x:auto}.console-tab{color:#8b949e;white-space:nowrap;cursor:pointer;background:0 0;border:none;border-bottom:2px solid #0000;align-items:center;gap:6px;margin-bottom:-2px;padding:10px 14px;font-size:13px;font-weight:500;line-height:1.2;text-decoration:none;display:inline-flex}.console-tab:hover{color:#e6edf3}.console-tab[data-active=true]{color:#e6edf3;border-bottom-color:#2f81f7;font-weight:700}.console-tab-badge{text-align:center;color:#e6edf3;background:#484f58;border-radius:20px;min-width:20px;padding:1px 7px;font-size:11px;font-weight:700;line-height:1.5}.console-tab-badge[data-zero=true]{color:#8b949e;background:#30363d}.console-tab-pjname{color:#8b949e;align-self:center;margin-left:auto;padding:0 8px;font-size:11.5px}.console-tab-geninfo{color:#8b949e;align-self:center;padding:0 4px;font-size:11px}.console-list{-webkit-overflow-scrolling:touch;flex:1;min-height:0;margin:0;padding:12px 18px 18px;list-style:none;overflow-y:auto}.console-list-group{list-style:none}.console-item-row .console-item-icon{flex:none;margin-top:3px}.console-group-header{background:#0b0f14;border-bottom:1px solid #21262d;justify-content:space-between;align-items:center;padding:6px 12px;display:flex}.console-storytag{align-items:center;gap:8px;font-size:13px;font-weight:700;display:inline-flex}.console-story-dot{border-radius:999px;width:10px;height:10px;display:inline-block}.console-group-count{color:#8b949e;font-size:12px}.console-item-row{color:#e6edf3;text-align:left;cursor:pointer;background:#161b22;border:1px solid #30363d;border-radius:8px;align-items:flex-start;gap:14px;width:100%;margin-bottom:10px;padding:12px 16px;display:flex}.console-item-row:hover{background:#1a2029;border-color:#484f58}.console-item-row[data-active=true]{background:#1a2029;border-color:#4493f8}.console-item-meta{flex:1;min-width:0}.console-item-title{font-size:14.5px;font-weight:600;display:block}.console-item-sub{color:#8b949e;margin-top:3px;font-size:12.5px;display:block}.console-item-pill{color:#8b949e;border:1px solid #30363d;border-radius:20px;margin-right:6px;padding:1px 8px;font-size:11px;display:inline-block}.console-item-createdat{color:#8b949e;cursor:help}.console-item-fields{color:#adbac7;flex-wrap:wrap;gap:4px 10px;margin-top:4px;font-size:11.5px;display:flex}.console-item-field{word-break:break-all;align-items:baseline;gap:4px;min-width:0;display:inline-flex}.console-item-field-label{color:#6e7681;text-transform:uppercase;letter-spacing:.03em;font-size:10px}.console-list-message{color:#8b949e;padding:16px;font-size:14px}.console-list-empty{text-align:center;color:#8b949e;padding:40px;font-size:14px}.console-list-error,.console-comment-error,.console-files-error,.console-commits-error,.console-detail-body-error{color:#f85149}.console-detail{-webkit-overflow-scrolling:touch;flex-direction:column;flex:1;gap:12px;min-height:0;padding:16px;display:flex;overflow-y:auto}.console-detail-title{align-items:center;gap:8px;margin:0;font-size:20px;display:flex}.console-detail-title-text{flex:1}.console-detail-number{color:#8b949e;font-weight:400}.console-detail-closed-label{color:#a371f7;font-size:13px}.console-detail-subbar{align-items:center;gap:12px;font-size:13px;display:flex}.console-detail-link{color:#4493f8}.console-detail-repo{color:#8b949e;font-family:ui-monospace,SFMono-Regular,Menlo,monospace}.console-detail-pill,.console-label-chip,.console-detail-status-chip{border:1px solid #30363d;border-radius:999px;padding:2px 8px;font-size:12px;display:inline-block}.console-detail-labels{flex-wrap:wrap;gap:6px;display:flex}.console-detail-createdat{color:#8b949e;font-size:12px}.console-panel{border:1px solid #30363d;border-radius:8px;overflow:hidden}.console-panel-header{background:#161b22;justify-content:space-between;align-items:center;padding:6px 12px;display:flex}.console-panel-toggle{color:#e6edf3;cursor:pointer;background:0 0;border:none;align-items:center;gap:8px;font-size:14px;font-weight:600;display:inline-flex}.console-panel-body{padding:12px}.console-markdown{word-break:break-word;font-size:14px;line-height:1.5}.console-markdown ul{margin:.5em 0;padding-left:1.5em;list-style:outside}.console-markdown ol{margin:.5em 0;padding-left:1.5em;list-style:decimal}.console-markdown li{margin:.25em 0}.console-markdown table{border-collapse:collapse;margin:.5em 0}.console-markdown th,.console-markdown td{border:1px solid #30363d;padding:4px 8px}.console-markdown th{background:#161b22}.console-mermaid-error{color:#f85149;font-size:13px}.console-comment{border-top:1px solid #21262d;padding-top:8px}.console-comment-header{color:#8b949e;gap:8px;font-size:12px;display:flex}.console-comment-author{color:#e6edf3;font-weight:600}.console-files,.console-commits{margin:0;padding:0;list-style:none}.console-commit{align-items:center;gap:8px;padding:4px 0;font-size:13px;display:flex}.console-file{flex-direction:column;font-size:13px;display:flex}.console-file-badge{text-align:center;border:1px solid;border-radius:4px;width:18px;font-size:11px}.console-file-path,.console-commit-message{flex:1;font-family:ui-monospace,SFMono-Regular,Menlo,monospace}.console-file-add,.console-pr-add{color:#3fb950}.console-file-del,.console-pr-del{color:#f85149}.console-commit-sha{color:#8b949e;font-family:ui-monospace,SFMono-Regular,Menlo,monospace}.console-actionbar{padding:10px 16px;padding-bottom:calc(10px + env(safe-area-inset-bottom));background:#161b22;border-top:2px solid #30363d;flex-shrink:0}.console-operation-bar{flex-direction:column;gap:8px;max-width:920px;margin:0 auto;display:flex}.console-op-group{flex-wrap:wrap;justify-content:flex-end;align-items:center;gap:8px;display:flex}.console-op-group-review{gap:10px}.console-op-group-stories{max-height:50vh;overflow-y:auto}.console-op-button{color:#e6edf3;white-space:nowrap;cursor:pointer;background:#21262d;border:1px solid #30363d;border-radius:6px;padding:7px 16px;font-size:13px;font-weight:600}.console-op-button:hover{border-color:#484f58}.console-op-button-approve{color:#fff;background:#238636;border-color:#2ea043}.console-op-button-reject{color:#ffd166;background:#7d5000;border-color:#a06800}.console-op-button-wrong{color:#f85149;background:#3a1518;border-color:#f85149}.console-op-button-unneeded{color:#aab0b8;background:#2a2d31;border-color:#6e7681}.console-op-button-snooze{color:#79c0ff;background:#1c2b4a;border-color:#4493f8}.console-pr-section{border:1px solid #30363d;border-radius:8px;flex-direction:column;gap:10px;padding:12px;display:flex}.console-pr-statbar{color:#8b949e;gap:12px;font-size:12px;display:flex}.console-detail-screen{flex-direction:column;flex:1;min-height:0;display:flex}.console-panel-open-link{color:#4493f8;font-size:13px;font-weight:400}.console-composer{margin-top:4px}.console-composer-toggle{color:#8b949e;cursor:pointer;background:0 0;border:none;padding:2px 0;font-size:12.5px}.console-composer-toggle:hover{color:#e6edf3}.console-composer-posted{flex-direction:column;gap:8px;margin-top:8px;display:flex}.console-composer-form{margin-top:8px}.console-composer-input{box-sizing:border-box;color:#e6edf3;width:100%;font:inherit;resize:vertical;background:#21262d;border:1px solid #30363d;border-radius:6px;padding:8px;font-size:14px}.console-composer-row{align-items:center;gap:8px;margin-top:6px;display:flex}.console-composer-submit{color:#fff;cursor:pointer;background:#238636;border:1px solid #2ea043;border-radius:6px;padding:7px 16px;font-size:13px;font-weight:600}.console-composer-submit:disabled{opacity:.6;cursor:default}.console-composer-status{color:#8b949e;font-size:12px}.console-composer-error{color:#f85149}.console-undo-toast{z-index:9998;white-space:nowrap;border-radius:10px;align-items:center;gap:12px;max-width:92vw;padding:12px 18px;font-size:13.5px;display:flex;position:fixed;top:12px;left:50%;transform:translate(-50%);box-shadow:0 4px 20px #0009}.console-undo-toast-green{color:#3fb950;background:#0d3320;border:1px solid #2ea043}.console-undo-toast-amber{color:#ffd166;background:#3a2800;border:1px solid #a06800}.console-undo-toast-red{color:#f85149;background:#3a1518;border:1px solid #da3633}.console-undo-toast-gray{color:#aab0b8;background:#2a2d31;border:1px solid #6e7681}.console-undo-toast-blue{color:#79c0ff;background:#0d1f40;border:1px solid #4493f8}.console-undo-toast-error{color:#f85149;background:#3a1518;border:1px solid #f85149}.console-undo-toast-message{text-overflow:ellipsis;flex:1;min-width:0;overflow:hidden}.console-undo-toast-undo{cursor:pointer;color:inherit;background:#ffffff1f;border:none;border-radius:6px;flex:none;padding:4px 12px;font-size:13px;font-weight:700}.console-undo-toast-undo:hover{background:#ffffff38}.console-undo-toast-countdown{opacity:.7;flex:none;font-size:11px}.console-undo-toast-bar{opacity:.5;background:currentColor;border-radius:0 0 10px 10px;height:3px;transition:width .1s linear;position:absolute;bottom:0;left:0}.console-file-row{width:100%;color:inherit;font:inherit;text-align:left;cursor:pointer;background:0 0;border:none;align-items:center;gap:8px;padding:4px 0;font-size:13px;display:flex}.console-file-row:hover{background:#1a2029}.console-file-caret{color:#8b949e;flex:none;width:1em}.console-file-diff{border-collapse:collapse;width:100%;margin:4px 0 8px;font:13px/1.6 ui-monospace,SFMono-Regular,Menlo,monospace}.console-file-diff td{white-space:pre-wrap;word-break:break-word;vertical-align:top;padding:0 10px}.console-diff-ln{text-align:right;color:#6e7681;-webkit-user-select:none;user-select:none;white-space:nowrap;border-right:1px solid #30363d;width:1%;padding:0 8px}.console-file-diff td.console-diff-ln{white-space:nowrap;word-break:normal;overflow-wrap:normal}.console-diff-add td{background:#2ea04326}.console-diff-add .console-diff-code{color:#aff5b4}.console-diff-del td{background:#f8514926}.console-diff-del .console-diff-code{color:#ffdcd7}.console-diff-hunk td{color:#79c0ff;background:#161b22}.console-diff-ctx .console-diff-code{color:#c9d1d9}.console-file-diff-empty{color:#8b949e;padding:8px 14px;font-size:12px}.console-pr-header{flex-wrap:wrap;align-items:center;gap:10px;padding-top:4px;display:flex}.console-pr-section-title{color:#e6edf3;font-size:15px;font-weight:600}.console-pr-section-state{color:#8b949e;border:1px solid #6e7681;border-radius:999px;padding:1px 8px;font-size:11px}@property --tw-border-style{syntax:"*";inherits:false;initial-value:solid}@property --tw-font-weight{syntax:"*";inherits:false}@property --tw-outline-style{syntax:"*";inherits:false;initial-value:solid}@property --tw-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-shadow-color{syntax:"*";inherits:false}@property --tw-shadow-alpha{syntax:"<percentage>";inherits:false;initial-value:100%}@property --tw-inset-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-inset-shadow-color{syntax:"*";inherits:false}@property --tw-inset-shadow-alpha{syntax:"<percentage>";inherits:false;initial-value:100%}@property --tw-ring-color{syntax:"*";inherits:false}@property --tw-ring-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-inset-ring-color{syntax:"*";inherits:false}@property --tw-inset-ring-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-ring-inset{syntax:"*";inherits:false}@property --tw-ring-offset-width{syntax:"<length>";inherits:false;initial-value:0}@property --tw-ring-offset-color{syntax:"*";inherits:false;initial-value:#fff}@property --tw-ring-offset-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}