|
1 | 1 | import Head from 'next/head' |
2 | 2 | import useSWR from 'swr' |
| 3 | +import Link from 'next/link' |
| 4 | +import { ExternalLink } from 'lucide-react' |
3 | 5 | import { fetcher } from '@/lib/fetcher' |
4 | 6 | import { extractPackageName } from '@/lib/utils' |
5 | 7 | import { PackageInspectResult } from '@/components/package-inspector/types' |
6 | 8 | import ScoreCardChart from '@/components/package-inspector/ScoreCardChart' |
7 | 9 | import ProjectStats from '@/components/package-inspector/ProjectStats' |
8 | 10 | import OverallScoreGauge from '@/components/package-inspector/OverallScoreIcon' |
9 | 11 | import VulnerabilityList from '@/components/package-inspector/VulnerabilityList' |
| 12 | +import { Button } from '@/components/ui/button' |
10 | 13 |
|
11 | 14 | export default function PurlPageComponent({ purl }: { purl?: string }) { |
12 | 15 | const purlString = typeof purl === 'string' ? purl : '' |
@@ -59,45 +62,75 @@ export default function PurlPageComponent({ purl }: { purl?: string }) { |
59 | 62 | <p className="mb-1 text-sm font-medium uppercase tracking-wider text-gray-500"> |
60 | 63 | Package Inspector |
61 | 64 | </p> |
62 | | - <div className="flex items-baseline gap-3"> |
63 | | - <h1 className="text-3xl font-bold text-white"> |
64 | | - {packageName} |
65 | | - </h1> |
66 | | - {component.version && ( |
67 | | - <span className="text-lg text-gray-400"> |
68 | | - v{component.version} |
69 | | - </span> |
70 | | - )} |
71 | | - </div> |
72 | 65 | </div> |
73 | | - {/* Top row: Project stats + Overall score */} |
74 | | - <div className="mb-8 flex items-start gap-16"> |
75 | | - <div className="min-w-0 max-w-2xl flex-1"> |
76 | | - <ProjectStats |
77 | | - project={project} |
78 | | - purl={result.purl} |
79 | | - published={component.published} |
80 | | - isMalicious={result.maliciousPackage != null} |
81 | | - /> |
82 | | - </div> |
83 | | - <div className="shrink-0"> |
84 | | - <OverallScoreGauge score={project.scoreCardScore} /> |
| 66 | + |
| 67 | + {/* Hero card */} |
| 68 | + <div className="mb-4 rounded-xl border border-gray-700 bg-gray-800/50 p-6"> |
| 69 | + <div className="flex items-start justify-between gap-6"> |
| 70 | + <div className="min-w-0 flex-1"> |
| 71 | + <div className="mb-1 flex items-baseline gap-3"> |
| 72 | + <h1 className="text-3xl font-bold text-white"> |
| 73 | + {packageName} |
| 74 | + </h1> |
| 75 | + {component.version && ( |
| 76 | + <span className="text-lg text-gray-400"> |
| 77 | + v{component.version} |
| 78 | + </span> |
| 79 | + )} |
| 80 | + </div> |
| 81 | + <ProjectStats |
| 82 | + project={project} |
| 83 | + purl={result.purl} |
| 84 | + published={component.published} |
| 85 | + isMalicious={result.maliciousPackage != null} |
| 86 | + /> |
| 87 | + </div> |
| 88 | + <div className="shrink-0"> |
| 89 | + <OverallScoreGauge score={project.scoreCardScore} /> |
| 90 | + </div> |
85 | 91 | </div> |
86 | 92 | </div> |
87 | 93 |
|
88 | | - {/* Bottom row: Scorecard bars + Vulnerability list */} |
89 | | - <div className="grid items-start gap-12 md:grid-cols-2"> |
90 | | - <div> |
91 | | - <h2 className="mb-4 text-xl font-semibold text-white"> |
92 | | - Open SSF Scorecard Checks |
| 94 | + {/* Two-column: Scorecard + Vulnerabilities */} |
| 95 | + <div className="grid items-stretch gap-4 md:grid-cols-2"> |
| 96 | + <div className="rounded-xl border border-gray-700 bg-gray-800/50 p-6"> |
| 97 | + <h2 className="mb-4 text-base font-bold text-white"> |
| 98 | + Open SSF Scorecard |
93 | 99 | </h2> |
94 | 100 | <ScoreCardChart checks={project.scoreCard.checks} /> |
95 | 101 | </div> |
96 | 102 |
|
97 | | - <VulnerabilityList |
98 | | - vulns={vulns} |
99 | | - affectedComponents={affectedComponents} |
100 | | - /> |
| 103 | + <div className="rounded-xl border border-gray-700 bg-gray-800/50 p-6"> |
| 104 | + <h2 className="mb-4 text-base font-bold text-white"> |
| 105 | + Vulnerabilities fixed in later releases |
| 106 | + </h2> |
| 107 | + <VulnerabilityList |
| 108 | + vulns={vulns} |
| 109 | + affectedComponents={affectedComponents} |
| 110 | + /> |
| 111 | + </div> |
| 112 | + </div> |
| 113 | + |
| 114 | + {/* Bottom buttons */} |
| 115 | + <div className="mt-6 flex justify-end gap-3"> |
| 116 | + <div> |
| 117 | + <Button> |
| 118 | + <Link href="/package-inspector">Get Back</Link> |
| 119 | + </Button> |
| 120 | + </div> |
| 121 | + <div> |
| 122 | + <Button> |
| 123 | + <a |
| 124 | + target="_blank" |
| 125 | + href="https://main.devguard.org/" |
| 126 | + rel="noopener noreferrer" |
| 127 | + className="flex items-center gap-2" |
| 128 | + > |
| 129 | + Try DevGuard |
| 130 | + <ExternalLink size={16} /> |
| 131 | + </a> |
| 132 | + </Button> |
| 133 | + </div> |
101 | 134 | </div> |
102 | 135 | </div> |
103 | 136 | ) |
|
0 commit comments