Skip to content

feat: redesign repositories miner insights#154

Merged
MkDev11 merged 19 commits into
MkDev11:mainfrom
bitloi:feat/issue-153-repositories-miner-insights
May 26, 2026
Merged

feat: redesign repositories miner insights#154
MkDev11 merged 19 commits into
MkDev11:mainfrom
bitloi:feat/issue-153-repositories-miner-insights

Conversation

@bitloi
Copy link
Copy Markdown
Contributor

@bitloi bitloi commented May 26, 2026

Summary

Redesigns the /repositories page with a richer repo-focused experience: repository cards/list rows, comparison tooling, repository metadata, emission details, and repo-scoped miner insights.

Adds an active miners treemap for the selected repository that uses repo-scoped score and credibility data, limits the view to the top five miners, and improves responsive layout for small tiles and language lists.

Related Issues

Closes #153

Type of Change

  • Bug fix
  • New feature
  • Enhancement
  • Refactor
  • Documentation
  • Screenshots

Screenshots

image image image image

Testing

  • pnpm build passes
  • Manual browser smoke test (for UI changes)
  • N/A — docs / config only

Additional checks run:

  • git diff --check
  • corepack pnpm exec tsc --noEmit --incremental false

Checklist

  • Self-reviewed the diff
  • Follows existing code patterns and naming
  • No unrelated changes included
  • Documentation updated if behavior changed

Summary by CodeRabbit

  • New Features

    • Redesigned Repositories explorer: card/list views, strategy filters, 14/30-day sparklines, richer per-repo stats, compare tray/modal (up to 4), and a command palette (Cmd/Ctrl+K)
    • Repo detail drawer with contributor treemap, emission breakdown, languages, avatars, and a searchable palette
    • Live emission feed powering Market section, top-earners, and updated miner/contributor listings
    • New bulk metadata endpoint for descriptions, language shares, open-PR counts and 30-day issue bins
  • Documentation

    • Repositories docs updated with strategy-focused wording and refreshed sync cadence notes

Review Change Stack

bitloi added 9 commits May 25, 2026 12:07
Replaces the monolithic page with an extracted component/util layout
(_components/, _lib/) and adds /api/repos/metadata and /api/sn74-emission
to back the new card / drawer / market surfaces. Adds the optional 30d
stats fields on GtRepo and the closeOnScroll prop on Dropdown that the
new page depends on.
Replace the unclear "subnet" labels with explicit wording: drawer formula
reads "TAO (total miners emission)" and the card chip reads "of total
emission" to pair with the existing "of pool" chip. Also runs the drawer
formula's subnetTAO through formatTAO so it doesn't print 14 decimals.
GitHub's `issues.listForRepo` returns issues *and* PRs combined; with
per_page=100, PRs were exhausting the budget on any active repo and
older issue creates were silently truncated (e.g. ragflow: ~29 of 240
real issues visible, gittensor: ~31 of 175). Switch to
`search.issuesAndPullRequests` with `is:issue created:>=DATE` so PRs
are filtered server-side, paginate up to the 1000-row search cap, and
route through withRotation's search-quota lane (30/min per PAT, tracked
separately from the 5000/h core quota).

Also bumps PER_REPO_TIMEOUT_MS to 30s so a paginated fetch + one rate-
limit cooldown doesn't fall back to stale cache, and surfaces
incomplete_results from the search API when GitHub's index is partial.
- RepoCard / RepoListRow: clickable wrappers were <div onClick> with no
  keyboard path; add role=button, tabIndex, and Enter/Space handlers.
  Embedded compare button is excluded from the row handler so it doesn't
  double-fire.
- Palette: add ArrowUp/Down + Enter result navigation with an active
  highlight, scroll-into-view, and mouse-hover sync. Was previously
  Escape-only — keyboard users couldn't pick a result.
- Dropdown: introduce 'xsmall' (12px font, 24px height) and revert
  'small' to the legacy 14px font so existing callers (Pagination,
  ReposTable) keep their look. The repositories page sort picker opts
  into xsmall for its row of compact controls.
Adds `isEligible` and `uid` to RepoMiner so the repositories page can
tell which contributors actually earn from a given repo's emission
pool (vs. historical contributors who don't currently pass the
validator's per-repo credibility / token-score gate).

The route now joins three upstream sources:
  * /miners            — global roster (uid, totalScore)
  * /prs               — historical merged PRs (for ossContributions score)
  * /repos/{full}/miners — per-repo RepoEvaluation rows (isEligible, repo
                          credibility, base/total/collateral scores)

Per-repo eligibility is fetched on demand, cached for 30s, and in-flight
deduped so a burst of drawer opens doesn't multiply upstream load.
When a repo segment is selected in the emission bar, the inspector
now shows a Top Earners row with up to 3 eligible miners (rank chip,
avatar, username, score) right next to the existing stats. Filters
on `RepoMiner.isEligible === true` from the route change, so historical
contributors who no longer pass the gate don't appear. Explicit empty
state when no miners are currently eligible on the repo.
Adds a new "Active miners" section between Activity and Languages in
the drawer. Two views toggled via chip group:

  * Treemap (default) — hand-laid grid (leader takes half the canvas,
    others fill the right half) so 1-5 miners always render with
    readable 1.25:1-ish aspect tiles. Eligible miners get the Linear
    indigo palette graded by rank; ineligibles get a subtle gray wash
    so they fade into the background. Wide-short tiles switch to a
    horizontal avatar+name layout so the score/meta don't get clipped.
  * Ribbon — vertical leaderboard with accent strip, rank, avatar,
    name, share bar, TAO/score. Eligibles first, ineligibles dimmed.

Each tile shows avatar with a credibility ring (Linear green/yellow/
red palette by repo PR cred), uid in the top-right, name below avatar,
score + share/TAO at the bottom. Light-mode palette tuned so white
text stays legible across all eligible tiers and dark text reads on
the muted ineligible tiles. All tile drop/text shadows removed for a
flat Linear-style look.
Combines PR slice, Issue discovery slice, Merge rate, and Resolved
into a single 4-column grid under the TAO emission block. Drops the
now-duplicate Merge rate / Resolved row that sat at the bottom of the
Activity section. Also renames the miner treemap legend's "historical"
swatch to "ineligible" so the wording matches the tile text.
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented May 26, 2026

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Complete redesign of the repositories explorer: new server routes (per-repo miners, metadata, SN74 emission), enriched DTOs, client-side row/math utilities and squarify treemap, many UI components (market, drawer, compare, palette), and page wiring/styles.

Changes

SN74 Repositories Explorer Redesign

Layer / File(s) Summary
Backend APIs for repo mining and emissions
src/app/api/gt/repos/[owner]/[name]/miners/route.ts, src/app/api/gt/repositories/route.ts, src/app/api/repos/metadata/route.ts, src/app/api/sn74-emission/route.ts, src/types/entities.ts
Per-repo miners endpoint added with in-memory cache and in-flight dedupe; miners refresh() updated to drop PR aggregation and store global miners + repo maps; repositories route adds UTC day bucketing and 14/30-day aggregation/sparklines; new metadata route fetches GitHub descriptions, language shares, open PR counts and 30-day issue bins with bounded concurrency and partial backfill; SN74 emission route aggregates upstream snapshots into a short-lived cached snapshot; DTOs extended.
Data transformation and math utilities
src/app/repositories/_lib/rows.ts, src/app/repositories/_lib/colors.ts, src/app/repositories/_lib/incentives.ts, src/app/repositories/_lib/squarify.ts
Client modules build RepoRow[] merging policies and stats (30‑point PR/issue sparklines, eligibility overrides), provide color/icon maps, compute TAO emission splits and decision/reward scores, and implement the squarified treemap layout.
Avatar and language icon components
src/app/repositories/_components/Avatar.tsx, src/app/repositories/_components/LangIcon.tsx
Avatar renders GitHub avatar images with size variants; LangIcon shows Devicon SVG or a colored-letter fallback on error or missing spec.
Market visualization and trending leaderboard
src/app/repositories/_components/MarketSection.tsx
MarketSection shows emission headline, miner/validator/owner stats, interactive desktop bar and mobile treemap, bar inspector with top earners (queries per-repo miners), and a trending leaderboard by 7-day activity.
Repo drawer, miner treemap and reference panels
src/app/repositories/_components/Drawer.tsx, src/app/repositories/_components/RefPanels.tsx
Drawer renders repo details, TAO breakdown, 30d activity, and a squarified miner treemap (eligibility/credibility styling). RefPanels contains interactive formula, language weights, and PR archetypes reference panels.
Comparison modal, tray and palette search
src/app/repositories/_components/CompareModal.tsx, src/app/repositories/_components/CompareTray.tsx, src/app/repositories/_components/Palette.tsx
CompareModal provides side-by-side comparison (desktop grid + mobile stacked) with decision scoring and reasons; CompareTray shows selected repos (up to 4); Palette is a keyboard-search dialog returning up to 10 matches.
Repository card and list row rendering
src/app/repositories/_components/RepoCard.tsx, src/app/repositories/_components/RepoListRow.tsx
RepoCard shows identity, badges, TAO/day, stream split, 30-day sparkline, languages, and label reward bars. RepoListRow provides compact list row with TAO, multiplier cell, stream split, merged-30d/contributor counts, merge-rate metric, and sparkline; actions stop propagation for compare/track buttons.
Page orchestration, styling, and dropdown enhancement
src/app/repositories/page.tsx, src/app/repositories/page.module.css, src/components/Dropdown.tsx, src/app/docs/page.tsx
Top-level page rewritten as a client-side explorer using TanStack Query with hydration guard, strategy-driven filtering/sorting, compare/palette/drawer wiring, and global shortcut. Large CSS module added for styling; Dropdown adds xsmall and optional closeOnScroll. Repositories docs updated to reflect new UX text.

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~60 minutes

Possibly related PRs

  • MkDev11/gittensor-hub#122: Refactors miners route refresh/GET pipeline and per-repo miner shaping; closely related to the miners endpoint changes in this PR.

"I nibble lines of code by night,
Treemaps glow beneath moonlight,
Palette opens, comparisons bloom,
Miners ranked in tidy room,
A rabbit cheers the repo tune."

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 40.58% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The PR title 'feat: redesign repositories miner insights' accurately and concisely describes the main change—a comprehensive redesign of the /repositories page focused on miner insights.
Linked Issues check ✅ Passed All coding objectives from issue #153 are fully met: the redesign provides clearer repo-level miner insights with scores/credibility, adds responsive layouts, surfaces active miners distinctly, and presents them in a compact scannable format.
Out of Scope Changes check ✅ Passed All changes are directly related to the repositories redesign and miner insights objectives; no unrelated changes are present, though some infrastructure improvements (Dropdown enhancements, entity type extensions) directly support the feature.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 9

🧹 Nitpick comments (2)
src/app/repositories/_lib/squarify.ts (1)

29-29: ⚡ Quick win

Sort segments by area descending before packing.

Classic squarify assumes largest-first ordering; keeping caller order can noticeably worsen aspect ratios and visual stability.

Proposed fix
-  const items = segs.map((seg) => ({ data: seg.data, area: (seg.w / totalWeight) * totalArea }));
+  const items = segs
+    .map((seg) => ({ data: seg.data, area: (seg.w / totalWeight) * totalArea }))
+    .sort((a, b) => b.area - a.area);
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/app/repositories/_lib/squarify.ts` at line 29, The items array currently
preserves caller order which worsens squarify packing; compute each segment's
area as done in the existing expression (const items = segs.map(...) using area:
(seg.w / totalWeight) * totalArea) and then sort items by area descending before
any packing logic; specifically, after creating items (or inline during
creation) apply a sort by (b.area - a.area) so downstream packing routines that
consume items (the items variable in this module) receive largest-first
ordering.
src/app/repositories/_components/MarketSection.tsx (1)

98-101: 💤 Low value

Media query detection will not update after hydration.

useMemo runs once during render and caches the result. If the user resizes their window or changes device orientation after initial load, isTouchPrimary won't update. Consider using useState + useEffect with a media query listener, similar to the useNarrowTreemap pattern in Drawer.tsx.

♻️ Suggested pattern
-  const isTouchPrimary = useMemo(() => {
-    if (typeof window === 'undefined') return false;
-    return window.matchMedia('(pointer: coarse), (hover: none)').matches;
-  }, []);
+  const [isTouchPrimary, setIsTouchPrimary] = useState(false);
+  useEffect(() => {
+    const mq = window.matchMedia('(pointer: coarse), (hover: none)');
+    const update = () => setIsTouchPrimary(mq.matches);
+    update();
+    mq.addEventListener('change', update);
+    return () => mq.removeEventListener('change', update);
+  }, []);
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/app/repositories/_components/MarketSection.tsx` around lines 98 - 101,
isTouchPrimary is currently computed with useMemo so it never updates after
hydration; replace this with a useState and a useEffect that creates a
window.matchMedia('(pointer: coarse), (hover: none)') query, sets the state from
query.matches initially (guarding for typeof window === 'undefined'), adds a
listener to update the state on change, and removes the listener on
cleanup—follow the same pattern used by useNarrowTreemap in Drawer.tsx and
reference the isTouchPrimary variable when updating/reading the state.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/app/repositories/_components/CompareTray.tsx`:
- Around line 21-22: The tray is hidden visually but remains keyboard-focusable
when n === 0; update CompareTray so when n === 0 you either don't render the
interactive tray (conditional render based on n) or mark the inner container
(the div with styles.tray inside the div with styles.compareTray) as inert /
remove tab stops for its interactive children (e.g., set tabIndex=-1 on the
Clear/Compare buttons or apply an inert attribute) while keeping aria-hidden;
reference the variable n, the divs using styles.compareTray and styles.tray, and
the Clear/Compare buttons in lines ~87-97 when applying the change.
- Around line 90-95: The CompareTray button (the element with class
styles.priBtn and onClick handler onOpen) currently becomes icon-only on mobile
because the visible text span is hidden and the fallback span uses inline
display:none, leaving no accessible name; fix by adding an explicit accessible
name (e.g., aria-label="Compare side by side" or aria-labelledby pointing to a
visually-hidden span) to the button and replace the inline hidden fallback with
a screen-reader-only span (or use an existing SR-only CSS class) so assistive
tech always receives the label while preserving visual hide on mobile.

In `@src/app/repositories/_components/Drawer.tsx`:
- Line 535: The destructuring in the useMemo call inside Drawer.tsx is pulling
unused variables (totalRows, eligibleCount, ineligibleCount) which triggers
ESLint/CI warnings; edit the useMemo return/destructuring so only used values
are extracted (e.g., keep allRows, totalEligibleScore, top1Pct, conc) and remove
totalRows, eligibleCount, and ineligibleCount from the const { ... } =
useMemo(...) statement and from the returned object in that useMemo block
(adjust any dependent code if necessary).

In `@src/app/repositories/_components/RepoCard.tsx`:
- Around line 177-183: The default-label bar percentage calculation in RepoCard
(the LabelBarRow prop barPct currently set to (r.defaultLabel / 2) * 100) can
exceed 100% for values >2.0; clamp the computed value to the 0–100 range before
passing it to LabelBarRow (e.g., replace the expression with a clamped value
using Math.min/Math.max or a clamp utility) so the bar never overflows the
track.

In `@src/app/repositories/_components/RepoListRow.tsx`:
- Around line 83-86: The code in RepoListRow.tsx calls entries.reduce(...) on
Object.entries(r.labels) which will throw when r.labels is an empty object;
update the r.labels handling to first compute const entries =
Object.entries(r.labels) and then guard entries.length > 0 before calling
entries.reduce (or use a safe fallback) so that when there are no labels you
skip the reduce and set topLabel/topVal to a safe default (and set c =
LABEL_COLORS[...] ?? { fg: 'var(--fg-subtle)', soft: '' }) to avoid runtime
errors; make the check where entries is defined and ensure the rest of the
render logic uses the fallback values when entries is empty.

In `@src/app/repositories/_lib/squarify.ts`:
- Around line 27-30: Guard against zero/invalid weights before dividing:
validate segs' weights (ignore or coerce NaN/non-finite and negative values) and
compute totalWeight safely; if totalWeight <= 0, fall back to equal distribution
(area = totalArea / segs.length) or another defined fallback, then compute items
from segs using that safe weight or fallback. Update the code around
totalWeight, totalArea, and items so the map uses the sanitized weights/
fallback instead of directly dividing by totalWeight to avoid NaN/Infinity in
area calculations.

In `@src/app/repositories/page.module.css`:
- Line 67: Stylelint is flagging CSS Modules pseudo-class syntax like
:global([data-theme='light']) .scope (and other :global(...) occurrences) as
unknown; update the stylelint config to recognize CSS Modules by either
extending the stylelint-config-css-modules preset or adding an allow-list for
the pseudo-class and appropriate parser: add "selector-pseudo-class-no-unknown":
[true, {"ignorePseudoClasses": ["global"]}] and set customSyntax to a PostCSS
parser that supports CSS Modules (e.g., postcss-scss or postcss-modules), so
selectors such as :global(...) .scope no longer trigger
selector-pseudo-class-no-unknown errors.
- Around line 803-805: The linter flags a missing empty line before the
declaration following the custom property; in the CSS rule containing
--cred-color, add a blank line before the normal declarations so that
--cred-color: `#7b8494`; is separated from position: relative; (i.e., ensure an
empty line before the declaration for position: relative; to satisfy
declaration-empty-line-before and keep the custom property (--cred-color)
grouped separately).

In `@src/components/Dropdown.tsx`:
- Around line 117-124: The closeOnScroll listener currently closes the menu on
any scroll because onScroll does setOpen(false) unconditionally; change onScroll
to accept the Event and early-return when the scroll event originated from
inside the menu element (i.e., if the event.target is contained within the
dropdown's DOM node — the component's menuRef or dropdownRef), otherwise call
setOpen(false); ensure the same handler signature is used when adding and
removing the listener (window.addEventListener('scroll', onScroll, true) and
removeEventListener) so internal scrolls (overflowY: 'auto' in the portal) don't
close the dropdown.

---

Nitpick comments:
In `@src/app/repositories/_components/MarketSection.tsx`:
- Around line 98-101: isTouchPrimary is currently computed with useMemo so it
never updates after hydration; replace this with a useState and a useEffect that
creates a window.matchMedia('(pointer: coarse), (hover: none)') query, sets the
state from query.matches initially (guarding for typeof window === 'undefined'),
adds a listener to update the state on change, and removes the listener on
cleanup—follow the same pattern used by useNarrowTreemap in Drawer.tsx and
reference the isTouchPrimary variable when updating/reading the state.

In `@src/app/repositories/_lib/squarify.ts`:
- Line 29: The items array currently preserves caller order which worsens
squarify packing; compute each segment's area as done in the existing expression
(const items = segs.map(...) using area: (seg.w / totalWeight) * totalArea) and
then sort items by area descending before any packing logic; specifically, after
creating items (or inline during creation) apply a sort by (b.area - a.area) so
downstream packing routines that consume items (the items variable in this
module) receive largest-first ordering.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: a12b8614-5b5b-4c94-9801-40042b80d329

📥 Commits

Reviewing files that changed from the base of the PR and between aab5b71 and 7c4d6ab.

📒 Files selected for processing (23)
  • src/app/api/gt/repos/[owner]/[name]/miners/route.ts
  • src/app/api/gt/repositories/route.ts
  • src/app/api/repos/metadata/route.ts
  • src/app/api/sn74-emission/route.ts
  • src/app/docs/page.tsx
  • src/app/repositories/_components/Avatar.tsx
  • src/app/repositories/_components/CompareModal.tsx
  • src/app/repositories/_components/CompareTray.tsx
  • src/app/repositories/_components/Drawer.tsx
  • src/app/repositories/_components/LangIcon.tsx
  • src/app/repositories/_components/MarketSection.tsx
  • src/app/repositories/_components/Palette.tsx
  • src/app/repositories/_components/RefPanels.tsx
  • src/app/repositories/_components/RepoCard.tsx
  • src/app/repositories/_components/RepoListRow.tsx
  • src/app/repositories/_lib/colors.ts
  • src/app/repositories/_lib/incentives.ts
  • src/app/repositories/_lib/rows.ts
  • src/app/repositories/_lib/squarify.ts
  • src/app/repositories/page.module.css
  • src/app/repositories/page.tsx
  • src/components/Dropdown.tsx
  • src/types/entities.ts

Comment thread src/app/repositories/_components/CompareTray.tsx Outdated
Comment thread src/app/repositories/_components/CompareTray.tsx Outdated
Comment thread src/app/repositories/_components/Drawer.tsx Outdated
Comment thread src/app/repositories/_components/RepoCard.tsx
Comment thread src/app/repositories/_components/RepoListRow.tsx Outdated
Comment thread src/app/repositories/_lib/squarify.ts Outdated
Comment thread src/app/repositories/page.module.css
Comment thread src/app/repositories/page.module.css
Comment thread src/components/Dropdown.tsx
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/app/repositories/_components/Drawer.tsx`:
- Around line 465-471: The current fallback when !hasEligibleMiners still
produces an "Active miners" treemap; instead, stop producing an active-treemap
value and surface a dedicated historical/empty state. Change the branch that
currently returns Math.max(tileScale(baseRepoScore), 0.75) (the
!hasEligibleMiners branch using hasEligibleMiners, tileScale, baseRepoScore,
topEligibleUnit) to return a sentinel that signals "no active miners" (e.g.
null/undefined or a clear flag) and update the Drawer rendering logic that
consumes this value to render the historical/empty state UI rather than the
active-miners treemap. Apply the same change to the other identical path
referenced (the second occurrence using the same variables) so both paths
consistently show the historical/empty state when there are no eligible miners.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: f94cf37c-c1d1-4eab-96cb-4cd525c8a79d

📥 Commits

Reviewing files that changed from the base of the PR and between 6818aeb and 2fd5a7c.

📒 Files selected for processing (2)
  • src/app/repositories/_components/Drawer.tsx
  • src/app/repositories/page.module.css

Comment thread src/app/repositories/_components/Drawer.tsx Outdated
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
src/app/repositories/_components/Drawer.tsx (1)

619-627: ⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Avoid labeling every empty miner state as a benchmark repo.

This branch now fires whenever both active and historical rows are empty, which can also happen for a non-benchmark repo with no synced miner data yet. The current copy will be misleading in that case.

Suggested fix
-          Benchmark repo — no miners.
+          No miner data available for this repo yet.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/app/repositories/_components/Drawer.tsx` around lines 619 - 627, The
empty-state message currently shown when displayRows.length === 0 incorrectly
always says "Benchmark repo — no miners."; update the Drawer empty-state logic
(around displayRows and containerStyle) to choose the copy based on repo type
instead of always showing "Benchmark repo" — e.g., if there is an existing flag
or prop (use isBenchmarkRepo, repo.isBenchmark, or similar in the
parent/component) render "Benchmark repo — no miners.", otherwise render a
neutral message like "No miners yet." or "No miner data available." Ensure you
reference and use the existing symbols displayRows and containerStyle and add
the repo-type check in the same conditional block.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/app/repositories/_components/Drawer.tsx`:
- Around line 455-457: The historical-only UI must use baseScore exclusively;
update minerVisualScore to return only baseScore for historical-only miners
(i.e., when the historical-only condition is true/when m is not eligible)
instead of falling back to score, and ensure any other places that size or order
historical tiles (the sizing/sorting code paths referenced in Drawer.tsx that
currently call minerVisualScore or sort by score/repoWorkScore) are changed to
use baseScore for the historical-only path. Concretely: modify minerVisualScore
to return Math.max(m.baseScore ?? 0, 0) for the historical-only branch (and keep
the current behavior for eligible miners), and audit the other usages mentioned
so historical tiles are both ordered and sized by baseScore only.

---

Outside diff comments:
In `@src/app/repositories/_components/Drawer.tsx`:
- Around line 619-627: The empty-state message currently shown when
displayRows.length === 0 incorrectly always says "Benchmark repo — no miners.";
update the Drawer empty-state logic (around displayRows and containerStyle) to
choose the copy based on repo type instead of always showing "Benchmark repo" —
e.g., if there is an existing flag or prop (use isBenchmarkRepo,
repo.isBenchmark, or similar in the parent/component) render "Benchmark repo —
no miners.", otherwise render a neutral message like "No miners yet." or "No
miner data available." Ensure you reference and use the existing symbols
displayRows and containerStyle and add the repo-type check in the same
conditional block.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 18557bca-c215-429b-9de2-1c2c5723d69f

📥 Commits

Reviewing files that changed from the base of the PR and between 2fd5a7c and d7266ce.

📒 Files selected for processing (1)
  • src/app/repositories/_components/Drawer.tsx

Comment thread src/app/repositories/_components/Drawer.tsx Outdated
@bitloi bitloi force-pushed the feat/issue-153-repositories-miner-insights branch from 0105a0b to 0f66b97 Compare May 26, 2026 08:27
@MkDev11
Copy link
Copy Markdown
Owner

MkDev11 commented May 26, 2026

thanks for your contribution. looks much better.

@MkDev11
Copy link
Copy Markdown
Owner

MkDev11 commented May 26, 2026

I still don’t think this is ready to merge because the miner insight states are misleading:

  • /api/gt/repos/[owner]/[name]/miners returns [] for any non-OK upstream response, so a rate limit or upstream failure is shown as “no miners” instead of an error.
  • The empty state says Benchmark repo — no miners. for any empty response, but that can also happen for active repos with no synced miner data or an upstream failure.

Please fix these states so active, ineligible/historical, empty, and error cases are clearly distinct.

@MkDev11 MkDev11 merged commit e015a7d into MkDev11:main May 26, 2026
4 checks passed
@FairyPigDev
Copy link
Copy Markdown

so funny guys...
self miners...
lol

@gazeatcode
Copy link
Copy Markdown

hey, guys. @MkDev11 @bitloi @FairyPigDev
Don't make me laugh
Don't make such stupid interlude
Everyone knows you guys are all same team
Your such stupid interlude can not hide this truth
Plz stop doing that
It is okay to merge immediately without any comments

@FairyPigDev
Copy link
Copy Markdown

@gazeatcode how I can be same team with @MkDev11 and @bitloi ?
u are so stupid, too!

@gazeatcode
Copy link
Copy Markdown

@gazeatcode how I can be same team with @MkDev11 and @bitloi ? u are so stupid, too!

Haha, “you are stupid too” means you’re admitting that you’re stupid as well lol. Thanks for admitting it yourself, @FairyPigDev.

You’re trying really hard to pretend you’re not on the same team as @MkDev11, but you don’t need to. That “self miners…” sentence doesn’t hide anything, in fact, it just makes it more obvious that you’re on the same team. And honestly, it also makes you look pretty stupid. Haha.

@gazeatcode
Copy link
Copy Markdown

@MkDev11 plz make @FairyPigDev calm down!. I think you are super senior, but @FairyPigDev is super junior. plz teach him

@gazeatcode
Copy link
Copy Markdown

gazeatcode commented May 27, 2026

also @MkDev11 don't waste time to leave comments and don't make @bitloi hard work. it's okay to merge immediately without any comments. everyone knows everything and can understand from now

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Feature] Redesign repositories page miner insights

4 participants