/ components / PRSummaryBanner.tsx
PRSummaryBanner.tsx
 1  import { ExternalLink, Files, GitCommitHorizontal, Clock, ArrowLeft, Settings } from 'lucide-react';
 2  import { GitHubIcon } from '@/lib/constants';
 3  import { Card, CardContent } from '@/components/ui/card';
 4  import { Badge } from '@/components/ui/badge';
 5  import { Button } from '@/components/ui/button';
 6  import { riskConfig } from '@/lib/constants';
 7  import type { ReviewGuide } from '@/lib/types';
 8  import { formatDuration } from '@/lib/utils';
 9  
10  interface Props {
11    review: ReviewGuide;
12    onBack?: () => void;
13    onOpenSettings?: () => void;
14  }
15  
16  export function PRSummaryBanner({ review, onBack, onOpenSettings }: Props) {
17    const risk = riskConfig[review.riskLevel];
18  
19    return (
20      <Card className="rounded-none border-x-0 border-t-0 border-b">
21        <CardContent className="py-3">
22          <div className="flex items-center justify-between gap-4">
23            <div className="flex items-center gap-3 min-w-0">
24              {onBack && (
25                <Button variant="ghost" size="sm" onClick={onBack} className="gap-1 shrink-0 -ml-2">
26                  <ArrowLeft className="h-4 w-4" />
27                  Back
28                </Button>
29              )}
30              <h1 className="text-base font-semibold truncate font-display">{review.prTitle}</h1>
31              <Badge variant={risk.variant} className="shrink-0">
32                {risk.label}
33              </Badge>
34            </div>
35  
36            <div className="flex items-center gap-4 shrink-0 text-xs text-muted-foreground">
37              <span>{review.author}</span>
38              <span className="flex items-center gap-1">
39                <Files className="h-3 w-3" />
40                {review.totalFilesChanged}
41              </span>
42              <span className="flex items-center gap-1">
43                <GitCommitHorizontal className="h-3 w-3" />
44                {review.totalLinesChanged} lines
45              </span>
46              {review.generationDurationMs != null && (
47                <span className="flex items-center gap-1">
48                  <Clock className="h-3 w-3" />
49                  {formatDuration(review.generationDurationMs)}
50                </span>
51              )}
52              {onOpenSettings && (
53                <button
54                  onClick={onOpenSettings}
55                  className="text-muted-foreground hover:text-foreground"
56                  aria-label="Settings"
57                >
58                  <Settings className="h-3.5 w-3.5" />
59                </button>
60              )}
61              <a
62                href={review.prUrl}
63                target="_blank"
64                rel="noopener noreferrer"
65                className="text-muted-foreground hover:text-foreground flex items-center gap-1"
66              >
67                <GitHubIcon className="h-3.5 w-3.5" />
68                <ExternalLink className="h-3 w-3" />
69              </a>
70            </div>
71          </div>
72        </CardContent>
73      </Card>
74    );
75  }