@grove-dev/astro 0.2.19 → 0.2.20
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.
- package/dist/theme.test.js +14 -0
- package/dist/theme.test.js.map +1 -1
- package/package.json +1 -1
- package/src/components/CategoryGrid.astro +2 -11
- package/src/components/ContributorsGrid.astro +2 -11
- package/src/components/CurationGrid.astro +1 -1
- package/src/components/DecisionRow.astro +1 -1
- package/src/components/ExploreByCategory.astro +3 -3
- package/src/components/ExploreByStack.astro +3 -3
- package/src/components/FilterGroupMenu.astro +5 -5
- package/src/components/Hero.astro +8 -8
- package/src/components/Icon.astro +6 -33
- package/src/components/IndexRow.astro +5 -5
- package/src/components/ItemCard.astro +5 -16
- package/src/components/MinimalAbout.astro +2 -2
- package/src/components/OriginalCollection.astro +4 -4
- package/src/components/Pagination.astro +2 -2
- package/src/components/RecordSection.astro +1 -1
- package/src/components/RefinePanel.astro +1 -1
- package/src/components/SmartLensTabs.astro +3 -3
- package/src/components/StackGrid.astro +6 -15
- package/src/components/WhyThisExists.astro +3 -3
- package/src/layouts/Container.astro +4 -4
- package/src/layouts/Footer.astro +3 -3
- package/src/layouts/Header.astro +5 -5
- package/src/layouts/ThemeToggle.astro +1 -1
- package/src/styles.css +33 -339
- package/src/theme.test.ts +15 -0
- package/templates/default/public/icons/stacks/rag.svg +7 -0
- package/templates/default/public/llms-full.txt +1 -1
- package/templates/default/public/sitemap.xml +10 -10
- package/templates/default/src/pages/404.astro +5 -5
- package/templates/default/src/pages/[slug]/[recordSlug].astro +27 -31
- package/templates/default/src/pages/[slug]/index.astro +8 -8
- package/templates/default/src/pages/about.astro +9 -9
- package/templates/default/src/pages/contributors.astro +8 -17
- package/templates/default/src/pages/submit.astro +23 -31
|
@@ -101,18 +101,14 @@ const tags = record.tags ?? [];
|
|
|
101
101
|
const healthStatus = proj?.health?.status;
|
|
102
102
|
const healthLabel = healthStatus ? statusDisplay(healthStatus) : null;
|
|
103
103
|
|
|
104
|
-
//
|
|
105
|
-
//
|
|
106
|
-
//
|
|
107
|
-
// name — every badge became `grove-badge-{l}` regardless of value.
|
|
108
|
-
// Map each known id to its stable CSS class in the package
|
|
109
|
-
// stylesheet. Unknown ids (e.g. legacy "featured") fall back to the
|
|
110
|
-
// neutral `.grove-badge` look instead of producing broken classes.
|
|
104
|
+
// Map each known label to a static Tailwind class string so every
|
|
105
|
+
// utility is visible to Tailwind's source scanner. Unknown/legacy
|
|
106
|
+
// labels use the neutral secondary badge treatment.
|
|
111
107
|
const labelClassMap: Record<LabelId, string> = {
|
|
112
|
-
new: "
|
|
113
|
-
hot: "
|
|
114
|
-
mature: "
|
|
115
|
-
featured: "
|
|
108
|
+
new: "!bg-emerald-50 !text-emerald-700 dark:!bg-emerald-950/80 dark:!text-emerald-300",
|
|
109
|
+
hot: "!bg-orange-50 !text-orange-800 dark:!bg-orange-950/80 dark:!text-orange-300",
|
|
110
|
+
mature: "!bg-blue-50 !text-blue-700 dark:!bg-blue-950/80 dark:!text-blue-300",
|
|
111
|
+
featured: "inline-flex min-h-5 items-center justify-center gap-1 rounded-full border border-transparent bg-secondary px-2 py-0.5 align-middle text-xs font-medium leading-none text-secondary-foreground",
|
|
116
112
|
};
|
|
117
113
|
|
|
118
114
|
// ── Optional content markdown (record.content is a path under
|
|
@@ -248,8 +244,8 @@ if (isProject && proj) {
|
|
|
248
244
|
submitHref="/submit"
|
|
249
245
|
submitLabel={`Submit ${name}`}
|
|
250
246
|
>
|
|
251
|
-
<article class="
|
|
252
|
-
<div class="
|
|
247
|
+
<article class="py-12 sm:py-16">
|
|
248
|
+
<div class="mx-auto w-full max-w-wide px-5 sm:px-7">
|
|
253
249
|
<nav class="mb-6 text-2xs text-ink-500 dark:text-ink-400" aria-label="Breadcrumb">
|
|
254
250
|
<a href={`/${slug}`} class="hover:text-ink-900 dark:hover:text-ink-100 capitalize">
|
|
255
251
|
{slug}
|
|
@@ -259,7 +255,7 @@ if (isProject && proj) {
|
|
|
259
255
|
</nav>
|
|
260
256
|
|
|
261
257
|
{/* ── AppCard-style header ──────────────────────────────── */}
|
|
262
|
-
<header class="
|
|
258
|
+
<header class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors flex flex-col gap-5 p-6 sm:flex-row sm:items-start">
|
|
263
259
|
<div class="flex-shrink-0">
|
|
264
260
|
{avatarSrc ? (
|
|
265
261
|
<img
|
|
@@ -292,7 +288,7 @@ if (isProject && proj) {
|
|
|
292
288
|
</span>
|
|
293
289
|
)}
|
|
294
290
|
{curationLabels.map((l) => (
|
|
295
|
-
<span class={`
|
|
291
|
+
<span class={`inline-flex min-h-5 items-center justify-center gap-1 rounded-full border border-transparent bg-secondary px-2 py-0.5 align-middle text-xs font-medium leading-none text-secondary-foreground ${labelClassMap[l as LabelId] ?? ""}`} title={`Curated: ${labelDisplay(l) ?? l}`}>
|
|
296
292
|
{labelDisplay(l) ?? prettySlug(l)}
|
|
297
293
|
</span>
|
|
298
294
|
))}
|
|
@@ -308,7 +304,7 @@ if (isProject && proj) {
|
|
|
308
304
|
</span>
|
|
309
305
|
)}
|
|
310
306
|
{healthLabel && (
|
|
311
|
-
<span class="
|
|
307
|
+
<span class="inline-flex min-h-5 items-center justify-center gap-1 rounded-full border border-transparent bg-secondary px-2 py-0.5 align-middle text-xs font-medium leading-none text-secondary-foreground !bg-amber-50 !text-amber-800 dark:!bg-amber-950/80 dark:!text-amber-300">{healthLabel}</span>
|
|
312
308
|
)}
|
|
313
309
|
</div>
|
|
314
310
|
|
|
@@ -350,7 +346,7 @@ if (isProject && proj) {
|
|
|
350
346
|
href={repoUrl}
|
|
351
347
|
target="_blank"
|
|
352
348
|
rel="noopener noreferrer"
|
|
353
|
-
class="
|
|
349
|
+
class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 rounded-[var(--radius)] border border-transparent px-3 text-sm font-medium leading-none no-underline outline-none transition-colors focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 bg-primary text-primary-foreground hover:bg-primary/90"
|
|
354
350
|
>
|
|
355
351
|
View on GitHub →
|
|
356
352
|
</a>
|
|
@@ -360,7 +356,7 @@ if (isProject && proj) {
|
|
|
360
356
|
href={homepageUrl}
|
|
361
357
|
target="_blank"
|
|
362
358
|
rel="noopener noreferrer"
|
|
363
|
-
class="
|
|
359
|
+
class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 rounded-[var(--radius)] border border-transparent px-3 text-sm font-medium leading-none no-underline outline-none transition-colors focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 border-border bg-secondary text-foreground hover:bg-accent"
|
|
364
360
|
>
|
|
365
361
|
Homepage
|
|
366
362
|
</a>
|
|
@@ -371,7 +367,7 @@ if (isProject && proj) {
|
|
|
371
367
|
|
|
372
368
|
{/* ── Score bars ───────────────────────────────────────── */}
|
|
373
369
|
{proj && (
|
|
374
|
-
<section class="mt-8
|
|
370
|
+
<section class="mt-8 rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors p-6" aria-labelledby="scores-heading">
|
|
375
371
|
<h2 id="scores-heading" class="m-0 text-lg font-semibold tracking-tight text-ink-900 dark:text-ink-100">
|
|
376
372
|
Scores
|
|
377
373
|
</h2>
|
|
@@ -396,7 +392,7 @@ if (isProject && proj) {
|
|
|
396
392
|
|
|
397
393
|
{/* ── GitHub signals dl ────────────────────────────────── */}
|
|
398
394
|
{isProject && github && (
|
|
399
|
-
<section class="mt-8
|
|
395
|
+
<section class="mt-8 rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors p-6" aria-labelledby="signals-heading">
|
|
400
396
|
<h2 id="signals-heading" class="m-0 text-lg font-semibold tracking-tight text-ink-900 dark:text-ink-100">
|
|
401
397
|
GitHub signals
|
|
402
398
|
</h2>
|
|
@@ -461,8 +457,8 @@ if (isProject && proj) {
|
|
|
461
457
|
{/* ── Decision signals (3-col) ──────────────────────────── */}
|
|
462
458
|
{isProject && github && (
|
|
463
459
|
<section class="mt-8 grid grid-cols-1 gap-4 lg:grid-cols-3" aria-label="Decision signals">
|
|
464
|
-
{/* Repository health
|
|
465
|
-
<div class="
|
|
460
|
+
{/* Repository health card */}
|
|
461
|
+
<div class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors p-5">
|
|
466
462
|
<h3 class="m-0 text-[1rem] font-semibold tracking-tight text-ink-900 dark:text-ink-100">
|
|
467
463
|
Repository health
|
|
468
464
|
</h3>
|
|
@@ -501,7 +497,7 @@ if (isProject && proj) {
|
|
|
501
497
|
</div>
|
|
502
498
|
|
|
503
499
|
{/* Activity bar chart */}
|
|
504
|
-
<div class="
|
|
500
|
+
<div class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors p-5">
|
|
505
501
|
<h3 class="m-0 text-[1rem] font-semibold tracking-tight text-ink-900 dark:text-ink-100">
|
|
506
502
|
Activity
|
|
507
503
|
</h3>
|
|
@@ -537,7 +533,7 @@ if (isProject && proj) {
|
|
|
537
533
|
</div>
|
|
538
534
|
|
|
539
535
|
{/* Contribution readiness chips */}
|
|
540
|
-
<div class="
|
|
536
|
+
<div class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors p-5">
|
|
541
537
|
<h3 class="m-0 text-[1rem] font-semibold tracking-tight text-ink-900 dark:text-ink-100">
|
|
542
538
|
Contribution readiness
|
|
543
539
|
</h3>
|
|
@@ -563,7 +559,7 @@ if (isProject && proj) {
|
|
|
563
559
|
|
|
564
560
|
{/* ── Language mix ─────────────────────────────────────── */}
|
|
565
561
|
{isProject && languages.length > 0 && (
|
|
566
|
-
<section class="mt-4
|
|
562
|
+
<section class="mt-4 rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors p-5">
|
|
567
563
|
<h3 class="m-0 text-[1rem] font-semibold tracking-tight text-ink-900 dark:text-ink-100">
|
|
568
564
|
Language mix
|
|
569
565
|
</h3>
|
|
@@ -597,7 +593,7 @@ if (isProject && proj) {
|
|
|
597
593
|
Stack
|
|
598
594
|
</span>
|
|
599
595
|
{stacks.map((s) => (
|
|
600
|
-
<span class="
|
|
596
|
+
<span class="inline-flex min-h-5 items-center justify-center gap-1 rounded-full border border-transparent bg-secondary px-2 py-0.5 align-middle text-xs font-medium leading-none text-secondary-foreground items-center gap-1.5">
|
|
601
597
|
<Icon name={s} category="stack" size={14} />
|
|
602
598
|
{s}
|
|
603
599
|
</span>
|
|
@@ -610,7 +606,7 @@ if (isProject && proj) {
|
|
|
610
606
|
Platform
|
|
611
607
|
</span>
|
|
612
608
|
{platforms.map((p) => (
|
|
613
|
-
<span class="
|
|
609
|
+
<span class="inline-flex min-h-5 items-center justify-center gap-1 rounded-full border border-transparent bg-secondary px-2 py-0.5 align-middle text-xs font-medium leading-none text-secondary-foreground items-center gap-1.5">
|
|
614
610
|
<Icon name={p} category="platform" size={14} />
|
|
615
611
|
{p}
|
|
616
612
|
</span>
|
|
@@ -632,7 +628,7 @@ if (isProject && proj) {
|
|
|
632
628
|
<li>
|
|
633
629
|
<a
|
|
634
630
|
href={`/${slug}?q=${encodeURIComponent(t)}`}
|
|
635
|
-
class="
|
|
631
|
+
class="inline-flex min-h-5 items-center justify-center gap-1 rounded-full border border-transparent bg-secondary px-2 py-0.5 align-middle text-xs font-medium leading-none text-secondary-foreground items-center gap-1.5"
|
|
636
632
|
>
|
|
637
633
|
{t}
|
|
638
634
|
</a>
|
|
@@ -650,12 +646,12 @@ if (isProject && proj) {
|
|
|
650
646
|
</h2>
|
|
651
647
|
<ul class="mt-4 m-0 flex list-none flex-col gap-2 p-0">
|
|
652
648
|
{distribution.map((c) => (
|
|
653
|
-
<li class="
|
|
649
|
+
<li class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors flex flex-wrap items-baseline justify-between gap-2 p-3">
|
|
654
650
|
<div class="flex flex-col">
|
|
655
651
|
<span class="text-sm font-semibold text-ink-900 dark:text-ink-100">
|
|
656
652
|
{c.label ?? c.type}
|
|
657
653
|
{c.verified && (
|
|
658
|
-
<span class="ml-2
|
|
654
|
+
<span class="ml-2 inline-flex min-h-5 items-center justify-center gap-1 rounded-full border border-transparent bg-secondary px-2 py-0.5 align-middle text-xs font-medium leading-none text-secondary-foreground !bg-emerald-50 !text-emerald-700 dark:!bg-emerald-950/80 dark:!text-emerald-300">Verified</span>
|
|
659
655
|
)}
|
|
660
656
|
</span>
|
|
661
657
|
{c.notes && (
|
|
@@ -666,7 +662,7 @@ if (isProject && proj) {
|
|
|
666
662
|
href={c.url}
|
|
667
663
|
target="_blank"
|
|
668
664
|
rel="noopener noreferrer"
|
|
669
|
-
class="
|
|
665
|
+
class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 rounded-[var(--radius)] border border-transparent px-3 text-sm font-medium leading-none no-underline outline-none transition-colors focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 border-border bg-secondary text-foreground hover:bg-accent"
|
|
670
666
|
>
|
|
671
667
|
{c.platform ?? c.type} →
|
|
672
668
|
</a>
|
|
@@ -110,7 +110,7 @@ function hrefForRemove(key: keyof IndexFilters, value: string): string {
|
|
|
110
110
|
submitLabel={`Submit ${itemLabel()}`}
|
|
111
111
|
>
|
|
112
112
|
<section class="border-b border-ink-200 bg-white dark:border-ink-800 dark:bg-ink-950">
|
|
113
|
-
<div class="
|
|
113
|
+
<div class="mx-auto w-full max-w-wide px-5 pt-10 sm:px-7 sm:pt-12">
|
|
114
114
|
<span class="text-2xs font-medium uppercase tracking-wider text-ink-500 dark:text-ink-400">
|
|
115
115
|
{slug}
|
|
116
116
|
</span>
|
|
@@ -171,7 +171,7 @@ function hrefForRemove(key: keyof IndexFilters, value: string): string {
|
|
|
171
171
|
<path d="M4.22 6.22a.75.75 0 0 1 1.06 0L8 8.94l2.72-2.72a.75.75 0 1 1 1.06 1.06l-3.25 3.25a.75.75 0 0 1-1.06 0L4.22 7.28a.75.75 0 0 1 0-1.06Z" />
|
|
172
172
|
</svg>
|
|
173
173
|
</label>
|
|
174
|
-
<button type="submit" class="
|
|
174
|
+
<button type="submit" class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 rounded-[var(--radius)] border border-transparent px-3 text-sm font-medium leading-none no-underline outline-none transition-colors focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 bg-primary text-primary-foreground hover:bg-primary/90">Search</button>
|
|
175
175
|
</form>
|
|
176
176
|
|
|
177
177
|
<div class="mt-4">
|
|
@@ -192,8 +192,8 @@ function hrefForRemove(key: keyof IndexFilters, value: string): string {
|
|
|
192
192
|
</div>
|
|
193
193
|
</section>
|
|
194
194
|
|
|
195
|
-
<section class="
|
|
196
|
-
<div class="
|
|
195
|
+
<section class="py-10 sm:py-12">
|
|
196
|
+
<div class="mx-auto w-full max-w-wide px-5 sm:px-7">
|
|
197
197
|
<header class="mb-6">
|
|
198
198
|
<h2 class="m-0 text-[1.5rem] sm:text-[1.625rem] font-semibold tracking-tight text-ink-900 dark:text-ink-100">
|
|
199
199
|
{`All ${itemLabelPlural()}`}
|
|
@@ -220,7 +220,7 @@ function hrefForRemove(key: keyof IndexFilters, value: string): string {
|
|
|
220
220
|
{chips.map((chip) => (
|
|
221
221
|
<a
|
|
222
222
|
href={hrefForRemove(chip.key, chip.value)}
|
|
223
|
-
class="
|
|
223
|
+
class="inline-flex min-h-5 items-center justify-center gap-1 rounded-full border border-transparent bg-secondary px-2 py-0.5 align-middle text-xs font-medium leading-none text-secondary-foreground transition-colors hover:border-ink-400"
|
|
224
224
|
>
|
|
225
225
|
{chip.label} <span aria-hidden="true">x</span>
|
|
226
226
|
</a>
|
|
@@ -248,7 +248,7 @@ function hrefForRemove(key: keyof IndexFilters, value: string): string {
|
|
|
248
248
|
<p class="m-0 text-sm font-medium text-ink-700 dark:text-ink-200">
|
|
249
249
|
{`No ${itemLabel()}s match these filters.`}
|
|
250
250
|
</p>
|
|
251
|
-
<a href={`/${slug}`} class="
|
|
251
|
+
<a href={`/${slug}`} class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 rounded-[var(--radius)] border border-transparent px-3 text-sm font-medium leading-none no-underline outline-none transition-colors focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 border-border bg-secondary text-foreground hover:bg-accent mt-4">Clear filters</a>
|
|
252
252
|
</div>
|
|
253
253
|
<nav class="mt-8 flex flex-wrap items-center justify-center gap-1.5" aria-label="Pagination">
|
|
254
254
|
<Pagination current={page} total={pages} hrefFor={hrefForPage} />
|
|
@@ -257,7 +257,7 @@ function hrefForRemove(key: keyof IndexFilters, value: string): string {
|
|
|
257
257
|
</section>
|
|
258
258
|
|
|
259
259
|
<section class="border-t border-ink-200 dark:border-ink-800">
|
|
260
|
-
<div class="
|
|
260
|
+
<div class="mx-auto w-full max-w-wide px-5 sm:px-7">
|
|
261
261
|
<div class="flex flex-col items-center gap-3 py-12 text-center">
|
|
262
262
|
<h2 class="m-0 text-xl font-semibold tracking-tight text-ink-900 dark:text-ink-100">
|
|
263
263
|
{`Know a real ${itemLabel()} that belongs here?`}
|
|
@@ -267,7 +267,7 @@ function hrefForRemove(key: keyof IndexFilters, value: string): string {
|
|
|
267
267
|
</p>
|
|
268
268
|
<a
|
|
269
269
|
href={siteConfig.submitUrl ?? "/submit"}
|
|
270
|
-
class="
|
|
270
|
+
class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 rounded-[var(--radius)] border border-transparent px-3 text-sm font-medium leading-none no-underline outline-none transition-colors focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 bg-primary text-primary-foreground hover:bg-primary/90 mt-2"
|
|
271
271
|
>
|
|
272
272
|
{`Submit ${itemLabel()}`}
|
|
273
273
|
</a>
|
|
@@ -13,7 +13,7 @@
|
|
|
13
13
|
* - New: "A growing community knowledge site. A curated, health-
|
|
14
14
|
* aware developer directory…"
|
|
15
15
|
*
|
|
16
|
-
* The card
|
|
16
|
+
* The Tailwind card and button utilities match the
|
|
17
17
|
* rest of the framework, and the data fields it references
|
|
18
18
|
* (`siteConfig.tagline`, `siteConfig.repoUrl`) all flow from the
|
|
19
19
|
* site config — no hardcoded brand or copy.
|
|
@@ -57,7 +57,7 @@ const item = itemLabel();
|
|
|
57
57
|
</p>
|
|
58
58
|
</header>
|
|
59
59
|
|
|
60
|
-
<section class="
|
|
60
|
+
<section class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors mt-8 p-5 sm:p-6">
|
|
61
61
|
<span class="text-2xs font-medium uppercase tracking-wider text-ink-500 dark:text-ink-400">
|
|
62
62
|
Why
|
|
63
63
|
</span>
|
|
@@ -78,7 +78,7 @@ const item = itemLabel();
|
|
|
78
78
|
</p>
|
|
79
79
|
</section>
|
|
80
80
|
|
|
81
|
-
<section class="
|
|
81
|
+
<section class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors mt-4 p-5 sm:p-6">
|
|
82
82
|
<span class="text-2xs font-medium uppercase tracking-wider text-ink-500 dark:text-ink-400">
|
|
83
83
|
Why real {item}s
|
|
84
84
|
</span>
|
|
@@ -95,7 +95,7 @@ const item = itemLabel();
|
|
|
95
95
|
</p>
|
|
96
96
|
</section>
|
|
97
97
|
|
|
98
|
-
<section class="
|
|
98
|
+
<section class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors mt-4 p-5 sm:p-6">
|
|
99
99
|
<span class="text-2xs font-medium uppercase tracking-wider text-ink-500 dark:text-ink-400">
|
|
100
100
|
What you get
|
|
101
101
|
</span>
|
|
@@ -130,7 +130,7 @@ const item = itemLabel();
|
|
|
130
130
|
</ul>
|
|
131
131
|
</section>
|
|
132
132
|
|
|
133
|
-
<section class="
|
|
133
|
+
<section class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors mt-4 p-5 sm:p-6">
|
|
134
134
|
<span class="text-2xs font-medium uppercase tracking-wider text-ink-500 dark:text-ink-400">
|
|
135
135
|
Generic by design
|
|
136
136
|
</span>
|
|
@@ -145,7 +145,7 @@ const item = itemLabel();
|
|
|
145
145
|
</p>
|
|
146
146
|
</section>
|
|
147
147
|
|
|
148
|
-
<section class="
|
|
148
|
+
<section class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors mt-4 p-5 sm:p-6">
|
|
149
149
|
<span class="text-2xs font-medium uppercase tracking-wider text-ink-500 dark:text-ink-400">
|
|
150
150
|
Free to fork, free to extend
|
|
151
151
|
</span>
|
|
@@ -164,18 +164,18 @@ const item = itemLabel();
|
|
|
164
164
|
</section>
|
|
165
165
|
|
|
166
166
|
<section class="mt-8 flex flex-wrap items-center gap-3">
|
|
167
|
-
<a href={`/${slug}`} class="
|
|
167
|
+
<a href={`/${slug}`} class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 rounded-[var(--radius)] border border-transparent px-3 text-sm font-medium leading-none no-underline outline-none transition-colors focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 bg-primary text-primary-foreground hover:bg-primary/90">Browse the directory</a>
|
|
168
168
|
{githubUrl && (
|
|
169
169
|
<a
|
|
170
170
|
href={githubUrl}
|
|
171
171
|
target="_blank"
|
|
172
172
|
rel="noopener noreferrer"
|
|
173
|
-
class="
|
|
173
|
+
class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 rounded-[var(--radius)] border border-transparent px-3 text-sm font-medium leading-none no-underline outline-none transition-colors focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 border-border bg-secondary text-foreground hover:bg-accent"
|
|
174
174
|
>
|
|
175
175
|
View on GitHub
|
|
176
176
|
</a>
|
|
177
177
|
)}
|
|
178
|
-
<a href="/submit" class="
|
|
178
|
+
<a href="/submit" class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 rounded-[var(--radius)] border border-transparent px-3 text-sm font-medium leading-none no-underline outline-none transition-colors focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 bg-transparent text-foreground hover:bg-accent hover:text-accent-foreground">Submit a {item} →</a>
|
|
179
179
|
</section>
|
|
180
180
|
</article>
|
|
181
181
|
</Container>
|
|
@@ -82,8 +82,8 @@ const contributorsGraphHref = repoUrl ? `${repoUrl.replace(/\/$/, "")}/graphs/co
|
|
|
82
82
|
---
|
|
83
83
|
|
|
84
84
|
<BaseLayout title={title} description={description} site={siteConfig}>
|
|
85
|
-
<section class="
|
|
86
|
-
<div class="
|
|
85
|
+
<section class="py-12 sm:py-16">
|
|
86
|
+
<div class="mx-auto w-full max-w-wide px-5 py-12 sm:px-7 sm:py-16">
|
|
87
87
|
<span class="text-2xs font-medium uppercase tracking-wider text-ink-500 dark:text-ink-400">
|
|
88
88
|
Contributors
|
|
89
89
|
</span>
|
|
@@ -112,9 +112,9 @@ const contributorsGraphHref = repoUrl ? `${repoUrl.replace(/\/$/, "")}/graphs/co
|
|
|
112
112
|
</section>
|
|
113
113
|
|
|
114
114
|
{sorted.length === 0 ? (
|
|
115
|
-
<section class="
|
|
116
|
-
<div class="
|
|
117
|
-
<div class="
|
|
115
|
+
<section class="py-12 sm:py-16">
|
|
116
|
+
<div class="mx-auto w-full max-w-container px-5 pb-16 sm:px-7">
|
|
117
|
+
<div class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors flex flex-col items-center gap-3 p-8 text-center">
|
|
118
118
|
<p class="m-0 text-sm text-ink-500 dark:text-ink-400">
|
|
119
119
|
No contributors synced yet. Once the first sync runs, every
|
|
120
120
|
contributor avatar lands here.
|
|
@@ -123,8 +123,8 @@ const contributorsGraphHref = repoUrl ? `${repoUrl.replace(/\/$/, "")}/graphs/co
|
|
|
123
123
|
</div>
|
|
124
124
|
</section>
|
|
125
125
|
) : (
|
|
126
|
-
<section class="
|
|
127
|
-
<div class="
|
|
126
|
+
<section class="py-12 sm:py-16" aria-label="Contributors list">
|
|
127
|
+
<div class="mx-auto w-full max-w-wide px-5 pb-16 sm:px-7">
|
|
128
128
|
<ul
|
|
129
129
|
class="m-0 grid list-none grid-cols-2 gap-3 p-0 sm:grid-cols-3 md:grid-cols-4 lg:grid-cols-6"
|
|
130
130
|
aria-label="Contributors"
|
|
@@ -140,7 +140,7 @@ const contributorsGraphHref = repoUrl ? `${repoUrl.replace(/\/$/, "")}/graphs/co
|
|
|
140
140
|
href={href}
|
|
141
141
|
target="_blank"
|
|
142
142
|
rel="noopener noreferrer"
|
|
143
|
-
class="group
|
|
143
|
+
class="group rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors flex flex-col items-center gap-2 p-3 text-center no-underline hover:border-ink-300 dark:hover:border-ink-700"
|
|
144
144
|
data-event="contributor_click"
|
|
145
145
|
data-event-source="contributors_page"
|
|
146
146
|
>
|
|
@@ -173,12 +173,3 @@ const contributorsGraphHref = repoUrl ? `${repoUrl.replace(/\/$/, "")}/graphs/co
|
|
|
173
173
|
</section>
|
|
174
174
|
)}
|
|
175
175
|
</BaseLayout>
|
|
176
|
-
|
|
177
|
-
<style>
|
|
178
|
-
.line-clamp-1 {
|
|
179
|
-
display: -webkit-box;
|
|
180
|
-
-webkit-line-clamp: 1;
|
|
181
|
-
-webkit-box-orient: vertical;
|
|
182
|
-
overflow: hidden;
|
|
183
|
-
}
|
|
184
|
-
</style>
|
|
@@ -60,7 +60,7 @@ const pleaseAvoid = [
|
|
|
60
60
|
["2", "Edit the draft", "Fix the category, stack, platforms, and notes."],
|
|
61
61
|
["3", "Open a pull request", "Reviewers will validate and merge the record."],
|
|
62
62
|
].map(([number, heading, copy]) => (
|
|
63
|
-
<li class="
|
|
63
|
+
<li class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors flex items-start gap-2 p-3">
|
|
64
64
|
<span class="mt-0.5 inline-flex h-5 w-5 shrink-0 items-center justify-center rounded-full border border-ink-300 font-mono font-semibold text-ink-700 dark:border-ink-700 dark:text-ink-300">{number}</span>
|
|
65
65
|
<div>
|
|
66
66
|
<div class="font-medium text-ink-900 dark:text-ink-100">{heading}</div>
|
|
@@ -71,43 +71,43 @@ const pleaseAvoid = [
|
|
|
71
71
|
</ol>
|
|
72
72
|
|
|
73
73
|
<div class="mt-8 grid grid-cols-1 gap-6 lg:grid-cols-[minmax(0,1fr)_minmax(360px,0.8fr)]">
|
|
74
|
-
<form id="submit-form" class="
|
|
74
|
+
<form id="submit-form" class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors p-5">
|
|
75
75
|
<div class="grid gap-5">
|
|
76
76
|
<label class="grid gap-1.5">
|
|
77
|
-
<span class="
|
|
77
|
+
<span class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">GitHub URL</span>
|
|
78
78
|
<div class="flex flex-col gap-2 sm:flex-row">
|
|
79
|
-
<input id="repo-url" type="url" required placeholder="https://github.com/owner/repo" class="
|
|
80
|
-
<button id="fetch-repo" type="button" class="
|
|
79
|
+
<input id="repo-url" type="url" required placeholder="https://github.com/owner/repo" class="min-h-10 flex-1 rounded-[var(--radius)] border border-input bg-background px-3 py-2 text-sm text-foreground outline-none focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35" />
|
|
80
|
+
<button id="fetch-repo" type="button" class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 whitespace-nowrap rounded-[var(--radius)] border border-transparent bg-primary px-3 text-sm font-medium leading-none text-primary-foreground no-underline outline-none transition-colors hover:bg-primary/90 focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 min-h-10 justify-center">Generate draft</button>
|
|
81
81
|
</div>
|
|
82
|
-
<span class="
|
|
82
|
+
<span class="text-2xs text-muted-foreground">The repository must be public. We never write to it.</span>
|
|
83
83
|
</label>
|
|
84
84
|
|
|
85
85
|
<div class="grid grid-cols-1 gap-4 sm:grid-cols-2">
|
|
86
|
-
<label class="grid gap-1.5"><span class="
|
|
87
|
-
<label class="grid gap-1.5"><span class="
|
|
86
|
+
<label class="grid gap-1.5"><span class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">Name</span><input id="item-name" type="text" class="min-h-10 rounded-[var(--radius)] border border-input bg-background px-3 py-2 text-sm text-foreground outline-none focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35" /></label>
|
|
87
|
+
<label class="grid gap-1.5"><span class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">Slug</span><input id="item-slug" type="text" class="min-h-10 rounded-[var(--radius)] border border-input bg-background px-3 py-2 font-mono text-sm text-foreground outline-none focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35" /><span class="text-2xs text-muted-foreground">URL fragment, auto-filled from the repository name.</span></label>
|
|
88
88
|
</div>
|
|
89
89
|
|
|
90
90
|
<label class="grid gap-1.5">
|
|
91
|
-
<span class="
|
|
92
|
-
<textarea id="item-description" rows="3" class="
|
|
93
|
-
<span class="
|
|
91
|
+
<span class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">Description</span>
|
|
92
|
+
<textarea id="item-description" rows="3" class="min-h-10 resize-y rounded-[var(--radius)] border border-input bg-background px-3 py-2 text-sm text-foreground outline-none focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35"></textarea>
|
|
93
|
+
<span class="text-2xs text-muted-foreground">One or two sentences in plain language.</span>
|
|
94
94
|
</label>
|
|
95
95
|
|
|
96
96
|
<div class="grid grid-cols-1 gap-4 sm:grid-cols-2">
|
|
97
97
|
<label class="grid gap-1.5">
|
|
98
|
-
<span class="
|
|
99
|
-
<input id="item-category" list="category-options" class="
|
|
98
|
+
<span class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">Category</span>
|
|
99
|
+
<input id="item-category" list="category-options" class="min-h-10 rounded-[var(--radius)] border border-input bg-background px-3 py-2 text-sm text-foreground outline-none focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35" />
|
|
100
100
|
<datalist id="category-options">{categories.map((value) => <option value={value} />)}</datalist>
|
|
101
101
|
</label>
|
|
102
102
|
<label class="grid gap-1.5">
|
|
103
|
-
<span class="
|
|
104
|
-
<input id="primary-stack" list="stack-options" class="
|
|
103
|
+
<span class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">Primary stack</span>
|
|
104
|
+
<input id="primary-stack" list="stack-options" class="min-h-10 rounded-[var(--radius)] border border-input bg-background px-3 py-2 text-sm text-foreground outline-none focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35" />
|
|
105
105
|
<datalist id="stack-options">{stacks.map((value) => <option value={value} />)}</datalist>
|
|
106
106
|
</label>
|
|
107
107
|
</div>
|
|
108
108
|
|
|
109
109
|
<fieldset class="grid gap-2">
|
|
110
|
-
<legend class="
|
|
110
|
+
<legend class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">Platforms</legend>
|
|
111
111
|
<div class="grid grid-cols-2 gap-2 sm:grid-cols-3">
|
|
112
112
|
{platformOptions.map((platform) => (
|
|
113
113
|
<label class="flex min-h-9 items-center gap-2 rounded-md border border-ink-200 px-2 text-sm dark:border-ink-800">
|
|
@@ -118,14 +118,14 @@ const pleaseAvoid = [
|
|
|
118
118
|
</div>
|
|
119
119
|
</fieldset>
|
|
120
120
|
|
|
121
|
-
<label class="grid gap-1.5"><span class="
|
|
122
|
-
<label class="grid gap-1.5"><span class="
|
|
123
|
-
<label class="grid gap-1.5"><span class="
|
|
121
|
+
<label class="grid gap-1.5"><span class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">Tags</span><input id="item-tags" type="text" placeholder="self-hosted, developer-tools, offline-first" class="min-h-10 rounded-[var(--radius)] border border-input bg-background px-3 py-2 text-sm text-foreground outline-none focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35" /></label>
|
|
122
|
+
<label class="grid gap-1.5"><span class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">Website</span><input id="item-website" type="url" placeholder="https://example.com" class="min-h-10 rounded-[var(--radius)] border border-input bg-background px-3 py-2 text-sm text-foreground outline-none focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35" /></label>
|
|
123
|
+
<label class="grid gap-1.5"><span class="text-2xs font-medium uppercase tracking-[.05em] text-muted-foreground">Best for</span><textarea id="best-for" rows="3" class="min-h-10 resize-y rounded-[var(--radius)] border border-input bg-background px-3 py-2 text-sm text-foreground outline-none focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35" placeholder="One use case per line"></textarea></label>
|
|
124
124
|
</div>
|
|
125
125
|
</form>
|
|
126
126
|
|
|
127
127
|
<aside class="flex flex-col gap-4">
|
|
128
|
-
<div class="
|
|
128
|
+
<div class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors p-5">
|
|
129
129
|
<h2 class="m-0 text-[0.9375rem] font-semibold text-ink-900 dark:text-ink-100">Submission criteria</h2>
|
|
130
130
|
<p class="m-0 mt-1 text-2xs text-ink-500 dark:text-ink-400">Use this checklist before opening the draft.</p>
|
|
131
131
|
<div class="mt-4 grid grid-cols-1 gap-4 text-2xs sm:grid-cols-2 lg:grid-cols-1 xl:grid-cols-2">
|
|
@@ -140,12 +140,12 @@ const pleaseAvoid = [
|
|
|
140
140
|
</div>
|
|
141
141
|
</div>
|
|
142
142
|
|
|
143
|
-
<div class="
|
|
143
|
+
<div class="rounded-[calc(var(--radius)+0.25rem)] border-0 bg-muted shadow-none transition-colors flex min-h-[420px] flex-col p-5">
|
|
144
144
|
<div class="flex flex-wrap items-center justify-between gap-3">
|
|
145
145
|
<h2 class="m-0 text-base font-semibold text-ink-900 dark:text-ink-100">YAML draft</h2>
|
|
146
146
|
<div class="flex items-center gap-2">
|
|
147
|
-
<button id="copy-yaml" type="button" class="
|
|
148
|
-
<a id="open-pr-link" href="#" target="_blank" rel="noopener noreferrer" class="
|
|
147
|
+
<button id="copy-yaml" type="button" class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 whitespace-nowrap rounded-[var(--radius)] border border-border bg-secondary px-3 text-sm font-medium leading-none text-foreground no-underline outline-none transition-colors hover:bg-accent focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 pointer-events-none opacity-50" disabled>Copy YAML</button>
|
|
148
|
+
<a id="open-pr-link" href="#" target="_blank" rel="noopener noreferrer" class="inline-flex h-8 cursor-pointer items-center justify-center gap-1.5 whitespace-nowrap rounded-[var(--radius)] border border-border bg-secondary px-3 text-sm font-medium leading-none text-foreground no-underline outline-none transition-colors hover:bg-accent focus-visible:border-ring focus-visible:ring-3 focus-visible:ring-ring/35 pointer-events-none opacity-50">Open PR draft</a>
|
|
149
149
|
</div>
|
|
150
150
|
</div>
|
|
151
151
|
<pre class="mt-4 min-h-0 flex-1 overflow-auto rounded-md border border-ink-200 bg-ink-50 p-3 text-xs leading-relaxed text-ink-800 dark:border-ink-800 dark:bg-ink-900/60 dark:text-ink-200"><code id="yaml-preview">Paste a GitHub URL to generate a draft.</code></pre>
|
|
@@ -156,14 +156,6 @@ const pleaseAvoid = [
|
|
|
156
156
|
</section>
|
|
157
157
|
</Container>
|
|
158
158
|
|
|
159
|
-
<style>
|
|
160
|
-
.field { min-height: 2.5rem; border-radius: .375rem; border: 1px solid var(--color-ink-200); background: white; padding: .5rem .75rem; color: var(--color-ink-900); font-size: .875rem; outline: none; }
|
|
161
|
-
.field:focus { border-color: var(--color-ink-500); }
|
|
162
|
-
:global(.dark) .field { border-color: var(--color-ink-800); background: var(--color-ink-950); color: var(--color-ink-100); }
|
|
163
|
-
.label { font-size: var(--text-2xs); font-weight: 500; text-transform: uppercase; letter-spacing: .05em; color: var(--color-ink-500); }
|
|
164
|
-
.help { font-size: var(--text-2xs); color: var(--color-ink-500); }
|
|
165
|
-
</style>
|
|
166
|
-
|
|
167
159
|
<script is:inline define:vars={{ existingSlugs, existingFullNames, repoUrl }}>
|
|
168
160
|
// @ts-nocheck
|
|
169
161
|
const $ = (selector) => document.querySelector(selector);
|