mirror of
https://github.com/supabase/supabase.git
synced 2026-10-18 07:39:07 +03:00
* Init AiAssistantPanel * Temp * Temp * iterating on assistant ux * More spiking * Tweaking... * Moar tweaking.. * Even more tweaking * Tweek * More tweaks * Final tweaking... * TWEAK * Spelling * Fix * Assistant error handling and small bug fix in context for message * Add feature flag * Fix * Address all feedback * Minor
114 lines
3.5 KiB
TypeScript
114 lines
3.5 KiB
TypeScript
import { InsertCode, ReplaceCode } from 'icons'
|
|
import { Check, Copy } from 'lucide-react'
|
|
import { useEffect, useState } from 'react'
|
|
import { format } from 'sql-formatter'
|
|
import {
|
|
Button,
|
|
CodeBlock,
|
|
TooltipContent_Shadcn_,
|
|
TooltipTrigger_Shadcn_,
|
|
Tooltip_Shadcn_,
|
|
cn,
|
|
} from 'ui'
|
|
|
|
import { useSendEventMutation } from 'data/telemetry/send-event-mutation'
|
|
import { DiffType } from 'components/interfaces/SQLEditor/SQLEditor.types'
|
|
|
|
interface MessagePreProps {
|
|
onDiff: (type: DiffType, s: string) => void
|
|
children: string[]
|
|
className?: string
|
|
}
|
|
|
|
export const MessagePre = ({ onDiff, children, className }: MessagePreProps) => {
|
|
const [copied, setCopied] = useState(false)
|
|
|
|
const { mutate: sendEvent } = useSendEventMutation()
|
|
|
|
useEffect(() => {
|
|
if (!copied) return
|
|
const timer = setTimeout(() => setCopied(false), 2000)
|
|
return () => clearTimeout(timer)
|
|
}, [copied])
|
|
|
|
let formatted = (children || [''])[0]
|
|
try {
|
|
formatted = format(formatted, { language: 'postgresql', keywordCase: 'upper' })
|
|
} catch {}
|
|
|
|
if (formatted.length === 0) {
|
|
return null
|
|
}
|
|
|
|
function handleCopy(formatted: string) {
|
|
navigator.clipboard.writeText(formatted).then()
|
|
setCopied(true)
|
|
}
|
|
|
|
return (
|
|
<pre className={cn('rounded-md relative group', className)}>
|
|
<CodeBlock
|
|
value={formatted}
|
|
language="sql"
|
|
className={cn(
|
|
'!bg-transparent !py-3 !px-3.5 prose dark:prose-dark',
|
|
// change the look of the code block. The flex hack is so that the code is wrapping since
|
|
// every word is a separate span
|
|
'[&>code]:m-0 [&>code>span]:flex [&>code>span]:flex-wrap [&>code]:block'
|
|
)}
|
|
hideCopy
|
|
hideLineNumbers
|
|
/>
|
|
<div className="absolute top-2 right-2 bg-surface-100 border-muted border rounded-lg h-[28px] hidden group-hover:block">
|
|
<Tooltip_Shadcn_>
|
|
<TooltipTrigger_Shadcn_ asChild>
|
|
<Button
|
|
type="text"
|
|
size="tiny"
|
|
onClick={() => {
|
|
onDiff(DiffType.Addition, formatted)
|
|
sendEvent({
|
|
category: 'sql_editor_ai_assistant_v2',
|
|
label: 'sql-editor-ai-assistant-v2',
|
|
action: 'ai_suggestion_inserted',
|
|
})
|
|
}}
|
|
>
|
|
<InsertCode className="h-4 w-4 text-foreground-light" strokeWidth={1.5} />
|
|
</Button>
|
|
</TooltipTrigger_Shadcn_>
|
|
<TooltipContent_Shadcn_ side="bottom" className="font-sans">
|
|
Insert code
|
|
</TooltipContent_Shadcn_>
|
|
</Tooltip_Shadcn_>
|
|
|
|
<Tooltip_Shadcn_>
|
|
<TooltipTrigger_Shadcn_ asChild>
|
|
<Button
|
|
type="text"
|
|
size="tiny"
|
|
onClick={() => {
|
|
handleCopy(formatted)
|
|
sendEvent({
|
|
category: 'sql_editor_ai_assistant_v2',
|
|
label: 'sql-editor-ai-assistant-v2',
|
|
action: 'ai_suggestion_copied',
|
|
})
|
|
}}
|
|
>
|
|
{copied ? (
|
|
<Check size={16} className="text-brand-600" />
|
|
) : (
|
|
<Copy size={16} className="text-foreground-light" strokeWidth={1.5} />
|
|
)}
|
|
</Button>
|
|
</TooltipTrigger_Shadcn_>
|
|
<TooltipContent_Shadcn_ side="bottom" className="font-sans">
|
|
Copy code
|
|
</TooltipContent_Shadcn_>
|
|
</Tooltip_Shadcn_>
|
|
</div>
|
|
</pre>
|
|
)
|
|
}
|